Changeset View
Changeset View
Standalone View
Standalone View
sys/riscv/riscv/trap.c
Show First 20 Lines • Show All 194 Lines • ▼ Show 20 Lines | #endif | ||||
stval = frame->tf_stval; | stval = frame->tf_stval; | ||||
if (td->td_critnest != 0 || td->td_intr_nesting_level != 0 || | if (td->td_critnest != 0 || td->td_intr_nesting_level != 0 || | ||||
WITNESS_CHECK(WARN_SLEEPOK | WARN_GIANTOK, NULL, | WITNESS_CHECK(WARN_SLEEPOK | WARN_GIANTOK, NULL, | ||||
"Kernel page fault") != 0) | "Kernel page fault") != 0) | ||||
goto fatal; | goto fatal; | ||||
if (usermode) { | if (usermode) { | ||||
if (!VIRT_IS_VALID(stval)) { | |||||
call_trapsignal(td, SIGSEGV, SEGV_MAPERR, (void *)stval, | |||||
frame->tf_scause & SCAUSE_CODE); | |||||
goto done; | |||||
} | |||||
map = &td->td_proc->p_vmspace->vm_map; | map = &td->td_proc->p_vmspace->vm_map; | ||||
} else { | } else { | ||||
/* | /* | ||||
* Enable interrupts for the duration of the page fault. For | * Enable interrupts for the duration of the page fault. For | ||||
* user faults this was done already in do_trap_user(). | * user faults this was done already in do_trap_user(). | ||||
*/ | */ | ||||
intr_enable(); | intr_enable(); | ||||
if (!VIRT_IS_VALID(stval)) | |||||
goto fatal; | |||||
markj: In the user mode path, we call pmap_fault() without validating the address. Doesn't that mean… | |||||
Done Inline ActionsYeah... good catch there, thanks. mhorne: Yeah... good catch there, thanks. | |||||
if (stval >= VM_MAX_USER_ADDRESS) { | if (stval >= VM_MAX_USER_ADDRESS) { | ||||
map = kernel_map; | map = kernel_map; | ||||
} else { | } else { | ||||
if (pcb->pcb_onfault == 0) | if (pcb->pcb_onfault == 0) | ||||
goto fatal; | goto fatal; | ||||
map = &td->td_proc->p_vmspace->vm_map; | map = &td->td_proc->p_vmspace->vm_map; | ||||
} | } | ||||
▲ Show 20 Lines • Show All 189 Lines • Show Last 20 Lines |
In the user mode path, we call pmap_fault() without validating the address. Doesn't that mean that the assertion in pmap_l1() can be tripped from user mode?