diff options
author | dg <dg@FreeBSD.org> | 1993-11-28 09:28:54 +0000 |
---|---|---|
committer | dg <dg@FreeBSD.org> | 1993-11-28 09:28:54 +0000 |
commit | 1b23af429b7543685abb9ca7dab6605819353d17 (patch) | |
tree | 981bfd5da5e60c8b613256f7c074b6d01d640725 /sys/kern/subr_trap.c | |
parent | 7f3ca7c5402255f79207d7ac3abe5e9fca0da83e (diff) | |
download | FreeBSD-src-1b23af429b7543685abb9ca7dab6605819353d17.zip FreeBSD-src-1b23af429b7543685abb9ca7dab6605819353d17.tar.gz |
Patch from Gene Stark:
Subject: Page fault in PTE area fails in copyout
Index: sys/i386/i386/trap.c FreeBSD-1.0.2
Description:
Reading files of several megabytes into Emacs, or many small
files all at once, would fail with "IO error - bad address".
Repeat-By:
The bug can be exercised by a test program that malloc()'s
a 5MB chunk of memory, and then, without accessing the memory
first, filling it with data from a file using read().
(I read 64k chunks from /dev/wd0d into successive 64k regions
of the 5MB chunk.) The read() will fail with EFAULT at the first
virtual address boundary that is a multiple of 0x400000.
Fix:
The problem was code in sys/i386/i386/trap.c that tries to
figure out what kind of trap occurred and to handle it appropriately.
It was interpreting any page fault with virtual address
>= vm->vm_maxsaddr as being a user stack segment fault.
In fact, addresses >= USRSTACK are in the user structure/PTE area,
and if they are handled as stack faults, the proper PTE will
not be paged in when it is supposed to be. This situation comes
up in copyout() and copyoutstr(), if PTE's are accessed for the
first time ever. The page fault on accessing the nonexistent PTE
is mishandled as a stack fault, and then the fault that occurs on
the subsequent access to the page itself causes copyout to fail
with EFAULT.
Diffstat (limited to 'sys/kern/subr_trap.c')
-rw-r--r-- | sys/kern/subr_trap.c | 8 |
1 files changed, 5 insertions, 3 deletions
diff --git a/sys/kern/subr_trap.c b/sys/kern/subr_trap.c index e967477..d413307 100644 --- a/sys/kern/subr_trap.c +++ b/sys/kern/subr_trap.c @@ -34,7 +34,7 @@ * SUCH DAMAGE. * * from: @(#)trap.c 7.4 (Berkeley) 5/13/91 - * $Id: trap.c,v 1.7 1993/11/13 02:25:08 davidg Exp $ + * $Id: trap.c,v 1.8 1993/11/25 01:31:01 wollman Exp $ */ /* @@ -322,7 +322,7 @@ copyfault: */ nss = 0; if ((caddr_t)va >= vm->vm_maxsaddr - && (caddr_t)va < (caddr_t)VM_MAXUSER_ADDRESS + && (caddr_t)va < (caddr_t)USRSTACK && map != kernel_map && dostacklimits) { nss = clrnd(btoc((unsigned)vm->vm_maxsaddr @@ -474,7 +474,9 @@ int trapwrite(addr) nss = 0; p = curproc; vm = p->p_vmspace; - if ((caddr_t)va >= vm->vm_maxsaddr && dostacklimits) { + if ((caddr_t)va >= vm->vm_maxsaddr + && (caddr_t)va < (caddr_t)USRSTACK /* EWS 11/27/93 */ + && dostacklimits) { nss = clrnd(btoc((unsigned)vm->vm_maxsaddr + MAXSSIZ - (unsigned)va)); if (nss > btoc(p->p_rlimit[RLIMIT_STACK].rlim_cur)) |