Config_Def schema tables declare section/key/type/default per module. Typed getters: config_get_str, _u16, _u32, _flags. FLAGS type parses space/comma-separated tokens via a Config_Flag_Def table. config_defaults() gives schema defaults without a file. config_dump() prints effective values for diagnostics. config_cli: load a file or --defaults and dump effective config. dev/example.cfg: sample config covering node, discovery, transport. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
77 lines
2.5 KiB
C
77 lines
2.5 KiB
C
#pragma once
|
|
|
|
#include <stdint.h>
|
|
#include "error.h"
|
|
|
|
/*
|
|
* INI-style config file loader with schema-driven defaults and validation.
|
|
*
|
|
* File format:
|
|
* [section]
|
|
* key = value ; inline comments with ; or #
|
|
* key = value # same
|
|
*
|
|
* Whitespace around keys and values is stripped.
|
|
* Commas in values are treated as whitespace (useful for flag lists).
|
|
*/
|
|
|
|
typedef enum Config_Type {
|
|
CONFIG_STRING, /* arbitrary string value */
|
|
CONFIG_UINT16, /* decimal integer, fits u16 */
|
|
CONFIG_UINT32, /* decimal integer, fits u32 */
|
|
CONFIG_FLAGS, /* space/comma-separated tokens mapped via a flag table */
|
|
} Config_Type;
|
|
|
|
/*
|
|
* One entry in a flags table — maps a token string to a bitmask value.
|
|
* The table must be terminated by an entry with token = NULL.
|
|
*/
|
|
struct Config_Flag_Def {
|
|
const char *token;
|
|
uint32_t value;
|
|
};
|
|
|
|
/*
|
|
* One entry in a config schema.
|
|
* Provide a table of these terminated by an entry with section = NULL.
|
|
*/
|
|
struct Config_Def {
|
|
const char *section;
|
|
const char *key;
|
|
Config_Type type;
|
|
const char *default_val; /* string form of the default */
|
|
const struct Config_Flag_Def *flags; /* required when type = CONFIG_FLAGS */
|
|
};
|
|
|
|
struct Config;
|
|
|
|
/*
|
|
* Load a config file and validate it against the schema.
|
|
* Keys present in the file but absent from the schema are ignored.
|
|
* Keys absent from the file are filled with their schema default.
|
|
*/
|
|
struct App_Error config_load(struct Config **out,
|
|
const char *path,
|
|
const struct Config_Def *schema);
|
|
|
|
/*
|
|
* Load defaults only (no file). Useful when no config file is present
|
|
* but you still want schema-driven defaults.
|
|
*/
|
|
struct App_Error config_defaults(struct Config **out,
|
|
const struct Config_Def *schema);
|
|
|
|
void config_free(struct Config *cfg);
|
|
|
|
/*
|
|
* Typed getters. Return the effective value (file value or default).
|
|
* Caller must not free the returned string — it is owned by the Config.
|
|
*/
|
|
const char *config_get_str (struct Config *cfg, const char *section, const char *key);
|
|
uint16_t config_get_u16 (struct Config *cfg, const char *section, const char *key);
|
|
uint32_t config_get_u32 (struct Config *cfg, const char *section, const char *key);
|
|
uint32_t config_get_flags(struct Config *cfg, const char *section, const char *key);
|
|
|
|
/* Print all effective key/value pairs to stdout — useful for diagnostics. */
|
|
void config_dump(struct Config *cfg);
|