summaryrefslogtreecommitdiff
path: root/os/js/trap.c
diff options
context:
space:
mode:
authorKonstantin Kirik (snegovick) <snegovick@uprojects.org>2025-12-28 12:27:31 +0300
committerKonstantin Kirik (snegovick) <snegovick@uprojects.org>2025-12-28 12:27:31 +0300
commit78ee7d5717807e6ac779293d0d3c78341de6130a (patch)
treea43e3b0f61318ac45e6d907c7cc5bad2c6d7f497 /os/js/trap.c
parentbdaf46cf45bbb59261da245d548a179d95a42768 (diff)
Move existing boards into subdits split per arch
Diffstat (limited to 'os/js/trap.c')
-rw-r--r--os/js/trap.c472
1 files changed, 0 insertions, 472 deletions
diff --git a/os/js/trap.c b/os/js/trap.c
deleted file mode 100644
index b9117bfe..00000000
--- a/os/js/trap.c
+++ /dev/null
@@ -1,472 +0,0 @@
-#include "u.h"
-#include "../port/lib.h"
-#include "mem.h"
-#include "dat.h"
-#include "fns.h"
-#include "ureg.h"
-#include "io.h"
-#include "../port/error.h"
-
-void noted(Ureg**, ulong);
-void rfnote(Ureg**);
-int domuldiv(ulong, Ureg*);
-
-extern Label catch;
-extern void traplink(void);
-extern void syslink(void);
-static void faultsparc(Ureg *ur);
-static void faultasync(Ureg *ur);
-
- long ticks;
-static char excbuf[64]; /* BUG: not reentrant! */
-
-char *trapname[]={
- "reset",
- "instruction access exception",
- "illegal instruction",
- "privileged instruction",
- "fp: disabled",
- "window overflow",
- "window underflow",
- "unaligned address",
- "fp: exception",
- "data access exception",
- "tag overflow",
- "watchpoint detected",
-};
-
-char *fptrapname[]={
- "none",
- "IEEE 754 exception",
- "unfinished FP op",
- "unimplemented FP op",
- "sequence error",
- "hardware error",
- "invalid FP register",
- "reserved",
-}
-;
-
-char*
-excname(ulong tbr)
-{
- char xx[64];
- char *t;
-
- switch(tbr){
- case 8:
- if(up == 0)
- panic("fptrap in kernel\n");
- else{
-panic("fptrap not implemented\n");
-#ifdef notdef
- if(m->fpunsafe==0 && up->p->fpstate!=FPactive)
- panic("fptrap not active\n"); fsr = up->fpsave.env;
- sprint(excbuf, "fp: %s fppc=0x%lux",
- fptrapname[(fsr>>14)&7],
- up->fpsave.q[0].a, fsr);
-#endif
- }
- return excbuf;
- case 36:
- return "trap: cp disabled";
- case 37:
- return "trap: unimplemented instruction";
- case 40:
- return "trap: cp exception";
- case 42:
- return "trap: divide by zero";
- case 128:
- return "syscall";
- case 129:
- return "breakpoint";
- }
- t = 0;
- if(tbr < sizeof trapname/sizeof(char*))
- t = trapname[tbr];
- if(t == 0){
- if(tbr >= 130)
- sprint(xx, "trap instruction %ld", tbr-128);
- else if(17<=tbr && tbr<=31)
- sprint(xx, "interrupt level %ld", tbr-16);
- else
- sprint(xx, "unknown trap %ld", tbr);
- t = xx;
- }
- if(strncmp(t, "fp: ", 4) == 0)
- strcpy(excbuf, t);
- else
- sprint(excbuf, "trap: %s", t);
- return excbuf;
-
-}
-
-void
-trap(Ureg *ur)
-{
- int user;
- ulong tbr, iw;
-
- tbr = (ur->tbr&0xFFF)>>4;
- /*
- * Hack to catch bootstrap fault during probe
- */
- if(catch.pc)
- gotolabel(&catch);
-
- if(up)
- up->dbgreg = ur;
-
- user = !(ur->psr&PSRPSUPER);
- if(user) {
- panic("how did we get to user mode???");
- }
- if(tbr > 16){ /* interrupt */
- switch(tbr-16) {
- case 15: /* asynch mem err */
- faultasync(ur);
- break;
- case 14: /* processor counter */
- clock(ur);
- break;
- case 13: /* keyboard/mouse */
- ns16552intr(0);
- kbdintr();
- break;
- case 6: /* lance */
- lanceintr();
- break;
- default:
- print("unexp intr lev %ld\n", tbr-16);
- goto Error;
- }
- }else{
- switch(tbr){
- case 1: /* instr. access */
- case 9: /* data access */
- if(up && up->fpstate==FPACTIVE) {
- fpquiet();
- fpsave(&up->fpsave);
- up->fpstate = FPINACTIVE;
- }
- faultsparc(ur);
- goto Return;
- case 2: /* illegal instr, maybe mul */
- iw = *(ulong*)ur->pc;
- if((iw&0xC1500000) == 0x80500000){
- if(domuldiv(iw, ur))
- goto Return;
- tbr = ur->tbr;
- }
- break;
- case 4: /* floating point disabled */
-panic("some more floating point crapola");
-break;
-#ifdef notdef
- if(u && u->p){
- if(up->p->fpstate == FPINIT)
- restfpregs(initfpp, up->fpsave.fsr);
- else if(u->p->fpstate == FPinactive)
- restfpregs(&u->fpsave, u->fpsave.fsr);
- else
- break;
- u->p->fpstate = FPactive;
- ur->psr |= PSREF;
- return;
- }
- break;
-#endif
- case 8: /* floating point exception */
-panic("floating point crapola #3");
-break;
-#ifdef notdef
- /* if unsafe, trap happened shutting down FPU; just return */
- if(m->fpunsafe){
- m->fptrap = (fptrap()==0);
- return;
- }
- if(fptrap())
- goto Return; /* handled the problem */
- break;
-#endif
- default:
- break;
- }
- Error:
- panic("kernel trap: %s pc=0x%lux\n", excname(tbr), ur->pc);
- }
- Return:
- return;
-}
-
-void
-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+0) = a; /* CALL traplink(SB) */
- *(ulong*)(t+4) = 0xa7480000; /* MOVW PSR, R19 */
- a -= 16/4;
- t += 16;
- }
-
-#ifdef notdef
- flushpage(TRAPS);
-#else
- flushicache();
-#endif
-
- puttbr(TRAPS);
- setpsr(getpsr()|PSRET|SPL(15)); /* enable traps, not interrupts */
-}
-
-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 = &regs[(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;
-}
-
-void
-dumpregs(Ureg *ur)
-{
- int i;
- ulong *l;
-
- if(up) {
- print("registers for %s %ld\n",up->text,up->pid);
- if(ur->usp < (ulong)up->kstack ||
- ur->usp > (ulong)up->kstack+KSTACK-8)
- print("invalid stack pointer\n");
- } else
- print("registers for kernel\n");
-
- print("PSR=%lux PC=%lux TBR=%lux\n", ur->psr, ur->pc, ur->tbr);
- l = &ur->r0;
- 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]);
-}
-
-
-/* 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
- */
-void
-setregisters(Ureg *xp, char *pureg, char *uva, int n)
-{
- ulong psr;
-
- psr = xp->psr;
- memmove(pureg, uva, n);
- xp->psr = psr;
-}
-
-void
-dumpstack(void)
-{
-}
-
-/*
- * Must only be called splhi() when it is safe to spllo(). Because the FP unit
- * traps if you touch it when an exception is pending, and because if you
- * trap with ET==0 you halt, this routine sets some global flags to enable
- * the rest of the system to handle the trap that might occur here without
- * upsetting the kernel. Shouldn't be necessary, but safety first.
- */
-int
-fpquiet(void)
-{
- int i, notrap;
- ulong fsr;
- char buf[128];
-
- i = 0;
- notrap = 1;
- up->fpstate = FPINACTIVE;
- for(;;){
- m->fptrap = 0;
- fsr = getfsr();
- if(m->fptrap){
- /* trap occurred and up->fpsave contains state */
- sprint(buf, "sys: %s", excname(8));
-#ifdef notdef
- postnote(u->p, 1, buf, NDebug);
-#else
- panic(buf);
-#endif
- notrap = 0;
- break;
- }
- if((fsr&(1<<13)) == 0)
- break;
- if(++i > 1000){
- print("fp not quiescent\n");
- break;
- }
- }
- up->fpstate = FPACTIVE;
- return notrap;
-}
-
-enum
-{
- SE_WRITE = 4<<5,
- SE_PROT = 2<<2,
-};
-
-static void
-faultsparc(Ureg *ur)
-{
- ulong addr;
- char buf[ERRMAX];
- int read;
- ulong tbr, ser;
-
- tbr = (ur->tbr&0xFFF)>>4;
- addr = ur->pc; /* assume instr. exception */
- read = 1;
- if(tbr == 9){ /* data access exception */
- addr = getrmmu(SFAR);
- ser = getrmmu(SFSR);
- if(ser&(SE_WRITE)) /* is SE_PROT needed? */
- read = 0;
- }
-
- up->dbgreg = ur; /* for remote acid */
- spllo();
- sprint(buf, "sys: trap: fault %s addr=0x%lux",
- read? "read" : "write", addr);
-
- if(up->type == Interp)
- disfault(ur,buf);
- dumpregs(ur);
- panic("fault: %s", buf);
-}
-
-static void
-faultasync(Ureg *ur)
-{
- int user;
-
- print("interrupt 15 AFSR %lux AFAR %lux MFSR %lux MFAR %lux\n",
- getphys(AFSR), getphys(AFAR), getphys(MFSR), getphys(MFAR));
- dumpregs(ur);
- /*
- * Clear interrupt
- */
- putphys(PROCINTCLR, 1<<15);
- user = !(ur->psr&PSRPSUPER);
- if(user)
- pexit("Suicide", 0);
- panic("interrupt 15");
-}