x86, smap: Reduce the SMAP overhead for signal handling
[platform/adaptation/renesas_rcar/renesas_kernel.git] / arch / x86 / kernel / signal.c
index b280908..9326128 100644 (file)
@@ -114,11 +114,12 @@ int restore_sigcontext(struct pt_regs *regs, struct sigcontext __user *sc,
                regs->orig_ax = -1;             /* disable syscall checks */
 
                get_user_ex(buf, &sc->fpstate);
-               err |= restore_i387_xstate(buf);
 
                get_user_ex(*pax, &sc->ax);
        } get_user_catch(err);
 
+       err |= restore_i387_xstate(buf);
+
        return err;
 }
 
@@ -357,7 +358,6 @@ static int __setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
                put_user_ex(sig, &frame->sig);
                put_user_ex(&frame->info, &frame->pinfo);
                put_user_ex(&frame->uc, &frame->puc);
-               err |= copy_siginfo_to_user(&frame->info, info);
 
                /* Create the ucontext.  */
                if (cpu_has_xsave)
@@ -369,9 +369,6 @@ static int __setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
                put_user_ex(sas_ss_flags(regs->sp),
                            &frame->uc.uc_stack.ss_flags);
                put_user_ex(current->sas_ss_size, &frame->uc.uc_stack.ss_size);
-               err |= setup_sigcontext(&frame->uc.uc_mcontext, fpstate,
-                                       regs, set->sig[0]);
-               err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
 
                /* Set up to return from userspace.  */
                restorer = VDSO32_SYMBOL(current->mm->context.vdso, rt_sigreturn);
@@ -389,6 +386,11 @@ static int __setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
                put_user_ex(*((u64 *)&rt_retcode), (u64 *)frame->retcode);
        } put_user_catch(err);
 
+       err |= copy_siginfo_to_user(&frame->info, info);
+       err |= setup_sigcontext(&frame->uc.uc_mcontext, fpstate,
+                               regs, set->sig[0]);
+       err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
+
        if (err)
                return -EFAULT;
 
@@ -436,8 +438,6 @@ static int __setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
                put_user_ex(sas_ss_flags(regs->sp),
                            &frame->uc.uc_stack.ss_flags);
                put_user_ex(me->sas_ss_size, &frame->uc.uc_stack.ss_size);
-               err |= setup_sigcontext(&frame->uc.uc_mcontext, fp, regs, set->sig[0]);
-               err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
 
                /* Set up to return from userspace.  If provided, use a stub
                   already in userspace.  */
@@ -450,6 +450,9 @@ static int __setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
                }
        } put_user_catch(err);
 
+       err |= setup_sigcontext(&frame->uc.uc_mcontext, fp, regs, set->sig[0]);
+       err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
+
        if (err)
                return -EFAULT;
 
@@ -855,9 +858,6 @@ static int x32_setup_rt_frame(int sig, struct k_sigaction *ka,
                            &frame->uc.uc_stack.ss_flags);
                put_user_ex(current->sas_ss_size, &frame->uc.uc_stack.ss_size);
                put_user_ex(0, &frame->uc.uc__pad0);
-               err |= setup_sigcontext(&frame->uc.uc_mcontext, fpstate,
-                                       regs, set->sig[0]);
-               err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
 
                if (ka->sa.sa_flags & SA_RESTORER) {
                        restorer = ka->sa.sa_restorer;
@@ -869,6 +869,10 @@ static int x32_setup_rt_frame(int sig, struct k_sigaction *ka,
                put_user_ex(restorer, &frame->pretcode);
        } put_user_catch(err);
 
+       err |= setup_sigcontext(&frame->uc.uc_mcontext, fpstate,
+                               regs, set->sig[0]);
+       err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
+
        if (err)
                return -EFAULT;