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

1.1     ! root        1: /* @(#) match.c: 1.1 12/22/83                          */
        !             2: 
        !             3: # include "mfile2.h"
        !             4: # ifdef SDB
        !             5: # include "sdb.h"
        !             6: # endif
        !             7: 
        !             8: int fldsz, fldshf;
        !             9: 
        !            10: int sdebug = 0;
        !            11: int zflag = 0;                 /* non-zero to output stin line and cost for
        !            12:                                ** each assembly instruction
        !            13:                                */
        !            14: 
        !            15: ttype( t )
        !            16: register TWORD t; 
        !            17: {
        !            18:        /* return the coded type of t */
        !            19:        /* this is called only from the first pass */
        !            20: 
        !            21: # ifdef TWOPTRS
        !            22:        if( ISPTR(t) ) 
        !            23:        {
        !            24:                do 
        !            25:                {
        !            26:                        t = DECREF(t);
        !            27:                } while ( ISARY(t) );
        !            28:                /* arrays that are left are usually only
        !            29:                ** in structure references... 
        !            30:                */
        !            31:                if( TWOPTRS(t) ) return( TPOINT2 );
        !            32:                return( TPOINT );
        !            33:        }
        !            34: # endif
        !            35: 
        !            36:        if( t != BTYPE(t) ) return( TPOINT ); /* TPOINT means not simple! */
        !            37: 
        !            38:        switch( t )
        !            39:        {
        !            40: 
        !            41:        case CHAR:
        !            42:                return( TCHAR );
        !            43:        case SHORT:
        !            44:                return( TSHORT );
        !            45:        case STRTY:
        !            46:        case UNIONTY:
        !            47:                return( TSTRUCT );
        !            48:        case INT:
        !            49:                return( TINT );
        !            50:        case UNSIGNED:
        !            51:                return( TUNSIGNED );
        !            52:        case USHORT:
        !            53:                return( TUSHORT );
        !            54:        case UCHAR:
        !            55:                return( TUCHAR );
        !            56:        case ULONG:
        !            57:                return( TULONG );
        !            58:        case LONG:
        !            59:                return( TLONG );
        !            60:        case FLOAT:
        !            61:                return( TFLOAT );
        !            62:        case DOUBLE:
        !            63:                return( TDOUBLE );
        !            64:        case VOID:
        !            65:                return( TVOID );
        !            66:        }
        !            67:        cerror( "ttype(0%o)", t );
        !            68:        /* NOTREACHED */
        !            69: }
        !            70: 
        !            71: # define VALUE (RESC1|RESC2|RESC3|RLEFT|RRIGHT)
        !            72: 
        !            73: OPTAB *
        !            74: match( p, q )
        !            75: register NODE *p; 
        !            76: register OPTAB *q; 
        !            77: {
        !            78:        /* look for match in table */
        !            79:        /* given a tree, p, and a template q, returns the next template that
        !            80:        /* matches p */
        !            81:        /* q == NULL starts the process off */
        !            82:        /* match is not called recursively, so much of the setup can be done
        !            83:        /* into static variables */
        !            84: 
        !            85:        static NODE *r, *l;
        !            86:        static tl, tr, goal, tyop;
        !            87:        static pop, lflg;
        !            88:        int rr;
        !            89: 
        !            90:        if( !q ) {
        !            91:                /* startup code */
        !            92: 
        !            93:                q = ophead[pop=p->tn.op];
        !            94:                l = getlo( p, pop );            /* left child */
        !            95:                r = getro( p, pop );            /* right child */
        !            96:                tl = l->in.type;
        !            97:                tr = r->in.type;
        !            98:                lflg = asgop(pop);  /* forces a match on lvalues */
        !            99:                if( p->tn.goal == CCC ) goal = (VALUE|RESCC);
        !           100:                else if( p->tn.goal == NRGS ) goal = VALUE;
        !           101:                else goal = ~0;
        !           102:                tyop = p->in.type;
        !           103:        }
        !           104: 
        !           105:        else {
        !           106:                if( fast ) return( (OPTAB *)0 );  /* only first match */
        !           107:                else q = q->nextop;
        !           108:        }
        !           109:        if( !q ) return( (OPTAB *)0 );
        !           110: 
        !           111: # ifndef NODBG
        !           112:        if( sdebug ) {
        !           113:                printf( "match tree %d, op %s\n", p-node, opst[pop] );
        !           114:        }
        !           115: # endif
        !           116:        for( ; q ; q = q->nextop ){
        !           117: 
        !           118:                /* some templates are no good for computing values */
        !           119: 
        !           120:                if( !( tl & q->ltype ) ) continue;
        !           121:                if( !( tr & q->rtype ) ) continue;
        !           122: 
        !           123:                if( !( goal & q->rewrite ) ) continue;
        !           124: 
        !           125: # ifndef NODBG
        !           126:                if( sdebug ) {
        !           127:                        printf( "       try table entry, line %d, op %s\n",
        !           128:                                q->stinline, opst[q->op] );
        !           129:                }
        !           130: # endif
        !           131:                if( !( tyop & q->tyop ) ) {
        !           132: # ifndef NODBG
        !           133:                        if( sdebug ) {
        !           134:                                printf(
        !           135:                                "\tentry line %d fails tyop, %o vs %o\n",
        !           136:                                q->stinline, tyop, q->tyop );
        !           137:                        }
        !           138: # endif
        !           139:                        continue;
        !           140:                }
        !           141: 
        !           142:                if( q->rshape ){
        !           143:                        if( rr=mspine( q->rshape, (q->lshape)?r:p, 0, sha[1] )){
        !           144:                                sha[1][rr] = 0;
        !           145:                                if( !q->lshape ) ustrip(pop);
        !           146:                        }
        !           147:                        else continue;
        !           148:                }
        !           149:                else {
        !           150:                        sha[1][1] = sha[1][0] = (SHAPE *)0;
        !           151:                }
        !           152: 
        !           153:                if( q->lshape ){
        !           154:                        if( !lflg && asgop(q->op) ){
        !           155:                                /* q->op is an assignment op, pop isn't */
        !           156:                                /* thus, the lhs => a register or temp */
        !           157:                                rr = rtspine( q->lshape, p );
        !           158:                        }
        !           159:                        else rr = mspine( q->lshape, l, lflg, sha[0] );
        !           160:                        if( rr ) sha[0][rr] = 0;
        !           161:                        else continue;
        !           162:                }
        !           163:                else {
        !           164:                        sha[0][1] = sha[0][0] = (SHAPE *)0;
        !           165:                }
        !           166: 
        !           167:                /* at this point, we have a match */
        !           168: 
        !           169: # ifndef NODBG
        !           170:                if( sdebug ) {
        !           171:                        printf( "table line %d matches tree %d\n",
        !           172:                                q->stinline, p-node );
        !           173:                }
        !           174: # endif
        !           175: 
        !           176:                return( q );  /* found match */
        !           177:        }
        !           178:        return( (OPTAB *)0 );
        !           179: }
        !           180: 
        !           181: ustrip( o )
        !           182: {
        !           183:        /* strip out of sha[1] all shapes with op != o */
        !           184:        /* sty should do this someday, but for now, it's done here */
        !           185:        register i, j;
        !           186: 
        !           187:        for( j=i=0; sha[1][j]; ++j ) {
        !           188:                if( sha[1][j]->op == o ) sha[1][i++] = sha[1][j];
        !           189:        }
        !           190:        sha[1][i] = (SHAPE *)0;
        !           191: }
        !           192: 
        !           193: rtspine( ps, p )
        !           194: SHAPE **ps;
        !           195: NODE *p; {
        !           196:        /* special routine to put the lhs into a reg or a temp */
        !           197:        /* looks for reg and/or temp in s */
        !           198:        /* makes a list in sha[0] */
        !           199:        register rr;
        !           200:        register SHAPE *s;
        !           201: 
        !           202:        for( rr = 0; s = *ps; ++ps ) {
        !           203:                /* works because FREE, CCODES, REG, and TEMP are first */
        !           204:                switch( s->op ) {
        !           205: 
        !           206:                case FREE:
        !           207:                case CCODES:
        !           208:                        continue;
        !           209: 
        !           210:                case REG:
        !           211:                case TEMP:
        !           212:                        if( s->sh ) if( !spshape( s->sh, p ) ) continue;
        !           213:                        if( rr >= NSHP-1 ) cerror( "too many shapes" );
        !           214:                        sha[0][rr] = s;
        !           215:                        ++rr;
        !           216:                        continue;
        !           217: 
        !           218:                default:
        !           219:                        break;
        !           220:                }
        !           221: 
        !           222:                break;
        !           223:        }
        !           224: 
        !           225:        return( rr );
        !           226: }
        !           227: 
        !           228: restrip( pls )
        !           229: register SHAPE **pls; 
        !           230: {
        !           231:        /* throw away those shapes that can't be results */
        !           232:        register SHAPE **p;
        !           233: 
        !           234:        for( p=pls; *p = *pls; ++p, ++pls ) 
        !           235:        {
        !           236:                if( noresult( *p ) ) --p;  /* overwrite if result is illegal */
        !           237:        }
        !           238: }
        !           239: 
        !           240: noresult( s )
        !           241: register SHAPE *s; 
        !           242: {
        !           243:        if( !s ) return( 0 );
        !           244:        if( s->op == INCR || s->op == DECR ) return( 1 );
        !           245:        return( (s->sr && noresult(s->sr)) ||
        !           246:            (s->sl && noresult( s->sl )) );
        !           247: }
        !           248: 
        !           249: smspine( s, p, flag )
        !           250: register NODE  *p; 
        !           251: register SHAPE *s; 
        !           252: {
        !           253:        /* match the spine of s, including special shapes */
        !           254:        /* this is a submatch, called only by mspine */
        !           255:        /* flag is nonzero if STAR's must be skipped */
        !           256: 
        !           257:        register sop, pop;
        !           258: 
        !           259: again:
        !           260: 
        !           261:        sop = s->op;
        !           262:        pop = p->tn.op;
        !           263: 
        !           264: # ifndef NODBG
        !           265:        if( sdebug>1 )
        !           266:        {
        !           267:                printf( "                       smspine(%d[%s], %d[%s])\n",
        !           268:                s-shapes, opst[sop], p-node, opst[pop] );
        !           269:        }
        !           270: # endif
        !           271: 
        !           272:        if( ( s->sh ) && !spshape( s->sh,p) ) return( 0 );
        !           273:        if( sop != pop ) 
        !           274:        {
        !           275:                if( sop == CCODES || sop == FREE ) return(1);
        !           276:                return( !flag && (sop==REG || sop==TEMP) );
        !           277:        }
        !           278:        if( sop == STAR ) 
        !           279:        {
        !           280:                flag = 0;
        !           281:                goto recurse;
        !           282:        }
        !           283:        switch( optype( sop ) ) 
        !           284:        {
        !           285: 
        !           286:        case BITYPE:
        !           287:                if( !smspine( s->sr, p->in.right, 0 ) ) return(0);
        !           288:                flag = asgop(sop);
        !           289:                /* FALLTHRU */
        !           290: 
        !           291:        case UTYPE:
        !           292: recurse:
        !           293:                s = s->sl;
        !           294:                p = p->in.left;
        !           295:                goto again;
        !           296: 
        !           297:        default:
        !           298:                return( 1 );
        !           299:        }
        !           300: }
        !           301: 
        !           302: mspine( ps, p, flag, ppls )
        !           303: register NODE  *p;
        !           304: register SHAPE **ps;
        !           305: register SHAPE **ppls; 
        !           306: {
        !           307:        /* match the spine of s, including special shapes */
        !           308:        /* s points to a list of shapes */
        !           309:        /* those shapes that match are copied into **ppls, with a null at end */
        !           310:        /* flag = 1 forces regs and temps to match exactly */
        !           311:        /* rr, the number of matches, is returned */
        !           312: 
        !           313:        register SHAPE *s;
        !           314:        int pop, rr;
        !           315: 
        !           316: # ifndef NODBG
        !           317:        if( sdebug ) 
        !           318:        {
        !           319:                printf( "\tmspine( %d, %d, %d )\n", ps-pshape, p-node, flag );
        !           320:        }
        !           321: # endif
        !           322:        pop = p->tn.op;
        !           323: 
        !           324:        /* copy the wild-cards, and those where the op matches */
        !           325:        for( rr=0; s = *ps; ++ps ) 
        !           326:        {
        !           327:                switch( s->op ) 
        !           328:                {
        !           329: 
        !           330:                case REG:
        !           331:                case TEMP:
        !           332:                        if( flag ) break;
        !           333:                        if( s->sh ) if( !spshape(s->sh,p) ) continue;
        !           334:                        /* FALLTHRU */
        !           335: 
        !           336:                case FREE:
        !           337:                case CCODES:
        !           338:                        if( rr >= NSHP-1 ) cerror( "too many shapes" );
        !           339: 
        !           340: # ifndef NODBG
        !           341:                        if( sdebug )
        !           342:                        {
        !           343:                                printf(
        !           344:                                "\t\tmspine( %d[%s], %d[%s] ), becomes %d\n",
        !           345:                                s-shapes, opst[s->op], p-node,
        !           346:                                opst[pop], rr );
        !           347:                        }
        !           348: # endif
        !           349: 
        !           350:                        ppls[rr++] = s;
        !           351:                        continue;
        !           352: 
        !           353:                default:
        !           354:                        break;
        !           355:                }
        !           356:                break;
        !           357:        }
        !           358: 
        !           359:        /* now, either s is 0 or s has a "real" op */
        !           360:        /* the first condition survives the next two loops */
        !           361: 
        !           362:        /* we have matched the wild cards: find others where the op matches */
        !           363: 
        !           364:        for( ; (s= *ps) && s->op != pop; ++ps ) 
        !           365:        {
        !           366:                 ; 
        !           367:        }
        !           368: 
        !           369:        /* now, s is null or matches the op of p */
        !           370:        for( ; (s = *ps) && s->op == pop; ++ps ) 
        !           371:        {
        !           372: 
        !           373:                if( pop == STAR ) 
        !           374:                {
        !           375:                        if( !smspine( s->sl, p->in.left, 0 ) ) continue;
        !           376:                }
        !           377: 
        !           378:                /* general case: check the subtrees also */
        !           379:                else if( s->sl ) 
        !           380:                {
        !           381:                        if( s->sr ) 
        !           382:                        {
        !           383:                                if( !smspine( s->sr, p->in.right, 0 ) )
        !           384:                                        continue;
        !           385:                                if( !smspine( s->sl, p->in.left, asgop(s->op)) )
        !           386:                                        continue;
        !           387:                        }
        !           388:                        else 
        !           389:                        {
        !           390:                                if( !smspine( s->sl, p->in.left, flag ))
        !           391:                                        continue;
        !           392:                        }
        !           393:                }
        !           394:                else if( s->sr && !smspine( s->sr, p->in.right, 0 ) )
        !           395:                        continue;
        !           396: 
        !           397:                /* if we get this far, we are in good shape */
        !           398: 
        !           399:                if( s->sh ) if( !spshape( s->sh, p ) ) continue;
        !           400:                if( rr >= NSHP-1 ) cerror( "too many shapes" );
        !           401: 
        !           402: # ifndef NODBG
        !           403:                if( sdebug )
        !           404:                {
        !           405:                        printf( "\t\tmspine( %d[%s], %d[%s] ), becomes %d\n",
        !           406:                        s-shapes, opst[s->op], p-node,
        !           407:                        opst[pop], rr );
        !           408:                }
        !           409: # endif
        !           410: 
        !           411:                ppls[rr++] = s;
        !           412:        }
        !           413: 
        !           414:        /* fall out and we are done */
        !           415:        return( rr );
        !           416: }
        !           417: 
        !           418: 
        !           419: tempok( p )
        !           420: NODE *p; 
        !           421: 
        !           422: {
        !           423:        /* decide if the result of p is OK as a temp */
        !           424:        int o;
        !           425:        if( (o = p->tn.op) == TEMP ) return( 1 );
        !           426:        if( asgop(o) && o!=INCR && o!=DECR ) 
        !           427:        {
        !           428:                return( p->in.left->tn.op == TEMP );
        !           429:        }
        !           430:        return( 0 );
        !           431: }
        !           432: 
        !           433: int sideff;
        !           434: 
        !           435: rmside( p )
        !           436: NODE *p; 
        !           437: 
        !           438: {
        !           439:        /* p is a tree with side effects: remove them */
        !           440:        /* this is done in place */
        !           441:        int o;
        !           442:        NODE *q;
        !           443: 
        !           444:        o = p->tn.op;
        !           445:        switch( o ) 
        !           446:        {
        !           447: 
        !           448:        case INCR:
        !           449:        case DECR:
        !           450:        case ASG PLUS:
        !           451:        case ASG MINUS:
        !           452:                if( p->in.right->tn.op == ICON ) p->in.right->tn.op = FREE;
        !           453:                else 
        !           454:                {
        !           455:                        regrcl( p->in.right );
        !           456:                        tfree( p->in.right );
        !           457:                }
        !           458:                q = p->in.left;
        !           459:                *p = *q;
        !           460:                q->tn.op = FREE;
        !           461:                rmside( p );
        !           462:                return;
        !           463:        }
        !           464: 
        !           465:        switch( optype( o ) )
        !           466:        {
        !           467: 
        !           468:        case BITYPE:
        !           469:                rmside( p->in.right );
        !           470:        case UTYPE:
        !           471:                rmside( p->in.left );
        !           472:        }
        !           473: }
        !           474: 
        !           475: expand( p, goal, cp, q )
        !           476: NODE *p;  
        !           477: char *cp; 
        !           478: OPTAB *q;
        !           479: {
        !           480:        /* generate code by interpreting table entry */
        !           481: 
        !           482:        CONSZ val;
        !           483:        NODE *q1, *q2;
        !           484:        int c;
        !           485:        TWORD t;
        !           486: 
        !           487: /*# ifdef SDB
        !           488: /*     if( (c = p->tn.op) == CALL || c == UNARY CALL )
        !           489: /*     {
        !           490: /*             /* number of args (for sdb) */
        !           491: /*             pstab( S_NARGS, p->stn.argsize/SZINT);
        !           492: /*     }
        !           493: /*# endif
        !           494: /**/
        !           495: 
        !           496:        for( ; *cp; ++cp )
        !           497:        {
        !           498:                switch( *cp )
        !           499:                {
        !           500: 
        !           501:                case '\\':
        !           502:                        ++cp;
        !           503:                        /* FALLTHRU */
        !           504:                default:
        !           505:                        PUTCHAR( *cp );
        !           506:                        continue;  /* this is the usual case... */
        !           507: 
        !           508:                case '\n':
        !           509:                        if( zflag )
        !           510:                        {  /* add stin line number of production as a comment */
        !           511:                                printf( "\t\t%s %d", COMMENTSTR, q->stinline );
        !           512:                                if( p->in.cst[CEFF] < INFINITY )
        !           513:                                        printf( " = %d", p->in.cst[CEFF] );
        !           514:                        }
        !           515:                        PUTCHAR( *cp );
        !           516:                        continue;
        !           517: 
        !           518:                case 'Y':
        !           519:                        /* don't check this string: deleted by match */
        !           520:                        continue;
        !           521: 
        !           522:                case 'Z':  /* special machine dependent operations */
        !           523:                        zzzcode( p, &cp, q );
        !           524:                        continue;
        !           525: 
        !           526:                case 'E':       /* exit */
        !           527:                        if( zflag )
        !           528:                        {  /* add stin line number of production as a comment */
        !           529:                                printf( "\t%s\t%d = %d",
        !           530:                                COMMENTSTR, q->stinline, p->in.cst[CEFF] );
        !           531:                        }
        !           532:                        PUTCHAR( '\n' );
        !           533:                        return;
        !           534: 
        !           535: # ifndef STACK
        !           536:                case 'D':       /* test for dependency */
        !           537:                        q1 = getadr( p, &cp );
        !           538:                        if( cp[1] == '!' )
        !           539:                        {
        !           540:                                c=0;
        !           541:                                ++cp;
        !           542:                        }
        !           543:                        else c=1;
        !           544:                        q2 = getadr( p, &cp );
        !           545:                        if( q1->tn.op != REG ) cerror( "bad D" );
        !           546:                        if( ushare( q2, q1->tn.rval ) == c ) continue;
        !           547:                        goto cream;
        !           548: # endif
        !           549: 
        !           550:                case 'R':  /* put an operand into a particular register */
        !           551:                        /* if the operand is in the register, delete the line */
        !           552:                        q1 = getadr( p, &cp );
        !           553:                        c = (*++cp == '=');
        !           554:                        q2 = getadr( p, &cp );
        !           555:                        if( q1->tn.op != REG )
        !           556:                        {
        !           557:                                if( c ) goto cream;
        !           558:                                continue;
        !           559:                        }
        !           560:                        if( q2->tn.op != REG )
        !           561:                        {
        !           562:                                if( c ) goto cream;
        !           563:                                continue;
        !           564:                        }
        !           565:                        if( q1->tn.rval != q2->tn.rval )
        !           566:                        {
        !           567:                                if( c ) goto cream;
        !           568:                                continue;
        !           569:                        }
        !           570:                        if( c ) continue;
        !           571: cream:
        !           572:                        /* clobber a line to newline, or up to an E */
        !           573:                        while( *++cp != '\n' && *cp != 'E' ) 
        !           574:                        {
        !           575:                                if( *cp == '\\' ) ++cp; /* hide next char */
        !           576:                                if( !*cp ) return;
        !           577:                        }
        !           578:                        continue;
        !           579: 
        !           580:                case 'F':  /* this line deleted if FOREFF is active */
        !           581:                        if( goal & FOREFF ) goto cream;
        !           582:                        continue;
        !           583: 
        !           584:                case 'S':  /* field size */
        !           585:                case 'H':  /* field shift */
        !           586:                case 'M':  /* field mask, in place */
        !           587:                case 'N':  /* field mask, right shifted */
        !           588:                        c = *cp;
        !           589:                        if( cp[1] == '~' ) 
        !           590:                        {
        !           591:                                if( c == 'M' ) c = 'm';
        !           592:                                else if( c == 'N' ) c = 'n';
        !           593:                                else cerror( "bad ~ after S or H" );
        !           594:                                ++cp;
        !           595:                        }
        !           596:                        else if( cp[1] == '?' ) 
        !           597:                        {
        !           598:                                if( c == 'H' ) c = 'h';
        !           599:                                else cerror( "bad ? after S, M, or N" );
        !           600:                                ++cp;
        !           601:                        }
        !           602:                        q1 = getadr(p,&cp);
        !           603:                        if( q1->tn.op != FLD ) cerror( "bad FLD for %c", c );
        !           604:                        fldsz = UPKFSZ(q1->tn.rval);
        !           605: # ifdef RTOLBYTES
        !           606:                        fldshf = UPKFOFF(q1->tn.rval);
        !           607: # else
        !           608:                        t = q1->tn.type;
        !           609:                        if( t & (TLONG|TULONG) )
        !           610:                        {
        !           611:                                fldshf = SZLONG - fldsz - UPKFOFF(q1->tn.rval);
        !           612:                        }
        !           613:                        else if( t & (TSHORT|TUSHORT) )
        !           614:                        {
        !           615:                                fldshf = SZSHORT - fldsz - UPKFOFF(q1->tn.rval);
        !           616:                        }
        !           617:                        else if( t & (TCHAR|TUCHAR) )
        !           618:                        {
        !           619:                                fldshf = SZCHAR - fldsz - UPKFOFF(q1->tn.rval);
        !           620:                        }
        !           621:                        else fldshf = SZINT - fldsz - UPKFOFF(q1->tn.rval);
        !           622: # endif
        !           623:                        if( c == 'h' ) 
        !           624:                        {
        !           625:                                if( fldshf == 0 ) goto cream;
        !           626:                                continue;
        !           627:                        }
        !           628:                        if( c=='S' || c=='H' )
        !           629:                        {
        !           630:                                printf( "%d", c=='S' ? fldsz : fldshf );
        !           631:                                continue;
        !           632:                        }
        !           633:                        val = 1;
        !           634:                        val <<= fldsz;
        !           635:                        --val;
        !           636:                        if( c=='M' || c == 'm' ) val <<= fldshf;
        !           637:                        if( c=='m' || c == 'n' ) val = ~val;
        !           638: # ifdef MYMASK
        !           639:                        MYMASK(val);
        !           640: # else
        !           641:                        printf( "%ld" , val );
        !           642: # endif
        !           643:                        continue;
        !           644: 
        !           645:                case 'L':  /* output special label field */
        !           646:                        printf( "%d", p->bn.label );
        !           647:                        continue;
        !           648: 
        !           649:                case 'C': /* for constant value only */
        !           650:                        conput( q1 = getadr( p, &cp ) );
        !           651:                        if( !sideff ) cerror( "constant with side effects?" );
        !           652:                        continue;
        !           653: 
        !           654:                case 'I': /* in instruction */
        !           655:                        insput( q1 = getadr( p, &cp ) );
        !           656:                        if( sideff ) rmside( q1 );
        !           657:                        continue;
        !           658: 
        !           659:                case 'A': /* address of */
        !           660:                        adrput( q1 = getadr( p, &cp ) );
        !           661:                        if( sideff ) rmside( q1 );
        !           662:                        continue;
        !           663: 
        !           664:                case 'U': /* for upper half of address, only */
        !           665:                        upput( q1 = getadr( p, &cp ) );
        !           666:                        if( sideff ) rmside( q1 );
        !           667:                        continue;
        !           668: #ifdef TMPSRET
        !           669:                case 'T': /* grab a temp for structure return and give it */
        !           670:                          /* to adrput */
        !           671:                        q1 = talloc();
        !           672:                        q1->tn.op = TEMP;
        !           673:                        q1->tn.type = TSTRUCT;
        !           674:                        q1->tn.lval = freetemp(p->stn.stsize / SZINT);
        !           675:                        q1->tn.lval = BITOOR(q1->tn.lval);
        !           676:                        adrput(q1);
        !           677:                        tfree(q1);
        !           678:                        continue;
        !           679: #endif
        !           680: 
        !           681:                }
        !           682:        }
        !           683: }
        !           684: 
        !           685: NODE *
        !           686: getlr( p, c )
        !           687: NODE *p; 
        !           688: 
        !           689: {
        !           690: 
        !           691:        /* return the pointer to the left or right side of p, or p itself,
        !           692:        ** depending on the optype of p 
        !           693:        */
        !           694: 
        !           695:        switch( c ) 
        !           696:        {
        !           697: 
        !           698:        case '1':
        !           699:        case '2':
        !           700:        case '3':
        !           701:                return( &resc[c-'1'] );
        !           702: 
        !           703:        case 'L':
        !           704:                return( optype( p->in.op ) == LTYPE ? p : p->in.left );
        !           705: 
        !           706:        case 'R':
        !           707:                return( optype( p->in.op ) != BITYPE ? p : p->in.right );
        !           708: 
        !           709:        }
        !           710:        cerror( "bad getlr: %c", c );
        !           711:        /* NOTREACHED */
        !           712: }
        !           713: 
        !           714: NODE *
        !           715: getadr( p, pc )
        !           716: NODE *p; 
        !           717: char **pc; 
        !           718: 
        !           719: {
        !           720:        /* like getlr, but allows (LL), (LR), etc. */
        !           721:        int c;
        !           722:        sideff = 1;
        !           723:        c = *++(*pc);
        !           724:        if( c == '-' )
        !           725:        {
        !           726:                c = *++(*pc);
        !           727:                sideff = 0;
        !           728:        }
        !           729:        if( c == '.' ) return( p );
        !           730:        else if( c != '(' ) return( getlr( p, c ) );
        !           731: 
        !           732:        for(;;) 
        !           733:        {
        !           734:                switch( c = *++(*pc) ) 
        !           735:                {
        !           736: 
        !           737:                case ')':
        !           738:                        return( p );
        !           739: 
        !           740:                case 'L':
        !           741:                        p = getl( p );
        !           742:                        continue;
        !           743: 
        !           744:                case 'R':
        !           745:                        p = getr( p );
        !           746:                        continue;
        !           747: 
        !           748:                default:
        !           749:                        cerror( "bad table char in (): %c", c );
        !           750:                }
        !           751:        }
        !           752:        /* NOTREACHED */
        !           753: }
        !           754: 
        !           755: long pow2[] = 
        !           756: {
        !           757:        01L,    02L,    04L,
        !           758:        010L,   020L,   040L,
        !           759:        0100L,  0200L,  0400L,
        !           760:        01000L, 02000L, 04000L,
        !           761:        010000L,        020000L,        040000L,
        !           762:        0100000L,       0200000L,       0400000L,
        !           763:        01000000L,      02000000L,      04000000L,
        !           764:        010000000L,     020000000L,     040000000L,
        !           765:        0100000000L,    0200000000L,    0400000000L,
        !           766:        01000000000L,   02000000000L,   04000000000L,
        !           767:        010000000000L,  020000000000L,  040000000000L,
        !           768: };
        !           769: 
        !           770: spshape( sh, p )
        !           771: NODE *p; 
        !           772: 
        !           773: {
        !           774:        long val;
        !           775:        int t, i;
        !           776: 
        !           777:        if( !(sh&SPECIAL) ) cerror( "spshape" );
        !           778:        if( sh&SPTYPE )
        !           779:        {
        !           780: # ifndef NODBG
        !           781:                if( sdebug )
        !           782:                        printf( "SPTYPE(%d, %o), ttype=%o\n", p-node,
        !           783:                                sh, p->tn.type );
        !           784: # endif
        !           785: 
        !           786:                if( sh & p->tn.type ) return( 1 );
        !           787:                else return( 0 );
        !           788:        }
        !           789:        t = (sh&STMASK);
        !           790:        i = (sh&SVMASK);
        !           791: 
        !           792:        switch( t ) 
        !           793:        {
        !           794: 
        !           795:        case SRANGE0:
        !           796:        case SSRANGE:
        !           797:                if( i<0 || i>31 ) cerror( "bad shape range" );
        !           798:        case SVAL:
        !           799:        case SNVAL:
        !           800:        case NACON:
        !           801: 
        !           802:                if( p->tn.op != ICON || p->tn.name != (char *) 0 ) return( 0 );
        !           803:                if( t == NACON ) return(1);
        !           804:                val = p->tn.lval;
        !           805:                if( t==SVAL && val == i ) return( 1 );
        !           806:                else if( t==SNVAL && val == -i ) return( 1 );
        !           807:                else if( t==SRANGE0 && val>=0 && val<pow2[i] ) return( 1 );
        !           808:                else if( t==SSRANGE && val>= -pow2[i] && val<pow2[i] )return(1);
        !           809:                return( 0 );
        !           810: 
        !           811:        case SUSER:
        !           812:                return( special( sh, p ) );
        !           813: 
        !           814:        default:
        !           815:                cerror( "bad special call" );
        !           816:                /* NOTREACHED */
        !           817:        }
        !           818: }

unix.superglobalmegacorp.com

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