Commit-ID:  24d978b76ffd20ecff8a8d1c21b16fe740f8b119
Gitweb:     http://git.kernel.org/tip/24d978b76ffd20ecff8a8d1c21b16fe740f8b119
Author:     Andy Lutomirski <[email protected]>
AuthorDate: Thu, 28 Jan 2016 15:11:27 -0800
Committer:  Ingo Molnar <[email protected]>
CommitDate: Fri, 29 Jan 2016 09:46:38 +0100

x86/entry/64: Stop using int_ret_from_sys_call in ret_from_fork

ret_from_fork is now open-coded and is no longer tangled up with
the syscall code.  This isn't so bad -- this adds very little
code, and IMO the result is much easier to understand.

Signed-off-by: Andy Lutomirski <[email protected]>
Cc: Andy Lutomirski <[email protected]>
Cc: Borislav Petkov <[email protected]>
Cc: Brian Gerst <[email protected]>
Cc: Denys Vlasenko <[email protected]>
Cc: Frederic Weisbecker <[email protected]>
Cc: H. Peter Anvin <[email protected]>
Cc: Linus Torvalds <[email protected]>
Cc: Peter Zijlstra <[email protected]>
Cc: Thomas Gleixner <[email protected]>
Link: 
http://lkml.kernel.org/r/a0747e2a5e47084655a1e96351c545b755c41fa7.1454022279.git.l...@kernel.org
Signed-off-by: Ingo Molnar <[email protected]>
---
 arch/x86/entry/entry_64.S | 35 +++++++++++++++++++----------------
 1 file changed, 19 insertions(+), 16 deletions(-)

diff --git a/arch/x86/entry/entry_64.S b/arch/x86/entry/entry_64.S
index f7050a5..cb5d940 100644
--- a/arch/x86/entry/entry_64.S
+++ b/arch/x86/entry/entry_64.S
@@ -390,7 +390,6 @@ END(ptregs_\func)
  * rdi: prev task we switched from
  */
 ENTRY(ret_from_fork)
-
        LOCK ; btr $TIF_FORK, TI_flags(%r8)
 
        pushq   $0x0002
@@ -398,28 +397,32 @@ ENTRY(ret_from_fork)
 
        call    schedule_tail                   /* rdi: 'prev' task parameter */
 
-       RESTORE_EXTRA_REGS
-
        testb   $3, CS(%rsp)                    /* from kernel_thread? */
+       jnz     1f
 
        /*
-        * By the time we get here, we have no idea whether our pt_regs,
-        * ti flags, and ti status came from the 64-bit SYSCALL fast path,
-        * the slow path, or one of the 32-bit compat paths.
-        * Use IRET code path to return, since it can safely handle
-        * all of the above.
+        * We came from kernel_thread.  This code path is quite twisted, and
+        * someone should clean it up.
+        *
+        * copy_thread_tls stashes the function pointer in RBX and the
+        * parameter to be passed in RBP.  The called function is permitted
+        * to call do_execve and thereby jump to user mode.
         */
-       jnz     int_ret_from_sys_call
+       movq    RBP(%rsp), %rdi
+       call    *RBX(%rsp)
+       movl    $0, RAX(%rsp)
 
        /*
-        * We came from kernel_thread
-        * nb: we depend on RESTORE_EXTRA_REGS above
+        * Fall through as though we're exiting a syscall.  This makes a
+        * twisted sort of sense if we just called do_execve.
         */
-       movq    %rbp, %rdi
-       call    *%rbx
-       movl    $0, RAX(%rsp)
-       RESTORE_EXTRA_REGS
-       jmp     int_ret_from_sys_call
+
+1:
+       movq    %rsp, %rdi
+       call    syscall_return_slowpath /* returns with IRQs disabled */
+       TRACE_IRQS_ON                   /* user mode is traced as IRQS on */
+       SWAPGS
+       jmp     restore_regs_and_iret
 END(ret_from_fork)
 
 /*

Reply via email to