diff options
author | Taru Karttunen <taruti@taruti.net> | 2011-03-30 15:46:40 +0300 |
---|---|---|
committer | Taru Karttunen <taruti@taruti.net> | 2011-03-30 15:46:40 +0300 |
commit | e5888a1ffdae813d7575f5fb02275c6bb07e5199 (patch) | |
tree | d8d51eac403f07814b9e936eed0c9a79195e2450 /sys/src/cmd/acid/list.c |
Import sources from 2011-03-30 iso image
Diffstat (limited to 'sys/src/cmd/acid/list.c')
-rwxr-xr-x | sys/src/cmd/acid/list.c | 277 |
1 files changed, 277 insertions, 0 deletions
diff --git a/sys/src/cmd/acid/list.c b/sys/src/cmd/acid/list.c new file mode 100755 index 000000000..5ad7c54e4 --- /dev/null +++ b/sys/src/cmd/acid/list.c @@ -0,0 +1,277 @@ +#include <u.h> +#include <libc.h> +#include <bio.h> +#include <ctype.h> +#include <mach.h> +#define Extern extern +#include "acid.h" + +static List **tail; + +List* +construct(Node *l) +{ + List *lh, **save; + + save = tail; + lh = 0; + tail = &lh; + build(l); + tail = save; + + return lh; +} + +int +listlen(List *l) +{ + int len; + + len = 0; + while(l) { + len++; + l = l->next; + } + return len; +} + +void +build(Node *n) +{ + List *l; + Node res; + + if(n == 0) + return; + + switch(n->op) { + case OLIST: + build(n->left); + build(n->right); + return; + default: + expr(n, &res); + l = al(res.type); + l->Store = res.Store; + *tail = l; + tail = &l->next; + } +} + +List* +addlist(List *l, List *r) +{ + List *f; + + if(l == 0) + return r; + + for(f = l; f->next; f = f->next) + ; + f->next = r; + + return l; +} + +void +append(Node *r, Node *list, Node *val) +{ + List *l, *f; + + l = al(val->type); + l->Store = val->Store; + l->next = 0; + + r->op = OCONST; + r->type = TLIST; + + if(list->l == 0) { + list->l = l; + r->l = l; + return; + } + for(f = list->l; f->next; f = f->next) + ; + f->next = l; + r->l = list->l; +} + +int +listcmp(List *l, List *r) +{ + if(l == r) + return 1; + + while(l) { + if(r == 0) + return 0; + if(l->type != r->type) + return 0; + switch(l->type) { + case TINT: + if(l->ival != r->ival) + return 0; + break; + case TFLOAT: + if(l->fval != r->fval) + return 0; + break; + case TSTRING: + if(scmp(l->string, r->string) == 0) + return 0; + break; + case TLIST: + if(listcmp(l->l, r->l) == 0) + return 0; + break; + } + l = l->next; + r = r->next; + } + if(l != r) + return 0; + return 1; +} + +void +nthelem(List *l, int n, Node *res) +{ + if(n < 0) + error("negative index in []"); + + while(l && n--) + l = l->next; + + res->op = OCONST; + if(l == 0) { + res->type = TLIST; + res->l = 0; + return; + } + res->type = l->type; + res->Store = l->Store; +} + +void +delete(List *l, int n, Node *res) +{ + List **tl; + + if(n < 0) + error("negative index in delete"); + + res->op = OCONST; + res->type = TLIST; + res->l = l; + + for(tl = &res->l; l && n--; l = l->next) + tl = &l->next; + + if(l == 0) + error("element beyond end of list"); + *tl = l->next; +} + +List* +listvar(char *s, vlong v) +{ + List *l, *tl; + + tl = al(TLIST); + + l = al(TSTRING); + tl->l = l; + l->fmt = 's'; + l->string = strnode(s); + l->next = al(TINT); + l = l->next; + l->fmt = 'X'; + l->ival = v; + + return tl; +} + +static List* +listlocals(Map *map, Symbol *fn, uvlong fp) +{ + int i; + uvlong val; + Symbol s; + List **tail, *l2; + + l2 = 0; + tail = &l2; + s = *fn; + + for(i = 0; localsym(&s, i); i++) { + if(s.class != CAUTO) + continue; + if(s.name[0] == '.') + continue; + + if(geta(map, fp-s.value, &val) > 0) { + *tail = listvar(s.name, val); + tail = &(*tail)->next; + } + } + return l2; +} + +static List* +listparams(Map *map, Symbol *fn, uvlong fp) +{ + int i; + Symbol s; + uvlong v; + List **tail, *l2; + + l2 = 0; + tail = &l2; + fp += mach->szaddr; /* skip saved pc */ + s = *fn; + for(i = 0; localsym(&s, i); i++) { + if (s.class != CPARAM) + continue; + + if(geta(map, fp+s.value, &v) > 0) { + *tail = listvar(s.name, v); + tail = &(*tail)->next; + } + } + return l2; +} + +void +trlist(Map *map, uvlong pc, uvlong sp, Symbol *sym) +{ + List *q, *l; + + static List **tail; + + if (tracelist == 0) { /* first time */ + tracelist = al(TLIST); + tail = &tracelist; + } + + q = al(TLIST); + *tail = q; + tail = &q->next; + + l = al(TINT); /* Function address */ + q->l = l; + l->ival = sym->value; + l->fmt = 'X'; + + l->next = al(TINT); /* called from address */ + l = l->next; + l->ival = pc; + l->fmt = 'Y'; + + l->next = al(TLIST); /* make list of params */ + l = l->next; + l->l = listparams(map, sym, sp); + + l->next = al(TLIST); /* make list of locals */ + l = l->next; + l->l = listlocals(map, sym, sp); +} |