On Wednesday 09 July 2008 14:35:50 Rob Landley wrote: > On Tuesday 08 July 2008 16:40:14 Vladimir Dronnikov wrote: > > Cool! > > > > But we need to not just process continuations and comments but also to > > parse the line into some (possibly variable) amount of > > whitespaces-delimited tokens. > > There's no obvious reason to mix these two issues. A function that reads > comments and continuations and returns the next string from the file is > useful by itself, and you can feed the output of that into something that > tokenizes it. > > You may need different tokenizers if you have different file formats. (If > you > ever wind up caring about bind zone files you get into multiple nested > contexts. Heck, even something like "/etc/sudoers" is actually a bit more > complicated than it looks at first glance.) > > Rob
Hi, yes this is also my opinion: parsing the config file in the sense to rip out the non option stuff and pass only the options to the application is one thing that could be done in a common libbb way supporting the various cases: 1) comments 2) indented comments 3) end of line comments 4) multiline comments 5) options 6) indented options 7) multiline options 8) empty lines 9) empty config files 10) missing config files Trying to parse the contents of the options is not suitable to be done in a common way as only the application knows: 1) the keywords 2) the separator between keyword and option value (SHELL=/bin/bash or PIPPO: PLUTO or SHELL = /bin/bash er PIPPO : PLUTO etc) 3) the number of fields in non-keyworded options: 57 0 * * 0 root [ -x /usr/share/mdadm/checkarray ] && [ $(date +\%d) -le 7 ] && /usr/share/mdadm/checkarray --cron --all --quiet this for example is difficult to parse by whitespace or any other separator if you don't know the number of fields to expect 4) the type of values to expect in the fields so that they could be eventually sanitized I can imagine a flow of events like this if we don't try to make one big monster function but break the problem in more little pieces: 1) parse_config() readies the config file in a way suitable (linked list) to be passed to the app 2) char * parse_named_options(const char *name, char separator, llist_t *list) parses option names and returns the values found for them (removes them from the linked list and frees memory) 3) parse_option_lines(int fields, ...) parses the rest in the desired number of fields and passes the values to the desired number of varargs (removes them from the linked list and frees memory) For example: typedef struct crontab_t { char *min; char *hour; char *day; char *month; char *day_of_week; char *cmd; struct crontab_t *link; } crontab_t; int main(int argc, char**argv) { char *shell; char *path; list_t *option_list; crontab_t *old_head = NULL; crontab_t *new_head = NULL; option_list = parse_config("/etc/crontab"); shell = parse_named_option("SHELL", '=', &option_list); path = parse_named_option("PATH", '=', &option_list); while (option_list) { crontab_t *new_head = xmalloc(sizeof(crontab_t)); parse_option_lines(7, &new_head->min, &new_head->hour, &new_head->day, &new_head->month, &new_head->day_of_week, &new_head->cmd); new_head->link = *old_head; *old_head = new_head; } free(option_list); } This obviously is only pseudo code not tested nor compile tested, just an idea. Comments, hints, critics are welcome.... Ciao, Tito _______________________________________________ busybox mailing list busybox@busybox.net http://busybox.net/cgi-bin/mailman/listinfo/busybox