Annotation of 3BSD/cmd/as/asexpr.c, revision 1.1

1.1     ! root        1: /* Copyright (c) 1979 Regents of the University of California */
        !             2: #include <stdio.h>
        !             3: #include "as.h"
        !             4: #include "asexpr.h"
        !             5: 
        !             6: /*
        !             7:  * Tables for combination of operands.
        !             8:  */
        !             9: 
        !            10: /*
        !            11:  *     table for +
        !            12:  */
        !            13: readonly char pltab[6][6] = {
        !            14: /*             UND     ABS     TXT     DAT     BSS     EXT */
        !            15: 
        !            16: /*UND*/                XUNDEF, XUNDEF, XUNDEF, XUNDEF, XUNDEF, XUNDEF,
        !            17: /*ABS*/                XUNDEF, XABS,   XTEXT,  XDATA,  XBSS,   XXTRN,
        !            18: /*TXT*/                XUNDEF, XTEXT,  ERR,    ERR,    ERR,    ERR,
        !            19: /*DAT*/                XUNDEF, XDATA,  ERR,    ERR,    ERR,    ERR,
        !            20: /*BSS*/                XUNDEF, XBSS,   ERR,    ERR,    ERR,    ERR,
        !            21: /*EXT*/                XUNDEF, XXTRN,  ERR,    ERR,    ERR,    ERR,
        !            22: };
        !            23: 
        !            24: /*
        !            25:  *     table for -
        !            26:  */
        !            27: readonly char mintab[6][6] = {
        !            28: /*             UND     ABS     TXT     DAT     BSS     EXT */
        !            29: 
        !            30: /*UND*/                XUNDEF, XUNDEF, XUNDEF, XUNDEF, XUNDEF, XUNDEF,
        !            31: /*ABS*/                XUNDEF, XABS,   ERR,    ERR,    ERR,    ERR,
        !            32: /*TXT*/                XUNDEF, XTEXT,  XABS,   ERR,    ERR,    ERR,
        !            33: /*DAT*/                XUNDEF, XDATA,  ERR,    XABS,   ERR,    ERR,
        !            34: /*BSS*/                XUNDEF, XBSS,   ERR,    ERR,    XABS,   ERR,
        !            35: /*EXT*/                XUNDEF, XXTRN,  ERR,    ERR,    ERR,    ERR,
        !            36: };
        !            37: 
        !            38: /* 
        !            39:  *     table for other operators
        !            40:  */
        !            41: readonly char othtab[6][6] = {
        !            42: /*             UND     ABS     TXT     DAT     BSS     EXT */
        !            43: 
        !            44: /*UND*/                XUNDEF, XUNDEF, XUNDEF, XUNDEF, XUNDEF, XUNDEF,
        !            45: /*ABS*/                XUNDEF, XABS,   ERR,    ERR,    ERR,    ERR,
        !            46: /*TXT*/                XUNDEF, ERR,    ERR,    ERR,    ERR,    ERR,
        !            47: /*DAT*/                XUNDEF, ERR,    ERR,    ERR,    ERR,    ERR,
        !            48: /*BSS*/                XUNDEF, ERR,    ERR,    ERR,    ERR,    ERR,
        !            49: /*EXT*/                XUNDEF, ERR,    ERR,    ERR,    ERR,    ERR,
        !            50: };
        !            51: 
        !            52: struct exp *
        !            53: combine(op, exp1, exp2)
        !            54:        register struct exp *exp1, *exp2;
        !            55: {
        !            56:        register        e1_type, e2_type;
        !            57:        register        type;
        !            58: 
        !            59:        lastnam=0;                      /* kludge for jxxx instructions */
        !            60: 
        !            61:        e1_type = exp1->xtype&XTYPE;
        !            62:        e2_type = exp2->xtype&XTYPE;
        !            63: 
        !            64:        if (exp1->xtype==XXTRN+XUNDEF)
        !            65:                e1_type = XTXRN;
        !            66:        if (exp2->xtype==XXTRN+XUNDEF)
        !            67:                e2_type = XTXRN;
        !            68:        if (passno==1)
        !            69:                if (exp1->xloc!=exp2->xloc && e1_type==e2_type)
        !            70:                        e1_type = e2_type = XTXRN;      /* error on != loc ctrs */
        !            71:        e1_type >>= 1;          /*dispost of the external (XXTRN) bit*/
        !            72:        e2_type >>= 1;
        !            73: 
        !            74:        switch (op) {
        !            75:        case PLUS:
        !            76:                exp1->xvalue += exp2->xvalue;
        !            77:                type = pltab[e1_type][e2_type];
        !            78:                break;
        !            79:        case MINUS:
        !            80:                exp1->xvalue -= exp2->xvalue;
        !            81:                type = mintab[e1_type][e2_type];
        !            82:                break;
        !            83:        case IOR:
        !            84:                exp1->xvalue |= exp2->xvalue;
        !            85:                goto comm;
        !            86:        case XOR:
        !            87:                exp1->xvalue ^= exp2->xvalue;
        !            88:                goto comm;
        !            89:        case AND:
        !            90:                exp1->xvalue &= exp2->xvalue;
        !            91:                goto comm;
        !            92:        case ORNOT:
        !            93:                exp1->xvalue |= ~exp2->xvalue;
        !            94:                goto comm;
        !            95:        case LSH:
        !            96:                exp1->xvalue <<= exp2->xvalue;
        !            97:                goto comm;
        !            98:        case RSH:
        !            99:                exp1->xvalue >>= exp2->xvalue;
        !           100:                goto comm;
        !           101:        case TILDE:
        !           102:                exp1->xvalue |= ~ exp2->xvalue;
        !           103:                goto comm;
        !           104:        case MUL:
        !           105:                exp1->xvalue *= exp2->xvalue;
        !           106:                goto comm;
        !           107:        case DIV:
        !           108:                if (exp2->xvalue == 0)
        !           109:                        yyerror("Divide check");
        !           110:                else
        !           111:                        exp1->xvalue /= exp2->xvalue;
        !           112:                goto comm;
        !           113:        case REGOP:
        !           114:                if (exp2->xvalue == 0)
        !           115:                        yyerror("Divide check (modulo)");
        !           116:                else
        !           117:                        exp1->xvalue %= exp2->xvalue;
        !           118:                goto comm;
        !           119:        
        !           120:        comm:
        !           121:                type = othtab[e1_type][e2_type];
        !           122:                break;
        !           123:        default:
        !           124:                yyerror("Internal error: unknown operator");
        !           125:        }
        !           126: 
        !           127:        if (e2_type==(XTXRN>>1))
        !           128:                exp1->xname = exp2->xname;
        !           129:        exp1->xtype = type | (
        !           130:                        (exp1->xtype|exp2->xtype) & (XFORW|XXTRN) );
        !           131:        if (type==ERR)
        !           132:                yyerror("Relocation error");
        !           133:        return(exp1);
        !           134: }
        !           135: 
        !           136: buildtokensets()
        !           137: {
        !           138: #define clobber(val, set) tokensets[(val)] |= (set)
        !           139: 
        !           140:        clobber(SEMI,   LINSTBEGIN);
        !           141:        clobber(NL,     LINSTBEGIN);
        !           142: 
        !           143:        clobber(NAME,   YUKKYEXPRBEG + LINSTBEGIN);
        !           144:        clobber(INSTn,  YUKKYEXPRBEG);
        !           145:        clobber(INST0,  YUKKYEXPRBEG);
        !           146:        clobber(REG,    YUKKYEXPRBEG);
        !           147: 
        !           148:        clobber(INT,    SAFEEXPRBEG);
        !           149:        clobber(FLTNUM, SAFEEXPRBEG);
        !           150: 
        !           151:        clobber(PLUS,   ADDOPS);
        !           152:        clobber(MINUS,  ADDOPS + EBEGOPS);
        !           153: 
        !           154:        clobber(LP,     EBEGOPS);
        !           155: 
        !           156:        clobber(IOR,    BOOLOPS);
        !           157:        clobber(XOR,    BOOLOPS);
        !           158:        clobber(AND,    BOOLOPS);
        !           159:        clobber(ORNOT,  BOOLOPS);
        !           160: 
        !           161:        clobber(TILDE,  MULOPS + EBEGOPS);
        !           162:        clobber(LSH,    MULOPS);
        !           163:        clobber(RSH,    MULOPS);
        !           164:        clobber(MUL,    MULOPS);
        !           165:        clobber(DIV,    MULOPS);
        !           166:        clobber(REGOP,  MULOPS);        /* % */
        !           167: }
        !           168: 
        !           169: /*
        !           170:  *     We keep the current token class in this global variable, so 
        !           171:  *     the recursive descent expression analyzers can talk amongst
        !           172:  *     themselves, and so that we may use the macros shift and shift over
        !           173:  */
        !           174: 
        !           175: extern int     yylval;         /*the value of the lexical value*/
        !           176: extern struct  exp     *xp;    /*the next free expression slot*/
        !           177: 
        !           178: static int     val;
        !           179: int exprparse(inval, backexpr) /*return the value the read head is sitting on*/
        !           180:        int     inval;
        !           181:        struct  exp **backexpr;
        !           182: {
        !           183:        register struct exp *lexpr;
        !           184:        int     op;
        !           185: 
        !           186:        val = inval;
        !           187:        lexpr = boolterm();
        !           188:        while (INTOKSET(val, ADDOPS)){
        !           189:                op = val;
        !           190:                shift;
        !           191:                lexpr = combine(op, lexpr, boolterm());
        !           192:        }
        !           193:        *backexpr = lexpr;
        !           194:        return(val);
        !           195: }
        !           196: 
        !           197: struct exp *boolterm()
        !           198: {
        !           199:        register        struct exp *lexpr;
        !           200:        int     op;
        !           201: 
        !           202:        lexpr = term();
        !           203:        while(INTOKSET(val, BOOLOPS)){
        !           204:                op = val;
        !           205:                shift;
        !           206:                lexpr = combine(op, lexpr, term());
        !           207:        }
        !           208:        return(lexpr);
        !           209: }
        !           210: 
        !           211: struct exp *term()
        !           212: {
        !           213:        register        struct  exp     *lexpr;
        !           214:        int             op;
        !           215: 
        !           216:        lexpr = factor();
        !           217:        while(INTOKSET(val, MULOPS)){
        !           218:                op = val;
        !           219:                shift;
        !           220:                lexpr = combine(op, lexpr, factor());
        !           221:        }
        !           222:        return(lexpr);
        !           223: }
        !           224: 
        !           225: struct exp *factor()
        !           226: {
        !           227:        struct  exp *lexpr;
        !           228:        int             op;
        !           229:        extern          int     droppedLP;      /*called exprparse after consuming an LP*/
        !           230: 
        !           231:        if (val == LP || droppedLP){
        !           232:                if (droppedLP)
        !           233:                        droppedLP = 0;
        !           234:                else
        !           235:                        shift;          /*the LP*/
        !           236:                val = exprparse(val, &lexpr);
        !           237:                if (val != RP)
        !           238:                        yyerror("right parenthesis expected");
        !           239:                else
        !           240:                        shift;
        !           241:        } else
        !           242:        if (INTOKSET(val, YUKKYEXPRBEG)){
        !           243:                lexpr = yukkyexpr(val, yylval);
        !           244:                shift;
        !           245:        }
        !           246:        else if (INTOKSET(val, SAFEEXPRBEG)){
        !           247:                lexpr = (struct exp *)yylval;
        !           248:                shift;
        !           249:        }
        !           250:        else if ( (val == TILDE) || (val == MINUS) ){
        !           251:                op = val;
        !           252:                shift;
        !           253:                lexpr = xp++;
        !           254:                lexpr->xtype = XABS;
        !           255:                lexpr->xvalue = 0;
        !           256:                lexpr = combine(op, lexpr, factor());
        !           257:        }
        !           258:        else {
        !           259:                yyerror("Bad expression syntax");
        !           260:                lexpr = xp++;
        !           261:                lexpr->xtype = XABS;
        !           262:                lexpr->xvalue = 0;
        !           263:        }
        !           264:        return(lexpr);
        !           265: }
        !           266: 
        !           267: struct exp *yukkyexpr(val, np)
        !           268:        int     val;
        !           269:        register        np;
        !           270: {
        !           271:        register        struct exp *locxp;
        !           272:        extern          int     exprisname;     /*last factor is a name*/
        !           273: 
        !           274:        exprisname = 0;
        !           275:        locxp = xp++;
        !           276:        if (val == NAME){
        !           277:                exprisname++;
        !           278:                locxp->xtype = ((struct symtab *)np)->type;
        !           279:                if (( ((struct symtab *)np)->type&XTYPE)==XUNDEF) { /*forward*/
        !           280:                        locxp->xname = (struct symtab *)np;
        !           281:                        locxp->xvalue = 0;
        !           282:                        if (passno==1)
        !           283:                                ((struct symtab *)np)->type |= XFORW;
        !           284:                } else {        /*otherwise, just get the value*/
        !           285:                        locxp->xvalue = ((struct symtab *)np)->value;
        !           286:                        locxp->xname = NULL;
        !           287:                }
        !           288:        } else {        /*INSTn or INST0 or REG*/
        !           289:                locxp->xtype = XABS;
        !           290:                locxp->xvalue = ( (int)np) & 0xFF;
        !           291:                locxp->xloc = 0;
        !           292:                locxp->xname = NULL;
        !           293:        }
        !           294: 
        !           295:        return(locxp);
        !           296: }

unix.superglobalmegacorp.com

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