From 951c2b57090768a74a9e788ffedc5a7e10400472 Mon Sep 17 00:00:00 2001 From: Anicka Bernathova Date: Sat, 12 Jul 2008 23:59:21 +0200 Subject: [PATCH] save headers --- Makefile | 4 ++- brum.c | 12 ++++++++- brum.h | 14 +++++++++++ cond.y | 7 ++++++ int.c | 74 +++++++++++++++++++++++++++++++++++++++++++++++++++++--- lex.c | 36 +++++++++++++++++---------- 6 files changed, 128 insertions(+), 19 deletions(-) diff --git a/Makefile b/Makefile index 08c3177..726c9c6 100644 --- a/Makefile +++ b/Makefile @@ -4,7 +4,7 @@ CC=gcc CFLAGS=-Wall -W -Wno-pointer-sign -O2 -g LDLIBS=-lpcre -brum: brum.c cond.tab.o int.o lex.o +brum: brum.c cond.tab.o int.o lex.o ham.o gcc -o $@ $^ $(LDLIBS) cond.tab.o: cond.tab.c lex.o @@ -13,6 +13,8 @@ lex.o: lex.c cond.tab.c int.o: int.c +ham.o: ham.c + cond.tab.c: cond.y bison -dvt cond.y diff --git a/brum.c b/brum.c index 5172d69..171cb07 100644 --- a/brum.c +++ b/brum.c @@ -2,10 +2,15 @@ #include "brum.h" int -main(void) +main(int argc, char** argv) { int res; + if (argc < 2) + die("Usage: ./brum conf_file"); + + read_conf(argv[1]); + // yydebug=1; res = yyparse (); @@ -15,6 +20,11 @@ main(void) print_tree(input_tree,0); var_hash = new_var_hash(); + + current_headers = make_hlist(); +// print_headers(current_headers); + + save_current_headers(var_hash); interp(input_tree, var_hash); print_vars(var_hash); diff --git a/brum.h b/brum.h index 16e4b9e..4346527 100644 --- a/brum.h +++ b/brum.h @@ -70,7 +70,9 @@ struct tree* input_tree; void* xmalloc(size_t size); char* xstrdup(char* s); void __attribute__ ((noreturn)) die(char* msg, ...); +void read_conf(char* filename); int line; +FILE* conf; /* int.c */ struct variable { @@ -79,9 +81,21 @@ struct variable { struct variable* next; }; +struct hlist { + char* name; + char* value; + struct hlist* next; +}; + struct variable** var_hash; void print_tree(struct tree* t, int ind); void interp(struct tree* t, struct variable** hash); struct variable** new_var_hash(void); void print_vars(struct variable** hash); +void save_current_headers(struct variable** hash); + +/* ham.c */ +struct hlist* current_headers; +struct hlist* make_hlist(); +void print_headers(); diff --git a/cond.y b/cond.y index 42a663d..fd5dc30 100644 --- a/cond.y +++ b/cond.y @@ -19,6 +19,7 @@ static struct tree* tree_malloc(int type); %token CONST %token NUM %token VAR +%token KW_DISCARD %token KW_PIPE KW_MAIL KW_COPY %token '(' ')' '{' '}' ';' %nonassoc KW_IF @@ -169,6 +170,12 @@ arrow: left ARROW right ass_right { $$->pt.arrow.kw_left = $1; $$->pt.arrow.kw_right = $3; } + | left ARROW KW_DISCARD { //FIXME: actually left does not make sense here + $$ = tree_malloc(ST_ARROW); + $$->pt.arrow.s = NULL; + $$->pt.arrow.kw_left = NULL; + $$->pt.arrow.kw_right = "discard"; + } ; left: /* empty */ { $$ = NULL;} diff --git a/int.c b/int.c index 73e34ff..6e9a814 100644 --- a/int.c +++ b/int.c @@ -1,6 +1,7 @@ #include #include #include +#include #include "cond.tab.h" #include "brum.h" @@ -34,6 +35,14 @@ get_bucket_number(char* name) return n; } +void +cap(char* s) +{ + char* p; + for(p = s; *p; p++) + *p = toupper(*p); +} + /* value NULL for finding without modyfiing */ static struct variable* find_var(char* name, char* value, struct variable** hash) @@ -41,6 +50,10 @@ find_var(char* name, char* value, struct variable** hash) int n; struct variable *p; + name = xstrdup(name); + if (isupper(*name)) + cap(name); + n = get_bucket_number(name); p = hash[n]; @@ -56,7 +69,7 @@ find_var(char* name, char* value, struct variable** hash) p = xmalloc(sizeof(struct variable)); p->next = hash[n]; hash[n] = p; - p->name = xstrdup(name); + p->name = name; p->value = (value? value:xstrdup("")); } @@ -132,7 +145,8 @@ print_tree(struct tree* t, int ind) printf("%*s ->\n", ind, ""); if (t->pt.arrow.kw_right) printf("%*s%s\n", ind+1, "", t->pt.arrow.kw_right); - print_tree(t->pt.arrow.s,ind+1); + if (t->pt.arrow.s) + print_tree(t->pt.arrow.s,ind+1); break; case ST_OP: print_tree(t->pt.op.left, ind+1); @@ -181,6 +195,7 @@ interp_ass_right(struct tree* t, struct variable** hash) } } +// FIXME: we would like to be able also do things like ($a & $b) == $c int interp_cond(struct tree* t, struct variable** hash) { @@ -189,7 +204,7 @@ interp_cond(struct tree* t, struct variable** hash) if (t->pt.cond.type == OP_REL){ if (t->pt.cond.left->st != ST_LEAF || t->pt.cond.right->st != ST_LEAF) - die("Chlemst"); + die("Chlemst"); char* left = (t->pt.cond.left->pt.leaf.type == L_VAR ? find_var(t->pt.cond.left->pt.leaf.value,NULL,hash)->value : t->pt.cond.left->pt.leaf.value); char* right = (t->pt.cond.right->pt.leaf.type == L_VAR ? find_var(t->pt.cond.right->pt.leaf.value,NULL,hash)->value : t->pt.cond.right->pt.leaf.value); @@ -202,7 +217,7 @@ interp_cond(struct tree* t, struct variable** hash) return regex_cmp(left,right); case CC('!','~'): return !regex_cmp(left,right); - } + } //TODO: add numbers } else { int left = interp_cond(t->pt.cond.left, hash); @@ -224,6 +239,12 @@ interp_cond(struct tree* t, struct variable** hash) } } +void +new_action(char* l, char* r, char* s) +{ + //TODO: modify headers according to variable values +} + void interp(struct tree* t, struct variable** hash) { @@ -244,6 +265,9 @@ interp(struct tree* t, struct variable** hash) else interp(t->pt.tif.e, hash); break; + case ST_ARROW: + new_action(t->pt.arrow.kw_left, t->pt.arrow.kw_right, interp_ass_right(t->pt.arrow.s, hash)); + break; case ST_EMPTY: break; default: @@ -266,3 +290,45 @@ print_vars(struct variable** hash) } } } + +static char* +unfold(char* u) +{ + char* new; + char* pu = u; + char* pn; + + new = xmalloc(strlen(u)+1); + pn = new; + +#define IS_WHITE(c) ((c) == '\t' || (c)==' ' || c=='\n') + + while (IS_WHITE(*pu)) + pu++; + + while (*pu != 0){ + if (IS_WHITE(*pu)){ + while (IS_WHITE(*pu)) + pu++; + if (*pu != 0) + *pn++ = ' '; + } else + *pn++ = *pu++; + } + *pn = 0; + + return new; +} + +void +save_current_headers(struct variable** hash) +{ + struct hlist* p; + char* u; + + for (p = current_headers;p;p = p->next){ + u = unfold(p->value); + find_var(p->name,u,hash); + } + +} diff --git a/lex.c b/lex.c index 07d86b3..25e3a8a 100644 --- a/lex.c +++ b/lex.c @@ -19,9 +19,19 @@ static struct keys kwds[] = {"else", KW_ELSE}, {"if", KW_IF}, {"mail", KW_MAIL}, - {"pipe", KW_PIPE} + {"pipe", KW_PIPE}, + {"discard", KW_DISCARD} }; +void +read_conf(char* filename) +{ + conf = fopen(filename, "r"); + + if (! conf) + die("read_conf: %m"); +} + void __attribute__ ((noreturn)) die(char* msg, ...) { @@ -77,7 +87,7 @@ get_string_out(int delim) int c; char buf[BUFSIZE]; - while ((c = getchar()) != delim || last == '\\'){ + while ((c = getc(conf)) != delim || last == '\\'){ if (last=='\\' && c != delim) buf[i-1] = c; else { @@ -115,7 +125,7 @@ yylex(void) { int c; - while ((c = getchar ()) == ' ' || c == '\t' || c =='\n'){ + while ((c = getc(conf)) == ' ' || c == '\t' || c =='\n'){ if (c == '\n') line++; } @@ -123,7 +133,7 @@ yylex(void) if (c == EOF) return 0; - int d = getchar(); + int d = getc(conf); if (d >= 0) { switch (CC(c,d)) { case CC('!','='): yylval.n = CC('!','='); return NEQ; @@ -134,7 +144,7 @@ yylex(void) case CC('~','~'): yylval.n = CC('~','~'); return RE; case CC('-','>'): yylval.n = CC('-','>'); return ARROW; } - ungetc(d,stdin); + ungetc(d,conf); } switch (c) { @@ -165,17 +175,17 @@ yylex(void) } if (c >= '0' && c <= '9'){ - ungetc(c,stdin); + ungetc(c,conf); int i = 0; char buf[BUFSIZE]; - while ((c = getchar())>= '0' && c<= '9'){ + while ((c = getc(conf))>= '0' && c<= '9'){ buf[i] = c; i++; if (i >= BUFSIZE-1) parse_err("Too long number"); } - ungetc(c,stdin); + ungetc(c,conf); buf[i] = 0; yylval.str = xstrdup(buf); @@ -186,13 +196,13 @@ yylex(void) int i = 0; char buf[BUFSIZE]; - while (is_var_id(c = getchar())){ + while (is_var_id(c = getc(conf))){ buf[i]=c; i++; if (i >= BUFSIZE-1) parse_err("Too long identifier, max allowed length is %d",BUFSIZE-1); } - ungetc(c,stdin); + ungetc(c,conf); buf[i] = 0; yylval.str = xstrdup(buf); @@ -203,14 +213,14 @@ yylex(void) char buf[KLEN]; int n, i = 0; - ungetc(c,stdin); - while (is_alpha(c = getchar())){ + ungetc(c,conf); + while (is_alpha(c = getc(conf))){ buf[i++] = c; if (i >= KLEN) parse_err("Keyword too long"); } buf[i] = 0; - ungetc(c,stdin); + ungetc(c,conf); n = (sizeof(kwds)/sizeof(struct keys)); for (i = 0; i < n; i++){ -- 2.39.2