From: Anicka Bernathova Date: Sun, 13 Jul 2008 18:37:20 +0000 (+0200) Subject: use clist for headers X-Git-Url: http://mj.ucw.cz/gitweb/?a=commitdiff_plain;h=80cb054f9559a0b1ef1221a29689f7431d458408;p=umpf.git use clist for headers --- diff --git a/Makefile b/Makefile index d594969..a699fee 100644 --- a/Makefile +++ b/Makefile @@ -4,7 +4,7 @@ CC=gcc CFLAGS=-Wall -W -Wno-pointer-sign -g LDLIBS=-lpcre -brum: brum.c cond.tab.o int.o lex.o ham.o +brum: brum.c cond.tab.o int.o lex.o ham.o lists.o gcc -o $@ $^ $(LDLIBS) cond.tab.o: cond.tab.c lex.o @@ -15,6 +15,8 @@ int.o: int.c ham.o: ham.c +lists.o: lists.c + cond.tab.c: cond.y bison -dvt cond.y diff --git a/brum.h b/brum.h index 2a5f939..95e8f16 100644 --- a/brum.h +++ b/brum.h @@ -1,3 +1,5 @@ +#include "lists.h" + /* cond.h */ int yylex (void); void yyerror (char const *); @@ -83,13 +85,13 @@ struct variable { }; struct hlist { + struct node car; char* name; char* value; - struct hlist* next; }; struct email { - struct hlist* headers; + struct list* headers; }; struct action { @@ -108,7 +110,7 @@ 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(); +struct list* current_headers; +struct list* make_hlist(void); +void print_headers(struct list* l); void do_action(struct action* a); diff --git a/ham.c b/ham.c index 40444e1..04153c5 100644 --- a/ham.c +++ b/ham.c @@ -8,7 +8,7 @@ int curbufsize; -static char* +static char* //TODO: rewrite buf_double(char* buf, int size) { buf = realloc(buf, 2*size); @@ -20,19 +20,15 @@ buf_double(char* buf, int size) } -static struct hlist* -new_header(char* buf, struct hlist* end) +static void +new_header(char* buf, struct list* h) { char* p; struct hlist* new; new = xmalloc(sizeof(struct hlist)); - if (end) - end->next = new; - p = strchr(buf, ':'); - if (!p) new->value = xstrdup(""); else { @@ -40,19 +36,19 @@ new_header(char* buf, struct hlist* end) new->value = xstrdup(p+1); } new->name = xstrdup(buf); - new->next = NULL; - return new; + list_add_last(h, &new->car); } -struct hlist* +struct list* make_hlist(void) { - struct hlist* start = NULL, *end = NULL; + struct list* l = xmalloc(sizeof(struct list)); char* buf; int i = 0; /* current position */ int c, last = 0; + list_init(l); buf = xmalloc(BUFSIZE); curbufsize = BUFSIZE; @@ -73,9 +69,7 @@ make_hlist(void) if (c != EOF) ungetc(c, stdin); buf[i] = 0; - end = new_header(buf, end); - if (!start) - start = end; + new_header(buf, l); i = 0; } else buf[i++] = c; @@ -83,18 +77,16 @@ make_hlist(void) last = c; } free(buf); - return start; + return l; } void -print_headers(struct hlist* h) +print_headers(struct list* l) { - struct hlist* p = h; + struct hlist* p; - while (p){ + LIST_FOREACH(p,l) printf("%s:%s",p->name,p->value); - p = p->next; - } } void diff --git a/int.c b/int.c index b83b435..fa7b08d 100644 --- a/int.c +++ b/int.c @@ -236,21 +236,19 @@ interp_cond(struct tree* t, struct variable** hash) } static void -modify_headers(struct hlist* headers, struct variable** hash) +modify_headers(struct list* headers, struct variable** hash) { struct hlist* p; - struct hlist* last = NULL; struct variable* pv; int i; - for(p = headers; p; p = p->next){ + LIST_FOREACH(p, headers){ pv = find_var(p->name,NULL,hash); if (pv->modified){ pv->modified = 0; - free(pv->value); - pv->value = xstrdup(p->value); //FIXME: fold it + free(p->value); + p->value = xstrdup(pv->value); //FIXME: fold it } - last = p; } /* find new headers */ @@ -258,33 +256,31 @@ modify_headers(struct hlist* headers, struct variable** hash) for(pv = hash[i]; pv; pv = pv->next){ if (isupper(pv->name[0]) && pv->modified){ pv->modified = 0; - p = xmalloc(sizeof(struct hlist)); - last->next = p; //FIXME - p->next = NULL; + p = xmalloc(sizeof(struct hlist)); p->name = xstrdup(pv->name); p->value = xstrdup(pv->value); + + list_add_last(headers,&p->car); } } } } -static struct hlist* -copy_headers(struct hlist* orig) +static struct list* +copy_headers(struct list* orig) { - struct hlist* new = NULL; - struct hlist* po, * pn = NULL; - - for (po = orig; po; po = po->next){ - if (!pn) - pn = xmalloc(sizeof(struct hlist)); - pn->next = xmalloc(sizeof(struct hlist)); - pn = pn->next; - pn->next = NULL; + struct list* new = xmalloc(sizeof(struct list)); + struct hlist* po, *pn; + + list_init(new); + + LIST_FOREACH(po, orig){ + pn = xmalloc(sizeof(struct hlist)); pn->name = xstrdup(po->name); pn->value = xstrdup(po->value); - if (!new) - new = pn; + + list_add_last(new, &pn->car); } return new; @@ -388,7 +384,7 @@ save_current_headers(struct variable** hash) struct variable* pv; char* u; - for (p = current_headers;p;p = p->next){ + LIST_FOREACH(p, current_headers){ u = unfold(p->value); pv = find_var(p->name,u,hash); pv->modified = 0; diff --git a/lists.c b/lists.c new file mode 100644 index 0000000..ae9c3d7 --- /dev/null +++ b/lists.c @@ -0,0 +1,113 @@ +#include +#include +#include "lists.h" + +void +list_init(struct list* l) +{ + l->head.next=&l->head; + l->head.prev=&l->head; +} + +int +list_is_empty(struct list* l) +{ + return (&l->head==l->head.next); +} + +/* return first element of the list or NULL if empty */ +void* +list_first(struct list* l) +{ + return (&l->head!=l->head.next?l->head.next:NULL); +} + +void* +list_last(struct list* l) +{ + return (&l->head!=l->head.prev?l->head.prev:NULL); +} + +void* +list_prev(struct list* l, struct node* n) +{ + return (n->prev!=&l->head?n->prev:NULL); +} + +void* +list_next(struct list* l, struct node* n) +{ + return (n->next!=&l->head?n->next:NULL); +} + +void +list_add_first(struct list* l, struct node* new) +{ + new->prev=&l->head; + new->next=l->head.next; + l->head.next->prev=new; + l->head.next=new; +} + +void +list_add_last(struct list* l, struct node* new) +{ + new->prev=l->head.prev; + new->next=&l->head; + l->head.prev->next=new; + l->head.prev=new; +} + +void +list_add_after(struct node* orig, struct node* new) +{ + new->prev=orig; + new->next=orig->next; + orig->next->prev=new; + orig->next=new; +} + +void +list_add_before(struct node* orig, struct node* new) +{ + new->prev=orig->prev; + new->next=orig; + orig->prev->next=new; + orig->prev=new; +} + +void +list_del_node(struct node* n) +{ + n->prev->next=n->next; + n->next->prev=n->prev; + n->prev=n->next=NULL; +} + +void* +list_del_first(struct list* l) +{ + struct node* del; + + if (list_is_empty(l)) + return NULL; + + del=l->head.next; + list_del_node(del); + + return del; +} + +void* +list_del_last(struct list* l) +{ + struct node* del; + + if (list_is_empty(l)) + return NULL; + + del=l->head.prev; + list_del_node(del); + + return del; +} diff --git a/lists.h b/lists.h new file mode 100644 index 0000000..e430f02 --- /dev/null +++ b/lists.h @@ -0,0 +1,23 @@ +struct node { + struct node* prev; + struct node* next; +}; + +struct list { + struct node head; +}; + +#define LIST_FOREACH(p,list) for(p=(void*)(list)->head.next; (struct node*)p!=&(list)->head; p=(void*)((struct node*) p)->next) +void list_init(struct list* l); +int list_is_empty(struct list* l); +void* list_first(struct list* l); +void* list_last(struct list* l); +void* list_prev(struct list* l, struct node* n); +void* list_next(struct list* l, struct node* n); +void list_add_first(struct list* l, struct node* new); +void list_add_last(struct list* l, struct node* new); +void list_add_after(struct node* orig, struct node* new); +void list_add_before(struct node* orig, struct node* new); +void list_del_node(struct node* n); +void* list_del_first(struct list* l); +void* list_del_last(struct list* l);