diff options
author | Ian Moffett <ian@osmora.org> | 2024-05-23 23:57:43 -0400 |
---|---|---|
committer | Ian Moffett <ian@osmora.org> | 2024-05-23 23:57:43 -0400 |
commit | 9c8b7aea1e3f941134689aca546f6cb0c6b659fd (patch) | |
tree | 8441f706bd698f82e540fb6d410ee7d4d43c139f /sys/arch/amd64 | |
parent | 453ceabb2ea69217b4f66856b8813f13efd42b1e (diff) |
kernel/amd64: trap: Handle cleanup before signal
Signed-off-by: Ian Moffett <ian@osmora.org>
Diffstat (limited to 'sys/arch/amd64')
-rw-r--r-- | sys/arch/amd64/amd64/trap.c | 32 |
1 files changed, 27 insertions, 5 deletions
diff --git a/sys/arch/amd64/amd64/trap.c b/sys/arch/amd64/amd64/trap.c index bf8e3b5..539ee48 100644 --- a/sys/arch/amd64/amd64/trap.c +++ b/sys/arch/amd64/amd64/trap.c @@ -146,6 +146,27 @@ handle_fatal(struct trapframe *tf) } /* + * Raise a fatal signal. + * + * @curtd: Current thread. + * @sched_tmr: Scheduler timer. + * @sig: Signal to raise. + */ +static void +raise_fatal(struct proc *curtd, struct timer *sched_tmr, int sig) +{ + /* + * trap_handler() disables interrupts. We will be + * killing the current process but before we do that + * we need to make sure interrupts are running and the + * scheduler timer is still going... + */ + intr_unmask(); + sched_tmr->oneshot_us(DEFAULT_TIMESLICE_USEC); + signal_raise(curtd, sig); +} + +/* * Handle a pagefault occuring in the userland * * @curtd: Current thread. @@ -153,7 +174,8 @@ handle_fatal(struct trapframe *tf) * @sched_tmr: Scheduler timer. */ static void -handle_user_pf(struct proc *curtd, struct trapframe *tf) +handle_user_pf(struct proc *curtd, struct trapframe *tf, + struct timer *sched_tmr) { uintptr_t fault_addr; vm_prot_t access_type; @@ -168,7 +190,7 @@ handle_user_pf(struct proc *curtd, struct trapframe *tf) KERR("Fault access mask: 0x%x\n", access_type); KERR("Raising SIGSEGV to PID %d...\n", curtd->pid); regdump(tf); - signal_raise(curtd, SIGSEGV); + raise_fatal(curtd, sched_tmr, SIGSEGV); } } @@ -224,16 +246,16 @@ trap_handler(struct trapframe *tf) case TRAP_ARITH_ERR: KERR("Got arithmetic error - raising SIGFPE...\n"); KERR("SIGFPE -> PID %d\n", curtd->pid); - signal_raise(curtd, SIGFPE); + raise_fatal(curtd, &sched_tmr, SIGFPE); break; case TRAP_PAGEFLT: - handle_user_pf(curtd, tf); + handle_user_pf(curtd, tf, &sched_tmr); break; default: KERR("Got %s - raising SIGSEGV...\n", trap_type[tf->trapno]); KERR("SIGSEGV -> PID %d\n", curtd->pid); regdump(tf); - signal_raise(curtd, SIGSEGV); + raise_fatal(curtd, &sched_tmr, SIGSEGV); break; } |