Messages in this thread Patch in this message |  | | Date | Thu, 27 Feb 2014 14:52:54 -0800 | From | "H. Peter Anvin" <> | Subject | Re: perf_fuzzer compiled for x32 causes reboot |
| |
On 02/27/2014 02:31 PM, Steven Rostedt wrote: > > Yeah, something is getting mesed up. >
What it *looks* like to me is that we try to nest the cr2 save/restore, which doesn't nest because it is a percpu variable.
... except in the x86-64 case, we *ALSO* save/restore cr2 inside entry_64.S, which makes the stuff in do_nmi completely redundant and there for no good reason.
I would actually suggest we do the equivalent on i386 as well.
Vince, could you try this patch as an experiment?
diff --git a/arch/x86/lib/usercopy.c b/arch/x86/lib/usercopy.c index ddf9ecb..938e45c 100644 --- a/arch/x86/lib/usercopy.c +++ b/arch/x86/lib/usercopy.c @@ -10,6 +10,8 @@ #include <asm/word-at-a-time.h> #include <linux/sched.h> +#include <asm/processor.h> + /* * We rely on the nested NMI work to allow atomic faults from the NMI path; the * nested NMI paths are careful to preserve CR2. @@ -18,6 +20,7 @@ unsigned long copy_from_user_nmi(void *to, const void __user *from, unsigned long n) { unsigned long ret; + unsigned long cr2; if (__range_not_ok(from, n, TASK_SIZE)) return 0; @@ -27,9 +30,11 @@ copy_from_user_nmi(void *to, const void __user *from, unsigned long n) * disable pagefaults so that its behaviour is consistent even when * called form other contexts. */ + cr2 = read_cr2(); pagefault_disable(); ret = __copy_from_user_inatomic(to, from, n); pagefault_enable(); + write_cr2(cr2); return ret; } |  |