]> Shamusworld >> Repos - rmac/commitdiff
Fixed problem with nested MACROs.
authorShamus Hammons <jlhamm@acm.org>
Mon, 26 Nov 2012 04:49:46 +0000 (22:49 -0600)
committerShamus Hammons <jlhamm@acm.org>
Mon, 26 Nov 2012 04:49:46 +0000 (22:49 -0600)
While the assembler is in better shape vis-a-vis 64-bitness, there's
still a long way to go towards refactoring the thing to remove all
the problems it has with crufty data structures, and I'm sure there's
still bugs left in things like the .rept directive.

14 files changed:
debug.c
direct.c
direct.h
expr.c
macro.c
macro.h
procln.c
procln.h
rmac.c
sect.c
symbol.c
symbol.h
token.c
token.h

diff --git a/debug.c b/debug.c
index 22452671ea6915be9f689de09d7d3cfbb93979b4..7d498c77eaa36d6fce4650d995222d449bd482ce 100644 (file)
--- a/debug.c
+++ b/debug.c
@@ -48,10 +48,10 @@ TOKEN * printexpr(TOKEN * tp)
                                tp++;
                                break;
                        case CONST:
-                               printf("$%ux ", *tp++);
+                               printf("$%X ", *tp++);
                                break;
                        case ACONST:
-                               printf("ACONST=($%ux,$%ux) ", *tp, tp[1]);
+                               printf("ACONST=($%X,$%X) ", *tp, tp[1]);
                                tp += 2;
                                break;
                        default:
@@ -61,7 +61,7 @@ TOKEN * printexpr(TOKEN * tp)
                }
        }
 
-       printf(";\n");
+//     printf(";\n");
        return tp + 1;
 }
 
@@ -73,7 +73,7 @@ int chdump(CHUNK * ch, int format)
 {
        while (ch != NULL)
        {
-               printf("chloc=$%08ux, chsize=$%ux\n", ch->chloc, ch->ch_size);
+               printf("chloc=$%08X, chsize=$%X\n", ch->chloc, ch->ch_size);
                mdump(ch->chptr, ch->ch_size, format, ch->chloc);
                ch = ch->chnext;
        }
@@ -105,7 +105,7 @@ int fudump(CHUNK * ch)
                        file = *p.wp++;
                        line = *p.wp++;
 
-                       printf("$%04x $%08ux %d.%d: ", (int)attr, loc, (int)file, (int)line);
+                       printf("$%04X $%08X %d.%d: ", (int)attr, loc, (int)file, (int)line);
 
                        if (attr & FU_EXPR)
                        {
@@ -115,12 +115,18 @@ int fudump(CHUNK * ch)
                        }
                        else
                        {
-                               printf("`%s' ;\n", (*p.sy)->sname);
+//                             printf("`%s' ;\n", (*p.sy)->sname);
+                               printf("`%s' ;", (*p.sy)->sname);
                                p.sy++;
                        }
 
                        if ((attr & 0x0F00) == FU_JR)
+                       {
+                               printf(" *=$%X", *p.lp);
                                p.lp++;
+                       }
+
+                       printf("\n");
                }
 
                ch = ch->chnext;
