|
|
1.1 ! root 1: # ! 2: /* ! 3: * ! 4: * UNIX debugger ! 5: * ! 6: */ ! 7: ! 8: #include "defs.h" ! 9: static char sccsid[] = "%Z%%M% %I% %G%"; ! 10: ! 11: extern MAP txtmap; ! 12: ! 13: MSG NOFORK; ! 14: MSG ENDPCS; ! 15: MSG BADWAIT; ! 16: ! 17: CHAR *lp; ! 18: ADDR sigint; ! 19: ADDR sigqit; ! 20: ! 21: /* breakpoints */ ! 22: BKPTR bkpthead; ! 23: ! 24: REGLIST reglist[]; ! 25: ! 26: CHAR lastc; ! 27: ! 28: INT fcor; ! 29: INT fsym; ! 30: STRING errflg; ! 31: INT errno; ! 32: INT signo; ! 33: ! 34: L_INT dot; ! 35: STRING symfil; ! 36: INT wtflag; ! 37: L_INT pid; ! 38: L_INT expv; ! 39: INT adrflg; ! 40: L_INT loopcnt; ! 41: ! 42: ! 43: ! 44: ! 45: ! 46: /* service routines for sub process control */ ! 47: ! 48: getsig(sig) ! 49: { return(expr(0) ? expv : sig); ! 50: } ! 51: ! 52: ADDR userpc = 1; ! 53: ! 54: runpcs(runmode,execsig) ! 55: { ! 56: INT rc; ! 57: REG BKPTR bkpt; ! 58: IF adrflg THEN userpc=dot; FI ! 59: printf("%s: running\n", symfil); ! 60: ! 61: WHILE --loopcnt>=0 ! 62: DO ! 63: #ifdef DEBUG ! 64: printf("\ncontinue %x %d\n",userpc,execsig); ! 65: #endif ! 66: IF runmode==SINGLE ! 67: THEN delbp(); /* hardware handles single-stepping */ ! 68: ELSE /* continuing from a breakpoint is hard */ ! 69: IF bkpt=scanbkpt(userpc) ! 70: THEN execbkpt(bkpt,execsig); execsig=0; ! 71: FI ! 72: setbp(); ! 73: FI ! 74: ptrace(runmode,pid,userpc,execsig); ! 75: bpwait(); chkerr(); execsig=0; delbp(); readregs(); ! 76: ! 77: IF (signo==0) ANDF (bkpt=scanbkpt(userpc)) ! 78: THEN /* stopped by BPT instruction */ ! 79: #ifdef DEBUG ! 80: printf("\n BPT code; '%s'%o'%o'%d", ! 81: bkpt->comm,bkpt->comm[0],EOR,bkpt->flag); ! 82: #endif ! 83: dot=bkpt->loc; ! 84: IF bkpt->flag==BKPTEXEC ! 85: ORF ((bkpt->flag=BKPTEXEC) ! 86: ANDF bkpt->comm[0]!=EOR ! 87: ANDF command(bkpt->comm,':') ! 88: ANDF --bkpt->count) ! 89: THEN execbkpt(bkpt,execsig); execsig=0; loopcnt++; ! 90: ELSE bkpt->count=bkpt->initcnt; rc=1; ! 91: FI ! 92: ELSE execsig=signo; rc=0; ! 93: FI ! 94: OD ! 95: return(rc); ! 96: } ! 97: ! 98: #define BPOUT 0 ! 99: #define BPIN 1 ! 100: INT bpstate = BPOUT; ! 101: ! 102: endpcs() ! 103: { ! 104: REG BKPTR bkptr; ! 105: IF pid ! 106: THEN ptrace(EXIT,pid,0,0); pid=0; userpc=1; ! 107: FOR bkptr=bkpthead; bkptr; bkptr=bkptr->nxtbkpt ! 108: DO IF bkptr->flag ! 109: THEN bkptr->flag=BKPTSET; ! 110: FI ! 111: OD ! 112: FI ! 113: bpstate=BPOUT; ! 114: } ! 115: ! 116: #ifdef VFORK ! 117: nullsig() ! 118: { ! 119: ! 120: } ! 121: #endif ! 122: ! 123: setup() ! 124: { ! 125: close(fsym); fsym = -1; ! 126: #ifndef VFORK ! 127: IF (pid = fork()) == 0 ! 128: #else ! 129: IF (pid = vfork()) == 0 ! 130: #endif ! 131: THEN ptrace(SETTRC,0,0,0); ! 132: #ifdef VFORK ! 133: signal(SIGTRAP,nullsig); ! 134: #endif ! 135: signal(SIGINT,sigint); signal(SIGQUIT,sigqit); ! 136: doexec(); exit(0); ! 137: ELIF pid == -1 ! 138: THEN error(NOFORK); ! 139: ELSE bpwait(); readregs(); lp[0]=EOR; lp[1]=0; ! 140: fsym=open(symfil,wtflag); ! 141: IF errflg ! 142: THEN printf("%s: cannot execute\n",symfil); ! 143: endpcs(); error(0); ! 144: FI ! 145: FI ! 146: bpstate=BPOUT; ! 147: } ! 148: ! 149: execbkpt(bkptr,execsig) ! 150: BKPTR bkptr; ! 151: { ! 152: #ifdef DEBUG ! 153: printf("exbkpt: %d\n",bkptr->count); ! 154: #endif ! 155: delbp(); ! 156: ptrace(SINGLE,pid,bkptr->loc,execsig); ! 157: bkptr->flag=BKPTSET; ! 158: bpwait(); chkerr(); readregs(); ! 159: } ! 160: ! 161: ! 162: doexec() ! 163: { ! 164: STRING argl[MAXARG]; ! 165: CHAR args[LINSIZ]; ! 166: STRING p, *ap, filnam; ! 167: extern STRING environ; ! 168: ap=argl; p=args; ! 169: *ap++=symfil; ! 170: REP IF rdc()==EOR THEN break; FI ! 171: *ap = p; ! 172: WHILE lastc!=EOR ANDF lastc!=SP ANDF lastc!=TB DO *p++=lastc; readchar(); OD ! 173: *p++=0; filnam = *ap+1; ! 174: IF **ap=='<' ! 175: THEN close(0); ! 176: IF open(filnam,0)<0 ! 177: THEN printf("%s: cannot open\n",filnam); _exit(0); ! 178: FI ! 179: ELIF **ap=='>' ! 180: THEN close(1); ! 181: IF creat(filnam,0666)<0 ! 182: THEN printf("%s: cannot create\n",filnam); _exit(0); ! 183: FI ! 184: ELSE ap++; ! 185: FI ! 186: PER lastc!=EOR DONE ! 187: *ap++=0; ! 188: exect(symfil, argl, environ); ! 189: perror(symfil); ! 190: } ! 191: ! 192: BKPTR scanbkpt(adr) ! 193: ADDR adr; ! 194: { ! 195: REG BKPTR bkptr; ! 196: FOR bkptr=bkpthead; bkptr; bkptr=bkptr->nxtbkpt ! 197: DO IF bkptr->flag ANDF bkptr->loc==adr ! 198: THEN break; ! 199: FI ! 200: OD ! 201: return(bkptr); ! 202: } ! 203: ! 204: delbp() ! 205: { ! 206: REG ADDR a; ! 207: REG BKPTR bkptr; ! 208: IF bpstate!=BPOUT ! 209: THEN ! 210: FOR bkptr=bkpthead; bkptr; bkptr=bkptr->nxtbkpt ! 211: DO IF bkptr->flag ! 212: THEN a=bkptr->loc; ! 213: IF a < txtmap.e1 THEN ! 214: ptrace(WIUSER,pid,a, ! 215: (bkptr->ins&0xFF)|(ptrace(RIUSER,pid,a,0)&~0xFF)); ! 216: ELSE ! 217: ptrace(WDUSER,pid,a, ! 218: (bkptr->ins&0xFF)|(ptrace(RDUSER,pid,a,0)&~0xFF)); ! 219: FI ! 220: FI ! 221: OD ! 222: bpstate=BPOUT; ! 223: FI ! 224: } ! 225: ! 226: setbp() ! 227: { ! 228: REG ADDR a; ! 229: REG BKPTR bkptr; ! 230: ! 231: IF bpstate!=BPIN ! 232: THEN ! 233: FOR bkptr=bkpthead; bkptr; bkptr=bkptr->nxtbkpt ! 234: DO IF bkptr->flag ! 235: THEN a = bkptr->loc; ! 236: IF a < txtmap.e1 THEN ! 237: bkptr->ins = ptrace(RIUSER, pid, a, 0); ! 238: ptrace(WIUSER, pid, a, BPT | (bkptr->ins&~0xFF)); ! 239: ELSE ! 240: bkptr->ins = ptrace(RDUSER, pid, a, 0); ! 241: ptrace(WDUSER, pid, a, BPT | (bkptr->ins&~0xFF)); ! 242: FI ! 243: IF errno ! 244: THEN prints("cannot set breakpoint: "); ! 245: psymoff(bkptr->loc,ISYM,"\n"); ! 246: FI ! 247: FI ! 248: OD ! 249: bpstate=BPIN; ! 250: FI ! 251: } ! 252: ! 253: bpwait() ! 254: { ! 255: REG ADDR w; ! 256: ADDR stat; ! 257: ! 258: signal(SIGINT, 1); ! 259: WHILE (w = wait(&stat))!=pid ANDF w != -1 DONE ! 260: signal(SIGINT,sigint); ! 261: IF w == -1 ! 262: THEN pid=0; ! 263: errflg=BADWAIT; ! 264: ELIF (stat & 0177) != 0177 ! 265: THEN IF signo = stat&0177 ! 266: THEN sigprint(); ! 267: FI ! 268: IF stat&0200 ! 269: THEN prints(" - core dumped"); ! 270: close(fcor); ! 271: setcor(); ! 272: FI ! 273: pid=0; ! 274: errflg=ENDPCS; ! 275: ELSE signo = stat>>8; ! 276: IF signo!=SIGTRAP ! 277: THEN sigprint(); ! 278: ELSE signo=0; ! 279: FI ! 280: flushbuf(); ! 281: FI ! 282: } ! 283: ! 284: readregs() ! 285: { ! 286: /*get REG values from pcs*/ ! 287: REG i; ! 288: FOR i=24; --i>=0; ! 289: DO *(ADDR *)(((ADDR)&u)+reglist[i].roffs) = ! 290: ptrace(RUREGS, pid, reglist[i].roffs, 0); ! 291: OD ! 292: userpc= *(ADDR *)(((ADDR)&u)+PC); ! 293: } ! 294: ! 295:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.