## diffname ss/trap.c 1990/1223 ## diff -e /dev/null /n/bootesdump/1990/1223/sys/src/9/sparc/trap.c 0a #include "u.h" #include "lib.h" #include "mem.h" #include "dat.h" #include "fns.h" #include "ureg.h" #include "io.h" #include "errno.h" void notify(Ureg*); void noted(Ureg**); void rfnote(Ureg**); char *regname[]={ "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", "A0", "A1", "A2", "A3", "A4", "A5", "A6", "A7", }; long ticks; char *trapname[]={ "reset isp", "reset ipc", "bus error", "address error", "illegal instruction", "zero divide", "chk, chk2 instruction", "cptrapcc, trapcc, trapv instruction", "privilege violation", "trace", "line 1010 emulator", "line 1111 emulator", "reserved", "coprocessor protocol violation", "format error", "uninitialized interrupt", "unassigned 0x40", "unassigned 0x44", "unassigned 0x48", "unassigned 0x4C", "unassigned 0x50", "unassigned 0x54", "unassigned 0x58", "unassigned 0x5C", "spurious interrupt", "level 1 autovector (tac)", "level 2 autovector (port)", "level 3 autovector (incon)", "level 4 autovector (mouse)", "level 5 autovector (uart)", "level 6 autovector (sync)", "level 7 autovector", }; char* excname(unsigned vo) { static char buf[32]; /* BUG: not reentrant! */ vo &= 0x0FFF; vo >>= 2; if(vo < sizeof trapname/sizeof(char*)) return trapname[vo]; sprint(buf, "offset 0x%ux", vo<<2); return buf; } void trap(Ureg *ur) { int user; char buf[64]; user = !(ur->sr&SUPER); if(u) u->p->pc = ur->pc; /* BUG */ if(user){ sprint(buf, "sys: trap: pc=0x%lux %s", ur->pc, excname(ur->vo)); postnote(u->p, 1, buf, NDebug); }else{ print("kernel trap vo=0x%ux pc=0x%lux\n", ur->vo, ur->pc); dumpregs(ur); exit(); } if(user && u->nnote) notify(ur); } void dumpstack(void) { ulong l, v; extern ulong etext; if(u) for(l=(ulong)&l; lp->text, u->p->pid); else print("registers for kernel\n"); print("SR=%ux PC=%lux VO=%lux, USP=%lux\n", ur->sr, ur->pc, ur->vo, ur->usp); l = &ur->r0; for(i=0; ip->debug); if(u->nnote==0){ unlock(&u->p->debug); return; } if(u->note[0].flag!=NUser && (u->notified || u->notify==0)){ if(u->note[0].flag == NDebug) pprint("suicide: %s\n", u->note[0].msg); Die: unlock(&u->p->debug); pexit(u->note[0].msg, u->note[0].flag!=NDebug); } if(!u->notified){ if(!u->notify) goto Die; sp = ur->usp; sp -= sizeof(Ureg); u->ureg = (void*)sp; memcpy((Ureg*)sp, ur, sizeof(Ureg)); sp -= ERRLEN; memcpy((char*)sp, u->note[0].msg, ERRLEN); sp -= 3*BY2WD; *(ulong*)(sp+2*BY2WD) = sp+3*BY2WD; /* arg 2 is string */ *(ulong*)(sp+1*BY2WD) = (ulong)u->ureg; /* arg 1 is ureg* */ *(ulong*)(sp+0*BY2WD) = 0; /* arg 0 is pc */ ur->usp = sp; ur->pc = (ulong)u->notify; u->notified = 1; u->nnote--; memcpy(&u->note[0], &u->note[1], u->nnote*sizeof(Note)); } unlock(&u->p->debug); } /* * Return user to state before notify() */ void noted(Ureg **urp) { lock(&u->p->debug); if(!u->notified){ unlock(&u->p->debug); return; } u->notified = 0; memcpy(*urp, u->ureg, sizeof(Ureg)); unlock(&u->p->debug); splhi(); rfnote(urp); } #undef CHDIR /* BUG */ #include "/sys/src/libc/680209sys/sys.h" typedef long Syscall(ulong*); Syscall sysr1, sysfork, sysexec, sysgetpid, syssleep, sysexits, sysdeath, syswait; Syscall sysopen, sysclose, sysread, syswrite, sysseek, syserrstr, sysaccess, sysstat, sysfstat; Syscall sysdup, syschdir, sysforkpgrp, sysbind, sysmount, syspipe, syscreate; Syscall sysbrk_, sysremove, syswstat, sysfwstat, sysnotify, sysnoted; Syscall *systab[]={ sysr1, syserrstr, sysbind, syschdir, sysclose, sysdup, sysdeath, sysexec, sysexits, sysfork, sysforkpgrp, sysfstat, sysdeath, sysmount, sysopen, sysread, sysseek, syssleep, sysstat, syswait, syswrite, syspipe, syscreate, sysdeath, sysbrk_, sysremove, syswstat, sysfwstat, sysnotify, sysnoted, sysdeath, /* sysfilsys */ }; long syscall(Ureg *aur) { long ret; ulong sp; ulong r0; Ureg *ur; char *msg; u->p->insyscall = 1; ur = aur; u->p->pc = ur->pc; if(ur->sr & SUPER) panic("recursive system call"); /* * since the system call interface does not * guarantee anything about registers, but the fpcr is more than * just a register... BUG */ splhi(); fpsave(&u->fpsave); if(u->p->fpstate==FPactive || u->fpsave.type){ fprestore(&initfp); u->p->fpstate = FPinit; m->fpstate = FPinit; } spllo(); r0 = ur->r0; sp = ur->usp; u->nerrlab = 0; ret = -1; if(!waserror()){ if(r0 >= sizeof systab/BY2WD){ pprint("bad sys call number %d pc %lux\n", r0, ((Ureg*)UREGADDR)->pc); msg = "sys: bad sys call"; Bad: postnote(u->p, 1, msg, NDebug); error(Ebadarg); } if(sp & (BY2WD-1)){ pprint("odd sp in sys call pc %lux sp %lux\n", ((Ureg*)UREGADDR)->pc, ((Ureg*)UREGADDR)->sp); msg = "sys: odd stack"; goto Bad; } if(sp<(USTKTOP-BY2PG) || sp>(USTKTOP-5*BY2WD)) validaddr(sp, 5*BY2WD, 0); ret = (*systab[r0])((ulong*)(sp+BY2WD)); } u->nerrlab = 0; u->p->insyscall = 0; if(r0 == NOTED) /* ugly hack */ noted(&aur); /* doesn't return */ if(u->nnote){ ur->r0 = ret; notify(ur); } return ret; } #include "errstr.h" void error(int code) { strncpy(u->error, errstrtab[code], NAMELEN); nexterror(); } void errors(char *err) { strncpy(u->error, err, NAMELEN); nexterror(); } void nexterror(void) { gotolabel(&u->errlab[--u->nerrlab]); } . ## diffname ss/trap.c 1990/1226 ## diff -e /n/bootesdump/1990/1223/sys/src/9/sparc/trap.c /n/bootesdump/1990/1226/sys/src/9/sparc/trap.c 296a } void execpc(ulong entry) { ((Ureg*)UREGADDR)->pc = entry - 4; /* syscall advances it */ ((Ureg*)UREGADDR)->npc = entry; . 293c ur->r7 = ret; . 290c if(r7 == NOTED) /* ugly hack */ . 287a ur->pc += 4; ur->npc = ur->pc+4; . 286c ret = (*systab[r7])((ulong*)(sp+2*BY2WD)); . 272,273c if(r7 >= sizeof systab/BY2WD){ pprint("bad sys call number %d pc %lux\n", r7, ((Ureg*)UREGADDR)->pc); . 266c r7 = ur->r7; . 264a #endif . 258d 252a #ifdef asdf . 251c if(ur->psr & PSRPSUPER) . 244c ulong r7; . 197c #include "/sys/src/libc/sparc9sys/sys.h" . 131,132c for(i=0; i<32; i+=2, l+=2) print("R%d\t%.8lux\tR%d\t%.8lux\n", i, l[0], i+1, l[1]); . 129c print("PSR=%ux PC=%lux TBR=%lux\n", ur->psr, ur->pc, ur->tbr); . 105a trapinit(void) { int i; long t, a; a = ((ulong)traplink-TRAPS)>>2; a += 0x40000000; /* CALL traplink(SB) */ t = TRAPS; for(i=0; i<256; i++){ *(ulong*)t = a; /* CALL traplink(SB) */ *(ulong*)(t+4) = 0xa7480000; /* MOVW PSR, R19 */ a -= 16/4; t += 16; } /* * Vector 128 goes directly to syslink */ t = TRAPS+128*16; a = ((ulong)syslink-t)>>2; a += 0x40000000; *(ulong*)t = a; /* CALL syscall(SB) */ *(ulong*)(t+4) = 0xa7480000; /* MOVW PSR, R19 */ puttbr(TRAPS); } void . 98a for(;;); . 97c print("kernel trap: %s pc=0x%lux\n", excname(ur->tbr), ur->pc); . 94c print("user trap: %s pc=0x%lux\n", excname(ur->tbr), ur->pc); dumpregs(ur); for(;;); sprint(buf, "sys: trap: pc=0x%lux %s", ur->pc, excname(ur->tbr)); . 89,91c user = !(ur->psr&PSRPSUPER); /* if(u) . 75,79c tbr &= 0xFFF; tbr >>= 4; if(tbr < sizeof trapname/sizeof(char*)) return trapname[tbr]; if(tbr == 36) return "cp disabled"; if(tbr == 40) return "cp exception"; if(tbr >= 128) sprint(buf, "trap instruction %d", tbr-128); else if(17<=tbr && tbr<=31) sprint(buf, "interrupt level %d", tbr-16); else sprint(buf, "unknown trap %d", tbr); . 71c excname(ulong tbr) . 41,67c "privileged instruction", "fp disabled", "window overflow", "window underflow", "unaligned address", "fp exception", "data access exception", "tag overflow", . 36,39c "reset", "instruction access exception", . 14,31c extern void traplink(void); extern void syslink(void); . ## diffname ss/trap.c 1990/1227 ## diff -e /n/bootesdump/1990/1226/sys/src/9/sparc/trap.c /n/bootesdump/1990/1227/sys/src/9/sparc/trap.c 72c print("kernel trap: %s pc=0x%lux\n", excname(tbr), ur->pc); . 69c sprint(buf, "sys: trap: pc=0x%lux %s", ur->pc, excname(tbr)); . 66c print("user trap: %s pc=0x%lux\n", excname(tbr), ur->pc); . 60a tbr = (ur->tbr&0xFFF)>>4; if(tbr == 30){ /* interrupt 14: counter 1 */ clock(ur); return; } . 59a ulong tbr; . 38,39d ## diffname ss/trap.c 1990/1231 ## diff -e /n/bootesdump/1990/1227/sys/src/9/sparc/trap.c /n/bootesdump/1990/1231/sys/src/9/sparc/trap.c 62a return; } if(tbr == 16+12){ /* interrupt 12: keyboard and mouse */ duartintr(); return; } if(tbr == 16+5){ /* interrupt 5: lance */ lanceintr(); . 61c if(tbr == 16+14){ /* interrupt 14: counter 1 */ . ## diffname ss/trap.c 1991/0109 ## diff -e /n/bootesdump/1990/1231/sys/src/9/sparc/trap.c /n/bootesdump/1991/0109/sys/src/9/sparc/trap.c 167a print("suicide: %s\n", u->note[0].msg); . 160c if(u->nnote == 0){ . 91a print("notifyed %d\n", u->p->pid); } . 90c if(user && u->nnote){ print("notify %d\n", u->p->pid); . 83a print("return from postnote\n"); . 82a print("call postnote\n"); . 81d ## diffname ss/trap.c 1991/0110 ## diff -e /n/bootesdump/1991/0109/sys/src/9/sparc/trap.c /n/bootesdump/1991/0110/sys/src/9/sparc/trap.c 172d 84d 82d 80d 60a if(tbr == 16+15){ /* interrupt 14: counter 1 */ faultasync(ur); return; } . ## diffname ss/trap.c 1991/0112 ## diff -e /n/bootesdump/1991/0110/sys/src/9/sparc/trap.c /n/bootesdump/1991/0112/sys/src/9/sparc/trap.c 326d 210a (*urp)->r7 = -1; /* return error from the interrupted call */ . 190a ur->npc = (ulong)u->notify+4; . 165c if(u->nnote==0){ . 95,96d 92,93c if(user && u->nnote) . 83d ## diffname ss/trap.c 1991/0115 ## diff -e /n/bootesdump/1991/0112/sys/src/9/sparc/trap.c /n/bootesdump/1991/0115/sys/src/9/sparc/trap.c 331c strncpy(u->error, errstrtab[code], ERRLEN); . 83a if(tbr == 8) sprint(buf+strlen(buf), " FSR %lux", getfsr()); . 76a if(tbr == 8) /* floating point exception */ clearfpintr(); . ## diffname ss/trap.c 1991/01151 ## diff -e /n/bootesdump/1991/0115/sys/src/9/sparc/trap.c /n/bootesdump/1991/01151/sys/src/9/sparc/trap.c 287c . 285c ur->psr &= ~PSREF; . 281,283c if(u->p->fpstate == FPactive) { . 278,279c * guarantee anything about registers, . 275c . 95,96c Return: if(user && u && u->p->fpstate == FPinactive) { restfpregs(&u->fpsave); u->p->fpstate = FPactive; ur->psr |= PSREF; } . 90,93c switch(tbr){ case 1: /* instr. access */ case 9: /* data access */ if(u && u->p->fpstate==FPactive) { savefpregs(&u->fpsave); u->p->fpstate = FPinactive; ur->psr &= ~PSREF; } if(u){ x = u->p->insyscall; u->p->insyscall = 1; faultsparc(ur); u->p->insyscall = x; }else faultsparc(ur); goto Return; case 4: /* floating point disabled */ if(u && u->p){ if(u->p->fpstate == FPinit) restfpregs(&initfp); else if(u->p->fpstate == FPinactive) restfpregs(&u->fpsave); else break; u->p->fpstate = FPactive; ur->psr |= PSREF; return; } break; case 8: /* floating point exception */ clearfpintr(); break; default: break; } if(user){ spllo(); sprint(buf, "sys: trap: pc=0x%lux %s", ur->pc, excname(tbr)); if(tbr == 8) sprint(buf+strlen(buf), " FSR %lux", u->fpsave.fsr); postnote(u->p, 1, buf, NDebug); }else{ Error: print("kernel trap: %s pc=0x%lux\n", excname(tbr), ur->pc); dumpregs(ur); for(;;); } if(user && u->nnote) notify(ur); . 84,88c user = !(ur->psr&PSRPSUPER); tbr = (ur->tbr&0xFFF)>>4; if(tbr > 16){ /* interrupt */ if(u && u->p->state==Running){ if(u->p->fpstate == FPactive) { savefpregs(&u->fpsave); u->p->fpstate = FPinactive; ur->psr &= ~PSREF; } } switch(tbr-16){ case 15: /* asynch mem err */ faultasync(ur); break; case 14: /* counter 1 */ clock(ur); break; case 12: /* keyboard and mouse */ duartintr(); break; case 5: /* lance */ lanceintr(); break; default: goto Error; } . 60,82c if(u) . 56c int user, x; . ## diffname ss/trap.c 1991/0318 ## diff -e /n/bootesdump/1991/0201/sys/src/9/sparc/trap.c /n/bootesdump/1991/0318/sys/src/9/slc/trap.c 259c memmove(*urp, u->ureg, sizeof(Ureg)); . 242c memmove(&u->note[0], &u->note[1], u->nnote*sizeof(Note)); . 232c memmove((char*)sp, u->note[0].msg, ERRLEN); . 230c memmove((Ureg*)sp, ur, sizeof(Ureg)); . ## diffname ss/trap.c 1991/0322 ## diff -e /n/bootesdump/1991/0318/sys/src/9/slc/trap.c /n/bootesdump/1991/0322/sys/src/9/slc/trap.c 387c strncpy(u->error, err, ERRLEN); . ## diffname ss/trap.c 1991/0503 ## diff -e /n/bootesdump/1991/0322/sys/src/9/slc/trap.c /n/bootesdump/1991/0503/sys/src/9/slc/trap.c 338a print("syscall %s %d %d\n", u->p->text, u->p->pid, r7); . 216a print("suicide: %s\n", u->note[0].msg); . ## diffname ss/trap.c 1991/0504 ## diff -e /n/bootesdump/1991/0503/sys/src/9/slc/trap.c /n/bootesdump/1991/0504/sys/src/9/slc/trap.c 340d 217d ## diffname ss/trap.c 1991/0513 ## diff -e /n/bootesdump/1991/0504/sys/src/9/slc/trap.c /n/bootesdump/1991/0513/sys/src/9/slc/trap.c 282c sysalarm, . 273c Syscall sysbrk_, sysremove, syswstat, sysfwstat, sysnotify, sysnoted, sysalarm; . ## diffname ss/trap.c 1991/0604 ## diff -e /n/bootesdump/1991/0513/sys/src/9/slc/trap.c /n/bootesdump/1991/0604/sys/src/9/slc/trap.c 80c sccintr(); . ## diffname ss/trap.c 1991/0614 ## diff -e /n/bootesdump/1991/0604/sys/src/9/slc/trap.c /n/bootesdump/1991/0614/sys/src/9/slc/trap.c 358c if(u->nerrlab){ print("unbalanced error stack: %d extra\n", u->nerrlab); for(i = 0; i < NERR; i++) print("sp=%lux pc=%lux\n", u->errlab[i].sp, u->errlab[i].pc); panic("bad rob"); } . 354a poperror(); . 352,353c if(sp<(USTKTOP-BY2PG) || sp>(USTKTOP-(2+MAXSYSARG)*BY2WD)) validaddr(sp, ((2+MAXSYSARG)*BY2WD), 0); . 311a int i; . ## diffname ss/trap.c 1991/0709 ## diff -e /n/bootesdump/1991/0614/sys/src/9/slc/trap.c /n/bootesdump/1991/0709/sys/src/9/slc/trap.c 364c panic("error stack"); . 361c print("bad error stack [%d]: %d extra\n", r7, u->nerrlab); . ## diffname ss/trap.c 1991/0710 ## diff -e /n/bootesdump/1991/0709/sys/src/9/slc/trap.c /n/bootesdump/1991/0710/sys/src/9/slc/trap.c 380,402d 267c #include "/sys/src/libc/9syscall/sys.h" . ## diffname ss/trap.c 1991/0711 ## diff -e /n/bootesdump/1991/0710/sys/src/9/slc/trap.c /n/bootesdump/1991/0711/sys/src/9/slc/trap.c 351a } if(((ulong*)ur->pc)[-2] != 0x82206004){ /* new calling convention: look for ADD $-4, SP */ pprint("new system call linkage\n"); sp -= BY2WD; . 334a print("got low in syscall\n"); . 333c print("syscall %d\n", ur->r7); . 323a } u->p->insyscall = 1; u->p->pc = ur->pc; . 321,322c if(ur->psr & PSRPSUPER){ dumpregs(ur); . 319d 184a } . 183c print("%lux=%lux ", l, v); ++i; if((i&7) == 0) print("\n"); . 179c if(u){ i = 0; . 177a print("no dumpstack\n"); return; . 176a int i; . ## diffname ss/trap.c 1991/0712 ## diff -e /n/bootesdump/1991/0711/sys/src/9/slc/trap.c /n/bootesdump/1991/0712/sys/src/9/slc/trap.c 345d 343d 331d 328,329c if(ur->psr & PSRPSUPER) . ## diffname ss/trap.c 1991/0713 ## diff -e /n/bootesdump/1991/0712/sys/src/9/slc/trap.c /n/bootesdump/1991/0713/sys/src/9/slc/trap.c 364,366c if(sp<(USTKTOP-BY2PG) || sp>(USTKTOP-(1+MAXSYSARG)*BY2WD)) validaddr(sp, ((1+MAXSYSARG)*BY2WD), 0); ret = (*systab[r7])((ulong*)(sp+1*BY2WD)); . 360,362c if(((ulong*)ur->pc)[-2] == 0x82206004){ /* new calling convention: look for ADD $-4, SP */ pprint("old system call linkage\n"); sp += BY2WD; . ## diffname ss/trap.c 1991/0717 ## diff -e /n/bootesdump/1991/0713/sys/src/9/slc/trap.c /n/bootesdump/1991/0717/sys/src/9/slc/trap.c 379c noted(&aur, *(ulong*)(sp+1*BY2WD)); /* doesn't return */ . 269,271c switch(arg0){ case NCONT: splhi(); unlock(&u->p->debug); rfnote(urp); break; /* never returns */ default: pprint("unknown noted arg 0x%lux\n", arg0); u->lastnote.flag = NDebug; /* fall through */ case NTERM: if(u->lastnote.flag == NDebug) pprint("suicide: %s\n", u->lastnote.msg); unlock(&u->p->debug); pexit(u->lastnote.msg, u->lastnote.flag!=NDebug); } . 260a Ureg *nur; nur = u->ureg; validaddr(nur->pc, 1, 0); validaddr(nur->usp, BY2WD, 0); if(nur->psr!=u->svpsr){ pprint("bad noted ureg psr %lux\n", nur->psr); pexit("Suicide", 0); } . 259c noted(Ureg **urp, ulong arg0) . 249a memmove(&u->lastnote, &u->note[0], sizeof(Note)); . 234a u->svpsr = ur->psr; . 11c void noted(Ureg**, ulong); . ## diffname ss/trap.c 1991/0718 ## diff -e /n/bootesdump/1991/0717/sys/src/9/slc/trap.c /n/bootesdump/1991/0718/sys/src/9/slc/trap.c 293c case NDFLT: . ## diffname ss/trap.c 1991/0722 ## diff -e /n/bootesdump/1991/0718/sys/src/9/slc/trap.c /n/bootesdump/1991/0722/sys/src/9/slc/trap.c 237a if(waserror()){ pprint("suicide: trap in notify\n"); unlock(&u->p->debug); pexit("Suicide", 0); } validaddr((ulong)u->notify, 1, 0); validaddr(sp-ERRLEN-3*BY2WD, sizeof(Ureg)+ERRLEN-3*BY2WD, 0); poperror(); . ## diffname ss/trap.c 1991/0724 ## diff -e /n/bootesdump/1991/0722/sys/src/9/slc/trap.c /n/bootesdump/1991/0724/sys/src/9/slc/trap.c 415c if(u->nnote && r7!=FORK){ . 287d ## diffname ss/trap.c 1991/0727 ## diff -e /n/bootesdump/1991/0724/sys/src/9/slc/trap.c /n/bootesdump/1991/0727/sys/src/9/slc/trap.c 220a u->p->notepending = 0; . ## diffname ss/trap.c 1991/0731 ## diff -e /n/bootesdump/1991/0727/sys/src/9/slc/trap.c /n/bootesdump/1991/0731/sys/src/9/slc/trap.c 309,350c #include "../port/systab.h" . ## diffname ss/trap.c 1991/0814 ## diff -e /n/bootesdump/1991/0731/sys/src/9/slc/trap.c /n/bootesdump/1991/0814/sys/src/9/slc/trap.c 289a if(waserror()){ pprint("suicide: trap in noted\n"); unlock(&u->p->debug); goto Die; } validaddr(nur->pc, 1, 0); validaddr(nur->usp, BY2WD, 0); poperror(); . 284c pprint("call to noted() when not notified\n"); goto Die; . 278a Die: . 275,276d ## diffname ss/trap.c 1991/0926 ## diff -e /n/bootesdump/1991/0814/sys/src/9/slc/trap.c /n/bootesdump/1991/0926/sys/src/9/slc/trap.c 379a u->p->psstate = 0; . 367a u->p->psstate = sysctab[r7]; . ## diffname ss/trap.c 1991/1105 ## diff -e /n/bootesdump/1991/0926/sys/src/9/slc/trap.c /n/bootesdump/1991/1105/sys/src/9/slc/trap.c 361,364d 253c *(ulong*)(sp+1*BY2WD) = (ulong)u->ureg; /* arg 1 is ureg* (compat) */ ur->r7 = (ulong)u->ureg; /* arg 1 is ureg* */ . ## diffname ss/trap.c 1991/1108 ## diff -e /n/bootesdump/1991/1105/sys/src/9/slc/trap.c /n/bootesdump/1991/1108/sys/src/9/slc/trap.c 371,376c u->nerrlab = 0; if(u->p->procctl) procctl(u->p); . 344a if(u->p->procctl) procctl(u->p); . 179,180d 140,143c if(user) { if(u->p->procctl) procctl(u->p); if(u->nnote) notify(ur); if(u->p->fpstate == FPinactive) { restfpregs(&u->fpsave); u->p->fpstate = FPactive; ur->psr |= PSREF; } . 136,137d ## diffname ss/trap.c 1991/1111 ## diff -e /n/bootesdump/1991/1108/sys/src/9/slc/trap.c /n/bootesdump/1991/1111/sys/src/9/slc/trap.c 395a } /* This routine must save the values of registers the user is not permitted * to write from devproc and restore them before returning */ void setregisters(Ureg *xp, char *pureg, char *uva, int n) { print("setregisters: no idea\n"); . 385c if(u->p->procctl || (u->nnote && r7!=FORK)){ . 348,350d 221a if(u->p->procctl) procctl(u->p); if(u->nnote == 0) return; . 139,142c notify(ur); . 131d 123a Error: . ## diffname ss/trap.c 1991/1113 ## diff -e /n/bootesdump/1991/1111/sys/src/9/slc/trap.c /n/bootesdump/1991/1113/sys/src/9/slc/trap.c 222a . 170a . 127c sprint(buf, "sys: %s pc=0x%lux", excname(tbr), ur->pc); . 61a u->dbgreg = ur; } . 60c if(u) { . 49a } Return: . 48c else switch(tbr){ case 36: return "cp disabled"; case 40: return "cp exception"; case 128: return "syscall"; case 129: return "breakpoint"; default: . 40,44c if(tbr >= 130) . 36c static char buf[64]; /* BUG: not reentrant! */ . ## diffname ss/trap.c 1991/1114 ## diff -e /n/bootesdump/1991/1113/sys/src/9/slc/trap.c /n/bootesdump/1991/1114/sys/src/9/slc/trap.c 414c ulong psr; status = xp->psr; memmove(pureg, uva, n); xp->psr = psr; . 408,409c /* This routine must save the values of registers the user is not permitted to write * from devproc and the restore the saved values before returning . 395c splhi(); if(r7!=FORK && (u->p->procctl || u->nnote)){ . 279a splx(s); . 234a s = spllo(); /* need to go low as may fault */ . 228c ulong s, sp; . 222,224d ## diffname ss/trap.c 1991/1115 ## diff -e /n/bootesdump/1991/1114/sys/src/9/slc/trap.c /n/bootesdump/1991/1115/sys/src/9/slc/trap.c 417c psr = xp->psr; . ## diffname ss/trap.c 1991/1214 ## diff -e /n/bootesdump/1991/1115/sys/src/9/slc/trap.c /n/bootesdump/1991/1214/sys/src/9/slc/trap.c 406c ulong *sp; sp = (ulong*)(USTKTOP - ssize); *--sp = nargs; ((Ureg*)UREGADDR)->usp = (ulong)sp; ((Ureg*)UREGADDR)->pc = entry - 4; /* syscall advances it */ return USTKTOP-BY2WD; /* address of user-level clock */ . 403,404c long execregs(ulong entry, ulong ssize, ulong nargs) . ## diffname ss/trap.c 1991/1216 ## diff -e /n/bootesdump/1991/1214/sys/src/9/slc/trap.c /n/bootesdump/1991/1216/sys/src/9/slc/trap.c 327c qunlock(&u->p->debug); . 314c qunlock(&u->p->debug); . 307c qunlock(&u->p->debug); . 297c qunlock(&u->p->debug); . 295c qlock(&u->p->debug); . 277c qunlock(&u->p->debug); . 254c qunlock(&u->p->debug); . 243c qunlock(&u->p->debug); . 236c qunlock(&u->p->debug); . 233c qlock(&u->p->debug); . ## diffname ss/trap.c 1991/12171 ## diff -e /n/bootesdump/1991/1216/sys/src/9/slc/trap.c /n/bootesdump/1991/12171/sys/src/9/slc/trap.c 28c "fp: exception", . 24c "fp: disabled", . ## diffname ss/trap.c 1991/1218 ## diff -e /n/bootesdump/1991/12171/sys/src/9/slc/trap.c /n/bootesdump/1991/1218/sys/src/9/slc/trap.c 244c pexit(n->msg, n->flag!=NDebug); . 241c pprint("suicide: %s\n", n->msg); . 239c if(n->flag!=NUser && (u->notified || u->notify==0)){ . 235,237c n = &u->note[0]; if(strncmp(n->msg, "sys:", 4) == 0){ l = strlen(n->msg); if(l > ERRLEN-15) /* " pc=0x12345678\0" */ l = ERRLEN-15; sprint(n->msg+l, " pc=0x%.8lux", ur->pc); . 232c s = spllo(); . 229c if(u->nnote==0) . 225a Note *n; . 224a int l; . 137c sprint(buf, "sys: %s", excname(tbr)); . 56c if(tbr < sizeof trapname/sizeof(char*)) t = trapname[tbr]; else{ if(tbr >= 130) sprint(xx, "trap instruction %d", tbr-128); else if(17<=tbr && tbr<=31) sprint(xx, "interrupt level %d", tbr-16); else sprint(xx, "unknown trap %d", tbr); t = xx; } if(strncmp(t, "fp: ", 4) == 0) strcpy(buf, t); else sprint(buf, "trap: %s", t); . 53,54d 48c return "trap: cp exception"; . 38,46c switch(tbr){ return "trap: cp disabled"; . 36a char xx[64]; char *t; . ## diffname ss/trap.c 1992/0102 ## diff -e /n/bootesdump/1991/1218/sys/src/9/slc/trap.c /n/bootesdump/1992/0102/sys/src/9/slc/trap.c 410a return ur->r7; . 409c u->svr7 = ret; . 314a (*urp)->r7 = u->svr7; . ## diffname ss/trap.c 1992/0108 ## diff -e /n/bootesdump/1992/0102/sys/src/9/slc/trap.c /n/bootesdump/1992/0108/sys/src/9/slc/trap.c 411,412c if(notify(ur)) return ur->r7; . 290a return 1; . 238,239c if(u->nnote == 0) return 0; . 229c int . 10d ## diffname ss/trap.c 1992/0111 ## diff -e /n/bootesdump/1992/0108/sys/src/9/slc/trap.c /n/bootesdump/1992/0111/sys/src/9/slc/trap.c 8c #include "../port/error.h" . ## diffname ss/trap.c 1992/0120 ## diff -e /n/bootesdump/1992/0111/sys/src/9/slc/trap.c /n/bootesdump/1992/0120/sys/src/9/slc/trap.c 428a ulong userpc(void) { return ((Ureg*)UREGADDR)->pc; } . ## diffname ss/trap.c 1992/0124 ## diff -e /n/bootesdump/1992/0120/sys/src/9/slc/trap.c /n/bootesdump/1992/0124/sys/src/9/slc/trap.c 290c return sent; . 259a sent = 1; . 256a sent = 0; . 231c int l, sent; . ## diffname ss/trap.c 1992/0209 ## diff -e /n/bootesdump/1992/0124/sys/src/9/slc/trap.c /n/bootesdump/1992/0209/sys/src/9/slc/trap.c 197c print("no dumpstack\n"); return; . ## diffname ss/trap.c 1992/0321 ## diff -e /n/bootesdump/1992/0209/sys/src/9/slc/trap.c /n/bootesdump/1992/0321/sys/src/9/slc/trap.c 2c #include "../port/lib.h" . ## diffname ss/trap.c 1992/0409 ## diff -e /n/bootesdump/1992/0321/sys/src/9/slc/trap.c /n/bootesdump/1992/0409/sys/src/9/slc/trap.c 413c ur->r7 = ret; /* load up for noted() */ . 280a u->svr7 = ur->r7; /* save away r7 */ . ## diffname ss/trap.c 1992/0430 ## diff -e /n/bootesdump/1992/0409/sys/src/9/slc/trap.c /n/bootesdump/1992/0430/sys/src/9/slc/trap.c 413c if(r7!=RFORK && (u->p->procctl || u->nnote)){ . ## diffname ss/trap.c 1992/0616 ## diff -e /n/bootesdump/1992/0430/sys/src/9/slc/trap.c /n/bootesdump/1992/0616/sys/src/9/slc/trap.c 327,329d 322c if(!okaddr(nur->pc, 1, 0) || !okaddr(nur->usp, BY2WD, 0)){ . 271,273d 266,267c if(!okaddr((ulong)u->notify, 1, 0) || !okaddr(sp-ERRLEN-3*BY2WD, sizeof(Ureg)+ERRLEN-3*BY2WD, 0)){ pprint("suicide: bad address in notify\n"); . ## diffname ss/trap.c 1992/0620 ## diff -e /n/bootesdump/1992/0616/sys/src/9/slc/trap.c /n/bootesdump/1992/0620/sys/src/9/slc/trap.c 395a . 388c postnote(u->p, 1, msg, NDebug); error(Ebadarg); . 386c pprint("odd sp in sys call pc %lux sp %lux\n", ur->pc, ur->sp); . 381d 379c pprint("bad sys call number %d pc %lux\n", r7, ur->pc); . ## diffname ss/trap.c 1992/0625 ## diff -e /n/bootesdump/1992/0620/sys/src/9/slc/trap.c /n/bootesdump/1992/0625/sys/src/9/slc/trap.c 393c ret = (*systab[r7])(u->s.args); . 390,391c if(sp<(USTKTOP-BY2PG) || sp>(USTKTOP-sizeof(Sargs))) validaddr(sp, sizeof(Sargs), 0); u->s = *((Sargs*)(sp+1*BY2WD)); . 386,387c postnote(u->p, 1, "sys: odd stack", NDebug); . 383a . 380,381c postnote(u->p, 1, "sys: bad sys call", NDebug); . 354d ## diffname ss/trap.c 1992/06271 ## diff -e /n/bootesdump/1992/0625/sys/src/9/slc/trap.c /n/bootesdump/1992/06271/sys/src/9/slc/trap.c 411c if(u->scallnr!=RFORK && (u->p->procctl || u->nnote)){ . 407c if(u->scallnr == NOTED) /* ugly hack */ . 395c ret = (*systab[u->scallnr])(u->s.args); . 393c u->p->psstate = sysctab[u->scallnr]; . 377,378c if(u->scallnr >= sizeof systab/BY2WD){ pprint("bad sys call number %d pc %lux\n", u->scallnr, ur->pc); . 371c u->scallnr = ur->r7; . 352d ## diffname ss/trap.c 1992/0714 ## diff -e /n/bootesdump/1992/06271/sys/src/9/slc/trap.c /n/bootesdump/1992/0714/sys/src/9/slc/trap.c 252c if(n->flag == NDebug) . ## diffname ss/trap.c 1992/0720 ## diff -e /n/bootesdump/1992/0714/sys/src/9/slc/trap.c /n/bootesdump/1992/0720/sys/src/9/slc/trap.c 349d ## diffname ss/trap.c 1992/0721 ## diff -e /n/bootesdump/1992/0720/sys/src/9/slc/trap.c /n/bootesdump/1992/0721/sys/src/9/slc/trap.c 188a } void mulu(ulong u1, ulong u2, ulong *lop, ulong *hip) { ulong lo1, lo2, hi1, hi2, lo, hi, t1, t2, t; lo1 = u1 & 0xffff; lo2 = u2 & 0xffff; hi1 = u1 >> 16; hi2 = u2 >> 16; lo = lo1 * lo2; t1 = lo1 * hi2; t2 = lo2 * hi1; hi = hi1 * hi2; t = lo; lo += t1 << 16; if(lo < t) hi++; t = lo; lo += t2 << 16; if(lo < t) hi++; hi += (t1 >> 16) + (t2 >> 16); *lop = lo; *hip = hi; } void muls(long l1, long l2, long *lop, long *hip) { ulong t, lo, hi; ulong mlo, mhi; int sign; sign = 0; if(l1 < 0){ sign ^= 1; l1 = -l1; } if(l2 < 0){ sign ^= 1; l2 = -l2; } mulu(l1, l2, &mlo, &mhi); lo = mlo; hi = mhi; if(sign){ t = lo = ~lo; hi = ~hi; lo++; if(lo < t) hi++; } *lop = lo; *hip = hi; } int domuldiv(ulong iw, Ureg *ur) { long op1, op2; long *regp; long *regs; regs = (long*)ur; if(iw & (1<<13)){ /* signed immediate */ op2 = iw & 0x1FFF; if(op2 & 0x1000) op2 |= ~0x1FFF; }else op2 = regs[iw&0x1F]; op1 = regs[(iw>>14)&0x1F]; regp = ®s[(iw>>25)&0x1F]; if(iw & (4<<19)){ /* divide */ if(ur->y!=0 && ur->y!=~0){ unimp: ur->tbr = 37; /* "unimplemented instruction" */ return 0; /* complex Y is too hard */ } if(op2 == 0){ ur->tbr = 42; /* "zero divide" */ return 0; } if(iw & (1<<19)){ if(ur->y && (op1&(1<<31))==0) goto unimp; /* Y not sign extension */ *regp = op1 / op2; }else{ if(ur->y) goto unimp; *regp = (ulong)op1 / (ulong)op2; } }else{ if(iw & (1<<19)) muls(op1, op2, regp, (long*)&ur->y); else mulu(op1, op2, (ulong*)regp, &ur->y); } if(iw & (16<<19)){ /* set CC */ ur->psr &= ~(0xF << 20); if(*regp & (1<<31)) ur->psr |= 8 << 20; /* N */ if(*regp == 0) ur->psr |= 4 << 20; /* Z */ /* BUG: don't get overflow right on divide */ } ur->pc += 4; ur->npc = ur->pc+4; return 1; . 120a case 2: /* illegal instr, maybe mul */ iw = *(ulong*)ur->pc; if((iw&0xC1500000) == 0x80500000){ if(domuldiv(iw, ur)) goto Return; tbr = ur->tbr; } break; . 71c ulong tbr, iw; . 50c if(t == 0){ . 47a t = 0; . 42a case 42: return "trap: divide by zero"; . 40a case 37: return "trap: unimplemented instruction"; . 39a case 36: . 29a "watchpoint detected", . 11a int domuldiv(ulong, Ureg*); . ## diffname ss/trap.c 1992/0726 ## diff -e /n/bootesdump/1992/0721/sys/src/9/slc/trap.c /n/bootesdump/1992/0726/sys/src/9/slc/trap.c 160,161d 151c if(fptrap()){ /* do NOT talk to the FPU: see fptrap.c */ return; } . 70,71c sprint(excbuf, "trap: %s", t); return excbuf; . 68c strcpy(excbuf, t); . 41a case 8: if(u == 0){ fsr = getfsr(); sprint(excbuf, "fp: %s FSR %lux", fptrapname[(fsr>>14)&7], fsr); }else{ fsr = u->fpsave.fsr; sprint(excbuf, "fp: %s FQpc=0x%lux", fptrapname[(fsr>>14)&7], u->fpsave.q[0].a, fsr); } return excbuf; . 39a ulong fsr; . 37d 33a char *fptrapname[]={ "none", "IEEE 754 exception", "unfinished FP op", "unimplemented FP op", "sequence error", "hardware error", "invalid FP register", "reserved", }; . 17c long ticks; static char excbuf[64]; /* BUG: not reentrant! */ . ## diffname ss/trap.c 1992/0727 ## diff -e /n/bootesdump/1992/0726/sys/src/9/slc/trap.c /n/bootesdump/1992/0727/sys/src/9/slc/trap.c 516a fpquiet(); . 164c restfpregs(initfpp); . 140a fpquiet(); . 114c if(u->p->fpstate == FPactive){ fpquiet(); . 98a fpquiet(void) { int i; ulong fsr; i = 0; fsr = getfsr(); while(fsr & (1<<13)){ if(fsr & 0x1F){ print("trap in fpquiet\n"); break; } if(++i > 1000){ print("fp not quiescent\n"); break; } } } void . 97a /* * This routine is frightening. See comment in fptrap.c */ . ## diffname ss/trap.c 1992/0801 ## diff -e /n/bootesdump/1992/0727/sys/src/9/slc/trap.c /n/bootesdump/1992/0801/sys/src/9/slc/trap.c 535a /* SS2 bug: flush cache line holding trap entry in table */ if(conf.ss2) putw2(CACHETAGS+((TRAPS+16*128)&(VACSIZE-1)), 0); . 253d 240c /* ss2: must flush cache line for table */ *(ulong*)(t+0) = a; /* CALL traplink(SB) */ . 134a /* SS2 bug: flush cache line holding trap entry in table */ if(conf.ss2) putw2(CACHETAGS+((TRAPS+16*tbr)&(VACSIZE-1)), 0); . ## diffname ss/trap.c 1992/0802 ## diff -e /n/bootesdump/1992/0801/sys/src/9/slc/trap.c /n/bootesdump/1992/0802/sys/src/9/slc/trap.c 446c sp -= sizeof(Ureg)+ERRLEN+3*BY2WD; sp &= ~7; /* SP must be 8-byte aligned */ sp += ERRLEN+3*BY2WD; . 223c /* * Handled the interrupt; now it's safe to look at the FPQ */ if(fpunsafe) fpquiet(); if(user){ . 216,220c }else panic("kernel trap: %s pc=0x%lux\n", excname(tbr), ur->pc); . 206a if(fptrap()) goto Return; /* handled the problem */ . 203,204c /* if unsafe, trap happened shutting down FPU; just return */ if(m->fpunsafe){ m->fptrap = (fptrap()==0); . 171d 168,169c fpunsafe = 1; m->fpunsafe = 1; . 144d 141,142c fpunsafe = 1; m->fpunsafe = 1; . 139a /* if active, FPop at head of Q is probably an excep */ . 132a fpunsafe = 0; . 124c int user, x, fpunsafe; . 102,121d 98,100d 55,59c if(u == 0) panic("fptrap in kernel\n"); else{ if(m->fpunsafe==0 && u->p->fpstate!=FPactive) panic("fptrap not active\n"); . ## diffname ss/trap.c 1992/0803 ## diff -e /n/bootesdump/1992/0802/sys/src/9/slc/trap.c /n/bootesdump/1992/0803/sys/src/9/slc/trap.c 570,572d 538a if(u->p->procctl) procctl(u->p); . ## diffname ss/trap.c 1992/0804 ## diff -e /n/bootesdump/1992/0803/sys/src/9/slc/trap.c /n/bootesdump/1992/0804/sys/src/9/slc/trap.c 572a if(u->p->procctl) procctl(u->p); . 539,541d 534a u->fpsave.fsr = getfsr(); . 528,531d 208c restfpregs(&u->fpsave, u->fpsave.fsr); . 171c restfpregs(&u->fpsave, u->fpsave.fsr); . 169c restfpregs(initfpp, initfpp->fsr); . ## diffname ss/trap.c 1992/0805 ## diff -e /n/bootesdump/1992/0804/sys/src/9/slc/trap.c /n/bootesdump/1992/0805/sys/src/9/slc/trap.c 592a u->fpsave.fsr = initfpp->fsr; . 169c restfpregs(initfpp, u->fpsave.fsr); . 108d 105,106c if(u) . ## diffname ss/trap.c 1992/0806 ## diff -e /n/bootesdump/1992/0805/sys/src/9/slc/trap.c /n/bootesdump/1992/0806/sys/src/9/slc/trap.c 524c putsysspace(CACHETAGS+((TRAPS+16*128)&(VACSIZE-1)), 0); . 410c sprint(n->msg+l, " pc=0x%lux", ur->pc); . 113c putsysspace(CACHETAGS+((TRAPS+16*tbr)&(VACSIZE-1)), 0); . 61c sprint(excbuf, "fp: %s fppc=0x%lux", . ## diffname ss/trap.c 1992/0807 ## diff -e /n/bootesdump/1992/0807/sys/src/9/slc/trap.c /n/bootesdump/1992/0807/sys/src/9/ss/trap.c 524c putsysspace(CACHETAGS+((TRAPS+16*128)&(conf.vacsize-1)), 0); . 135a case 3: /* lance */ scsiintr(); break; . 112,113c if(conf.ss2cachebug) putsysspace(CACHETAGS+((TRAPS+16*tbr)&(conf.vacsize-1)), 0); . ## diffname ss/trap.c 1992/0810 ## diff -e /n/bootesdump/1992/0807/sys/src/9/ss/trap.c /n/bootesdump/1992/0810/sys/src/9/ss/trap.c 110d 104a tbr = (ur->tbr&0xFFF)>>4; /* * Hack to catch bootstrap fault during probe */ if(catch.pc) longjmp(&catch, 1); . 13a extern Label catch; . ## diffname ss/trap.c 1992/0811 ## diff -e /n/bootesdump/1992/0810/sys/src/9/ss/trap.c /n/bootesdump/1992/0811/sys/src/9/ss/trap.c 247a setpsr(getpsr()|PSRET|SPL(15)); /* enable traps, not interrupts */ . 111c gotolabel(&catch); . ## diffname ss/trap.c 1992/0914 ## diff -e /n/bootesdump/1992/0811/sys/src/9/ss/trap.c /n/bootesdump/1992/0914/sys/src/9/ss/trap.c 381a print("\n"); . 377,379c ++i; if((i&3) == 0) print("\n"); } . 375c if(KTZERO < v && v < (ulong)&etext){ . 369,370c static int dumping; if(dumping == 1){ print("no dumpstack\n"); return; } dumping = 1; . 208,212d 154,155c fpquiet(); savefpregs(&u->fpsave); . 125,126c fpquiet(); savefpregs(&u->fpsave); . 116d 102c int user, x; . ## diffname ss/trap.c 1993/0225 ## diff -e /n/bootesdump/1992/0914/sys/src/9/ss/trap.c /n/bootesdump/1993/0225/sys/src/9/ss/trap.c 456a *(ulong*)(sp+1*BY2WD) = (ulong)u->ureg; /* arg 1 0(FP) is ureg* */ . ## diffname ss/trap.c 1993/0501 # deleted ## diff -e /n/bootesdump/1993/0225/sys/src/9/ss/trap.c /n/fornaxdump/1993/0501/sys/src/brazil/ss/trap.c 1,626d