|
|
1.1 ! root 1: static char sccsid[] = "@(#)display.c 4.3 8/17/82"; ! 2: #include "head.h" ! 3: #include <a.out.h> ! 4: #include <stab.h> ! 5: #include "cdefs.h" ! 6: struct user u; ! 7: BKPTR bkpthead; ! 8: ! 9: #ifdef FLEXNAMES ! 10: #define bread(a,b,c) stread(b,c) ! 11: #define blseek(a,b,c) stseek(b,c) ! 12: #endif ! 13: ! 14: /* initialize frame pointers to top of call stack */ ! 15: /* MACHINE DEPENDENT */ ! 16: struct proct * ! 17: initframe() { ! 18: argp = *(ADDR *) (((ADDR) &u) + AP); ! 19: frame = *(ADDR *) (((ADDR) &u) + FP); ! 20: callpc = *(ADDR *) (((ADDR) &u) + PC); ! 21: if ((frame == 0) || (frame & 0xf0000000 != 0x70000000)) ! 22: return(badproc); ! 23: return(adrtoprocp(callpc++)); /* ++ because UNIX backs up instrs */ ! 24: } ! 25: ! 26: ! 27: struct proct * ! 28: nextframe() { ! 29: callpc = get(frame+16, DSP); ! 30: argp = get(frame+8, DSP); ! 31: frame = get(frame+12, DSP) & EVEN; ! 32: if (callpc > 0x70000000) { ! 33: /* error handler kludge */ ! 34: callpc = get(frame+64, DSP); ! 35: argp = get(frame+8, DSP); ! 36: frame = get(frame+12, DSP) & EVEN; ! 37: } ! 38: if ((frame == 0) || (frame & 0xf0000000 != 0x70000000)) ! 39: return(badproc); ! 40: return(adrtoprocp(callpc-1)); ! 41: } ! 42: ! 43: /* returns core image address for variable */ ! 44: /* MACHINE DEPENDENT */ ! 45: ADDR ! 46: formaddr(class, addr) ! 47: u_char class; ! 48: ADDR addr; { ! 49: if (debug) printf("formaddr(%o, %d)\n", class & 0377, addr); ! 50: switch(class & STABMASK) { ! 51: case N_RSYM: ! 52: return(stackreg(addr)); ! 53: case N_GSYM: ! 54: case N_SSYM: ! 55: case N_STSYM: ! 56: case N_LCSYM: ! 57: return(addr); ! 58: ! 59: case N_PSYM: ! 60: return(argp+addr); ! 61: ! 62: case N_LSYM: ! 63: return(frame+addr); ! 64: ! 65: default: ! 66: printf("Bad class in formaddr: 0%o", ! 67: class & 0377); ! 68: return(0); ! 69: } ! 70: } ! 71: ! 72: char class; ! 73: ! 74: /* ! 75: * stackreg(reg): ! 76: * If the register for the current frame is somewhere on the stack ! 77: * then return the address of where it is, otherwise its still in ! 78: * the register so return the register number. ! 79: * We distinguish the two by noting that register numbers are less ! 80: * than 16 and that stack addresses are greater. ! 81: * ! 82: * MACHINE DEPENDENT ! 83: */ ! 84: ADDR ! 85: stackreg(reg) { ! 86: register int curframe, regfl, mask, i; ! 87: struct proct *procp; ! 88: ADDR regaddr; ! 89: ! 90: curframe = frame; ! 91: regaddr = reg; ! 92: regfl = 0x10000 << reg; ! 93: for (procp=initframe(); frame!=curframe; procp=nextframe()) { ! 94: if (procp == badproc) { ! 95: error("Stackreg error: frame"); ! 96: return(-1); ! 97: } ! 98: mask = get(frame+4, DSP); ! 99: if (mask & regfl) { ! 100: regaddr = frame + 20; ! 101: for (i=0; i<reg; i++) { ! 102: if (mask & 0x10000) ! 103: regaddr += WORDSIZE; ! 104: mask = mask >> 1; ! 105: } ! 106: if (!(mask & 0x10000)) { ! 107: error("Stackreg error: contents"); ! 108: return(-1); ! 109: } ! 110: } ! 111: } ! 112: return(regaddr); ! 113: } ! 114: ! 115: /* returns address of proc:var. Sets externals class and subflag */ ! 116: ADDR ! 117: varaddr(proc, var) ! 118: char *proc, *var; { ! 119: return(findvar(proc, var, "", 0)); ! 120: } ! 121: ! 122: /* ! 123: * displays values of variables matching proc:var, ! 124: * returns its address ! 125: */ ! 126: ADDR ! 127: dispvar(proc, var, fmt) ! 128: char *proc, *var, *fmt; { ! 129: return(findvar(proc, var, fmt, 1)); ! 130: } ! 131: ! 132: /* ! 133: * Find and print values of all variables matching proc:var ! 134: * using specified format. ! 135: * Returns address of last matching variable. ! 136: * ! 137: * prvar==0 => no output, ! 138: * prvar==1 => output value, ! 139: * prvar==2 => output addr ! 140: */ ! 141: ADDR ! 142: findvar(proc, var, fmt, prvar) ! 143: char *proc, *var, *fmt; { ! 144: ADDR addr = -1, a = -1; ! 145: int metaflag = 0, match=0, nullflag=0, depthcnt = -1; ! 146: char *comblk; ! 147: register struct proct *procp; ! 148: ! 149: if (percentflag) { /* kludge for register names */ ! 150: return(regout(var, prvar, fmt)); ! 151: } ! 152: ! 153: if (var[0] == '\0') { ! 154: error("Unexpected null variable name"); ! 155: return(-1); ! 156: } ! 157: ! 158: metaflag = eqany('*', proc) || eqany('?', proc) || ! 159: eqany('*', var) || eqany('?', var); ! 160: ! 161: if (proc[0] == '\0') { ! 162: nullflag++; ! 163: proc = curproc()->pname; ! 164: } ! 165: ! 166: comblk = colonflag ? "" : "*"; ! 167: ! 168: if (integ && !eqany(var[0], "->.[")) { ! 169: depthcnt = integ; ! 170: } ! 171: if (integ) { ! 172: if (eqany(var[0], "->.[")) ! 173: match++; ! 174: else ! 175: depthcnt = integ; ! 176: } ! 177: ! 178: procp = initframe(); ! 179: if (!eqany(var[0], "->.[") && !(nullflag && colonflag)) { ! 180: do { ! 181: if (eqpat(proc, procp->pname)) { ! 182: match++; ! 183: if (--depthcnt==0 || integ==0) { ! 184: a = outvar(procp->pname, var, fmt, ! 185: metaflag, integ, N_GSYM, ! 186: 0, prname, comblk, prvar); ! 187: if (a != -1) ! 188: addr = a; ! 189: if (depthcnt == 0) ! 190: break; ! 191: } ! 192: } ! 193: } while ((procp=nextframe()) != badproc); ! 194: } ! 195: ! 196: if ((colonflag || metaflag || a == -1) && ! 197: (nullflag || eqpat(proc, ""))) { ! 198: a = outvar("", var, fmt, metaflag, integ, ! 199: N_GSYM, 0, prname, comblk, prvar); ! 200: if (a != -1) { ! 201: addr = a; ! 202: match++; ! 203: } ! 204: } ! 205: ! 206: if (match==0 && colonflag) { ! 207: procp = initframe(); ! 208: do { ! 209: if (eqstr(curproc()->pname, procp->pname)) ! 210: break; ! 211: } while ((procp=nextframe()) != badproc); ! 212: a = outvar(curproc()->pname, var, fmt, metaflag, ! 213: integ, N_GSYM, 0, prname, ! 214: nullflag ? "_BLNK_" : proc, prvar); ! 215: if (a != -1) { ! 216: addr = a; ! 217: match++; ! 218: } ! 219: } ! 220: ! 221: if (addr == -1 && match == 0) { ! 222: addr = extoutvar(var, fmt, metaflag, prvar); ! 223: if (addr != -1) ! 224: return(addr); ! 225: } ! 226: if (match == 0) { ! 227: printf("%s not an active procedure\n", proc); ! 228: return(-1); ! 229: } ! 230: if (addr == -1) { ! 231: if (var[0] == '.') ! 232: var++; ! 233: if (proc[0]) ! 234: #ifndef FLEXNAMES ! 235: printf("%.16s:%s not found\n", proc, var); ! 236: #else ! 237: printf("%s:%s not found\n", proc, var); ! 238: #endif ! 239: else ! 240: printf("%s not found\n", var); ! 241: return(-1); ! 242: } ! 243: return(addr); ! 244: } ! 245: ! 246: char * ! 247: typetodesc(type, subflag) ! 248: short type; { ! 249: register int ptr, ftn, ary; ! 250: register char *desc; ! 251: ! 252: static char *typedesc[] = { ! 253: "d", /* undef */ ! 254: "d", /* farg */ ! 255: "c", /* char */ ! 256: "hd", /* short */ ! 257: "d", /* int */ ! 258: "ld", /* long */ ! 259: "f", /* float */ ! 260: "g", /* double */ ! 261: "d", /* strty */ ! 262: "d", /* unionty */ ! 263: "d", /* enumty */ ! 264: "d", /* moety */ ! 265: "bu", /* uchar */ ! 266: "hu", /* ushort */ ! 267: "u", /* unsigned */ ! 268: "lu", /* ulong */ ! 269: "d" /* ? */ ! 270: }; ! 271: ! 272: ptr = ftn = ary = 0; ! 273: ! 274: desc = typedesc[type&BTMASK]; ! 275: for (; type & TMASK; type = DECREF(type)) { ! 276: if (ISPTR(type)) ptr++; ! 277: else if (ISFTN(type)) ftn++; ! 278: else if (ISARY(type)) ary++; ! 279: } ! 280: ! 281: if ((ptr-subflag == 1 || ary-subflag == 1) && desc[0] == 'c') ! 282: return("s"); ! 283: if (debug) ! 284: printf ("PTR %d; FTN %d; ARY %d; DESC %s\n",ptr,ftn,ary,desc); ! 285: if (ptr + ary == subflag) ! 286: return(desc); ! 287: if (ptr) return("x"); ! 288: if (ptr==1 && ftn==1) return("p"); ! 289: return(desc); ! 290: } ! 291: ! 292: typetosize(type, stsize) ! 293: short type; { ! 294: register int ptr, ftn, ary; ! 295: register int size; ! 296: ! 297: static char typesize[] = { ! 298: 4, /* undef */ ! 299: 4, /* farg */ ! 300: 1, /* char */ ! 301: 2, /* short */ ! 302: WORDSIZE, /* int */ ! 303: 4, /* long */ ! 304: 4, /* float */ ! 305: 8, /* double */ ! 306: 0, /* strty */ ! 307: 0, /* unionty */ ! 308: 4, /* enumty */ ! 309: 4, /* moety */ ! 310: 1, /* uchar */ ! 311: 2, /* ushort */ ! 312: 4, /* unsigned */ ! 313: 4, /* ulong */ ! 314: 4 /* ? */ ! 315: }; ! 316: ! 317: ptr = ftn = ary = 0; ! 318: ! 319: size = typesize[type&BTMASK]; ! 320: for (; type & TMASK; type = DECREF(type)) { ! 321: if (ISPTR(type)) ptr++; ! 322: else if (ISFTN(type)) ftn++; ! 323: else if (ISARY(type)) ary++; ! 324: } ! 325: ! 326: if (debug) ! 327: printf ("PTR %d; FTN %d; ARY %d; SIZE %d; STSIZE %d\n", ! 328: ptr,ftn,ary,size,stsize); ! 329: if (ptr>1) return(4); ! 330: if (size == 0) return(stsize); ! 331: else return(size); ! 332: } ! 333: ! 334: ! 335: /* print breakpoints */ ! 336: prbkpt() { ! 337: register BKPTR bkptr; ! 338: register int cnt; ! 339: char *cmdp; ! 340: ! 341: cnt = 0; ! 342: ! 343: for (bkptr = bkpthead; bkptr; bkptr=bkptr->nxtbkpt) ! 344: if (bkptr->flag) { ! 345: cnt++; ! 346: printbkpt("", adrtoprocp(bkptr->loc), bkptr->loc); ! 347: cmdp = bkptr->comm; ! 348: if (*cmdp != '\n') { ! 349: printf(" <"); ! 350: while (*cmdp != '\n') ! 351: printf("%c", *cmdp++); ! 352: printf(">\n"); ! 353: } ! 354: else ! 355: printf("\n"); ! 356: } ! 357: if (cnt == 0) ! 358: printf("No breakpoints set\n"); ! 359: } ! 360: ! 361: /* interactively delete breakpoints */ ! 362: ! 363: idbkpt() { ! 364: register BKPTR bkptr; ! 365: register int yesflg, cnt; ! 366: char c; ! 367: ! 368: cnt = 0; ! 369: ! 370: for (bkptr = bkpthead; bkptr; bkptr=bkptr->nxtbkpt) ! 371: if (bkptr->flag) { ! 372: printbkpt(" ? ", adrtoprocp(bkptr->loc), bkptr->loc); ! 373: yesflg = 0; ! 374: cnt++; ! 375: do { ! 376: c = getchar(); ! 377: if (c == 'y' || c == 'd') yesflg++; ! 378: } while (c != '\n'); ! 379: if (yesflg) ! 380: bkptr->flag = 0; ! 381: } ! 382: if (cnt == 0) ! 383: printf("No breakpoints set\n"); ! 384: } ! 385: ! 386: /* delete all breakpoints */ ! 387: ! 388: dabkpt() { ! 389: register BKPTR bkptr; ! 390: ! 391: for (bkptr = bkpthead; bkptr; bkptr=bkptr->nxtbkpt) ! 392: bkptr->flag = 0; ! 393: } ! 394: ! 395: /* ! 396: * Print name of breakpoint for a, b, d commands: ! 397: */ ! 398: printbkpt(s, procp, dot) ! 399: char *s; struct proct *procp; ADDR dot; { ! 400: adrtolineno(dot); ! 401: if (dot != lnfaddr) ! 402: printf("0x%x (", dot); ! 403: prlnoff(procp, dot); ! 404: if (dot != lnfaddr) ! 405: printf(")"); ! 406: printf("%s", s); ! 407: } ! 408: ! 409: /* print call frame */ ! 410: prframe() { ! 411: prfrx(0); ! 412: } ! 413: ! 414: /* set top to print just the top procedure */ ! 415: prfrx(top) { ! 416: int narg; ! 417: long offset; ! 418: u_char class; ! 419: register int endflg; ! 420: char *p; ! 421: struct proct *procp; ! 422: struct nlist stentry; ! 423: ! 424: if ((procp = initframe()) == badproc) return; ! 425: do { ! 426: if (get(frame+12, DSP) == 0) return; ! 427: p = procp->pname; ! 428: if (eqstr("__dbsubc", p)) return; ! 429: if (p[0] == '_') { ! 430: endflg = 1; ! 431: #ifndef FLEXNAMES ! 432: printf("%.15s(", p+1); ! 433: #else ! 434: printf("%s(", p+1); ! 435: #endif ! 436: } ! 437: else { ! 438: #ifndef FLEXNAMES ! 439: printf("%.16s(", p); ! 440: #else ! 441: printf("%s(", p); ! 442: #endif ! 443: endflg = 0; ! 444: } ! 445: if (endflg == 0) { ! 446: offset = procp->st_offset; ! 447: blseek(&sbuf, offset, 0); ! 448: do { ! 449: if (bread(&sbuf, &stentry, sizeof stentry) < ! 450: sizeof stentry) { ! 451: endflg++; ! 452: break; ! 453: } ! 454: class = stentry.n_type & STABMASK; ! 455: } while (class == N_FUN); ! 456: while (class != N_PSYM) { ! 457: if (bread(&sbuf, &stentry, sizeof stentry) < ! 458: sizeof stentry) { ! 459: endflg++; ! 460: break; ! 461: } ! 462: class = stentry.n_type & STABMASK; ! 463: if (class == N_FUN) { ! 464: endflg++; ! 465: break; ! 466: } ! 467: } ! 468: } ! 469: narg = get(argp, DSP); ! 470: if (narg & ~0xff) narg = 0; ! 471: argp += WORDSIZE; ! 472: while (narg) { ! 473: if (endflg) { ! 474: printf("%d", get(argp, DSP)); ! 475: argp += 4; ! 476: } else { ! 477: int length; ! 478: #ifndef FLEXNAMES ! 479: printf("%.16s=", stentry.n_name); ! 480: #else ! 481: printf("%s=", stentry.n_un.n_name); ! 482: #endif ! 483: dispx(argp, "", N_GSYM, stentry.n_desc, ! 484: 0, 0, DSP); ! 485: length = typetosize(stentry.n_desc, 0); ! 486: if (length > WORDSIZE) ! 487: argp += length; ! 488: else ! 489: argp += WORDSIZE; ! 490: } ! 491: do { ! 492: if (endflg) break; ! 493: if (bread(&sbuf, &stentry, sizeof stentry) < ! 494: sizeof stentry) { ! 495: endflg++; ! 496: break; ! 497: } ! 498: class = stentry.n_type & STABMASK; ! 499: if (class == N_FUN) { ! 500: endflg++; ! 501: break; ! 502: } ! 503: } while (class != N_PSYM); ! 504: l1: if (--narg != 0) printf(","); ! 505: } ! 506: printf(")"); ! 507: if (debug) printf(" @ 0x%x ", callpc); ! 508: if (procp->sfptr != badfile) ! 509: printf(" [%s:%d]", adrtofilep(callpc-1)->sfilename, ! 510: adrtolineno(callpc-1)); ! 511: printf("\n"); ! 512: } while (((procp = nextframe()) != badproc) && !top); ! 513: } ! 514: ! 515: INT signo; ! 516: STRING signals[]; ! 517: extern nsig; ! 518: sigprint() ! 519: { ! 520: ! 521: if (signo < nsig) ! 522: printf("%s", signals[signo]); ! 523: else ! 524: printf("signal %d???", signals[signo]); ! 525: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.