Annotation of researchv9/jerq/sgs/comp/local.c, revision 1.1

1.1     ! root        1: /*     @(#) local.c: 1.7 3/19/84       */
        !             2: /*     local.c - machine dependent stuff for front end
        !             3:  *
        !             4:  *             WE 32000
        !             5:  *
        !             6:  */
        !             7: 
        !             8: #include <signal.h>
        !             9: #include "mfile1.h"
        !            10: 
        !            11: int dsflag = 0;                        /* symbol info initially enabled */
        !            12: static int dlflag = 0;         /* line number info initially enabled */
        !            13: 
        !            14:        /* location counters for PROG, DATA, ADATA, ISTRNG, STRNG */
        !            15: char *locnames[] =
        !            16: {
        !            17:        "       .text\n",
        !            18:        "       .data\n",
        !            19:        "       .data\n",
        !            20:        "       .data   1\n",
        !            21:        "       .data   1\n",
        !            22: };
        !            23: 
        !            24: int minrvar = TOTREGS;
        !            25: 
        !            26: static char *tmpfn;
        !            27: static FILE *outfile = stdout;
        !            28: static FILE *tmpfp;
        !            29: 
        !            30: #ifdef M32B
        !            31:        int wloop_level = LL_BOT;       /* place "while" test at loop end */
        !            32:        int floop_level = LL_BOT;       /* place "for" test at loop end */
        !            33: #else
        !            34:        int wloop_level = LL_BOT;       /* place "while" test at loop end */
        !            35:        int floop_level = LL_BOT;       /* place "for" test at top and bot */
        !            36: #endif
        !            37: 
        !            38: 
        !            39: myexit(n)
        !            40: {
        !            41:        unlink(tmpfn);
        !            42:        if (n == 1)
        !            43:                n = 51;
        !            44:        exit(n);
        !            45: }
        !            46: 
        !            47: getout()
        !            48: {
        !            49:        myexit(55);
        !            50: }
        !            51: 
        !            52: FILE *fopen();
        !            53: static int proflag;
        !            54: 
        !            55: main(argc, argv)
        !            56: int argc;
        !            57: char **argv;
        !            58: {
        !            59:        int j, m, n;
        !            60:        char buf[BUFSIZ], *gotnm = NULL, *findnm;
        !            61: 
        !            62:        /* catch signals if they're not now being ignored */
        !            63: 
        !            64:        if (signal(SIGHUP, SIG_IGN) != SIG_IGN)
        !            65:            signal(SIGHUP, getout);
        !            66:        if (signal(SIGINT, SIG_IGN) != SIG_IGN)
        !            67:            signal(SIGINT, getout);
        !            68:        if (signal(SIGQUIT, SIG_IGN) != SIG_IGN)
        !            69:            signal(SIGQUIT, getout);
        !            70:        if (signal(SIGTERM, SIG_IGN) != SIG_IGN)
        !            71:            signal(SIGTERM, getout);
        !            72: 
        !            73:        for (m = 1; m < argc && argv[m][0] == '-'; ++m)
        !            74:        {
        !            75:                switch( argv[m][1] )
        !            76:                {
        !            77:                case 'i':       /* input file name */
        !            78:                        if (!freopen(argv[m+1], "r", stdin))
        !            79:                        {
        !            80:                                fprintf(stderr, "Can't open %s\n", argv[m+1]);
        !            81:                                myexit(2);
        !            82:                        }
        !            83:                        n = 2;
        !            84:                        break;
        !            85: 
        !            86:                case 'o':       /* output file name */
        !            87:                        if (!freopen(argv[m+1], "w", stdout))
        !            88:                        {
        !            89:                                fprintf(stderr, "Can't open %s\n", argv[m+1]);
        !            90:                                myexit(2);
        !            91:                        }
        !            92:                        n = 2;
        !            93:                        break;
        !            94: 
        !            95:                case 'f':       /* .c source file name */
        !            96:                        for (gotnm = findnm = argv[m+1]; *findnm; ++findnm)
        !            97:                                if (*findnm == '/')
        !            98:                                        gotnm = findnm + 1;
        !            99:                        n = 2;
        !           100:                        break;
        !           101: 
        !           102:                case 'd':       /* prevent symbolic debug output */
        !           103:                        if (argv[m][2] == 'l' || argv[m][3] == 'l')
        !           104:                                dlflag = 1;
        !           105:                        if (argv[m][2] == 's' || argv[m][3] == 's')
        !           106:                                dsflag = 1;
        !           107:                        n = 1;
        !           108:                        break;
        !           109: 
        !           110:                case '1':       /* debug flags to front */
        !           111:                        argv[m][1] = 'X';
        !           112:                        continue;
        !           113: 
        !           114:                case '2':       /* debug flags to back */
        !           115:                        argv[m]++;
        !           116:                        argv[m][0] = '-';
        !           117:                        continue;
        !           118: 
        !           119:                case 'V':       /* print version info */
        !           120:                        fputs("WE32000 pcc2 compiler: @(#)local.c       SVR2\n",
        !           121:                            stderr);
        !           122:                        n = 1;
        !           123:                        break;
        !           124: 
        !           125:                case 'p':
        !           126:                        ++proflag;
        !           127:                        n = 1;
        !           128:                        break;
        !           129: 
        !           130:                default:
        !           131:                        continue;
        !           132: 
        !           133:                }
        !           134: 
        !           135:                argc -= n;
        !           136:                for( j = m; j < argc; ++j )
        !           137:                        argv[j] = argv[j+n];
        !           138:                m--;
        !           139:        }
        !           140: 
        !           141:        if (gotnm != NULL)
        !           142:        {
        !           143:                strcpy(ftitle, "\"");
        !           144:                strcat(ftitle, gotnm);
        !           145:                strcat(ftitle, "\"");
        !           146:        }
        !           147:        n = mainp1(argc, argv);
        !           148:        fclose(tmpfp);
        !           149:        if (!(tmpfp = fopen(tmpfn, "r")))
        !           150:                cerror("string file disappeared???");
        !           151:        while (m = fread(buf, 1, BUFSIZ, tmpfp))
        !           152:                fwrite(buf, 1, m, stdout);
        !           153:        myexit(n);
        !           154: }
        !           155: 
        !           156: beg_file()
        !           157: {
        !           158:        /* called as the very first thing by the parser to do machine
        !           159:         * dependent stuff
        !           160:         */
        !           161:        register char *p, *s;
        !           162:        char *mktemp();
        !           163: 
        !           164:                        /* note: double quotes already in ftitle... */
        !           165:        p = ftitle + strlen( ftitle ) - 2;
        !           166:        s = p - 14;     /* max name length */
        !           167:        while ( p > s && *p != '"' && *p != '/' )
        !           168:                --p;
        !           169:        printf( "\t.file\t\"%.15s\n", p + 1 );
        !           170:        if(!(tmpfp= fopen(tmpfn = mktemp("pcc2SXXXXXX"), "w")))
        !           171:                cerror("can't create string file\n");
        !           172: }
        !           173: 
        !           174: locctr(l)              /* output the location counter */
        !           175: {
        !           176:        static int lastloc = PROG, lastpd = PROG;
        !           177:        int retval = lastloc;           /* value to return at end */
        !           178: 
        !           179:        curloc = l;
        !           180:        switch (l)
        !           181:        {
        !           182:        case PROG:
        !           183:                if (lastloc == PROG)
        !           184:                        break;
        !           185:                if (lastpd == DATA)
        !           186:                        puts("  .text");
        !           187:                lastpd = PROG;
        !           188:                outfile = stdout;
        !           189:                break;
        !           190: 
        !           191:        case DATA:
        !           192:        case ADATA:
        !           193:                if (lastloc == DATA || lastloc == ADATA)
        !           194:                        break;
        !           195:                if (lastpd == PROG)
        !           196:                        puts("  .data");
        !           197:                lastpd = DATA;
        !           198:                outfile = stdout;
        !           199:                break;
        !           200: 
        !           201:        case STRNG:
        !           202:        case ISTRNG:
        !           203:                /* output string initializers to a temporary file for now
        !           204:                 * don't update lastloc
        !           205:                 */
        !           206:                
        !           207:                outfile = tmpfp;
        !           208:                break;
        !           209: 
        !           210:        default:
        !           211:                cerror( "illegal location counter" );
        !           212:        }
        !           213: 
        !           214:        lastloc = l;
        !           215:        return( retval );               /* declare previous loc. ctr. */
        !           216: }
        !           217: 
        !           218: NODE *
        !           219: treecpy(p)             /* first pass version of tcopy() */
        !           220:        register NODE *p; 
        !           221: {
        !           222:        /* make a fresh copy of p */
        !           223:        register NODE *q;
        !           224: 
        !           225:        q = talloc();
        !           226:        *q = *p;
        !           227:        switch (optype(q->in.op))
        !           228:        {
        !           229:        case BITYPE:
        !           230:                q->in.right = treecpy(p->in.right);
        !           231:        case UTYPE:
        !           232:                q->in.left = treecpy(p->in.left);
        !           233:        }
        !           234:        return (q);
        !           235: }
        !           236: 
        !           237: 
        !           238: NODE *
        !           239: clocal(p)                      /* manipulate the parse tree for local xforms */
        !           240: register NODE *p;
        !           241: {
        !           242:        register NODE *l, *r;
        !           243: 
        !           244: #if defined(M32B) && defined(IMPREGAL)
        !           245:        if ((p->in.op == VAUTO || p->in.op == VPARAM) && p->in.pad[0] == '@')
        !           246:        {
        !           247:                raname(p);
        !           248:                p->in.pad[0] = '~';     /*has been raname()'d*/
        !           249:        }
        !           250: #endif
        !           251:        if (!asgbinop(p->in.op) && p->in.op != ASSIGN)
        !           252:                return (p);
        !           253:        r = p->in.right;
        !           254:        if (optype(r->in.op) == LTYPE)
        !           255:                return (p);
        !           256:        l = r->in.left;
        !           257:        if (r->in.op == QUEST ||
        !           258:                (r->in.op == CONV && l->in.op == QUEST) ||
        !           259:                (r->in.op == CONV && l->in.op == CONV &&
        !           260:                l->in.left->in.op == QUEST))
        !           261:                                /* distribute assigns over colons */
        !           262:        {
        !           263:                register NODE *pwork;
        !           264:                NODE *pcpy = treecpy(p), *pnew;
        !           265: #ifndef NODBG
        !           266:                extern int xdebug, eprint();
        !           267: 
        !           268:                if (xdebug)
        !           269:                {
        !           270:                        puts("Entering [op]=?: distribution");
        !           271:                        eprint(p);
        !           272:                }
        !           273: #endif
        !           274:                pnew = pcpy->in.right;
        !           275:                while (pnew->in.op != QUEST)
        !           276:                        pnew = pnew->in.left;
        !           277:                /*
        !           278:                * pnew is top of new tree
        !           279:                */
        !           280:                if ((pwork = p)->in.right->in.op == QUEST)
        !           281:                {
        !           282:                        tfree(pwork->in.right);
        !           283:                        pwork->in.right = pnew->in.right->in.left;
        !           284:                        pnew->in.right->in.left = pwork;
        !           285:                        /* at this point, 1/2 distributed. Tree looks like:
        !           286:                        *               ASSIGN|ASGOP
        !           287:                        *       LVAL                    QUEST
        !           288:                        *               EXPR1           COLON
        !           289:                        *                       ASSIGN|ASGOP    EXPR3
        !           290:                        *               LVAL            EXPR2
        !           291:                        * pnew "holds" new tree from QUEST node
        !           292:                        */
        !           293:                }
        !           294:                else
        !           295:                {
        !           296:                        NODE *pholdtop = pwork;
        !           297: 
        !           298:                        pwork = pwork->in.right;
        !           299:                        while (pwork->in.left->in.op != QUEST)
        !           300:                                pwork = pwork->in.left;
        !           301:                        tfree(pwork->in.left);
        !           302:                        pwork->in.left = pnew->in.right->in.left;
        !           303:                        pnew->in.right->in.left = pholdtop;
        !           304:                        /* at this point, 1/2 distributed. Tree looks like:
        !           305:                        *               ASSIGN|ASGOP
        !           306:                        *       LVAL                    ANY # OF CONVs
        !           307:                        *                       QUEST
        !           308:                        *               EXPR1           COLON
        !           309:                        *                       ASSIGN|ASGOP    EXPR3
        !           310:                        *               LVAL            ANY # OF CONVs
        !           311:                        *                       EXPR2
        !           312:                        * pnew "holds" new tree from QUEST node
        !           313:                        */
        !           314:                }
        !           315:                if ((pwork = pcpy)->in.right->in.op == QUEST)
        !           316:                {
        !           317:                        pwork->in.right = pnew->in.right->in.right;
        !           318:                        pnew->in.right->in.right = pwork;
        !           319:                        /*
        !           320:                        * done with the easy case
        !           321:                        */
        !           322:                }
        !           323:                else
        !           324:                {
        !           325:                        NODE *pholdtop = pwork;
        !           326: 
        !           327:                        pwork = pwork->in.right;
        !           328:                        while (pwork->in.left->in.op != QUEST)
        !           329:                                pwork = pwork->in.left;
        !           330:                        pwork->in.left = pnew->in.right->in.right;
        !           331:                        pnew->in.right->in.right = pholdtop;
        !           332:                        /*
        !           333:                        * done with the CONVs case
        !           334:                        */
        !           335:                }
        !           336:                p = pnew;
        !           337: #ifndef NODBG
        !           338:                if (xdebug)
        !           339:                {
        !           340:                        puts("Leaving [op]=?: distribution");
        !           341:                        eprint(p);
        !           342:                }
        !           343: #endif
        !           344:        }
        !           345:        return(p);
        !           346: }
        !           347: 
        !           348: 
        !           349: cisreg(t)                      /* can auto of type t go in reg */
        !           350: TWORD t;
        !           351: {
        !           352:        int nregs;
        !           353: 
        !           354:        /*
        !           355:        * Only allow register basic types or pointers.
        !           356:        * Someday, maybe allow register small-struct
        !           357:        */
        !           358:        switch (t)
        !           359:        {
        !           360:        case CHAR:      case SHORT:     case INT:       case LONG:
        !           361:        case UCHAR:     case USHORT:    case UNSIGNED:  case ULONG:
        !           362:        case FLOAT:     case DOUBLE:
        !           363:                break;
        !           364:        default:
        !           365:                if (ISPTR(t))
        !           366:                        break;
        !           367:                return (0);
        !           368:        }
        !           369:        nregs = (t == DOUBLE ? 2 : 1);
        !           370:        if (regvar + nregs <= TOTREGS-NRGS)     /* check for too many */
        !           371:        {
        !           372:                regvar += nregs;        /* number now in use */
        !           373:                if ((TOTREGS - regvar) < minrvar)
        !           374:                        minrvar -= nregs;
        !           375:                nextrvar = TOTREGS - regvar;
        !           376:                return (1);
        !           377:        }
        !           378:        else
        !           379:                return (0);
        !           380: }
        !           381: 
        !           382: incode( p, sz )
        !           383: register NODE *p;
        !           384: {
        !           385:        /* generate initialization code for assigning a constant c
        !           386:         *      to a field of width sz
        !           387:         * we assume that the proper alignment has been obtained and sz < SZINT
        !           388:         * inoff is updated to have the proper final value
        !           389:         */
        !           390:        if (inoff % SZINT == 0 )
        !           391:                printf("        .word   %d:%d", sz, p->tn.lval);
        !           392:        else
        !           393:                printf(",%d:%d", sz, p->tn.lval);
        !           394:        inoff += sz;
        !           395:        if (inoff % SZINT == 0)
        !           396:                putchar('\n');
        !           397: }
        !           398: 
        !           399: vfdzero(n)             /* define n bits of zeros in a vfd */
        !           400: int n;
        !           401: {
        !           402:        if( n <= 0 )
        !           403:                return;
        !           404:        if (inoff % SZINT == 0 )
        !           405:                printf("        .word   %d:0", n);
        !           406:        else
        !           407:                printf(",%d:0", n);
        !           408:        inoff += n;
        !           409:        if (inoff % SZINT == 0)
        !           410:                putchar('\n');
        !           411: }
        !           412: 
        !           413: fincode(d, sz)         /* floating initialization */
        !           414: double d;
        !           415: int sz;
        !           416: {
        !           417: #if defined(u3b) || defined(u3b5) || defined(u3b2)
        !           418:        union { double d; float f; int i[2] } cheat;
        !           419: 
        !           420:        if (sz == SZDOUBLE)
        !           421:        {
        !           422:                cheat.d = d;
        !           423:                printf("        .word   0x%x,0x%x\n", cheat.i[0], cheat.i[1]);
        !           424:        }
        !           425:        else
        !           426:        {
        !           427:                cheat.f = d;
        !           428:                printf("        .word   0x%x\n", cheat.i[0]);
        !           429:        }
        !           430: #else
        !           431:         printf("\t.%s\t%.15e\n", sz == SZDOUBLE ? "double" : "float", d);
        !           432: #endif
        !           433:        inoff += sz;
        !           434: }
        !           435: 
        !           436: 
        !           437: char *
        !           438: exname(p)                      /* a name using external naming conventions */
        !           439: char *p;
        !           440: {
        !           441:     return( p );
        !           442: }
        !           443: 
        !           444: 
        !           445: commdec(id)                    /* generate a .comm from stab index id */
        !           446: int id;
        !           447: {
        !           448:        register struct symtab *psym;
        !           449:        OFFSZ n;
        !           450: 
        !           451:        psym = &stab[id];
        !           452:        n = tsize(psym->stype, psym->dimoff, psym->sizoff) / SZCHAR;
        !           453: # ifndef NOSYMB
        !           454:        if ( psym->slevel == 0)
        !           455:                    prdef(psym, dsflag);        /* output debug info */
        !           456: # endif
        !           457:        if (psym->sclass == STATIC)
        !           458:                printf("        .bss    %s,%ld,%ld\n", exname(psym->sname),
        !           459:                    n, nalign(psym->stype));
        !           460:        else if (psym->sclass == EXTERN)
        !           461:                printf("        .comm   %s,%ld\n", exname(psym->sname), n);
        !           462: 
        !           463: 
        !           464:        else
        !           465:                cerror("Non-static/external in common");
        !           466: }
        !           467: 
        !           468: 
        !           469: static
        !           470: nalign(t)              /* figure alignment for type t */
        !           471: TWORD t;
        !           472: {
        !           473:        int aln;
        !           474: 
        !           475:        if (ISPTR(t))
        !           476:                aln = ALPOINT;
        !           477:        else switch (BTYPE(t))
        !           478:        {
        !           479:        case CHAR:
        !           480:        case UCHAR:
        !           481:                aln = ALCHAR;
        !           482:                break;
        !           483:        case SHORT:
        !           484:        case USHORT:
        !           485:                aln = ALSHORT;
        !           486:                break;
        !           487:        case INT:
        !           488:        case UNSIGNED:
        !           489:        case ENUMTY:
        !           490:                aln = ALINT;
        !           491:                break;
        !           492:        case LONG:
        !           493:        case ULONG:
        !           494:                aln = ALLONG;
        !           495:                break;
        !           496:        case FLOAT:
        !           497:                aln = ALFLOAT;
        !           498:                break;
        !           499:        case DOUBLE:
        !           500:                aln = ALDOUBLE;
        !           501:                break;
        !           502:        case STRTY:
        !           503:        case UNIONTY:
        !           504:                aln = ALSTRUCT;
        !           505:                break;
        !           506:        default:
        !           507:                cerror("Confused type in nalign");
        !           508:                /*NOTREACHED*/
        !           509:        }
        !           510:        return (aln / SZCHAR);
        !           511: }
        !           512: 
        !           513: 
        !           514: branch(n)                      /* branch to label n or return */
        !           515: int n;
        !           516: {
        !           517:        if (!reached)                   /* return <expr>; } comes here 2x */
        !           518:                return;
        !           519:        else
        !           520:                printf("        jmp     .L%d\n", n);
        !           521: }
        !           522: 
        !           523: 
        !           524: defalign(n)                    /* align to multiple of n */
        !           525: int n;
        !           526: {
        !           527:        if ((n /= SZCHAR) > 1)
        !           528:                printf("        .align  %d\n", n);
        !           529: }
        !           530: 
        !           531: 
        !           532: deflab(n)                      /* label n */
        !           533: int n;
        !           534: {
        !           535:        fprintf(outfile, ".L%d:\n", n);
        !           536: }
        !           537: 
        !           538: 
        !           539: efcode()                       /* wind up a function */
        !           540: {
        !           541:        extern int maxboff, maxtemp, maxarg;
        !           542:        extern int strftn;      /* non-zero if function is structure function,
        !           543:                                ** contains label number of local static value
        !           544:                                */
        !           545:        register int i, enterval;
        !           546: 
        !           547:        deflab(retlab);
        !           548: 
        !           549:        efdebug();              /* end of function debug info */
        !           550: 
        !           551:        if (strftn)                     /* return addr in 1st auto */
        !           552:                printf("        movw    0(%%fp),%%r0\n", ftnno);
        !           553:        printf("\t.set\t.F%d,%d\n\t.set\t.R%d,%d\n\tret\t&.R%d\n", ftnno,
        !           554:                (maxtemp + maxboff) / SZCHAR, ftnno, TOTREGS - minrvar, ftnno);
        !           555:        minrvar = TOTREGS;
        !           556: }
        !           557: 
        !           558: 
        !           559: bfcode(a, n)                   /* begin function code. a is array of n stab */
        !           560: int a[], n;                    /* indices corresponding to incoming args */
        !           561: {
        !           562:        int temp;
        !           563: 
        !           564: #if defined(M32B) && defined(IMPREGAL)
        !           565:        rainit();
        !           566: #endif
        !           567:        printf("        save    &.R%d\n", ftnno);
        !           568:        if (proflag)
        !           569:        {
        !           570:                puts("  .data");
        !           571:                temp = getlab();
        !           572:                deflab(temp);
        !           573:                puts("\t.align\t4\n\t.word      0\n     .text");
        !           574:                printf("        movw    &.L%d,%%r0\n",temp);
        !           575:                puts("  jsb     _mcount");
        !           576:        }
        !           577:        printf("        addw2   &.F%d,%%sp\n", ftnno);
        !           578:        retlab = getlab();
        !           579:        bfdebug( a, n, dsflag );        /* do debug info at fcn begin */
        !           580: }
        !           581: 
        !           582: 
        !           583: defnam(psym)                   /* current location is name from psym */
        !           584: register struct symtab *psym;
        !           585: {
        !           586:        /* define the current location as the name psym->sname
        !           587:         * first give the debugging info for external definitions
        !           588:         */
        !           589:        if( psym->slevel == 0 ) /* make sure it's external */
        !           590:                ISFTN(psym->stype) ? prdef(psym,0) : prdef(psym,dsflag);
        !           591: 
        !           592:        if (psym->sclass == EXTDEF)
        !           593:                printf("        .globl  %s\n", exname(psym->sname));
        !           594:        printf("%s:\n", exname(psym->sname));
        !           595: }
        !           596: 
        !           597: 
        !           598: bycode(ch, loc)                        /* byte ch into string location loc */
        !           599: int ch, loc;
        !           600: {
        !           601:        if (ch < 0)             /* eos */
        !           602:        {
        !           603:                if (loc)
        !           604:                        putc('\n', outfile);
        !           605:        }
        !           606:        else
        !           607:        {
        !           608:                if ((loc % 10) == 0)
        !           609:                        fputs("\n       .byte   ", outfile);
        !           610:                else
        !           611:                        putc(',', outfile);
        !           612:                fprintf(outfile, "%d", ch);
        !           613:        }
        !           614: }
        !           615: 
        !           616: zecode(n)                      /* n words of 0 */
        !           617: register int n;
        !           618: {
        !           619:        if (n <= 0)             /* this is possible, folks */
        !           620:                return;
        !           621:        printf("        .zero   %d\n", (SZINT / SZCHAR) * n);
        !           622:        inoff += n * SZINT;
        !           623: }
        !           624: 
        !           625: struct sw heapsw[SWITSZ];      /* heap for switches */
        !           626: 
        !           627: genswitch(p, n)
        !           628: register struct sw *p;
        !           629: int n;
        !           630: {
        !           631:        /* p points to an array of structures, each consisting  */
        !           632:        /* of a constant value and a label.                     */
        !           633:        /* The first is >=0 if there is a default label; its    */
        !           634:        /* value is the label number. The entries p[1] to p[n]  */
        !           635:        /* are the nontrivial cases                             */
        !           636: 
        !           637:        register int i;
        !           638:        register CONSZ j, range;
        !           639:        register int dlab, swlab;
        !           640: 
        !           641:        range = p[n].sval-p[1].sval;
        !           642:        if (range > 0 && range <= (3 * n) && n >= 4)
        !           643:        {                               /* implement a direct switch */
        !           644:                dlab = (p->slab >= 0) ? p->slab : getlab();
        !           645:                if (p[1].sval)
        !           646: #if defined(M32B) && defined(IMPSWREG)
        !           647:                        {
        !           648:                        printf("\tsubw3\t&%ld,%%r%d,%%r0\n\tjneg\t.L%d\n",
        !           649:                                p[1].sval, swregno, dlab);
        !           650:                        swregno = 0;
        !           651:                        }
        !           652: #else
        !           653:                        printf("\tsubw2\t&%ld,%%r0\n\tjneg\t.L%d\n",
        !           654:                                p[1].sval, dlab);
        !           655: #endif
        !           656:                swlab = getlab();
        !           657: #if defined(M32B) && defined(IMPSWREG)
        !           658:                printf("\tcmpw\t%%r%d,&%d\n\tjg\t.L%d\n\tALSW3\t&2,%%r%d,%%r0\n"
        !           659:                        , swregno, range, dlab, swregno);
        !           660:                printf("\tcmpw\t%%r%d,&0\n\tjneg\t.L%d\n",
        !           661:                        swregno, dlab);
        !           662: #else
        !           663:                printf("\tcmpw\t%%r0,&%d\n\tjg\t.L%d\n\tALSW3\t&2,%%r0,%%r0\n",
        !           664:                        range, dlab);
        !           665:                printf("\tcmpw\t%%r0,&0 \n\tjneg\t.L%d\n", dlab);
        !           666: #endif
        !           667:                printf("\tjmp\t*.L%d(%%r0)\n", swlab);
        !           668:                locctr(ADATA);                  /* output table */
        !           669:                defalign(ALPOINT);
        !           670:                puts("#SWBEG");
        !           671:                deflab(swlab);
        !           672:                for (i = 1, j = p[1].sval; i <= n; ++j)
        !           673:                        printf("        .word   .L%d\n",
        !           674:                            (j == p[i].sval) ? p[i++].slab : dlab );
        !           675:                puts("#SWEND");
        !           676:                locctr(PROG);
        !           677:                if (p->slab < 0)
        !           678:                        deflab(dlab);
        !           679:        }
        !           680:        else if ( n > 8 )
        !           681:        {
        !           682:                heapsw[0].slab = dlab = p->slab >= 0 ? p->slab : getlab();
        !           683:                makeheap( p, n, 1 );    /* build heap */
        !           684:                walkheap( 1, n );       /* produce code */
        !           685:                if( p->slab >= 0 )
        !           686:                        branch( dlab );
        !           687:                else
        !           688:                        deflab( dlab );
        !           689:        }
        !           690:        else                                    /* simple switch code */
        !           691:        {
        !           692:                for (i = 1; i <= n; ++i)
        !           693: #if defined(M32B) && defined(IMPSWREG)
        !           694:                        printf("\tcmpw\t&%ld,%%r%d\n\tje\t.L%d\n",
        !           695:                                p[i].sval, swregno, p[i].slab);
        !           696: #else
        !           697:                        printf("\tcmpw\t&%ld,%%r0\n\tje\t.L%d\n",
        !           698:                                p[i].sval, p[i].slab);
        !           699: #endif
        !           700:                if (p->slab >= 0)
        !           701:                        branch(p->slab);
        !           702:        }
        !           703: }
        !           704: 
        !           705: makeheap( p, m, n )
        !           706:        register struct sw *p;
        !           707: {
        !           708:        register int q;
        !           709: 
        !           710:        if( n >= SWITSZ )
        !           711:                cerror( "heap switch size exceeded" );
        !           712:        q = select( m );
        !           713:        heapsw[n] = p[q];
        !           714:        if( q > 1 )
        !           715:                makeheap( p, q-1, 2*n );
        !           716:        if( q < m )
        !           717:                makeheap( p+q, m-q, 2*n+1 );
        !           718: }
        !           719: 
        !           720: select( m )
        !           721: {
        !           722:        register int l, i, k;
        !           723: 
        !           724:        for( i=1; ; i*=2 )
        !           725:                if( (i-1) > m ) break;
        !           726:        l = ((k = i/2 - 1) + 1)/2;
        !           727:        return( l + (m-k < l ? m-k : l) );
        !           728: }
        !           729: 
        !           730: walkheap( start, limit )
        !           731: {
        !           732:        int label;
        !           733: 
        !           734:        if( start > limit )
        !           735:                return;
        !           736: #if defined(M32B) && defined(IMPSWREG)
        !           737:        fprintf( outfile, "\tcmpw\t%%r%d,&%ld\n\tje\t.L%d\n",
        !           738:                swregno, heapsw[start].sval, heapsw[start].slab );
        !           739: #else
        !           740:        fprintf( outfile, "\tcmpw\t%%r0,&%ld\n\tje\t.L%d\n",
        !           741:                heapsw[start].sval, heapsw[start].slab );
        !           742: #endif
        !           743:        if( (2*start) > limit )
        !           744:        {
        !           745:                fprintf( outfile, "     jmp     .L%d\n", heapsw[0].slab );
        !           746:                return;
        !           747:        }
        !           748:        if( (2*start+1) <= limit )
        !           749:        {
        !           750:                label = getlab();
        !           751:                fprintf( outfile, "     jg      .L%d\n", label );
        !           752:        }
        !           753:        else
        !           754:                fprintf( outfile, "     jg      .L%d\n", heapsw[0].slab );
        !           755:        walkheap( 2*start, limit );
        !           756:        if( (2*start+1) <= limit )
        !           757:        {
        !           758:                fprintf( outfile, ".L%d:\n", label );
        !           759:                walkheap( 2*start+1, limit );
        !           760:        }
        !           761: }
        !           762: 
        !           763: #ifdef M32B
        !           764: NODE *
        !           765: setswreg( p )
        !           766:        NODE *p;
        !           767: {
        !           768:        NODE *q;
        !           769: 
        !           770:        swregno = 0;
        !           771: #ifdef IMPSWREG
        !           772:        if (p->in.op == ASSIGN && p->in.left->in.op == SNODE)
        !           773:        {
        !           774:                q = p->in.right;
        !           775:                if( q->in.op == REG )
        !           776:                {
        !           777:                        swregno = q->tn.rval;
        !           778:                        p->in.op = FREE;
        !           779:                        p->in.left->in.op = FREE;
        !           780:                        p = q;
        !           781:                }
        !           782:        }
        !           783: #endif
        !           784:        return( p );
        !           785: }
        !           786: 
        !           787: NODE *
        !           788: myand(p)
        !           789:        NODE *p;
        !           790: {
        !           791: #ifdef IMPREGAL
        !           792:        raua(p);
        !           793: #endif
        !           794:        return(p);
        !           795: }
        !           796: #endif
        !           797: 
        !           798: 
        !           799: 
        !           800: /* interface routines to debug output */
        !           801: 
        !           802: fixdef(p)
        !           803: struct symtab * p;
        !           804: {
        !           805:     fix1def(p,dsflag);                 /* pass along flag */
        !           806:     return;
        !           807: }
        !           808: 
        !           809: strend(dimst)
        !           810: int dimst;
        !           811: {
        !           812:     str1end( dimst, dsflag );          /* pass along flag */
        !           813:     return;
        !           814: }
        !           815: 
        !           816: sdbline()
        !           817: {
        !           818:     sdbln1( dlflag );                  /* pass along flag */
        !           819:     return;
        !           820: }
        !           821: 
        !           822: aoend()
        !           823: {
        !           824:     aoend1( dsflag );                  /* pass along flag */
        !           825:     return;
        !           826: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.