|
|
1.1 ! root 1: /* ! 2: * instruction decoding ! 3: * VAX instructions; works only on a VAX for now ! 4: */ ! 5: ! 6: #include "defs.h" ! 7: #include "space.h" ! 8: ! 9: #define LOBYTE 0377 ! 10: ! 11: /* instruction printing */ ! 12: ! 13: /* ! 14: * Argument access types ! 15: */ ! 16: #define ACCA (8<<3) /* address only */ ! 17: #define ACCR (1<<3) /* read */ ! 18: #define ACCW (2<<3) /* write */ ! 19: #define ACCM (3<<3) /* modify */ ! 20: #define ACCB (4<<3) /* branch displacement */ ! 21: #define ACCI (5<<3) /* XFC code */ ! 22: ! 23: /* ! 24: * Argument data types ! 25: */ ! 26: #define TYPB 0 /* byte */ ! 27: #define TYPW 1 /* word */ ! 28: #define TYPL 2 /* long */ ! 29: #define TYPQ 3 /* quad */ ! 30: #define TYPF 4 /* floating */ ! 31: #define TYPD 5 /* double floating */ ! 32: ! 33: typedef struct optab *OPTAB; ! 34: struct optab { ! 35: char *iname; ! 36: char val; ! 37: char nargs; ! 38: char argtype[6]; ! 39: } optab[]; ! 40: struct optab junkoptab = {"???"}; ! 41: char *regname[]; ! 42: char *fltimm[]; ! 43: static ADDR incp; ! 44: ! 45: short ioptab[256]; /* index by opcode to optab */ ! 46: ! 47: mkioptab() {/* set up ioptab */ ! 48: register OPTAB p=optab; ! 49: register int i; ! 50: ! 51: for (i = 0; i < 256; i++) ! 52: ioptab[i] = -1; /* flag invalid */ ! 53: while (p->iname){ ! 54: ioptab[p->val&LOBYTE]=p-optab; ! 55: p++; ! 56: } ! 57: } ! 58: ! 59: printins(idsp) ! 60: { ! 61: register short argno; /* argument index */ ! 62: register short mode; /* mode */ ! 63: register char **r; /* register name */ ! 64: register unsigned char ins; ! 65: long d; /* assembled byte, word, long or float */ ! 66: long snarf(); ! 67: register char * ap; ! 68: register OPTAB ip; ! 69: ! 70: ins = cget(dot, idsp); ! 71: chkerr(); ! 72: if (ioptab[ins] == -1) ! 73: ip = &junkoptab; ! 74: else ! 75: ip = &optab[ioptab[ins]]; ! 76: printf("%s%8t",ip->iname); ! 77: incp = 1; ! 78: ap = ip->argtype; ! 79: for (argno=0; argno<ip->nargs; argno++,ap++) { ! 80: var[argno] = 0x80000000; ! 81: if (argno!=0) printc(','); ! 82: top: ! 83: if (*ap&ACCB) ! 84: mode = 0xAF + ((*ap&7)<<5); /* branch displacement */ ! 85: else{ ! 86: mode = cget(inkdot((WORD)incp), idsp); ! 87: chkerr(); ! 88: ++incp; ! 89: } ! 90: if (mode & 0300) {/* not short literal */ ! 91: r = ®name[mode&0xF]; ! 92: mode >>= 4; ! 93: switch ((int)mode) { ! 94: case 4: /* [r] */ ! 95: printf("[%s]",*r); ! 96: goto top; ! 97: case 5: /* r */ ! 98: printf("%s",*r); ! 99: break; ! 100: case 6: /* (r) */ ! 101: printf("(%s)",*r); ! 102: break; ! 103: case 7: /* -(r) */ ! 104: printf("-(%s)",*r); ! 105: break; ! 106: case 9: /* *(r)+ */ ! 107: printc('*'); ! 108: case 8: /* (r)+ */ ! 109: if (r==(regname+0xF)) { ! 110: printc('$'); ! 111: if (mode==9){ /* PC absolute, always 4 bytes*/ ! 112: d = snarf(4, idsp); ! 113: goto disp; ! 114: } ! 115: switch(*ap&7){ ! 116: case TYPB: ! 117: d = snarf(1, idsp); ! 118: goto disp; ! 119: case TYPW: ! 120: d = snarf(2, idsp); ! 121: goto disp; ! 122: case TYPL: ! 123: d = snarf(4, idsp); ! 124: goto disp; ! 125: case TYPQ: ! 126: d = snarf(4, idsp); ! 127: printquad(d, snarf(4, idsp)); ! 128: break; ! 129: case TYPF: ! 130: printfloating(snarf(4, idsp), 0L); ! 131: break; ! 132: case TYPD: ! 133: d = snarf(4, idsp); ! 134: printfloating(d, snarf(4, idsp)); ! 135: break; ! 136: } /*end of type switch */ ! 137: /* ! 138: * here only for TYPQ, TYPf, TYPD ! 139: * others went to disp ! 140: */ ! 141: } else { /*it's not PC immediate or abs*/ ! 142: printf("(%s)+",*r); ! 143: } ! 144: break; ! 145: case 0xB: /* byte displacement defferred*/ ! 146: printc('*'); ! 147: case 0xA: /* byte displacement */ ! 148: d = snarf(1, idsp); ! 149: goto disp; ! 150: case 0xD: /* word displacement deferred */ ! 151: printc('*'); ! 152: case 0xC: /* word displacement */ ! 153: d = snarf(2, idsp); ! 154: goto disp; ! 155: case 0xF: /* long displacement deferred */ ! 156: printc('*'); ! 157: case 0xE: /* long displacement */ ! 158: d = snarf(4, idsp); ! 159: goto disp; ! 160: disp: ! 161: var[argno]=d; ! 162: if (r==(regname+0xF) && mode>=0xA){ ! 163: /* PC offset addressing */ ! 164: var[argno] += dot+incp; ! 165: } ! 166: psymoff(var[argno],ANYSP,""); ! 167: if (r != regname+0xF) ! 168: printf("(%s)",*r); ! 169: break; ! 170: } /* end of the mode switch */ ! 171: } else { /* short literal */ ! 172: var[argno]=mode; ! 173: if((*ap&7)==TYPF || (*ap&7)==TYPD) ! 174: printf("$%s",fltimm[mode]); ! 175: else ! 176: printf("$%r",mode); ! 177: } ! 178: } ! 179: if (ins==0xCF || ins==0xAF || ins==0x8F) {/* CASEx instr */ ! 180: for (argno=0; argno<=var[2]; ++argno) { ! 181: printc(EOR); ! 182: printf(" %R: ",argno+var[1]); ! 183: d=sget(inkdot((WORD)incp+argno+argno),idsp); ! 184: if (d&0x8000) d -= 0x10000; ! 185: psymoff((WORD)(inkdot((WORD)incp)+d),ANYSP,""); ! 186: } ! 187: incp += var[2]+var[2]+2; ! 188: } ! 189: dotinc=incp; ! 190: } ! 191: ! 192: /* ! 193: * magic values to mung an offset to a register into ! 194: * something that psymoff can understand.. all magic ! 195: */ ! 196: /* 0 1 2 3 4 */ ! 197: static long magic_masks[5] = { ! 198: 0, 0x80, 0x8000, 0, 0}; ! 199: static long magic_compl[5] = { ! 200: 0, 0x100, 0x10000,0, 0}; ! 201: ! 202: static ! 203: long ! 204: snarf(nbytes, idsp) ! 205: int nbytes; ! 206: { ! 207: register int byteindex; ! 208: union Long{ ! 209: char long_bytes[4]; ! 210: long long_value; ! 211: } d; ! 212: ! 213: d.long_value = 0; ! 214: for (byteindex = 0; byteindex < nbytes; byteindex++){ ! 215: d.long_bytes[byteindex] = cget(inkdot((WORD)incp), idsp); ! 216: chkerr(); ! 217: ++incp; ! 218: } ! 219: if (d.long_value & magic_masks[nbytes]) ! 220: d.long_value -= magic_compl[nbytes]; ! 221: return(d.long_value); ! 222: } ! 223: ! 224: static ! 225: printfloating(word_first, word_last) ! 226: long word_first; ! 227: long word_last; ! 228: { ! 229: union Double{ ! 230: struct { ! 231: long word_first; ! 232: long word_last; ! 233: } composite; ! 234: double dvalue; ! 235: } reconstructed; ! 236: ! 237: reconstructed.composite.word_first = word_first; ! 238: reconstructed.composite.word_last = word_last; ! 239: fpout('F', (char *)&reconstructed.dvalue); ! 240: } ! 241: ! 242: static ! 243: printquad(word_first, word_last) ! 244: long word_first; ! 245: long word_last; ! 246: { ! 247: union Quad { ! 248: char quad_bytes[8]; ! 249: long quad_long[2]; ! 250: } reconstructed; ! 251: int leading_zero = 1; ! 252: int byteindex; ! 253: int nibbleindex; ! 254: register int ch; ! 255: ! 256: reconstructed.quad_long[0] = word_first; ! 257: reconstructed.quad_long[1] = word_last; ! 258: for (byteindex = 7; byteindex >= 0; --byteindex){ ! 259: for (nibbleindex = 4; nibbleindex >= 0; nibbleindex -= 4){ ! 260: ch = (reconstructed.quad_bytes[byteindex] ! 261: >> nibbleindex) & 0x0F; ! 262: if ( ! (leading_zero &= (ch == 0) ) ){ ! 263: if (ch <= 0x09) ! 264: printc(ch + '0'); ! 265: else ! 266: printc(ch - 0x0A + 'a'); ! 267: } ! 268: } ! 269: } ! 270: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.