|
|
1.1 ! root 1: #include "ed8.h" ! 2: #include "symtab.pri" ! 3: #include "dtype.pri" ! 4: #include "symbol.h" ! 5: SRCFILE("ed8symtab.c") ! 6: ! 7: char *N_Name(int n_type) ! 8: { ! 9: char *type; ! 10: static char name[64]; ! 11: ! 12: switch( n_type&~N_EXT ){ ! 13: default: type = Name("N_0x%X", n_type ); ! 14: case N_ABS: type = "ABS"; break; ! 15: case N_BCOMM: type = "BCOMM"; break; ! 16: case N_BSS: type = "BSS"; break; ! 17: case N_BSTR: type = "BSTR"; break; ! 18: case N_COMM: type = "COMM"; break; ! 19: case N_DATA: type = "DATA"; break; ! 20: case N_DIM: type = "DIM"; break; ! 21: case N_ECOML: type = "ECOML"; break; ! 22: case N_ECOMM: type = "ECOMM"; break; ! 23: case N_BFUN: type = "BFUN"; break; ! 24: case N_EFUN: type = "EFUN"; break; ! 25: case N_ENTRY: type = "ENTRY"; break; ! 26: case N_ESO: type = "ESO"; break; ! 27: case N_ESTR: type = "ESTR"; break; ! 28: case N_FN: type = "FN"; break; ! 29: case N_FNAME: type = "FNAME"; break; ! 30: case N_GSYM: type = "GSYM"; break; ! 31: case N_LBRAC: type = "LBRAC"; break; ! 32: case N_LCSYM: type = "LCSYM"; break; ! 33: case N_LENG: type = "LENG"; break; ! 34: case N_LSYM: type = "LSYM"; break; ! 35: case N_PSYM: type = "PSYM"; break; ! 36: case N_RBRAC: type = "RBRAC"; break; ! 37: case N_RFUN: type = "RFUN"; break; ! 38: case N_RSYM: type = "RSYM"; break; ! 39: case N_SFLD: type = "SFLD"; break; ! 40: case N_SLINE: type = "SLINE"; break; ! 41: case N_SO: type = "SO"; break; ! 42: case N_SOL: type = "SOL"; break; ! 43: case N_SSYM: type = "SSYM"; break; ! 44: case N_STSYM: type = "STSYM"; break; ! 45: case N_TEXT: type = "TEXT"; break; ! 46: case N_TYID: type = "TYID"; break; ! 47: case N_UNDF: type = "UNDF"; break; ! 48: case N_VER: type = "VER"; break; ! 49: } ! 50: sprintf( name, "%s%s", type, n_type&N_EXT ? "'" : "" ); ! 51: return name; ! 52: } ! 53: ! 54: DType Ed8SymTab::chain(int t, nlist *n) ! 55: { ! 56: DType d; ! 57: ! 58: trace( "%d.chain(0%o,%d) %s", this, t, n, PccName(t) ); ! 59: if( t&TMASK ){ ! 60: d.pcc = t&TMASK; ! 61: d.univ = new DType; ! 62: *(d.ref()) = chain(DECREF(t), n); ! 63: } else { ! 64: d.pcc = t; ! 65: if((t==STRTY || t==ENUMTY || t==UNIONTY) && (++n)->n_type==N_TYID) ! 66: d.univ = idtosym(U_UTYPE,n->n_un.n_name,0); ! 67: } ! 68: return d; ! 69: } ! 70: ! 71: DType Ed8SymTab::gatherdtype(nlist *n) ! 72: { ! 73: DType d, *dp; ! 74: ! 75: trace( "%d.gatherdtype(%d)", this, n); ! 76: d = chain(n->n_desc,n); ! 77: if( (++n)->n_type==N_TYID ) ++n; ! 78: for( dp = &d; dp; dp = dp->ref() ) ! 79: if( dp->isary() && n->n_type==N_DIM ) ! 80: dp->dim = n++->n_value; ! 81: trace( "%s", d.text() ); ! 82: return d; ! 83: } ! 84: ! 85: Ed8SymTab::Ed8SymTab(Core* c, int fd, SymTab *i):(c, fd, i) ! 86: { ! 87: hdr = new exec; ! 88: } ! 89: ! 90: Ed8SymTab::~Ed8SymTab() { delete hdr; } ! 91: ! 92: char *Ed8SymTab::gethdr() ! 93: { ! 94: trace( "%d.gethdr()", this ); OK( "Ed8SymTab::gethdr" ); ! 95: if( lseek( fd, 0L, 0 ) == -1 || !ReadOK(fd, (char*)hdr, sizeof *hdr) ) ! 96: return SysErr( "symbol table: " ); ! 97: _magic = hdr->a_magic; ! 98: if( N_BADMAG(*hdr) || hdr->a_trsize || hdr->a_drsize ) ! 99: return "symbol table: not executable text"; ! 100: entries = hdr->a_syms/sizeof(nlist); ! 101: return 0; ! 102: } ! 103: ! 104: Block *Ed8SymTab::gatherfunc(Func *func) ! 105: { ! 106: register struct nlist *f, *n; ! 107: register Block *ablk, *lblk; ! 108: Var *arg = 0, *lcl = 0; ! 109: register Stmt *stmt = 0; ! 110: long bfun = func->begin, size = func->size, i, inasrc = 1; ! 111: char *so = func->source()->_text; ! 112: ! 113: ++FunctionGathered; ! 114: SymbolStats(); ! 115: trace( "%d.gatherfunc(%d,%d,%s)", this, bfun, size, so ); OK(0); ! 116: IF_LIVE( bfun < 0 || bfun+size > entries ) return 0; ! 117: if (size == 0) ! 118: return fakeblk(); ! 119: if( !(n = f = nlistvector(bfun,size)) ) return 0; ! 120: IF_LIVE( n->n_type != N_BFUN ) return 0; ! 121: ablk = new Block( this, 0, 0, sf("%s().arg_blk",n->n_un.n_name) ); ! 122: lblk = new Block( this, ablk, 0, sf("%s().lcl_blk",n->n_un.n_name) ); ! 123: ablk->child = lblk; ! 124: for( i = 0; i < size; ++i, ++n ){ ! 125: if( n->n_type == N_SOL ){ ! 126: inasrc = eqstr( n->n_un.n_name, so ); ! 127: n->n_type = N_SLINE; ! 128: } ! 129: if( !inasrc ) continue; ! 130: switch( n->n_type ){ ! 131: case N_PSYM: ! 132: gathervar( n, &arg, ablk, U_ARG ); ! 133: break; ! 134: case N_LSYM: ! 135: gathervar( n, &lcl, lblk, U_AUT ); ! 136: lcl->range.lo = - lcl->range.lo; /* VAX */ ! 137: break; ! 138: case N_STSYM: ! 139: case N_LCSYM: ! 140: gathervar( n, &lcl, lblk, U_STA ); ! 141: break; ! 142: case N_RSYM: ! 143: gathervar( n, &lcl, lblk, U_REG ); ! 144: break; ! 145: case N_BFUN: ! 146: case N_RFUN: ! 147: case N_SLINE: // cfront screws up ! 148: if( stmt && n->n_desc > stmt->lineno ) ! 149: func->lines.hi = n->n_desc; ! 150: if( stmt ) stmt->range.hi = n->n_value; ! 151: stmt = new Stmt(this,lblk,stmt); ! 152: if( !ablk->stmt ) ablk->stmt = stmt; ! 153: stmt->lineno = n->n_desc; ! 154: stmt->range.lo = n->n_value; ! 155: if( !ablk->range.lo ) ! 156: ablk->range.lo = n->n_value; ! 157: ablk->range.hi = n->n_value; ! 158: break; ! 159: case N_EFUN: ! 160: if( stmt ) stmt->range.hi = n->n_value; ! 161: goto BreakOut; ! 162: } ! 163: } ! 164: BreakOut: ! 165: delete f; ! 166: uncfront( ablk->var, (char *)0 ); ! 167: uncfront( lblk->var, (char *)0 ); ! 168: return ablk; ! 169: } ! 170: ! 171: void Ed8SymTab::gathervar( nlist *n, Var **v, Block *b, UDisc d ) ! 172: { ! 173: trace( "%d.gathervar(%d,%d,%d,%d)", n, v, b, d ); VOK; ! 174: IF_LIVE( !v ) return; ! 175: *v = new Var( this, b, *v, d, n->n_un.n_name ); ! 176: if( b && !b->var ) b->var = *v; ! 177: (*v)->range.lo = n->n_value; ! 178: (*v)->type = gatherdtype(n); ! 179: } ! 180: ! 181: char *Ed8SymTab::gettbl() ! 182: { ! 183: trace( "%d.gettbl()" ); OK("SymTab.gettbl"); ! 184: base = new nlist[entries]; ! 185: symoff = (nlist*)N_SYMOFF(*hdr); ! 186: if( lseek(fd, (long)symoff, 0) == 1 ! 187: || !ReadOK(fd, (char*)base, hdr->a_syms) ! 188: || !ReadOK(fd, (char*)&strsize, 4) ){ ! 189: delete base; base = 0; ! 190: return SysErr( "symbol table: " ); ! 191: } ! 192: strings = new char[strsize]; ! 193: if( lseek( fd, -4, 1 ) == -1 || !ReadOK(fd, strings, strsize) ){ ! 194: delete strings; strings = 0; ! 195: delete base; base = 0; ! 196: return SysErr( "strings table: " ); ! 197: } ! 198: strcpy( strings, "???" ); /* zero string index */ ! 199: return 0; ! 200: } ! 201: ! 202: Source *Ed8SymTab::tree() ! 203: { ! 204: register nlist *n, *base_entries, *r; ! 205: Source *src = 0; ! 206: Func *func = 0; ! 207: Block *fake = fakeblk(); ! 208: Var *glb = 0, *fst = 0, *resolve; ! 209: UType *u; ! 210: register long regstrings, inafunc = 0, inasrc = 0; ! 211: ! 212: trace( "%d.tree()", this ); OK(0); ! 213: if( _warn = gettbl() ) return 0; ! 214: base_entries = base+entries; ! 215: regstrings = (long) strings; ! 216: glb = globregs(_blk, 18 ); ! 217: for( n = base; n < base_entries; ++n ){ ! 218: n->n_un.n_strx += (long) regstrings; ! 219: switch( n->n_type ){ ! 220: case N_BSTR: ! 221: for( r = n+1; r->n_type != N_ESTR; ++r ) {} ! 222: if( u = (UType*) idtosym(U_UTYPE,n->n_un.n_name,0) ){ ! 223: if( u->size<r+1-n ){ /* use the biggest */ ! 224: u->size = r+1-n; ! 225: u->begin = n-base; ! 226: u->range.lo = r->n_value; ! 227: u->type.pcc = n->n_desc; ! 228: } ! 229: break; ! 230: } ! 231: ++UTypeStubs; ! 232: u = new UType(this, n-base, r+1-n, n->n_un.n_name ); ! 233: u->range.lo = r->n_value; ! 234: u->type.pcc = n->n_desc; ! 235: u->type.univ = u; ! 236: u->rsib = utype; ! 237: utype = u; ! 238: } ! 239: } ! 240: for( n = base; n < base_entries; ++n ){ ! 241: switch( n->n_type ){ ! 242: case N_ABS|N_EXT: ! 243: if( n->n_un.n_name[0] != '_' ) break; /* ? */ ! 244: case N_BSS|N_EXT: ! 245: case N_DATA|N_EXT: ! 246: if( *n->n_un.n_name == '_' ) ++n->n_un.n_name; ! 247: resolve = (Var*)idtosym(U_GLB, n->n_un.n_name, 0); ! 248: if( resolve ){ ! 249: if( !resolve->range.lo ) ! 250: resolve->range.lo = n->n_value; ! 251: } else { ! 252: n->n_desc = LONG; ! 253: gathervar( n, &glb, _blk, U_GLB ); ! 254: break; ! 255: } ! 256: break; ! 257: case N_GSYM: ! 258: if( !inasrc || inafunc ) break; ! 259: if( !idtosym(U_GLB, n->n_un.n_name, 0) ) ! 260: gathervar( n, &glb, _blk, U_GLB ); ! 261: break; ! 262: case N_LCSYM: ! 263: case N_STSYM: ! 264: if( !inasrc || inafunc || !src || !src->blk ) break; ! 265: gathervar( n, &fst, src->blk, U_FST ); ! 266: break; ! 267: ! 268: case N_SO: ! 269: inasrc = 1; ! 270: src = new Source(this,src,n->n_un.n_name,0); ! 271: func = 0; ! 272: inafunc = 0; ! 273: fst = 0; ! 274: break; ! 275: case N_SOL: ! 276: inasrc = src && eqstr(src->_text,n->n_un.n_name); ! 277: break; ! 278: case N_TEXT|N_EXT: ! 279: if( *n->n_un.n_name == '_' ) ++n->n_un.n_name; ! 280: if( idtosym(U_FUNC, n->n_un.n_name, 0) ) break; ! 281: func = new Func(this,0,0,0,n->n_un.n_name); ! 282: func->range.lo = n->n_value; ! 283: func->_blk = fake; ! 284: DType *t = new DType; ! 285: t->pcc = LONG; ! 286: func->type = t->incref(); ! 287: func->type.pcc = FTN; ! 288: break; ! 289: case N_BFUN: ! 290: if( !inasrc || !src ) break; ! 291: inafunc = 1; ! 292: ++FunctionStubs; ! 293: func = new Func(this,src,func,n-base,n->n_un.n_name); ! 294: if( !src->child ) src->child = src->linefunc = func; ! 295: func->range.lo = n->n_value; ! 296: func->lines.lo = n->n_desc; ! 297: if( !strcmp(n->n_un.n_name,(n+1)->n_un.n_name) ) ! 298: func->type = gatherdtype(++n); ! 299: break; ! 300: case N_ESO: ! 301: inasrc = inafunc = 0; ! 302: break; ! 303: case N_EFUN: ! 304: /* if( !inasrc ) break; screws yyparse() */ ! 305: if( !inafunc || !func ) break; ! 306: inafunc = 0; ! 307: func->lines.hi = n->n_desc; ! 308: func->size = n-base - func->begin + 1; ! 309: } ! 310: } ! 311: while( src && src->lsib ) src = (Source*) src->lsib; ! 312: if( base ) { delete base; base = 0; } ! 313: return src; ! 314: } ! 315: ! 316: Var *Ed8SymTab::gatherutype(UType *u) ! 317: { ! 318: nlist *f, *n; ! 319: Var *first = 0, *v = 0; ! 320: long bstr = u->begin, size = u->size; ! 321: ! 322: ++UTypeGathered; ! 323: SymbolStats(); ! 324: trace( "%d.gatherutype(%d %d)", this, bstr, size ); ! 325: if( !(f = n = nlistvector(bstr,size)) ) return 0; ! 326: for( ++n; n->n_type != N_ESTR; ++n ){ ! 327: switch( n->n_type ){ ! 328: case N_SFLD: ! 329: int length = n->n_desc>>BTSHIFT; ! 330: n->n_value = (32 - (n->n_value & 0x1f) - length) + ! 331: (n->n_value & ~0x1f); ! 332: switch( n->n_desc & BTMASK ){ ! 333: case INT: n->n_desc = BITS; break; ! 334: case UNSIGNED: n->n_desc = UBITS; ! 335: } ! 336: gathervar(n, &v, 0, U_MOT); ! 337: v->type.dim = length; ! 338: break; ! 339: case N_SSYM: ! 340: gathervar(n, &v, 0, U_MOT); ! 341: } ! 342: if( !first ) first = v; ! 343: } ! 344: delete f; ! 345: uncfront(first, u->_text); ! 346: return first; ! 347: } ! 348: ! 349: nlist *Ed8SymTab::nlistvector(long start, long size ) ! 350: { ! 351: struct nlist *n; ! 352: int i; ! 353: ! 354: trace( "%d.nlistvector(%d,%d) %d", this, start, size, symoff ); ! 355: lseek(fd, (long) (symoff + start), 0); ! 356: n = new nlist[size]; ! 357: IF_LIVE( !ReadOK(fd, (char*) n, size * sizeof *n) ){ ! 358: delete n; ! 359: return 0; ! 360: } ! 361: for( i = 0; i < size; ++i ) ! 362: n[i].n_un.n_strx += (long) strings; ! 363: return n; ! 364: } ! 365:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.