Date: Wed, 3 Jan 2007 19:44:54 GMT From: Oleksandr Tymoshenko <gonzo@FreeBSD.org> To: Perforce Change Reviews <perforce@FreeBSD.org> Subject: PERFORCE change 112453 for review Message-ID: <200701031944.l03Jisr8052417@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=112453 Change 112453 by gonzo@gonzo_hq on 2007/01/03 19:44:47 o Proper handle memory faults for both userland and kernel. Affected files ... .. //depot/projects/mips2/src/sys/mips/include/trap.h#4 edit .. //depot/projects/mips2/src/sys/mips/mips/trap.c#13 edit Differences ... ==== //depot/projects/mips2/src/sys/mips/include/trap.h#4 (text+ko) ==== @@ -53,6 +53,8 @@ #define TrCacheErr 30 /* MIPS64 */ #define TrVCED 31 +#define TrUser 32 /* Flag to mark userland-inititated traps */ + #ifndef LOCORE /* XXX */ struct trapframe; ==== //depot/projects/mips2/src/sys/mips/mips/trap.c#13 (text+ko) ==== @@ -133,22 +133,57 @@ code = (cause & MIPS3_CR_EXC_CODE) >> MIPS_CR_EXC_CODE_SHIFT; kernelmode = (tf->tf_regs[TF_SR] & MIPS_SR_KSU_USER) == 0; + if(! kernelmode) + code |= TrUser; + /* * Handle that which we can. */ + va = trunc_page(badvaddr); + td = curthread; + switch (code) { case TrMod: - va = trunc_page(badvaddr); + /* + * Kernel mode, KVA + */ if (va >= KERNBASE) + { + pt_entry_t *pte; + pte = tlb_kern_pte_find( + kernel_pmap->pm_private.pm_direct_map, va); + tlb_modified(kernel_pmap, (void *)va); - else - tlb_modified(&curthread->td_proc->p_vmspace->vm_pmap, - (void *)va); - goto done; + goto done; + } + /* FALLTHROUGH */ + case TrMod + TrUser: + /* + * UVA, both kernel and user modes + */ + { + pmap_t pmap; + pt_entry_t *pte; + + pmap = vmspace_pmap(td->td_proc->p_vmspace); + pte = pmap_segmap(pmap, va); + pte += (va >> PAGE_SHIFT) & (NPTEPG - 1); + + if (pte_ro(pte) ) + { + ftype = VM_PROT_WRITE; + map = &td->td_proc->p_vmspace->vm_map; + goto heavy; + } + + tlb_modified(pmap, (void *)va); + goto done; + } + break; + case TrTLBL: case TrTLBS: - va = trunc_page(badvaddr); - td = curthread; + ftype = (code == TrTLBL) ? VM_PROT_READ : VM_PROT_WRITE; if (va >= KERNBASE) { pt_entry_t *pte; @@ -167,14 +202,22 @@ tlb_update(va, kernel_pmap->pm_asid, pte[0], pte[1]); goto done; - } else - map = &td->td_proc->p_vmspace->vm_map; + } + + map = &td->td_proc->p_vmspace->vm_map; + goto heavy; + + case TrTLBL + TrUser: + map = &td->td_proc->p_vmspace->vm_map; + ftype = VM_PROT_READ; + goto heavy; + + case TrTLBS + TrUser: + map = &td->td_proc->p_vmspace->vm_map; + ftype = VM_PROT_WRITE; heavy: - if (code == TrTLBL) - ftype = VM_PROT_READ; - else - ftype = VM_PROT_WRITE; + error = vm_fault(map, va, ftype, (ftype & VM_PROT_WRITE) ? VM_FAULT_DIRTY : VM_FAULT_NORMAL); @@ -188,7 +231,8 @@ error, va, tf->tf_regs[TF_EPC] ); panic("TODO: signal on memory access errors"); - case TrSys: + + case TrSys + TrUser: syscall(curthread, tf); goto done; break; @@ -213,6 +257,11 @@ break; } + /* + * Clear out TrUser flag. Once we get here we need it cleared + * to access mnemonic/description strings. + */ + code &= ~TrUser; printf("\n\nFatal trap type %d in %s mode:", code, kernelmode ? "kernel" : "user"); if (code <= MAXTRAPID && code >= 0) {
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200701031944.l03Jisr8052417>