/* ---------------------------------------------- * gabsCODE.c * * C Code generation: implementation file * ---------------------------------------------- */ #include "gabsGA.h" #include "gabsCODE.h" /* ---------------------------------------------- * Main driver function for code generation * ---------------------------------------------- */ void codeGeneration( BlockList bl ) { printf("/* -----------------------------------\n"); printf(" * Production Selectors\n"); printf(" * -----------------------------------\n"); printf(" */\n\n"); psBlockList(bl); printf("/* -----------------------------------\n"); printf(" * Abstract Data Types Definition\n"); printf(" * -----------------------------------\n"); printf(" */\n\n"); codeBlockList(bl); printf("/* -----------------------------------\n"); printf(" * Constructor Function Signatures\n"); printf(" * -----------------------------------\n"); printf(" */\n\n"); cfBlockList(bl); } /* ---------------------------------------------- * AST traversal for the abstract data types generation * ---------------------------------------------- */ void codeBlockList( BlockList bl ) { if(bl->flag != BLOCKLISTNIL) { codeBlock(bl->u.blocklist.b); codeBlockList(bl->u.blocklist.bl); } } void codeBlock( Block b ) { printf("/* --- %s ---*/\n", b->u.block.simbN); printf("typedef struct s%s \n", b->u.block.simbN); printf("{ int flag;\n union { \n"); codeDList(b->u.block.dl,1); printf(" } u;\n} *%s;\n\n", b->u.block.simbN); } void codeDList( DList dl, int dcont) { if(dl->flag == DLISTNIL) printf("\n"); else { printf(" struct {\n"); codeDeriv(dl->u.dlist.d); printf(" } d%d;\n",dcont); codeDList(dl->u.dlist.dl,++dcont); } } void codeDeriv( Deriv d ) { codeSimbList(d->u.deriv.sl, 1); } void codeSimbList( SimbList sl, int scont ) { if(sl->flag != SIMBLISTNIL) { codeSimb(sl->u.simblist.s, scont); codeSimbList(sl->u.simblist.sl, ++scont); } } void codeSimb( Simb s, int scont ) { if(s->flag == TERMINAL) printf(" %s s%d;\n",s->u.term.s, scont); else printf(" %s s%d;\n",s->u.nterm.s, scont); } /* ---------------------------------------------- * AST traversal for production selectors generation * ---------------------------------------------- */ int production = 0; void psBlockList( BlockList bl ) { if(bl->flag != BLOCKLISTNIL) { psBlock(bl->u.blocklist.b); psBlockList(bl->u.blocklist.bl); } } void psBlock( Block b ) { psDList(b->u.block.dl); } void psDList( DList dl) { if(dl->flag == DLISTNIL) printf("\n"); else { psDeriv(dl->u.dlist.d); psDList(dl->u.dlist.dl); } } void psDeriv( Deriv d ) { printf("#define PS%s %d\n", d->u.deriv.id, 2000+(production++)); } /* ---------------------------------------------- * AST traversal for constructor function signature generation * ---------------------------------------------- */ void cfBlockList( BlockList bl ) { if(bl->flag != BLOCKLISTNIL) { cfBlock(bl->u.blocklist.b); cfBlockList(bl->u.blocklist.bl); } } void cfBlock( Block b ) { cfDList(b->u.block.dl, b->u.block.simbN); } void cfDList( DList dl, char *cftype) { if(dl->flag == DLISTNIL) printf("\n"); else { printf("%s ", cftype); cfDeriv(dl->u.dlist.d); cfDList(dl->u.dlist.dl, cftype); } } void cfDeriv( Deriv d ) { printf(" %s();\n", d->u.deriv.id); } void cfSimbList( SimbList sl, int scont ) { if(sl->flag != SIMBLISTNIL) { cfSimb(sl->u.simblist.s, scont); cfSimbList(sl->u.simblist.sl, ++scont); } } void cfSimb( Simb s, int scont ) { if(s->flag == TERMINAL) printf(" %s s%d;\n",s->u.term.s, scont); else printf(" %s s%d;\n",s->u.nterm.s, scont); }