void confload_configuration(struct Configuration *cfg, const char *filename, const struct CF_Token *token) { unsigned char line[267]; FILE *fp; struct ConfParse *conf = confparse_create(filename, confload_toplevel, cfg); /* If this is the first configuration file, then record it as the base * directory until it changes. * WARNING: BIND9 uses the current-working-directory as the initial * base, but I don't like that. Therefore, I'm going to use the * config file as the base */ if (cfg->options.directory == 0) { cfg->options.directory = filename_get_directory(filename); } fp = fopen(filename, "rt"); if (fp == NULL) { if (token) CONF_ERR(conf, token, "%s\n", strerror(errno)); else perror(filename); return; } while (fgets((char*)line, sizeof(line), fp)) confparse_parse(conf, line, strlen((char*)line)); printf("\n\n"); fclose(fp); }
static int mln_conf_item_init(mln_conf_t *cf, mln_conf_lex_struct_t *cls, mln_conf_item_t *ci) { if (!mln_isvalid_item(cls)) { CONF_ERR(cf->lex, cls, "Invalid type of item"); return -1; } switch (cls->type) { case CONF_TK_DEC: ci->type = CONF_INT; ci->val.i = atol((char *)(cls->text->data)); break; case CONF_TK_REAL: ci->type = CONF_FLOAT; ci->val.f = atof((char *)(cls->text->data)); break; case CONF_TK_STRING: ci->type = CONF_STR; ci->val.s = mln_string_dup(cls->text); if (ci->val.s == NULL) { fprintf(stderr, "No memory.\n"); return -1; } break; case CONF_TK_ON: ci->type = CONF_BOOL; ci->val.b = 1; break; case CONF_TK_OFF: ci->type = CONF_BOOL; ci->val.b = 0; break; case CONF_TK_CHAR: ci->type = CONF_CHAR; ci->val.c = (mln_s8_t)(cls->text->data[0]); break; default: fprintf(stderr, "No such token type.\n"); abort(); } return 0; }
/* * load and free configurations */ static int mln_conf_item_recursive(mln_conf_t *cf, \ mln_conf_cmd_t *cc, \ mln_conf_lex_struct_t *cls, \ mln_u32_t cnt) { if (cls == NULL) { fprintf(stderr, "Get token error. %s\n", mln_lex_strerror(cf->lex)); return -1; } if (cls->type == CONF_TK_EOF) { CONF_ERR(cf->lex, cls, "Invalid end of file"); mln_conf_lex_free(cls); return -1; } if (cls->type == CONF_TK_SEMIC) { if (!cnt) { mln_conf_lex_free(cls); return 0; } cc->arg_tbl = (mln_conf_item_t *)calloc(cnt, sizeof(mln_conf_item_t)); if (cc->arg_tbl == NULL) { fprintf(stderr, "No memory.\n"); mln_conf_lex_free(cls); return -1; } cc->n_args = cnt; mln_conf_lex_free(cls); return 0; } mln_conf_lex_struct_t *next = mln_conf_token(cf->lex); if (mln_conf_item_recursive(cf, cc, next, cnt+1) < 0) { mln_conf_lex_free(cls); return -1; } mln_conf_item_t *ci = &cc->arg_tbl[cnt]; int ret = mln_conf_item_init(cf, cls, ci); mln_conf_lex_free(cls); if (ret < 0) return -1; return 0; }
static int _mln_conf_load(mln_conf_t *cf, mln_conf_domain_t *current) { mln_conf_lex_struct_t *fir, *next; mln_conf_cmd_t *cmd; mln_conf_domain_t *cd; mln_rbtree_node_t *rn; while ( 1 ) { fir = mln_conf_token(cf->lex); if (fir == NULL) { fprintf(stderr, "Get token error. %s\n", mln_lex_strerror(cf->lex)); return -1; } else if (fir->type == CONF_TK_EOF) { mln_conf_lex_free(fir); break; } else if (fir->type == CONF_TK_RBRACE) { if (mln_string_strcmp(current->domain_name, &default_domain)) { mln_conf_lex_free(fir); return 0; } CONF_ERR(cf->lex, fir, "Invalid right brace"); mln_conf_lex_free(fir); return -1; } else if (fir->type != CONF_TK_ID) { CONF_ERR(cf->lex, fir, "Unexpected token"); mln_conf_lex_free(fir); return -1; } next = mln_conf_token(cf->lex); if (next == NULL) { mln_conf_lex_free(fir); fprintf(stderr, "Get token error. %s\n", mln_lex_strerror(cf->lex)); return -1; } else if (next->type == CONF_TK_EOF) { CONF_ERR(cf->lex, next, "Invalid end of file"); mln_conf_lex_free(fir); mln_conf_lex_free(next); return -1; } /*as domain*/ if (next->type == CONF_TK_LBRACE) { mln_conf_lex_free(next); if (mln_string_strcmp(current->domain_name, &default_domain)) { CONF_ERR(cf->lex, fir, "Illegal domain"); mln_conf_lex_free(fir); return -1; } cd = mln_conf_domain_init(cf, fir->text); mln_conf_lex_free(fir); if (cd == NULL) { fprintf(stderr, "No memory.\n"); return -1; } if ((rn = mln_rbtree_new_node(cf->domain, cd)) == NULL) { fprintf(stderr, "No memory.\n"); mln_conf_domain_destroy(cd); return -1; } mln_rbtree_insert(cf->domain, rn); if (_mln_conf_load(cf, cd) < 0) return -1; continue; } /*as command*/ cmd = mln_conf_cmd_init(fir->text); mln_conf_lex_free(fir); if (cmd == NULL) { fprintf(stderr, "No memory.\n"); mln_conf_lex_free(next); return -1; } if ((rn = mln_rbtree_new_node(current->cmd, cmd)) == NULL) { fprintf(stderr, "No memory.\n"); mln_conf_cmd_destroy(cmd); mln_conf_lex_free(next); return -1; } mln_rbtree_insert(current->cmd, rn); if (mln_conf_item_recursive(cf, cmd, next, 0) < 0) return -1; /* * we don't need to free the pointer 'next' here, * because it has already freed in mln_conf_item_recursive(). */ } return 0; }