#include #include #include #include "map.h" #define QUOTE(...) #__VA_ARGS__ static void ppmapget(Node*, char*, Node*); static void ppmapset(Node*, char*, Node*); static void ppmapgc(Pointer*); static Metatable mapmeta = { .index = ppmapget, .newindex = ppmapset, .gc = ppmapgc, }; static void ppmapget(Node *n, char *nam, Node *res) { Map *m; Pointer *p; Node *k; p = n->store.pval; assert(p->meta == &mapmeta); m = p->v; k = mapget(m, nam); if(k == nil){ ppsetnil(res); return; } res->op = k->op; res->store = k->store; } static void ppmapset(Node *n, char *nam, Node *res) { Pointer *p; Map *m; Node *k; p = n->store.pval; assert(p->meta == &mapmeta); m = p->v; k = ppdup(res); pppin(k); mapset(m, nam, k); } static void ppmapgc(Pointer *p) { Map *m; assert(p->meta = &mapmeta); m = p->v; mapfree(m); } static void ppmapfree(void *v) { Node *n; n = v; ppunpin(n); } static void ppmap(Node *r, Node **av, int na) { Map *map; USED(av); USED(na); map = mapnew(ppmapfree); r->op = OCONST; r->store.type = TPOINTER; r->store.pval = pppointernode(map, &mapmeta); } static void usage(void) { fprint(2, "usage: %s\n", argv0); exits("usage"); } void main(int argc, char *argv[]) { ARGBEGIN{ default: usage(); }ARGEND static char ppscript[] = QUOTE( m = map(); m.answer = "42"; m.num = 3.14; m.list = {1, 2, 3}; assert(m.answer == "42"); assert(m.num == 3.14); assert(m.list == {1,2,3}); assert(m.notexist == nil); m = {}; ); ppsetup(); ppbind("map", ppmap); if(ppcall("interpret", ppstring(ppscript), nil) < 0) sysfatal("interpret: %r"); extern void gc(int); gc(1); gc(1); ppdestroy(); exits(nil); }