NAME
ggLoadConfig, ggFreeConfig, ggConfigIterTarget, ggConfigIterLocation -
Configuration helpers
SYNOPSIS
int ggLoadConfig(const char *file, gg_config *config);
void ggFreeConfig(gg_config config);
struct gg_location_iter {
struct gg_iter iter;
const void * config;
const char * name;
char * location;
const char * symbol;
void * _state;
};
int ggConfigIterLocation(struct gg_location_iter * iter);
struct gg_target_iter {
struct gg_iter iter;
void * config;
const char * input;
char * target;
char * options;
void * nested;
};
int ggConfigIterTarget(struct gg_target_iter *iter);
DESCRIPTION
These functions provides a simple way of handling configuration files.
ggLoadConfig tries to load the configuration file given as parameter.
It adds the content to the config handle found at *config. If the
handle is NULL, a new one is created.
ggFreeConfig deletes the internal structure for the configuration
handle config. This handle becomes invalid and should not be used
anymore.
ggConfigIterLocation allows to retreive the location and symbol
associated to canonical names. This function is mainly used together
with the scope abstraction to query application modules at runtime.
This function will prepare the iter structure to be used as an iterator
that will generate correct matches. iter is a pointer to a
gg_location_iter structure owned by the caller. This user part of the
structure must be set by the caller before calling
ggConfigIterLocation. The config field must be filled with the config
handle which contains target information; the name field must be filled
with the canonical name that is being looked for. location and symbol
are placeholders in which the results will be found along the
iteration. The resulting strings *do* belong to libgg and *must not* be
freed or altered, and they may be invalidated if not used during the
iteration process. They must be copied if needed later. _state is an
internal opaque pointer that keeps track of the iterator state. Its
value must never be touched by the caller.
ggConfigIterTarget allows to iterate over canonical target names and
options strings found in a target spec string. This function also work
as a generator. iter is a pointer to a gg_target_iter structure owned
by the caller. This user part of the structure must be set by the
caller before calling ggConfigIterTarget. The config field must be
filled with the config handle which contains target information; the
input field must be filled with the initial input spec string. target
and options are placeholders in which the results will be found along
the iteration. Here again, the resulting strings *do* belong to libgg
and *must not* be freed or altered, and they may be invalidated if not
used during the iteration process. They must be copied if needed later.
nested is an internal opaque pointer that keeps track of the iterator
state. Its value must never be touched by the caller.
RETURN VALUE
ggLoadConfig returns GGI_OK on success, or:
· GGI_ENOMEM if it can not allocate a new configuration handle. Note
that if subsequent memory allocations fail (when feeding the
handle), those will not be reported as an error. The handle will be
incomplete with regard to the config file contents;
· GGI_ENOTFOUND if the file does not exists. Note that missing files
in include directives will not be reported an error. Also, other
parse error in the file will simply cause the incriminated lines to
be ignored.
ggConfigIterLocation returns GGI_OK on success or GGI_ENOMEM.
ggConfigIterTarget always return GGI_OK and will never fail.
CONFIG FILE FORMAT
The configuration file is line oriented. Each line may define a mapping
between a canonical name and a location. The generic format is:
<pattern> <location>[:<symbol>]
alias <name> <expansion>
On the first line pattern is a canonical name that may contain one * as
a wildcard, location is a string that corresponds to a scope location,
and symbol is an optional string that gives the name of the symbol to
retreive from the scope. If not given, NULL will be reported. The
second line defines an alias. When a target called name is found while
iterating over target spec strings, the iterator parse expansion as a
sub-input spec, and aggregate all option strings that where found on
upstream aliases.
In addition, the configuration file loader knowns the following
directives:
.root <path>
.include <file>
When locations following the .root directive are given as relative
path, path will be prepended. .include will parse the given file
recursively, before continuing with the current one.
EXAMPLE
This code demonstrates how to get the first module init function
accessible from a scope for a given name. It also shows how to use the
libgg iterator scheme:
int openModule(gg_config cfg, const char * moduleName,
const char * defaultSymbol) {
struct gg_location_iter match;
gg_scope scope;
module_init_func *init;
/* prepare the iterator */
match.name = name;
match.config = cfg;
ggConfigMatchIter(&match);
/* iterate over the matches */
GG_ITER_FOREACH(&match) {
/* try to retreive the collection at suggested location */
if((scope = ggGetScope(match.location)) == NULL)
continue;
/* use default symbol if none suggested */
if (match.symbol == NULL) match.symbol = defaultSymbol;
/* try to retreive the symbol from that scope */
if((init = ggFromScope(scope, match.symbol)) == NULL) {
ggDelScope(scope);
continue;
}
/* try to initialize the module */
if(init() != GGI_OK) {
ggDelScope(scope);
continue;
}
/* the module is up, abort iteration and return */
GG_ITER_DONE(&match);
return GGI_OK;
}
/* module not found */
GG_ITER_DONE(&match);
return GGI_ENOTFOUND;
Note that this code is not completely correct, because the scope cannot
be deleted later if it is not remembered somewhere. This next example
shows how to list all targets and options specified by a string:
static void showAllTargets(void * cfg, const char * input)
{
struct gg_target_iter match;
match.config = cfg;
match.input = input;
ggConfigIterTarget(&match);
GG_ITER_FOREACH(&match) {
printf("Target \"%s\" with options \"%s\".\n",
match.target, match.options);
}
GG_ITER_DONE(&match);
}
SEE ALSO
ggGetScope(3)