Undo the mistake made in revision 1.77 of trap.c and which was the

ultimate trigger for the follow-up fixes in revisions 1.78, 1.80,
1.81 and 1.82 of trap.c. I was simply too pre-occupied with the
gateway page and how it blurs kernel space with user space and
vice versa that I couldn't see that it was all a load of bollocks.

It's not the IP address that matters, it's the privilege level that
counts. We never run in user space with lifted permissions and we
sure can not run in kernel space without it. Sure, the gateway page
is the exception, but not if you look at the privilege level. It's
user space if you run with user permissions and kernel space otherwise.

So, we're back to looking at the privilege level like it should be.
There's no other way.

Pointy hat: marcel
This commit is contained in:
marcel 2003-08-20 05:30:35 +00:00
parent 5c48e77ef1
commit dd5e41ad29
2 changed files with 15 additions and 25 deletions

View File

@ -1,4 +1,3 @@
/* $FreeBSD$ */
/* From: src/sys/alpha/alpha/trap.c,v 1.33 */
/* $NetBSD: trap.c,v 1.31 1998/03/26 02:21:46 thorpej Exp $ */
@ -29,6 +28,9 @@
* rights to redistribute these changes.
*/
#include <sys/cdefs.h>
__FBSDID("$FreeBSD$");
#include "opt_ddb.h"
#include "opt_ktrace.h"
@ -343,10 +345,11 @@ trap(int vector, struct trapframe *framep)
int i, user;
u_int sticks;
user = ((framep->tf_special.iip >> 61) < 5) ? 1 : 0;
user = TRAPF_USERMODE(framep) ? 1 : 0;
/* Short-circuit break instruction based system calls. */
if (vector == IA64_VEC_BREAK && framep->tf_special.ifa == 0x100000) {
if (vector == IA64_VEC_BREAK && user &&
framep->tf_special.ifa == 0x100000) {
break_syscall(framep);
return;
}
@ -639,14 +642,7 @@ trap(int vector, struct trapframe *framep)
goto out;
no_fault_in:
/*
* Additionally check the privilege level. We don't want to
* panic when we're in the gateway page, running at user
* level. This happens for the signal trampolines. Note that
* when that happens, user is defined as 0 above. We need to
* set user to 1 to force calling userret() and do_ast().
*/
if (!TRAPF_USERMODE(framep)) {
if (!user) {
/* Check for copyin/copyout fault. */
if (td != NULL && td->td_pcb->pcb_onfault != 0) {
framep->tf_special.iip =
@ -656,9 +652,8 @@ trap(int vector, struct trapframe *framep)
goto out;
}
goto dopanic;
} else
user = 1;
ucode = va;
}
ucode = va;
i = (rv == KERN_PROTECTION_FAILURE) ? SIGBUS : SIGSEGV;
break;
}

View File

@ -56,20 +56,12 @@ struct clockframe {
struct trapframe cf_tf;
};
#define CLKF_PC(cf) ((cf)->cf_tf.tf_special.iip)
#define CLKF_USERMODE(cf) ((CLKF_PC(cf) >> 61) < 5)
/* Used by signaling code. */
#define cpu_getstack(td) ((td)->td_frame->tf_special.sp)
#define CLKF_CPL(cf) ((cf)->cf_tf.tf_special.psr & IA64_PSR_CPL)
#define CLKF_USERMODE(cf) (CLKF_CPL(cf) == IA64_PSR_CPL_USER)
#define TRAPF_PC(tf) ((tf)->tf_special.iip)
#define TRAPF_CPL(tf) ((tf)->tf_special.psr & IA64_PSR_CPL)
/*
* User mode for use by ast() and VM faults. It's takes into account
* that the gateway page is kernel space when looking at the VA, but
* is to be treated as user space when running with user priveleges.
*/
#define TRAPF_USERMODE(tf) \
((TRAPF_PC(tf) >> 61) < 5 || TRAPF_CPL(tf) == IA64_PSR_CPL_USER)
#define TRAPF_USERMODE(tf) (TRAPF_CPL(tf) == IA64_PSR_CPL_USER)
/*
* CTL_MACHDEP definitions.
@ -96,6 +88,9 @@ struct clockframe {
*/
#define get_cyclecount ia64_get_itc
/* Used by signaling code. */
#define cpu_getstack(td) ((td)->td_frame->tf_special.sp)
void cpu_halt(void);
void cpu_reset(void);
void fork_trampoline(void); /* MAGIC */