|
|
1.1 ! root 1: #include "asm.pri" ! 2: #include "core.pub" ! 3: #include "format.pub" ! 4: #include "parse.h" ! 5: #include "expr.pub" ! 6: #include "frame.pub" ! 7: #include "process.pub" ! 8: #include "symtab.pub" ! 9: #include "symbol.h" ! 10: #include "bpts.pub" ! 11: SRCFILE("asm.c") ! 12: ! 13: char *Instr::arg(int) { return "<arg>"; } ! 14: char *Instr::mnemonic() { return sf("0x%X?", opcode&0xFF); } ! 15: int Instr::argtype(int) { return 0; } ! 16: int Instr::nargs() { return 0; } ! 17: char *Asm::literaldelimiter() { return "<literal>"; } ! 18: Instr *Asm::newInstr(long) { return 0; } ! 19: ! 20: Asm::Asm(Core *c) ! 21: { ! 22: trace( "%d.Asm(%d)", this, c ); VOK; ! 23: core = c; ! 24: fmt = F_SYMBOLIC|F_HEX; ! 25: } ! 26: ! 27: void Asm::userclose() ! 28: { ! 29: trace( "%d.userclose()", this ); VOK; ! 30: delete pad; ! 31: pad = 0; ! 32: Instr *instrsetsib; ! 33: for( ; instrset; instrset = instrsetsib ){ ! 34: instrsetsib = instrset->sib; // new malloc ! 35: delete instrset; ! 36: } ! 37: } ! 38: ! 39: void Asm::banner() ! 40: { ! 41: trace( "%d.banner()", this ); VOK; ! 42: if( pad ){ ! 43: pad->banner("Assembler: %s", core->procpath()); ! 44: pad->name("Asm %s", basename(core->procpath())); ! 45: } ! 46: } ! 47: ! 48: void Asm::open(long a) ! 49: { ! 50: trace("%d.open(%d)", this, a); VOK; ! 51: if( !pad ){ ! 52: Menu m; ! 53: pad = new Pad( (PadRcv*) this ); ! 54: banner(); ! 55: m.last( "display pc", (Action)&Asm::displaypc ); ! 56: if( core->online() ){ ! 57: m.first( "run", (Action)&Asm::go ); ! 58: m.last( "step 1 instr ", (Action)&Asm::instrstep, 1 ); ! 59: m.last( "step 4 instrs", (Action)&Asm::instrstep, 4 ); ! 60: m.last( "step 16 instrs", (Action)&Asm::instrstep, 16 ); ! 61: m.last( "step 64 instrs", (Action)&Asm::instrstep, 64 ); ! 62: m.last( "step over call", (Action)&Asm::stepover ); ! 63: } ! 64: pad->menu(m); ! 65: } ! 66: pad->makecurrent(); ! 67: if( a ) newInstr(a); ! 68: } ! 69: ! 70: void Asm::go() ! 71: { ! 72: trace( "%d.go()", this ); VOK; ! 73: core->process()->go(); ! 74: } ! 75: ! 76: void Asm::displaypc() ! 77: { ! 78: trace("%d.displaypc()", this); VOK; ! 79: open(core->pc()); ! 80: } ! 81: ! 82: char *Asm::help() ! 83: { ! 84: trace( "%d.help()", this ); ! 85: return ".=<expr> {display instruction at address}"; ! 86: } ! 87: ! 88: char *Asm::kbd(char *s) ! 89: { ! 90: Parse y(G_DOTEQ_CONEX,0); ! 91: Expr *e; ! 92: Bls error; ! 93: ! 94: trace( "%d.kbd(%s)", this, s ); OK("kbd"); ! 95: if( !(e = (Expr*)y.parse(s)) ) ! 96: return sf("%s: %s", y.error, s); ! 97: e->evaltext(core->process()->globals, error); ! 98: if( e->evalerr ) ! 99: return sf("%s: %s", s, error.text); ! 100: newInstr(e->val.lng); ! 101: return 0; ! 102: } ! 103: ! 104: char *Instr::literal(long f) /* is Format right? */ ! 105: { ! 106: static char t[128]; ! 107: ! 108: trace( "%d.literal(0x%X) 0x%X %g", this, f, m.lng, m.flt ); OK("literal"); ! 109: sprintf( t, "%s%s", _asm->literaldelimiter(), ! 110: Format(f&~F_SYMBOLIC).f(m.lng,m.dbl) ); ! 111: return t; ! 112: } ! 113: ! 114: char *Instr::symbolic(char *prefix) /* is Format right? */ ! 115: { ! 116: static char t[128]; ! 117: ! 118: trace( "%d.symbolic(%s) 0x%X", this, prefix, m.lng ); OK("symbolic"); ! 119: strcpy(t, prefix); ! 120: strcat(t, Format(fmt, _asm->core->symtab()).f(m.lng)); ! 121: return t; ! 122: } ! 123: ! 124: Var *Instr::local(UDisc d, long a) /* VAX */ ! 125: { ! 126: Func *f; ! 127: Block *b; ! 128: ! 129: trace("%d.local(0x%X,%d)", this, d, a); OK(0); ! 130: if( !(f = (Func*)_asm->core->symtab()->loctosym(U_FUNC, addr)) ) return 0; ! 131: if( !(b = f->blk(addr)) ) return 0; ! 132: BlkVars bv(b); ! 133: Var *v; ! 134: while( v = bv.gen() ) ! 135: if( v->disc() == d && v->range.lo == a ) ! 136: break; ! 137: return v; ! 138: } ! 139: ! 140: Var *Instr::field(Var *v, long a) ! 141: { ! 142: trace( "%d.field(%d,%d)", this, v, a ); OK(0); ! 143: if( !v->type.isptr() ) return 0; ! 144: DType *d = v->type.decref(); ! 145: if( !d->isstrun() ) return 0; ! 146: TypMems tm(d->utype()); ! 147: while( v = tm.gen() ) ! 148: if( v->range.lo == a ) break; ! 149: return v; ! 150: } ! 151: ! 152: char *Instr::regarg(char *lay, long f) /* is Format right? */ ! 153: { ! 154: static char t[128]; ! 155: char *o, *r; ! 156: Var *v; ! 157: ! 158: trace("%d.regarg(%s,0x%X) %d 0x%X", this, lay, f, reg, m.lng); OK("regarg"); ! 159: r = _asm->core->regname(reg); ! 160: o = Format(f&~F_SYMBOLIC).f(m.lng); ! 161: if( f&F_SYMBOLIC ){ ! 162: if( reg == _asm->core->REG_AP() ){ ! 163: if( v = local(U_ARG, m.lng) ) ! 164: o = v->text(); ! 165: } else if( reg == _asm->core->REG_FP() ){ ! 166: if( v = local(U_AUT, m.lng) ) ! 167: o = v->text(); ! 168: } else { ! 169: if( v = local(U_REG, reg) ){ ! 170: r = sf("%s=%s", v->text(), r); ! 171: if( v = field(v, m.lng) ) ! 172: o = v->text(); ! 173: } ! 174: } ! 175: } ! 176: sprintf(t, lay, o, r); ! 177: return t; ! 178: } ! 179: ! 180: void Instr::dobpt(int setorclr) ! 181: { ! 182: trace( "%d.dobpt(%d)", this, setorclr ); VOK; ! 183: Stmt *stmt = new Stmt(0,0,0); ! 184: stmt->range.lo = addr; ! 185: stmt->process = _asm->core->process(); ! 186: stmt->dobpt(setorclr); ! 187: } ! 188: ! 189: Instr::Instr(Asm *a, long l) ! 190: { ! 191: trace( "%d.Instr(%d,%d)", this, a, l ); VOK; ! 192: if( !l ) return; ! 193: addr = l; ! 194: _asm = a; ! 195: sib = _asm->instrset; ! 196: _asm->instrset = this; ! 197: _asm->banner(); /* why here? */ ! 198: fmt = _asm->fmt; ! 199: bpt = _asm->core->process()->bpts()->isasmbpt(addr); ! 200: } ! 201: ! 202: void Instr::display() ! 203: { ! 204: int i; ! 205: Bls t; ! 206: ! 207: trace( "%d.display()", this ); VOK; ! 208: if( !addr ) return; ! 209: t.af("%s%s", bpt?">>>":"", Format(fmt,_asm->core->symtab()).f(addr)); ! 210: opcode = _asm->core->peekcode(addr)->chr; ! 211: next = addr+1; ! 212: char *mnem = mnemonic(); ! 213: if( mnem ){ ! 214: t.af(": %s ", mnem); ! 215: int n = nargs(); ! 216: for( i = 0; i < n; ++i ) ! 217: t.af("%s%s", i?",":"", arg(i)); ! 218: } ! 219: _asm->pad->insert(addr, SELECTLINE, (PadRcv*)this, carte(), "%s", t.text); ! 220: } ! 221: ! 222: void Instr::showsrc() ! 223: { ! 224: trace( "%d.showsrc()", this ); ok(); ! 225: Stmt *stmt = (Stmt*) _asm->core->symtab()->loctosym(U_STMT, addr); ! 226: if( stmt ) stmt->select(); ! 227: } ! 228: ! 229: long AF[] = { F_OCTAL, F_SIGNED, F_HEX, F_SYMBOLIC, 0 }; ! 230: ! 231: Index Instr::carte() ! 232: { ! 233: Menu m, f; ! 234: ! 235: trace( "%d.carte()", this ); ok(); ! 236: if( _asm->core->online() ){ ! 237: if( bpt ) ! 238: m.last( "clr bpt", (Action)&Instr::dobpt, 0 ); ! 239: else ! 240: m.last( "set bpt", (Action)&Instr::dobpt, 1 ); ! 241: } ! 242: if( _asm->core->symtab()->loctosym(U_STMT, addr) ) ! 243: m.last( "src text", (Action)&Instr::showsrc, 0 ); ! 244: m.last( "open frame", (Action)&Instr::openframe ); ! 245: m.last( "next 1", (Action)&Instr::succ, 1 ); ! 246: m.last( "next 5", (Action)&Instr::succ, 5 ); ! 247: m.last( "next 10", (Action)&Instr::succ, 10 ); ! 248: for( int i = 0; AF[i]; ++i ){ ! 249: long b = AF[i]; ! 250: if( fmt&b ) b |= F_TURNOFF; ! 251: f.last(FmtName(b), (Action)&Instr::reformat, b); ! 252: } ! 253: m.last(f.index("format")); ! 254: m.last( "refresh", (Action)&Instr::succ, -1 ); ! 255: m.last( "raw mem", (Action)&Instr::memory, 0 ); ! 256: return m.index(); ! 257: } ! 258: ! 259: void Instr::openframe() ! 260: { ! 261: trace( "%d.openframe()", this ); VOK; ! 262: _asm->core->process()->openframe(addr); ! 263: } ! 264: ! 265: void Instr::reformat(int f) ! 266: { ! 267: trace( "%d.reformat(0x%X) 0x%X", this, f, fmt ); VOK; ! 268: if( f&F_TURNOFF) ! 269: fmt &= ~f; ! 270: else ! 271: fmt |= f; ! 272: if( !fmt ) fmt = F_HEX; ! 273: _asm->fmt = fmt; ! 274: _asm->newInstr(addr); ! 275: } ! 276: ! 277: void Instr::succ(int n) /* think about it! */ ! 278: { ! 279: trace( "%d.succ(%d)", this, n ); VOK; ! 280: _asm->fmt = fmt; ! 281: if( n>0 ) _asm->newInstr(next)->succ(n-1); ! 282: else if( n<0 ) _asm->newInstr(addr); ! 283: } ! 284: ! 285: void Instr::memory() ! 286: { ! 287: trace( "%d.memory()" ); VOK; ! 288: _asm->core->process()->openmemory(addr); ! 289: } ! 290: ! 291: void Asm::instrstep(long i) ! 292: { ! 293: trace( "%d.instrstep(%d)", this, i ); VOK; ! 294: core->process()->instrstep(i); ! 295: } ! 296: ! 297: void Asm::stepover() ! 298: { ! 299: trace( "%d.stepover()", this ); VOK; ! 300: core->process()-> ! 301: stepover( core->pc(), newInstr(core->pc())->next ); ! 302: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.