|
|
1.1 ! root 1: #include <sys/types.h> ! 2: #include <sys/timeb.h> ! 3: struct timeb tp; ! 4: long times_check[8000]; ! 5: long times_ndx; ! 6: ! 7: static char sccsid[] = "@(#)access.c 2.7"; ! 8: ! 9: /* most of this file is MACHINE DEPENDENT !! ! 10: * EVERY line should be examined for potential problems, including ! 11: * byte sex (had any lately??) ! 12: * regsiter vs int size problems ! 13: * word, long, byte alignment problems ! 14: * Other random droppings from the Bird of Happiness ! 15: * ! 16: * Many of these are fixable by modifying various definitions ! 17: * in pas.h, cdb.h, and particularly macdefs.h ! 18: * ! 19: * WARNING: As of 3-7-83, it is the assumption of virtually ! 20: * all of these routines that the byte sex of the debugger's ! 21: * machine is the same as that of the debuggee's machine. ! 22: * I currently do not have a fix for it, but this is clearly ! 23: * the file which needs to deal with this problem. ! 24: */ ! 25: ! 26: #include <errno.h> ! 27: #ifndef REGULUS ! 28: ! 29: #ifdef BSD42 ! 30: #include <machine/reg.h> ! 31: #else ! 32: #include <sys/reg.h> ! 33: #endif ! 34: ! 35: #endif ! 36: #include "macdefs.h" ! 37: #include "cdb.h" ! 38: ! 39: export int vpid; /* process ID of child */ ! 40: export int vimap; /* selects alternate mapping - sorta kludgey */ ! 41: export ADRT vsp, vpc, vfp, vap; ! 42: export REGT *v_ar0; /* value stored in u.u_ar0 - see InitAll */ ! 43: ! 44: #ifdef SUN ! 45: int vrgOffset[] = { ! 46: R0, R1, R2, R3, ! 47: R4, R5, R6, R7, ! 48: AR0, AR1, AR2, AR3, ! 49: AR4, AR5, AR6, AR7, ! 50: PC, PS, AR6, SP /* AR6 is FP */ ! 51: }; ! 52: #endif ! 53: #ifdef REGULUS ! 54: #define cbUserRegs 18*4 ! 55: int vrgOffset[] = { ! 56: 0, 1, 2, 3, 4, 5, 6, 7, ! 57: 8, 9, 10, 11, 12, 13, 14, 15, ! 58: 16, 17, 14, 15 /* last two are sp and fp */ ! 59: }; ! 60: #endif ! 61: #ifdef ONYX ! 62: int vrgOffset[] = { ! 63: R0, R1, R2, R3, ! 64: R4, R5, R6, R7, ! 65: R8, R9, R10, R11, ! 66: R12, R13, R14, R15, ! 67: SP, PC, R14, FCW /* frame pointer is R14 on Onyx */ ! 68: }; ! 69: #endif ! 70: #ifdef TAHOE ! 71: int vrgOffset[] = { ! 72: R0, R1, R2, R3, ! 73: R4, R5, R6, R7, ! 74: R8, R9, R10, R11, ! 75: R12, FP, SP, PC, ! 76: PS, ! 77: }; ! 78: #endif ! 79: ! 80: #ifdef VAX ! 81: int vrgOffset[] = { ! 82: R0, R1, R2, R3, ! 83: R4, R5, R6, R7, ! 84: R8, R9, R10, R11, ! 85: R12, R13, AP, FP, ! 86: SP, PS, PC, ! 87: }; ! 88: #endif ! 89: ! 90: ! 91: /* G E T U S E R */ ! 92: ! 93: export REGT GetUser(adr) ! 94: ADRT adr; ! 95: { ! 96: int val; ! 97: ! 98: if (vpid != pidNil) { ! 99: val = ptrace(ptReadUser, vpid, adr, 0); ! 100: if (val == -1 AND errno == EIO) { ! 101: if (FOdd(adr)) ! 102: UError("Attempt to write to ODD address"); ! 103: #ifdef REGULUS ! 104: Panic("Failed on ptReadUser - %#lo, %ld", adr, val); ! 105: #else ! 106: Panic("Failed on ptReadUser - %#o, %d", adr, val); ! 107: #endif ! 108: } /* if */ ! 109: } ! 110: else if (vfnCore != fnNil) { ! 111: if (lseek(vfnCore, lengthen(adr), 0) < 0L) ! 112: UError("address not found"); ! 113: if (read(vfnCore, &val, CBPOINT) < 1) ! 114: UError("Cannot read that location"); ! 115: } ! 116: else { ! 117: UError("No child process AND no core file"); ! 118: } /* if */ ! 119: return(val); ! 120: } /* GetUser */ ! 121: ! 122: ! 123: /* P U T U S E R */ ! 124: ! 125: export void PutUser(adr, val) ! 126: ADRT adr; ! 127: REGT val; ! 128: { ! 129: int i; ! 130: ! 131: if (vpid != pidNil) { ! 132: i = ptrace(ptWriteUser, vpid, adr, val); ! 133: if (i == -1 AND errno == EIO) { ! 134: if (FOdd(adr)) ! 135: UError("Attempt to write to ODD address"); ! 136: #ifdef REGULUS ! 137: Panic("Failed on ptWriteUser - %#lo, %ld", adr, val); ! 138: #else ! 139: Panic("Failed on ptWriteUser - %#o, %d", adr, val); ! 140: #endif ! 141: } /* if */ ! 142: } ! 143: else if (vfnCore != fnNil) { ! 144: if (lseek(vfnCore, lengthen(adr), 0) < 0L) ! 145: UError("address not found"); ! 146: if (write(vfnCore, &val, CBPOINT) < 1 ) ! 147: UError("Cannot write that location"); ! 148: } ! 149: else { ! 150: UError("No child process AND no core file"); ! 151: } /* if */ ! 152: } /* PutUser */ ! 153: ! 154: ! 155: /* G E T R E G */ ! 156: ! 157: export REGT GetReg(reg) ! 158: int reg; ! 159: { ! 160: ADRT adr; ! 161: ! 162: adr = (ADRT)(v_ar0 + vrgOffset[reg]); ! 163: return(GetUser(adr)); ! 164: } /* GetReg */ ! 165: ! 166: ! 167: /* P U T R E G */ ! 168: ! 169: export void PutReg(reg, val) ! 170: int reg; ! 171: REGT val; ! 172: { ! 173: ADRT adr; ! 174: ! 175: /* keep our globals up to date */ ! 176: switch (reg) { ! 177: case upc: ! 178: vpc = val; ! 179: break; ! 180: case ufp: ! 181: vfp = val; ! 182: break; ! 183: case usp: ! 184: vsp = val; ! 185: break; ! 186: #ifdef VAX ! 187: case uap: ! 188: vap = val; ! 189: break; ! 190: #endif ! 191: } /* switch */ ! 192: adr = (ADRT)(v_ar0 + vrgOffset[reg]); ! 193: PutUser(adr, val); ! 194: } /* PutReg */ ! 195: ! 196: ! 197: /* S A V E R E G S */ ! 198: ! 199: export void SaveRegs(regs) ! 200: REGT *regs; ! 201: { ! 202: #ifndef REGULUS ! 203: int i; ! 204: for (i = 0; i < uregMax; i++) ! 205: regs[i] = GetReg(i); ! 206: #else ! 207: if (trace(ptWriteUser, vpid, cbUserRegs, regs, v_ar0) < 0) ! 208: Panic("Bad register"); ! 209: #endif ! 210: regs[upc] = vpc; /* we do this because it may have been up-dated */ ! 211: } /* SaveRegs */ ! 212: ! 213: ! 214: /* R E S T O R E R E G S */ ! 215: ! 216: export void RestoreRegs(regs) ! 217: REGT *regs; ! 218: { ! 219: #ifndef REGULUS ! 220: int i; ! 221: ! 222: for (i = 0; i< uregMax; i++) ! 223: PutReg(i, regs[i]); ! 224: #else ! 225: if (trace(ptWriteUser, vpid, cbUserRegs, regs, v_ar0) < 0) ! 226: Panic("Bad register"); ! 227: #endif ! 228: vpc = regs[upc]; ! 229: vsp = regs[usp]; ! 230: vfp = regs[ufp]; ! 231: #ifndef VAX ! 232: vap = vfp; ! 233: #else ! 234: vap = regs[uap]; ! 235: #endif ! 236: } /* RestoreRegs */ ! 237: ! 238: ! 239: /* P U T S T A T E */ ! 240: ! 241: export void PutState() ! 242: { ! 243: #ifdef VAX ! 244: PutReg(uap, vap); ! 245: #endif ! 246: PutReg(ufp, vfp); ! 247: PutReg(usp, vsp); ! 248: PutReg(upc, vpc); ! 249: } /* PutState */ ! 250: ! 251: ! 252: /* G E T S T A T E */ ! 253: ! 254: export void GetState() ! 255: { ! 256: vfp = GetReg(ufp); ! 257: vsp = GetReg(usp); ! 258: vpc = GetReg(upc); ! 259: #ifndef VAX ! 260: vap = vfp; ! 261: #else ! 262: vap = GetReg(uap); ! 263: if (vpc > 0x70000000) { ! 264: vpc -= 0x7fff0000; /* BSD 4.X sticks this crud on top of pc */ ! 265: vpc--; /* back up to problem statement */ ! 266: } /* if */ ! 267: #endif ! 268: } /* GetState */ ! 269: ! 270: ! 271: /* G E T W O R D */ ! 272: ! 273: export int GetWord(adr, space) ! 274: ADRT adr; ! 275: int space; ! 276: { ! 277: return(Access(accRead, adr, space, 0)); ! 278: } /* GetWord */ ! 279: ! 280: ! 281: /* G E T B Y T E */ ! 282: ! 283: export int GetByte(adr, space) ! 284: ADRT adr; ! 285: int space; ! 286: { ! 287: STUFFU stuff; ! 288: ! 289: #ifdef EVENBYTES ! 290: ADRT adrOnWord; ! 291: ! 292: adrOnWord = adr & ~1; ! 293: #ifdef M68000 ! 294: stuff.lng = Access(accRead, adrOnWord, space, 0); ! 295: return((adrOnWord == adr) ? stuff.chars.chHiHi : stuff.chars.chHiLo); ! 296: #else ! 297: stuff.shorts.shortLo = Access(accRead, adrOnWord, space, 0); ! 298: return((adrOnWord == adr) ? stuff.chars.chLoHi : stuff.chars.chLoLo); ! 299: #endif ! 300: #endif ! 301: #ifdef TAHOE ! 302: stuff.lng = Access(accRead, adr, space, 0); ! 303: return(stuff.chars.chHiHi); ! 304: #endif ! 305: #ifdef VAX ! 306: stuff.lng = Access(accRead, adr, space, 0); ! 307: return(stuff.chars.chLoLo); ! 308: #endif ! 309: } /* GetByte */ ! 310: ! 311: ! 312: /* P U T W O R D */ ! 313: ! 314: export void PutWord(adr, space, val) ! 315: ADRT adr; ! 316: int space, val; ! 317: { ! 318: Access(accWrite, adr, space, val); ! 319: } /* PutWord */ ! 320: ! 321: ! 322: /* P U T B Y T E */ ! 323: ! 324: export void PutByte(adr, space, val) ! 325: ADRT adr; ! 326: int space, val; ! 327: { ! 328: STUFFU stuff; ! 329: ! 330: #ifdef EVENBYTES ! 331: ADRT adrOnWord; ! 332: ! 333: adrOnWord = adr & ~1; ! 334: #ifdef M68000 ! 335: stuff.lng = Access(accRead, adrOnWord, space, 0); ! 336: if (adrOnWord == adr) ! 337: stuff.chars.chHiHi = val; ! 338: else ! 339: stuff.chars.chHiLo = val; ! 340: Access(accWrite, adrOnWord, space, stuff.lng); ! 341: #else ! 342: stuff.shorts.shortLo = Access(accRead, adrOnWord, space, 0); ! 343: if (adrOnWord == adr) ! 344: stuff.chars.chLoHi = val; ! 345: else ! 346: stuff.chars.chLoLo = val; ! 347: Access(accWrite, adrOnWord, space, stuff.shorts.shortLo); ! 348: #endif ! 349: #endif ! 350: #ifdef TAHOE ! 351: stuff.lng = Access(accRead, adr, space, 0); ! 352: stuff.chars.chHiHi = val; ! 353: Access(accWrite, adr, space, stuff.lng); ! 354: #endif ! 355: #ifdef VAX ! 356: stuff.lng = Access(accRead, adr, space, 0); ! 357: stuff.chars.chLoLo = val; ! 358: Access(accWrite, adr, space, stuff.lng); ! 359: #endif ! 360: } /* PutByte */ ! 361: ! 362: ! 363: /* Get Block and PutBlock could be sped up by knowing about where ! 364: * word boundaries are and such, but it doesn't seem worth it at the ! 365: * moment. Maybe later. ! 366: */ ! 367: ! 368: /* G E T B L O C K */ ! 369: ! 370: export void GetBlock(adr, space, adrValue, cb) ! 371: ADRT adr, adrValue; ! 372: int space, cb; ! 373: { ! 374: #ifndef REGULUS ! 375: char *pCh; ! 376: ! 377: pCh = (char *) adrValue; /* point to receiving area */ ! 378: while (cb--) ! 379: *pCh++ = GetByte(adr++, space); ! 380: #else ! 381: if (trace(ptReadD, vpid, cb, adrValue, adr) < 0) ! 382: UError("address not found"); ! 383: #endif ! 384: } /* GetBlock */ ! 385: ! 386: ! 387: /* P U T B L O C K */ ! 388: ! 389: export void PutBlock(adr, space, adrValue, cb) ! 390: ADRT adr, adrValue; ! 391: int space, cb; ! 392: { ! 393: #ifndef REGULUS ! 394: char *pCh; ! 395: ! 396: pCh = (char *) adrValue; /* point to sending area */ ! 397: while (cb--) ! 398: PutByte(adr++, space, *pCh++); ! 399: #else ! 400: if (trace(ptWriteD, vpid, cb, adrValue, adr) < 0) ! 401: UError("address not found"); ! 402: #endif ! 403: } /* PutBlock */ ! 404: ! 405: ! 406: /* A C C E S S */ ! 407: ! 408: export int Access(accRequest, adrIn, space, value) ! 409: int accRequest, space, value; ! 410: ADRT adrIn; ! 411: { ! 412: int ret, val, pt, fn; ! 413: long adrLong; ! 414: FLAGT fRead; ! 415: ! 416: fRead = (accRequest == accRead); ! 417: if (vpid != pidNil) { /* we have a live process */ ! 418: if (space == spaceData) ! 419: pt = (fRead) ? ptReadD : ptWriteD; /* data space */ ! 420: else ! 421: pt = (fRead) ? ptReadI : ptWriteI; /* instruction space */ ! 422: ! 423: val = ptrace(pt, vpid, adrIn, value); ! 424: if (errno != 0) ! 425: UError("bad access"); ! 426: return(val); ! 427: } /* if */ ! 428: ! 429: /* we do NOT have a process, see if we have a core file to get it from */ ! 430: ! 431: adrLong = adrIn; ! 432: val = 0; ! 433: if (!FAdrGood(&adrLong, space)) ! 434: return(0); ! 435: fn = (space == spaceData) ? vmapCore.fn : vmapText.fn; ! 436: if (fn == fnNil) ! 437: UError("No core file"); ! 438: if (lseek(fn, adrLong, 0) < 0L) ! 439: UError("address not found"); ! 440: ret = (fRead) ? read(fn, &val, CBINT) ! 441: : write(fn, &value, CBINT); ! 442: if (ret != CBINT) ! 443: UError("Cannot %s that location", (fRead) ? "read" : "write"); ! 444: return(val); ! 445: } /* Access */ ! 446: ! 447: ! 448: /* F A D R G O O D */ ! 449: ! 450: export int FAdrGood(padrLong, space) ! 451: long *padrLong; ! 452: int space; ! 453: { ! 454: pMAPR map; ! 455: ! 456: #define FWithin(x, lbd, ubd) ((x>=lbd) && (x<ubd)) ! 457: ! 458: map = (space == spaceData) ? &vmapCore : &vmapText; ! 459: if ((vimap == 0) ! 460: AND (FWithin(*padrLong, map->b1, map->e1))) { ! 461: *padrLong += (map->f1)-(map->b1); ! 462: } ! 463: else if (FWithin(*padrLong, map->b2, map->e2)) { ! 464: *padrLong += (map->f2) - (map->b2); ! 465: } ! 466: else { ! 467: UError("No such address"); ! 468: } /* if */ ! 469: return(true); ! 470: } /* FAdrGood */ ! 471: ! 472: ! 473: /* M O V E B Y T E S */ ! 474: ! 475: export void MoveBytes(adrDest, adrSrc, cb) ! 476: ADRT adrDest, adrSrc; ! 477: int cb; ! 478: { ! 479: char *dest, *src; ! 480: ! 481: dest = (char *)adrDest; ! 482: src = (char *)adrSrc; ! 483: ! 484: /* ! 485: * this routine will do overlapping moves to the right or left. ! 486: */ ! 487: if (dest < src) { ! 488: while (cb--) ! 489: *dest++ = *src++; ! 490: } ! 491: else { ! 492: dest += cb; ! 493: src += cb; ! 494: while (cb--) ! 495: *--dest = *--src; ! 496: } /* if */ ! 497: } /* MoveBytes */ ! 498: ! 499: ! 500: /* L O N G R O U N D */ ! 501: ! 502: export long LongRound(a, b) ! 503: long a, b; ! 504: { ! 505: return( ((a+b-1)/b)*b ); ! 506: } /* LongRound */ ! 507: ! 508: ! 509: /* D O M A P */ ! 510: ! 511: export void DoMap() ! 512: { ! 513: int i; ! 514: char ch; ! 515: long *pl, tempLong; ! 516: TKE tk; ! 517: pTYR ty; ! 518: ! 519: tk = TkNext(); ! 520: if (tk != tkNil) { ! 521: ch = vsbTok[0]; ! 522: if ( (tk != tkStr) ! 523: OR (ch != 't' AND ch != 'c') ) { ! 524: UError("usage: M (t|c) number; number; .. (up to 6 numbers)"); ! 525: } ! 526: else { ! 527: pl = (ch == 't') ? &(vmapText.b1) : &(vmapCore.b1); ! 528: } /* if */ ! 529: tk = TkNext(); ! 530: for (i=0; i<6; i++, pl++) { ! 531: if (tk == tkSemi) { ! 532: tk = TkNext(); ! 533: continue; /* field separator */ ! 534: } /* if */ ! 535: tempLong = GetExpr(&ty, tk); ! 536: tk = vtk; ! 537: if (tk == tkSemi) ! 538: tk = TkNext(); /* eat the semicolon */ ! 539: if (ty == tyNil) ! 540: break; ! 541: *pl = tempLong; ! 542: } /* for */ ! 543: } /* if */ ! 544: ! 545: printf("Object file (%s):\n", vsbSymfile); ! 546: printf(" %10s", SbFAdr(vmapText.b1, false)); ! 547: printf(" %10s", SbFAdr(vmapText.e1, false)); ! 548: printf(" %10s\n", SbFAdr(vmapText.f1, false)); ! 549: printf(" %10s", SbFAdr(vmapText.b2, false)); ! 550: printf(" %10s", SbFAdr(vmapText.e2, false)); ! 551: printf(" %10s\n", SbFAdr(vmapText.f2, false)); ! 552: printf("Core file (%s):\n", vsbCorefile); ! 553: printf(" %10s", SbFAdr(vmapCore.b1, false)); ! 554: printf(" %10s", SbFAdr(vmapCore.e1, false)); ! 555: printf(" %10s\n", SbFAdr(vmapCore.f1, false)); ! 556: printf(" %10s", SbFAdr(vmapCore.b2, false)); ! 557: printf(" %10s", SbFAdr(vmapCore.e2, false)); ! 558: printf(" %10s\n", SbFAdr(vmapCore.f2, false)); ! 559: } /* DoMap */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.