From: Robert Spalek Date: Wed, 19 Apr 2006 10:02:37 +0000 (+0200) Subject: implemented a few functions of the new configuration mechanism: X-Git-Tag: holmes-import~645^2~11^2~107 X-Git-Url: http://mj.ucw.cz/gitweb/?a=commitdiff_plain;h=b48097fe5ddf0d0a6b7df4d2ebc4c9f6110edaa3;p=libucw.git implemented a few functions of the new configuration mechanism: - memory allocation - skeleton of future journal functions - parsers of all basic types and arrays of these types --- diff --git a/lib/Makefile b/lib/Makefile index 757d2149..39885a9f 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -6,15 +6,12 @@ ifdef CONFIG_UCW_DBTOOL PROGS+=$(o)/lib/db-tool endif -# hey dude, I'm Robert! -PROGS+=$(o)/lib/conf2-test - LIBUCW_MODS= \ alloc alloc_str realloc mempool mempool-str mempool-fmt \ mmap pagecache partmap hashfunc \ lists slists sorter bitsig kmp \ log log-file proctitle \ - conf ipaccess \ + conf conf2 ipaccess \ profile \ fastbuf ff-printf ff-utf8 \ fb-file carefulio fb-mem fb-temp fb-mmap fb-limfd fb-buffer fb-grow \ diff --git a/lib/conf2.c b/lib/conf2.c new file mode 100644 index 00000000..90483d4c --- /dev/null +++ b/lib/conf2.c @@ -0,0 +1,257 @@ +/* + * UCW Library -- Reading of configuration files + * + * (c) 2001--2006 Robert Spalek + * (c) 2003--2006 Martin Mares + * + * This software may be freely distributed and used according to the terms + * of the GNU Lesser General Public License. + */ + +#include "lib/lib.h" +#include "lib/conf2.h" +#include "lib/mempool.h" + +#include +#include + +/* Memory allocation */ + +static struct mempool *cf_pool; + +void * +cf_malloc(uns size) +{ + return mp_alloc(cf_pool, size); +} + +void * +cf_malloc_zero(uns size) +{ + return mp_alloc_zero(cf_pool, size); +} + +byte * +cf_strdup(byte *s) +{ + return mp_strdup(cf_pool, s); +} + +byte * +cf_printf(char *fmt, ...) +{ + va_list args; + va_start(args, fmt); + byte *res = mp_vprintf(cf_pool, fmt, args); + va_end(args); + return res; +} + +/* Undo journal */ + +static uns journal_active; + +uns +cf_journal_active(uns flag) +{ + uns f = journal_active; + journal_active = flag; + return f; +} + +void +cf_journal_block(void *ptr UNUSED, uns len UNUSED) +{ +} + +/* Parsers for standard types */ + +struct unit { + uns name; // one-letter name of the unit + uns num, den; // fraction +}; + +static const struct unit units[] = { + { 'd', 86400, 1 }, + { 'h', 3600, 1 }, + { 'k', 1000, 1 }, + { 'm', 1000000, 1 }, + { 'g', 1000000000, 1 }, + { 'K', 1024, 1 }, + { 'M', 1048576, 1 }, + { 'G', 1073741824, 1 }, + { '%', 1, 100 }, + { 0, 0, 0 } +}; + +static const struct unit * +lookup_unit(byte *value, byte *end, byte **msg) +{ + if (end && *end) { + if (end == value || end[1] || *end >= '0' && *end <= '9') + *msg = "Invalid number"; + else { + for (const struct unit *u=units; u->name; u++) + if (u->name == *end) + return u; + *msg = "Invalid unit"; + } + } + return NULL; +} + +static char cf_rngerr[] = "Number out of range"; + +static byte * +cf_parse_int(uns number, byte **pars, int *ptr) +{ + cf_journal_block(ptr, number * sizeof(int)); + for (uns i=0; inum; + if (y % u->den) + msg = "Number is not an integer"; + else { + y /= u->den; + if (y > 0xffffffff) + msg = cf_rngerr; + ptr[i] = y; + } + } else + ptr[i] = x; + } + if (msg) + return number==1 ? msg : cf_printf("Item #%d: %s", i+1, msg); + } + return NULL; +} + +static byte * +cf_parse_u64(uns number, byte **pars, u64 *ptr) +{ + cf_journal_block(ptr, number * sizeof(u64)); + for (uns i=0; i ~(u64)0 / u->num) + msg = "Number out of range"; + else { + x *= u->num; + if (x % u->den) + msg = "Number is not an integer"; + else + ptr[i] = x / u->den; + } + } else + ptr[i] = x; + } + if (msg) + return number==1 ? msg : cf_printf("Item #%d: %s", i+1, msg); + } + return NULL; +} + +static byte * +cf_parse_double(uns number, byte **pars, double *ptr) +{ + cf_journal_block(ptr, number * sizeof(double)); + for (uns i=0; inum / u->den; + else + ptr[i] = x; + } + if (msg) + return number==1 ? msg : cf_printf("Item #%d: %s", i+1, msg); + } + return NULL; +} + +static byte * +cf_parse_string(uns number, byte **pars, byte **ptr) +{ + cf_journal_block(ptr, number * sizeof(byte*)); + for (uns i=0; i