@@ -146,7 +152,7 @@ int mudump(void)
 
        for(mch=firstmch; mch!=NULL; mch=mch->mcnext)
        {
-               printf("mch=$%08ux mcptr=$%08ux mcalloc=$%ux mcused=$%x\n",
+               printf("mch=$%08X mcptr=$%08X mcalloc=$%X mcused=$%X\n",
                        (uint32_t)mch,
                        (mch->mcptr.lw),
                        mch->mcalloc,
@@ -170,8 +176,8 @@ int mudump(void)
                        if (w & MSYMBOL)
                                symbol = *p.sy++;
 
-                       printf("m=$%04x to=%d loc=$%ux from=%d siz=%s",
-                                       w, w & 0x00ff, loc, from, (w & MLONG) ? "long" : "word");
+                       printf("m=$%04X to=%d loc=$%X from=%d siz=%s",
+                                       w, w & 0x00FF, loc, from, (w & MLONG) ? "long" : "word");
 
                        if (symbol != NULL)
                                printf(" sym=`%s'", symbol->sname);
@@ -214,21 +220,21 @@ int mdump(char * start, LONG count, int flg, LONG base)
                        j = i;
 
                        if (base != -1)
-                               printf("%08ux  ", base);
+                               printf("%08X  ", base);
                }
 
                switch (flg & 3)
                {
                case 0:
-                       printf("%02x ", start[i] & 0xff);
+                       printf("%02X ", start[i] & 0xff);
                        ++i;
                        break;
                case 1:
-                       printf("%02x%02x ", start[i] & 0xff, start[i+1] & 0xff);
+                       printf("%02X%02X ", start[i] & 0xff, start[i+1] & 0xff);
                        i += 2;
                        break;
                case 2:
-                       printf("%02x%02x%02x%02x ", start[i] & 0xff, start[i+1] & 0xff,
+                       printf("%02X%02X%02X%02X ", start[i] & 0xff, start[i+1] & 0xff,
                                start[i+2] & 0xff, start[i+3] & 0xff);
                        i += 4;
                        break;
@@ -275,21 +281,19 @@ int dumptok(TOKEN * tk)
 
                if (*tk >= 128)
                {
-                       printf("REG=%ud", *tk++ - 128);
+                       printf("REG=%u", *tk++ - 128);
                        continue;
                }
 
                switch ((int)*tk++)
                {
                case CONST:                                        // CONST <value>
-                       printf("CONST=%ud", *tk++);
+                       printf("CONST=%u", *tk++);
                        break;
                case STRING:                                       // STRING <address>
-//                     printf("STRING='%s'", (char *)*tk++);
                        printf("STRING='%s'", string[*tk++]);
                        break;
                case SYMBOL:                                       // SYMBOL <address> 
-//                     printf("SYMBOL='%s'", (char *)*tk++);
                        printf("SYMBOL='%s'", string[*tk++]);
                        break;
                case EOL:                                          // End of line 
@@ -342,7 +346,7 @@ int dump_everything(void)
        {
                if (sect[i].scattr & SUSED)
                {
-                       printf("Section %d sloc=$%ux\n", i, sect[i].sloc);
+                       printf("Section %d sloc=$%X\n", i, sect[i].sloc);
                        printf("Code:\n");
                        chdump(sect[i].sfcode, 1);
 
@@ -354,8 +358,8 @@ int dump_everything(void)
        }
 
        printf("\nMarks:\n");
-       mudump();                                                // Dump marks
-       printf("Total memory allocated=$%ux\n", amemtot);
+       mudump();                                                               // Dump marks
+       printf("Total memory allocated=$%X\n", amemtot);
 
        return 0;
 }
index 623bae4a0ee7cf0332fa555de412766a613d0e2d..d3e03031d51a108855632ec7aa9d55af2c3df6dd 100644 (file)
--- a/direct.c
+++ b/direct.c
@@ -62,7 +62,7 @@ int (*dirtab[])() = {
    d_include,                  // 33 include 
    fpop,                               // 34 end 
    d_unimpl,                   // 35* macro 
-   exitmac,                            // 36* exitm 
+   ExitMacro,                  // 36* exitm 
    d_unimpl,                   // 37* endm 
    d_list,                             // 38 list 
    d_nlist,                            // 39 nlist 
index 732a52e267e2d099ae029e23c55219c19256b20e..6da4c3e2c77e69cb3419f49f96e528b3b6e26b4c 100644 (file)
--- a/direct.h
+++ b/direct.h
@@ -39,7 +39,7 @@ int d_assert(void);
 int d_if(void);
 int d_endif(void);
 int d_include(void);
-int exitmac(void);
+int ExitMacro(void);
 int d_list(void);
 int d_nlist(void);
 int d_title(void);
diff --git a/expr.c b/expr.c
index 6e0bd18b4360f92e587deef291dcb707bc1672e5..1747c8441666c4d79815b9b11dd20609d027dbf8 100644 (file)
--- a/expr.c
+++ b/expr.c
@@ -60,7 +60,7 @@ static VALUE str_value(char * p)
 {
        VALUE v;
 
-       for(v=0; *p; ++p)
+       for(v=0; *p; p++)
                v = (v << 8) | (*p & 0xFF);
 
        return v;
@@ -76,7 +76,7 @@ void init_expr(void)
        char * p;                                                               // Token pointer
 
        // Initialize token-class table
-       for(i=0; i<128; ++i)                                    // Mark all entries END
+       for(i=0; i<128; i++)                                    // Mark all entries END
                tokcl[i] = END;
 
        for(i=0, p=itokcl; *p!=1; p++)
@@ -162,16 +162,7 @@ int expr1(void)
 #else
                        p = string[*tok++];
 #endif
-
-#if 0
-                       if (lookup(p, MACRO, 0) == NULL)
-                               w = 0;
-                       else
-                               w = 1;
-#else
                        w = (lookup(p, MACRO, 0) == NULL ? 0 : 1);
-#endif
-
                        *tk++ = CONST;
                        *tk++ = (TOKEN)w;
                        break;
@@ -194,15 +185,7 @@ getsym:
                        if (*p == '.')
                                j = curenv;
 
-#if 0
-                       if ((sy = lookup(p, LABEL, j)) != NULL && (sy->sattr & w))
-                               w = 1;
-                       else
-                               w = 0;
-#else
                        w = ((sy = lookup(p, LABEL, j)) != NULL && (sy->sattr & w) ? 1 : 0);
-#endif
-
                        *tk++ = CONST;
                        *tk++ = (TOKEN)w;
                        break;
diff --git a/macro.c b/macro.c
index 6c67bb628b6887bdc6f5381c38e96bec0cfabbb0..e136c5a10145f86b1da550203aca567031372bde 100644 (file)
--- a/macro.c
+++ b/macro.c
@@ -16,6 +16,9 @@
 #include "symbol.h"
 #include "token.h"
 
+
+static void SetupDefaultMacros(void);
+
 LONG curuniq;                                                          // Current macro's unique number
 //TOKEN ** argp;                                                               // Free spot in argptrs[]
 int macnum;                                                                    // Unique number for macro definition
@@ -35,13 +38,13 @@ static int rptlevel;                                                // .rept nesting level
 //
 // Initialize Macro Processor
 //
-void init_macro(void)
+void InitMacro(void)
 {
        macuniq = 0;
        macnum = 1;
 //     argp = NULL;
        argp = 0;
-       ib_macro();
+       SetupDefaultMacros();
 }
 
 
@@ -51,8 +54,14 @@ void init_macro(void)
 // -- restore argument stack;
 // -- pop the macro.
 //
-int exitmac(void)
+int ExitMacro(void)
 {
+#warning !!! Bad macro exiting !!!
+/*
+This is a problem. Currently, the argument logic just keeps the current
+arguments and doesn't save anything if a new macro is called in the middle
+of another (nested macros). Need to fix that somehow.
+*/
        // Pop intervening include files and .rept blocks
        while (cur_inobj != NULL && cur_inobj->in_type != SRC_IMACRO)
                fpop();
@@ -68,8 +77,11 @@ int exitmac(void)
        IMACRO * imacro = cur_inobj->inobj.imacro;
        curuniq = imacro->im_olduniq;
 
-       /*TOKEN ** p = */argp--;
+//     /*TOKEN ** p = */argp--;
 //     argp = (TOKEN **)*argp;
+       DEBUG printf("ExitMacro: argp: %d -> ", argp);
+       argp -= imacro->im_nargs;
+       DEBUG printf("%d (nargs = %d)\n", argp, imacro->im_nargs);
 
        fpop();
        mjump_align = 0;
@@ -435,8 +447,9 @@ int InvokeMacro(SYM * mac, WORD siz)
        int dry_run;
        WORD arg_siz = 0;
 //     TOKEN ** argptr = NULL;
-//Doesn't need to be global! (or does it???)
-       argp = 0;
+//Doesn't need to be global! (or does it???--it does)
+//     argp = 0;
+       DEBUG printf("InvokeMacro: argp: %d -> ", argp);
 
        if ((!strcmp(mac->sname, "mjump") || !strcmp(mac->sname, "mpad")) && !in_main)
        {
@@ -449,6 +462,11 @@ int InvokeMacro(SYM * mac, WORD siz)
        imacro->im_siz = siz;
        WORD nargs = 0;
        TOKEN * beg_tok = tok;                                          // 'tok' comes from token.c
+       TOKEN * startOfArg;
+       TOKEN * dest;
+       int stringNum = 0;
+       int argumentNum = 0;
+       int i;
 
        for(dry_run=1; ; dry_run--)
        {
@@ -457,11 +475,14 @@ int InvokeMacro(SYM * mac, WORD siz)
                        if (dry_run)
                                nargs++;
                        else
+                       {
 #if 0                          
                                *argptr++ = p;
 #else
                                argPtrs[argp++] = p;
+                               startOfArg = p;
 #endif
+                       }
 
                        // Keep going while tok isn't pointing at a comma or EOL
                        while (*tok != ',' && *tok != EOL)
@@ -474,6 +495,7 @@ int InvokeMacro(SYM * mac, WORD siz)
                                {
                                case CONST:
                                case SYMBOL:
+//Shamus: Possible bug. ACONST has 2 tokens after it, not just 1
                                case ACONST:
                                        if (dry_run)
                                        {
@@ -481,7 +503,9 @@ int InvokeMacro(SYM * mac, WORD siz)
                                                tok++;
                                        }
                                        else
+                                       {
                                                *p++ = *tok++;
+                                       }
                                // FALLTHROUGH (picks up the arg after a CONST, SYMBOL or ACONST)
                                default:
                                        if (dry_run)
@@ -490,7 +514,9 @@ int InvokeMacro(SYM * mac, WORD siz)
                                                tok++;
                                        }
                                        else
+                                       {
                                                *p++ = *tok++;
+                                       }
 
                                        break;
                                }
@@ -505,6 +531,31 @@ int InvokeMacro(SYM * mac, WORD siz)
                        // If we hit the comma instead of an EOL, skip over it
                        if (*tok == ',')
                                tok++;
+
+                       // Do our QnD token grabbing (this will be redone once we get all
+                       // the data structures fixed as this is a really dirty hack)
+                       if (!dry_run)
+                       {
+                               dest = imacro->argument[argumentNum].token;
+                               stringNum = 0;
+
+                               do
+                               {
+                                       // Remap strings to point the IMACRO internal token storage
+                                       if (*startOfArg == SYMBOL || *startOfArg == STRING)
+                                       {
+                                               *dest++ = *startOfArg++;
+                                               imacro->argument[argumentNum].string[stringNum] = strdup(string[*startOfArg++]);
+                                               *dest++ = stringNum++;
+                                       }
+                                       else
+                                               *dest++ = *startOfArg++;
+                               }
+                               while (*startOfArg != EOL);
+
+                               *dest = *startOfArg;            // Copy EOL...
+                               argumentNum++;
+                       }
                }
 
                // Allocate space for argument ptrs and so on and then go back and
@@ -512,25 +563,38 @@ int InvokeMacro(SYM * mac, WORD siz)
                if (dry_run)
                {
                        if (nargs != 0)
-//Barfing here with memory corruption in glibc. TOKEN is defined as LONG, which is uint32_t
                                p = (TOKEN *)malloc(arg_siz);
 //                             p = (TOKEN *)malloc(arg_siz + sizeof(TOKEN));
 
-// This construct is meant to deal with nested macros, so the simple minded way
-// we deal with them now won't work. :-/ Have to think about how to fix.
+/*
+Shamus:
+This construct is meant to deal with nested macros, so the simple minded way
+we deal with them now won't work. :-/ Have to think about how to fix.
+What we could do is simply move the argp with each call, and move it back by the
+number of arguments in the macro that's ending. That would solve the problem nicely.
+[Which we do now. But that uncovered another problem: the token strings are all
+stale by the time a nested macro gets to the end. But they're supposed to be symbols,
+which means if we put symbol references into the argument token streams, we can
+alleviate this problem.]
+*/
 #if 0
                        argptr = (TOKEN **)malloc((nargs + 1) * sizeof(LONG));
                        *argptr++ = (TOKEN *)argp;
                        argp = argptr;
 #else
+                       // We don't need to do anything here since we already advance argp
+                       // when parsing the arguments.
+//                     argp += nargs;
 #endif
                }
                else 
                        break;
        }
 
+       DEBUG printf("%d\n", argp);
+
        // Setup imacro:
-       // o  #arguments;
+       // o  # arguments;
        // o  -> macro symbol;
        // o  -> macro definition string list;
        // o  save 'curuniq', to be restored when the macro pops;
@@ -541,16 +605,18 @@ int InvokeMacro(SYM * mac, WORD siz)
        imacro->im_nextln = mac->lineList;
        imacro->im_olduniq = curuniq;
        curuniq = macuniq++;
+       imacro->argBase = argp - nargs;                 // Shamus: keep track of argument base
 
        DEBUG
        {
                printf("nargs=%d\n", nargs);
 
-               for(nargs=0; nargs<imacro->im_nargs; ++nargs)
+               for(nargs=0; nargs<imacro->im_nargs; nargs++)
                {
                        printf("arg%d=", nargs);
 //                     dumptok(argp[imacro->im_nargs - nargs - 1]);
-                       dumptok(argPtrs[imacro->im_nargs - nargs - 1]);
+//                     dumptok(argPtrs[imacro->im_nargs - nargs - 1]);
+                       dumptok(argPtrs[(argp - imacro->im_nargs) + nargs]);
                }
        }
 
@@ -559,9 +625,9 @@ int InvokeMacro(SYM * mac, WORD siz)
 
 
 //
-// Setup inbuilt macros
+// Setup inbuilt macros (SubQMod)
 //
-void ib_macro(void)
+static void SetupDefaultMacros(void)
 {
        curmac = NewSymbol("mjump", MACRO, 0);
        curmac->svalue = 0;
diff --git a/macro.h b/macro.h
index 2418c2607c27cf1f3061bed075c59fd1c6db5c53..81aba9483d1212809456603a5afc72041e1ca121 100644 (file)
--- a/macro.h
+++ b/macro.h
@@ -18,13 +18,12 @@ extern int mjump_align;
 extern TOKEN * argPtrs[];
 
 // Prototypes
-void init_macro(void);
-int exitmac(void);
+void InitMacro(void);
+int ExitMacro(void);
 int DefineMacro(void);
 int defrept(void);
 int lncatch(int (*)(), char *);
 int kwmatch(char *, char *);
 int InvokeMacro(SYM *, WORD);
-void ib_macro(void);
 
 #endif // __MACRO_H__
index 8127d7337cf070a6f4cb28ac8d66b6b8f61261db..6963086c9f18e69e3a3ace6004ae1a24f8404678 100644 (file)
--- a/procln.c
+++ b/procln.c
@@ -103,7 +103,7 @@ void init_procln(void)
 //
 // Line Processor
 //
-void assemble(void)
+void Assemble(void)
 {
        int state;                                      // Keyword machine state (output)
        int j;                                          // Random int, must be fast
@@ -316,7 +316,7 @@ as68label:
                                if (label != NULL)
                                        warn(lab_ignored);
 
-                               exitmac();
+                               ExitMacro();
                        }
 
                        goto loop;
@@ -533,10 +533,15 @@ normal:
        if (label != NULL)
        {
 do_label:
+               // Check for dot in front of label; means this is a local label if present
+#if 0
                j = 0;
 
                if (*label == '.')
                        j = curenv;
+#else
+               j = (*label == '.' ? curenv : 0);
+#endif
 
                sy = lookup(label, LABEL, j);
 
@@ -570,7 +575,7 @@ do_label:
                lab_sym = sy;
 
                if (!j)
-                       ++curenv;
+                       curenv++;
 
                // Make label global
                if (labtyp == DCOLON)
index a6ebe84e44f571c96286f230cdab05859b635b2b..7409b18034add656e825540a5e3eda4fd0097297 100644 (file)
--- a/procln.h
+++ b/procln.h
@@ -26,7 +26,7 @@ extern LONG amsktab[];
 
 // Prototypes
 void init_procln(void);
-void assemble(void);
+void Assemble(void);
 int eject(void);
 int d_if(void);
 int d_else(void);
diff --git a/rmac.c b/rmac.c
index eab212522bc526d46346baa01c2c4de910fb607d..fa64f777c72f866e5601ab7f305b897b23ea0c7b 100644 (file)
--- a/rmac.c
+++ b/rmac.c
@@ -569,7 +569,7 @@ int process(int argc, char ** argv)
        init_expr();                                    // Expression analyzer
        init_sect();                                    // Section manager / code generator
        init_mark();                                    // Mark tape-recorder
-       init_macro();                                   // Macro processor
+       InitMacro();                                    // Macro processor
        init_list();                                    // Listing generator
 
        // Process command line arguments and assemble source files
@@ -628,7 +628,7 @@ int process(int argc, char ** argv)
                                        break;
                                default:
                                        printf("-f: unknown object format specified\n");
-                                       ++errcnt;
+                                       errcnt++;
                                        return errcnt;
                                }
                                break;
@@ -645,7 +645,7 @@ int process(int argc, char ** argv)
                                list_fname = argv[argno] + 2;
                                listing = 1;
                                list_flag = 1;
-                               ++lnsave;
+                               lnsave++;
                                break;
                        case 'o':                                       // Direct object file output
                        case 'O':
@@ -656,7 +656,7 @@ int process(int argc, char ** argv)
                                        if (++argno >= argc)
                                        {
                                                printf("Missing argument to -o");
-                                               ++errcnt;
+                                               errcnt++;
                                                return errcnt;
                                        }
                                        objfname = argv[argno];
@@ -713,20 +713,20 @@ int process(int argc, char ** argv)
                                        firstfname = defname;
 
                                include(0, "(stdin)");
-                               assemble();
+                               Assemble();
                                break;
                        case 'h':                                       // Display command line usage
                        case 'H':
                        case '?':
                                display_version();
                                display_help();
-                               ++errcnt;
+                               errcnt++;
                                break;
                        default:
                                display_version();
                                printf("Unknown switch: %s\n\n", argv[argno]);
                                display_help();
-                               ++errcnt;
+                               errcnt++;
                                break;
                        }
                }
@@ -743,12 +743,12 @@ int process(int argc, char ** argv)
                        if (fd < 0)
                        {
                                printf("Cannot open: %s\n", fnbuf);
-                               ++errcnt;
+                               errcnt++;
                                continue;
                        }
 
                        include(fd, fnbuf);
-                       assemble();
+                       Assemble();
                }
        }
 
diff --git a/sect.c b/sect.c
index 3fd627a409560ea80ad3c38f5fc47ac1db93ffa1..1046588fd31e073351f6d363beb75e74a4da5a20 100644 (file)
--- a/sect.c
+++ b/sect.c
@@ -71,9 +71,7 @@ static char fusizoffs[] = {
 //
 void mksect(int sno, WORD attr)
 {
-       SECT * p;                                                 // Section pointer
-
-       p = &sect[sno];
+       SECT * p = &sect[sno];
        p->scattr = attr;
        p->sloc = 0;
        p->scode = p->sfcode = NULL;
@@ -125,13 +123,13 @@ void savsect(void)
 {
        SECT * p = &sect[cursect];
 
-       p->scattr = scattr;                                      // Bailout section vars
+       p->scattr = scattr;                                             // Bailout section vars
        p->sloc = sloc;
 
-       if (scode != NULL)                                        // Bailout code chunk
+       if (scode != NULL)                                              // Bailout code chunk
                scode->ch_size = ch_size;
 
-       if (sfix != NULL)                                         // Bailout fixup chunk
+       if (sfix != NULL)                                               // Bailout fixup chunk
                sfix->ch_size = fchsize;
 }
 
index 0e3cac04e49e182e48ae4778c419b6c3f518f02d..b13ef3c52fb1de59ea871a2f1531029cc83f6b79 100644 (file)
--- a/symbol.c
+++ b/symbol.c
@@ -20,6 +20,7 @@ static SYM * sorder;                                  // * -> Symbols, in order of reference
 static SYM * sordtail;                                 // * -> Last symbol in sorder list
 static SYM * sdecl;                                            // * -> Symbols, in order of declaration
 static SYM * sdecltail;                                        // * -> Last symbol in sdecl list
+static uint32_t currentUID;                            // Symbol UID tracking (done by NewSymbol())
 
 // Tags for marking symbol spaces
 // a = absolute
@@ -47,6 +48,7 @@ void InitSymbolTable(void)
        sordtail = NULL;
        sdecl = NULL;                                                   // Init symbol-decl list
        sdecltail = NULL;
+       currentUID = 0;
 }
 
 
@@ -79,18 +81,19 @@ SYM * NewSymbol(char * name, int type, int envno)
 
        if (symbol == NULL)
        {
-               printf("SYMALLOC ERROR (%s)\n", name);
+               printf("NewSymbol: MALLOC ERROR (symbol=\"%s\")\n", name);
                return NULL;
        }
 
-       symbol->sname = strdup(name);
-
        // Fill-in the symbol
+       symbol->sname  = strdup(name);
        symbol->stype  = (BYTE)type;
        symbol->senv   = (WORD)envno;
        symbol->sattr  = 0;
        symbol->sattre = (rgpu || rdsp ? RISCSYM : 0);
        symbol->svalue = 0;
+       symbol->sorder = NULL;
+       symbol->uid    = currentUID++;
 
        // Install symbol in symbol table
        int hash = HashSymbol(name, envno);
@@ -103,40 +106,43 @@ SYM * NewSymbol(char * name, int type, int envno)
        else
                sordtail->sorder = symbol;                      // Or append to tail of list
 
-       symbol->sorder = NULL;
        sordtail = symbol;
-
        return symbol;
 }
 
 
 //
-// Lookup the symbol `name', of the specified type, with the specified
-// enviroment level
+// Look up the symbol name by its UID and return the pointer to the name.
+// If it's not found, return NULL.
 //
-SYM * lookup(char * name, int type, int envno)
+char * GetSymbolNameByUID(uint32_t uid)
 {
-#if 0
-       SYM * sy;                                   // Symbol record pointer
-       int k, sum;                                 // Hash bucket calculation
-       char * s;                                   // String pointer
+       //problem is with string lookup, that's why we're writing this
+       //so once this is written, we can put the uid in the token stream
 
-       // Pick a hash-bucket (SAME algorithm as HashSymbol())
-       k = 0;
-       s = name;
+       // A much better approach to the symbol order list would be to make an
+       // array--that way you can do away with the UIDs and all the rest, and
+       // simply do an array lookup based on position. But meh, let's do this for
+       // now until we can rewrite things so they make sense.
+       SYM * symbol = sorder;
 
-       for(sum=envno; *s;)
+       for(; symbol; symbol=symbol->sorder)
        {
-               if (k++ == 1)
-                       sum += *s++ << 2;
-               else
-                       sum += *s++;
+               if (symbol->uid == uid)
+                       return symbol->sname;
        }
 
-       sy = symbolTable[sum & (NBUCKETS-1)];
-#else
+       return NULL;
+}
+
+
+//
+// Lookup the symbol `name', of the specified type, with the specified
+// enviroment level
+//
+SYM * lookup(char * name, int type, int envno)
+{
        SYM * symbol = symbolTable[HashSymbol(name, envno)];
-#endif
 
        // Do linear-search for symbol in bucket
        while (symbol != NULL)
@@ -146,8 +152,8 @@ SYM * lookup(char * name, int type, int envno)
                        && *name == *symbol->sname              // Fast check for first character
                        && !strcmp(name, symbol->sname))
                        break;
-               else
-                       symbol = symbol->snext;
+
+               symbol = symbol->snext;
        }
 
        return symbol;                                                  // Return NULL or matching symbol
@@ -157,20 +163,20 @@ SYM * lookup(char * name, int type, int envno)
 //
 // Put symbol on "order-of-declaration" list of symbols
 //
-void sym_decl(SYM * sym)
+void sym_decl(SYM * symbol)
 {
-       if (sym->sattr & SDECLLIST)
+       if (symbol->sattr & SDECLLIST)
                return;                                                         // Already on list
 
-       sym->sattr |= SDECLLIST;                                // Mark "already on list"
+       symbol->sattr |= SDECLLIST;                             // Mark "already on list"
 
        if (sdecl == NULL)
-               sdecl = sym;                                            // First on decl-list
+               sdecl = symbol;                                         // First on decl-list
        else 
-               sdecltail->sdecl = sym;                         // Add to end of list
+               sdecltail->sdecl = symbol;                      // Add to end of list
 
-       sym->sdecl = NULL;                                              // Fix up list's tail
-       sdecltail = sym;
+       symbol->sdecl = NULL;                                   // Fix up list's tail
+       sdecltail = symbol;
 }
 
 
@@ -423,7 +429,7 @@ int symtable(void)
                                        strcpy(ln2, "external");
                                else
                                {
-                                       sprintf(ln2, "%08ux", q->svalue);
+                                       sprintf(ln2, "%08X", q->svalue);
                                        uc_string(ln2);
                                }
 
index 9ce6b175e9b9235624ff7a7c4e63f7709daa2c4b..eaf9107d1a52c055842f18686190bdf8ae04a1d8 100644 (file)
--- a/symbol.h
+++ b/symbol.h
@@ -33,6 +33,7 @@ SYM
        char * sname;                                   // * -> Symbol's print-name
        struct LineList * lineList;             // * -> Macro's linked list of lines
        struct LineList * last;                 // * -> end of macro linked list
+       uint32_t uid;                                   // Symbol's unique ID
 };
 
 // Globals, externals etc
@@ -47,5 +48,6 @@ void sym_decl(SYM *);
 int syg_fix(void);
 int symtable(void);
 int sy_assign(char *, char *(*)());
+char * GetSymbolNameByUID(uint32_t);
 
 #endif // __SYMBOL_H__
diff --git a/token.c b/token.c
index 27a7f3201f20f2b5dcde958c12b3df670e8b89a3..f30db090dc2d217907ee2a7b09a70413bf02e728 100644 (file)
--- a/token.c
+++ b/token.c
@@ -32,7 +32,7 @@ WORD cfileno;                         // Current file number
 TOKEN * tok;                           // Ptr to current token
 TOKEN * etok;                          // Ptr past last token in tokbuf[]
 TOKEN tokeol[1] = {EOL};       // Bailout end-of-line token
-char * string[TOKBUFSIZE];     // Token buffer string pointer storage
+char * string[TOKBUFSIZE*2];   // Token buffer string pointer storage
 
 // File record, used to maintain a list of every include file ever visited
 #define FILEREC struct _filerec
@@ -143,8 +143,7 @@ INOBJ * a_inobj(int typ)
 
        // Allocate and initialize INOBJ first
        if (f_inobj == NULL)
-//             inobj = (INOBJ *)amem((LONG)sizeof(INOBJ));
-               inobj = (INOBJ *)malloc(sizeof(INOBJ));
+               inobj = malloc(sizeof(INOBJ));
        else
        {
                inobj = f_inobj;
@@ -155,8 +154,7 @@ INOBJ * a_inobj(int typ)
        {
        case SRC_IFILE:                                                 // Alloc and init an IFILE
                if (f_ifile == NULL)
-//                     ifile = (IFILE *)amem((LONG)sizeof(IFILE));
-                       ifile = (IFILE *)malloc(sizeof(IFILE));
+                       ifile = malloc(sizeof(IFILE));
                else
                {
                        ifile = f_ifile;
@@ -167,8 +165,7 @@ INOBJ * a_inobj(int typ)
                break;
        case SRC_IMACRO:                                                // Alloc and init an IMACRO 
                if (f_imacro == NULL)
-//                     imacro = (IMACRO *)amem((LONG)sizeof(IMACRO));
-                       imacro = (IMACRO *)malloc(sizeof(IMACRO));
+                       imacro = malloc(sizeof(IMACRO));
                else
                {
                        imacro = f_imacro;
@@ -178,8 +175,7 @@ INOBJ * a_inobj(int typ)
                inobj->inobj.imacro = imacro;
                break;
        case SRC_IREPT:                                                 // Alloc and init an IREPT
-//             inobj->inobj.irept = (IREPT *)amem((LONG)sizeof(IREPT));
-               inobj->inobj.irept = (IREPT *)malloc(sizeof(IREPT));
+               inobj->inobj.irept = malloc(sizeof(IREPT));
                DEBUG printf("alloc IREPT\n");
                break;
        }
@@ -218,8 +214,9 @@ int ExpandMacro(char * src, char * dest, int destsiz)
        char numbuf[20];                // Buffer for text of CONSTs
        TOKEN * tk;
        SYM * arg;
+       char ** symbolString;
 
-       DEBUG { printf("EM: src=\"%s\"\n", src); }
+       DEBUG { printf("ExM: src=\"%s\"\n", src); }
 
        IMACRO * imacro = cur_inobj->inobj.imacro;
        int macnum = (int)(imacro->im_macro->sattr);
@@ -284,7 +281,7 @@ int ExpandMacro(char * src, char * dest, int destsiz)
 
                                goto copy_d;
                        case '~':                                               // ==> unique label string Mnnnn... 
-                               sprintf(numbuf, "M%ud", curuniq);
+                               sprintf(numbuf, "M%u", curuniq);
 copystr:
                                d = numbuf;
 copy_d:
@@ -353,13 +350,25 @@ copy_d:
                                // macro invocation) then it is ignored.
                                i = (int)arg->svalue;
 arg_num:
-                               DEBUG printf("~argnumber=%d\n", i);
-
+                               DEBUG printf("~argnumber=%d (argBase=%u)\n", i, imacro->argBase);
                                tk = NULL;
 
                                if (i < imacro->im_nargs)
+                               {
+#if 0
 //                                     tk = argp[i];
-                                       tk = argPtrs[i];
+//                                     tk = argPtrs[i];
+                                       tk = argPtrs[imacro->argBase + i];
+#else
+                                       tk = imacro->argument[i].token;
+                                       symbolString = imacro->argument[i].string;
+//DEBUG
+//{
+//     printf("ExM: Preparing to parse argument #%u...\n", i);
+//     dumptok(tk);
+//}
+#endif
+                               }
 
                                // \?arg yields:
                                //    0  if the argument is empty or non-existant,
@@ -399,13 +408,22 @@ arg_num:
                                                        switch ((int)*tk++)
                                                        {
                                                        case SYMBOL:
+#if 0
 //                                                             d = (char *)*tk++;
                                                                d = string[*tk++];
+#else
+                                                               // This fix should be done for strings too
+                                                               d = symbolString[*tk++];
+DEBUG printf("ExM: SYMBOL=\"%s\"", d);
+#endif
                                                                break;
                                                        case STRING:
+#if 0
 //                                                             d = (char *)*tk++;
                                                                d = string[*tk++];
-
+#else
+                                                               d = symbolString[*tk++];
+#endif
                                                                if (dst >= edst)
                                                                        goto overflow;
 
@@ -516,10 +534,12 @@ strcopy:
        }
 
        *dst = EOS;
+       DEBUG { printf("ExM: dst=\"%s\"\n", dest); }
        return OK;
 
 overflow:
        *dst = EOS;
+       DEBUG printf("*** OVERFLOW LINE ***\n%s\n", dest);
        return fatal("line too long as a result of macro expansion");
 }
 
@@ -913,7 +933,7 @@ int tokln(void)
        case SRC_IMACRO:
                if ((ln = getmln()) == NULL)
                {
-                       exitmac();                                              // Exit macro (pop args, do fpop(), etc)
+                       ExitMacro();                                    // Exit macro (pop args, do fpop(), etc)
                        goto retry;                                             // Try for more lines...
                }
 
@@ -1050,7 +1070,7 @@ int tokln(void)
                        if (j < 0 || state < 0)
                        {
                                *tk++ = SYMBOL;
-#warning
+//#warning
 //problem here: nullspot is a char * but TOKEN is a uint32_t. On a 64-bit system,
 //this will cause all kinds of mischief.
 #if 0
@@ -1102,7 +1122,7 @@ int tokln(void)
                        case '\"':                                      // "string" 
                                c1 = ln[-1];
                                *tk++ = STRING;
-#warning
+//#warning
 // More char * stuffing (8 bytes) into the space of 4 (TOKEN).
 // Need to figure out how to fix this crap.
 #if 0
@@ -1513,7 +1533,7 @@ int d_goto(WORD unused)
 void DumpTokenBuffer(void)
 {
        TOKEN * t;
-       printf("Tokens: ");
+       printf("Tokens [%X]: ", sloc);
 
        for(t=tokbuf; *t!=EOL; t++)
        {
diff --git a/token.h b/token.h
index 6bc1102e3671b70faf0d857c7dfd8ef9cc7808e9..eaa7edbf25d5b1a5748f1f34bed8e8ea14d854d4 100644 (file)
--- a/token.h
+++ b/token.h
@@ -110,6 +110,12 @@ IFILE {
        char ifbuf[LNBUFSIZ];   // Line buffer
 };
 
+#define TOKENSTREAM struct _tokenstream
+TOKENSTREAM {
+       TOKEN token[10];                // 10 ought to be enough for anybody
+       char * string[10];              // same for attached strings
+};
+
 // Information about a macro invocation
 IMACRO {
        IMACRO * im_link;               // Pointer to ancient IMACROs
@@ -120,6 +126,8 @@ IMACRO {
        LONG im_olduniq;                // Old value of 'macuniq'
        SYM * im_macro;                 // Pointer to macro we're in
        char im_lnbuf[LNSIZ];   // Line buffer
+       uint32_t argBase;               // Base in argPtrs[] for current macro
+       TOKENSTREAM argument[20];       // Assume no more than 20 arguments in an invocation
 };
 
 // Information about a .rept invocation