To customize the way EWG generates wrappers, you can provide a configuration file. This file usually named config.ewg is written in XML. This section will describe it's structure.
Configuration support is quite new many very interesting things have not yet been implemented. Basically all you can do so far is control what from a header should be wrapped and what not.
Here is a simple example of how a config file can look like:
<?xml version="1.0"?>
<ewg_config name="my_example">
<rule_list>
<!-- This rule matches all C constructs who are named "foo". -->
<!-- Matching constructs will be wrapped using EWGs defaults -->
<rule>
<match>
<identifier name="foo"/>
</match>
<wrapper type="default">
</wrapper>
</rule>
<!-- This rule matches all C constructs. -->
<!-- Matching constructs will be ignored. -->
<!-- Thus no wrapper will be generated for them -->
<rule>
<match>
</match>
<wrapper type="none">
</wrapper>
</rule>
</rule_list>
</ewg_config>
The concept used is very similar to the concept used in XSLT. You have a ordered list of rules. For every parsed C construct EWG will go through the list of rules and use the first rule that matches on the construct. If no rule matches the construct will be ignored.
Each rule consists of two parts:
Describing what C constructs shall be matched by this rule.
Describing how the matched construct should be wrapped. Right now all you can specify is the wrapper type that should be used, using the type attribute. You can choose between the default wrapper, which will wrap the construct using EWG defaults, or the none wrapper, which will generate no wrapper for the matched construct.
If the match element is empty, all constructs match, but you can use sub-elements to constrain what constructs should match:
What header does the construct come from. Note that you have to specify the exact header the construct comes from. A header that only includes another header that contains a construct, will not match. Here is an example of how to use this element:
<?xml version="1.0"?> <match> <header name=".*foo.h"/> </match>
Note that the value of name can be a regular expression. In the above example any header that ends with foo.h will match.
Constrains the name of elements. Here is an example:
<?xml version="1.0"?> <match> <identifier name="foo"/> </match>
Note that the value of name can be a regular expression.
Constrains the construct type. Here is an example:
<?xml version="1.0"?> <match> <type name="function"/> </match>
Possible values for name are
any
none
struct
union
enum
function
callback
You can choose more than one constraint per match clause. In which case you constrain the match clause to all individual constraints.
If you choose to include a type who depends on a type which you choose to exclude, the dependent type will also be included. Confused? Let's say you have:
struct foo
{
int i;
};
struct bar
{
struct foo* pfoo;
}
And you specify the following config file:
<?xml version="1.0"?>
<ewg_config>
<rule_list>
<rule>
<match>
<identifier name="bar"/>
</match>
<wrapper type="default">
</wrapper>
</rule>
<rule>
<match>
</match>
<wrapper type="none">
</wrapper>
</rule>
</rule_list>
</ewg_config>
That would mean, struct bar will be wrapped and struct foo will not be wrapped. Now, because struct bar depends on struct foo, struct bar will be wrapped after all.
In the if you use ewg_library.eant based geant files, you can control whether ewg uses a config file via the ewg.use_config_file variable. Have a look at the GTK, SDL, OpenGL or BerkeleyDB examples to see how it is done. If you set this variable, the config file is expected to be named config.ewg.