Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > linux.kernel > #1285988 > unrolled thread
| Started by | Andy Lutomirski <luto@kernel.org> |
|---|---|
| First post | 2015-12-07 23:00 +0100 |
| Last post | 2015-12-09 20:40 +0100 |
| Articles | 19 — 4 participants |
Back to article view | Back to linux.kernel
This discussion starts older than the indexed window; earlier articles aren't shown. The article labeled Started by
below is the oldest one visible, not the original post.
[PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Andy Lutomirski <luto@kernel.org> - 2015-12-07 23:00 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Brian Gerst <brgerst@gmail.com> - 2015-12-08 02:00 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Andy Lutomirski <luto@amacapital.net> - 2015-12-08 02:20 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Brian Gerst <brgerst@gmail.com> - 2015-12-08 14:10 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Ingo Molnar <mingo@kernel.org> - 2015-12-08 20:00 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Andy Lutomirski <luto@amacapital.net> - 2015-12-08 23:00 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Brian Gerst <brgerst@gmail.com> - 2015-12-08 02:00 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Brian Gerst <brgerst@gmail.com> - 2015-12-09 05:50 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Andy Lutomirski <luto@amacapital.net> - 2015-12-09 06:50 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Andy Lutomirski <luto@amacapital.net> - 2015-12-09 07:30 +0100
Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path Brian Gerst <brgerst@gmail.com> - 2015-12-09 14:00 +0100
[PATCH] x86/entry/64: Remove duplicate syscall table for fast path Brian Gerst <brgerst@gmail.com> - 2015-12-09 14:10 +0100
Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path Andy Lutomirski <luto@amacapital.net> - 2015-12-09 20:00 +0100
Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path Brian Gerst <brgerst@gmail.com> - 2015-12-09 22:10 +0100
Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path Andy Lutomirski <luto@amacapital.net> - 2015-12-09 22:20 +0100
Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path Andy Lutomirski <luto@amacapital.net> - 2015-12-10 01:00 +0100
Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path Brian Gerst <brgerst@gmail.com> - 2015-12-10 06:50 +0100
Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path Andy Lutomirski <luto@amacapital.net> - 2015-12-10 07:00 +0100
[PATCH] x86/entry/64: Remove duplicate syscall table for fast path Andy Lutomirski <luto@kernel.org> - 2015-12-09 20:40 +0100
| From | Andy Lutomirski <luto@kernel.org> |
|---|---|
| Date | 2015-12-07 23:00 +0100 |
| Subject | [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDbZ9-1Mo-37@gated-at.bofh.it> |
64-bit syscalls currently have an optimization in which they are
called with partial pt_regs. A small handful require full pt_regs.
In the 32-bit and compat cases, I cleaned this up by forcing full
pt_regs for all syscalls. The performance hit doesn't really matter.
I want to clean up the 64-bit case as well, but I don't want to hurt
fast path performance. To do that, I want to force the syscalls
that use pt_regs onto the slow path. This will enable us to make
slow path syscalls be real ABI-compliant C functions.
Use the new syscall entry qualification machinery for this.
stub_clone is now stub_clone/ptregs.
The next patch will eliminate the stubs, and we'll just have
sys_clone/ptregs.
Signed-off-by: Andy Lutomirski <luto@kernel.org>
---
arch/x86/entry/entry_64.S | 17 +++++++++--------
arch/x86/entry/syscall_64.c | 18 ++++++++++++++++++
arch/x86/entry/syscalls/syscall_64.tbl | 16 ++++++++--------
3 files changed, 35 insertions(+), 16 deletions(-)
diff --git a/arch/x86/entry/entry_64.S b/arch/x86/entry/entry_64.S
index 9d34d3cfceb6..a698b8092831 100644
--- a/arch/x86/entry/entry_64.S
+++ b/arch/x86/entry/entry_64.S
@@ -182,7 +182,7 @@ entry_SYSCALL_64_fastpath:
#endif
ja 1f /* return -ENOSYS (already in pt_regs->ax) */
movq %r10, %rcx
- call *sys_call_table(, %rax, 8)
+ call *sys_call_table_fastpath_64(, %rax, 8)
movq %rax, RAX(%rsp)
1:
/*
@@ -238,13 +238,6 @@ tracesys:
movq %rsp, %rdi
movl $AUDIT_ARCH_X86_64, %esi
call syscall_trace_enter_phase1
- test %rax, %rax
- jnz tracesys_phase2 /* if needed, run the slow path */
- RESTORE_C_REGS_EXCEPT_RAX /* else restore clobbered regs */
- movq ORIG_RAX(%rsp), %rax
- jmp entry_SYSCALL_64_fastpath /* and return to the fast path */
-
-tracesys_phase2:
SAVE_EXTRA_REGS
movq %rsp, %rdi
movl $AUDIT_ARCH_X86_64, %esi
@@ -355,6 +348,14 @@ opportunistic_sysret_failed:
jmp restore_c_regs_and_iret
END(entry_SYSCALL_64)
+ENTRY(stub_ptregs_64)
+ /*
+ * Syscalls marked as needing ptregs that go through the fast path
+ * land here. We transfer to the slow path.
+ */
+ addq $8, %rsp
+ jmp tracesys
+END(stub_ptregs_64)
.macro FORK_LIKE func
ENTRY(stub_\func)
diff --git a/arch/x86/entry/syscall_64.c b/arch/x86/entry/syscall_64.c
index a1d408772ae6..601745c667ce 100644
--- a/arch/x86/entry/syscall_64.c
+++ b/arch/x86/entry/syscall_64.c
@@ -22,3 +22,21 @@ asmlinkage const sys_call_ptr_t sys_call_table[__NR_syscall_max+1] = {
[0 ... __NR_syscall_max] = &sys_ni_syscall,
#include <asm/syscalls_64.h>
};
+
+#undef __SYSCALL_64
+
+extern long stub_ptregs_64(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long);
+
+#define __SYSCALL_64_QUAL_(nr, sym) [nr] = sym,
+#define __SYSCALL_64_QUAL_ptregs(nr, sym) [nr] = stub_ptregs_64,
+
+#define __SYSCALL_64(nr, sym, qual) __SYSCALL_64_QUAL_##qual(nr, sym)
+
+asmlinkage const sys_call_ptr_t sys_call_table_fastpath_64[__NR_syscall_max+1] = {
+ /*
+ * Smells like a compiler bug -- it doesn't work
+ * when the & below is removed.
+ */
+ [0 ... __NR_syscall_max] = &sys_ni_syscall,
+#include <asm/syscalls_64.h>
+};
diff --git a/arch/x86/entry/syscalls/syscall_64.tbl b/arch/x86/entry/syscalls/syscall_64.tbl
index 278842fdf1f6..6b9db2e338f4 100644
--- a/arch/x86/entry/syscalls/syscall_64.tbl
+++ b/arch/x86/entry/syscalls/syscall_64.tbl
@@ -21,7 +21,7 @@
12 common brk sys_brk
13 64 rt_sigaction sys_rt_sigaction
14 common rt_sigprocmask sys_rt_sigprocmask
-15 64 rt_sigreturn stub_rt_sigreturn
+15 64 rt_sigreturn stub_rt_sigreturn/ptregs
16 64 ioctl sys_ioctl
17 common pread64 sys_pread64
18 common pwrite64 sys_pwrite64
@@ -62,10 +62,10 @@
53 common socketpair sys_socketpair
54 64 setsockopt sys_setsockopt
55 64 getsockopt sys_getsockopt
-56 common clone stub_clone
-57 common fork stub_fork
-58 common vfork stub_vfork
-59 64 execve stub_execve
+56 common clone stub_clone/ptregs
+57 common fork stub_fork/ptregs
+58 common vfork stub_vfork/ptregs
+59 64 execve stub_execve/ptregs
60 common exit sys_exit
61 common wait4 sys_wait4
62 common kill sys_kill
@@ -328,7 +328,7 @@
319 common memfd_create sys_memfd_create
320 common kexec_file_load sys_kexec_file_load
321 common bpf sys_bpf
-322 64 execveat stub_execveat
+322 64 execveat stub_execveat/ptregs
323 common userfaultfd sys_userfaultfd
324 common membarrier sys_membarrier
@@ -344,7 +344,7 @@
517 x32 recvfrom compat_sys_recvfrom
518 x32 sendmsg compat_sys_sendmsg
519 x32 recvmsg compat_sys_recvmsg
-520 x32 execve stub_x32_execve
+520 x32 execve stub_x32_execve/ptregs
521 x32 ptrace compat_sys_ptrace
522 x32 rt_sigpending compat_sys_rt_sigpending
523 x32 rt_sigtimedwait compat_sys_rt_sigtimedwait
@@ -369,4 +369,4 @@
542 x32 getsockopt compat_sys_getsockopt
543 x32 io_setup compat_sys_io_setup
544 x32 io_submit compat_sys_io_submit
-545 x32 execveat stub_x32_execveat
+545 x32 execveat stub_x32_execveat/ptregs
--
2.5.0
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
[toc] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-08 02:00 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDeNj-3D4-1@gated-at.bofh.it> |
| In reply to | #1285988 |
On Mon, Dec 7, 2015 at 7:50 PM, Brian Gerst <brgerst@gmail.com> wrote:
> On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote:
>> 64-bit syscalls currently have an optimization in which they are
>> called with partial pt_regs. A small handful require full pt_regs.
>>
>> In the 32-bit and compat cases, I cleaned this up by forcing full
>> pt_regs for all syscalls. The performance hit doesn't really matter.
>>
>> I want to clean up the 64-bit case as well, but I don't want to hurt
>> fast path performance. To do that, I want to force the syscalls
>> that use pt_regs onto the slow path. This will enable us to make
>> slow path syscalls be real ABI-compliant C functions.
>>
>> Use the new syscall entry qualification machinery for this.
>> stub_clone is now stub_clone/ptregs.
>>
>> The next patch will eliminate the stubs, and we'll just have
>> sys_clone/ptregs.
[Resend after gmail web interface fail]
I've got an idea on how to do this without the duplicate syscall table.
ptregs_foo:
leaq sys_foo(%rip), %rax
jmp stub_ptregs_64
stub_ptregs_64:
testl $TS_EXTRAREGS, <current->ti_status>
jnz 1f
SAVE_EXTRA_REGS
call *%rax
RESTORE_EXTRA_REGS
ret
1:
call *%rax
ret
This makes sure that the extra regs don't get saved a second time if
coming in from the slow path, but preserves the fast path if not
tracing.
--
Brian Gerst
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-08 02:20 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDf6G-40S-5@gated-at.bofh.it> |
| In reply to | #1286132 |
On Mon, Dec 7, 2015 at 4:54 PM, Brian Gerst <brgerst@gmail.com> wrote: > On Mon, Dec 7, 2015 at 7:50 PM, Brian Gerst <brgerst@gmail.com> wrote: >> On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote: >>> 64-bit syscalls currently have an optimization in which they are >>> called with partial pt_regs. A small handful require full pt_regs. >>> >>> In the 32-bit and compat cases, I cleaned this up by forcing full >>> pt_regs for all syscalls. The performance hit doesn't really matter. >>> >>> I want to clean up the 64-bit case as well, but I don't want to hurt >>> fast path performance. To do that, I want to force the syscalls >>> that use pt_regs onto the slow path. This will enable us to make >>> slow path syscalls be real ABI-compliant C functions. >>> >>> Use the new syscall entry qualification machinery for this. >>> stub_clone is now stub_clone/ptregs. >>> >>> The next patch will eliminate the stubs, and we'll just have >>> sys_clone/ptregs. > > [Resend after gmail web interface fail] > > I've got an idea on how to do this without the duplicate syscall table. > > ptregs_foo: > leaq sys_foo(%rip), %rax > jmp stub_ptregs_64 > > stub_ptregs_64: > testl $TS_EXTRAREGS, <current->ti_status> > jnz 1f > SAVE_EXTRA_REGS > call *%rax > RESTORE_EXTRA_REGS > ret > 1: > call *%rax > ret > > This makes sure that the extra regs don't get saved a second time if > coming in from the slow path, but preserves the fast path if not > tracing. I think there's value in having the entries in the table be genuine C ABI-compliant function pointers. In your example, it only barely works -- you can call them from C only if you have TS_EXTRAREGS set appropriately -- -otherwise you crash and burn. That will break the rest of the series. We could adjust it a bit and check whether we're in C land (by checking rsp for ts) and jump into the slow path if we aren't, but I'm not sure this is a huge win. It does save some rodata space by avoiding duplicating the table. --Andy -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-08 14:10 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDqbM-2Nk-25@gated-at.bofh.it> |
| In reply to | #1286136 |
On Mon, Dec 7, 2015 at 8:12 PM, Andy Lutomirski <luto@amacapital.net> wrote: > On Mon, Dec 7, 2015 at 4:54 PM, Brian Gerst <brgerst@gmail.com> wrote: >> On Mon, Dec 7, 2015 at 7:50 PM, Brian Gerst <brgerst@gmail.com> wrote: >>> On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote: >>>> 64-bit syscalls currently have an optimization in which they are >>>> called with partial pt_regs. A small handful require full pt_regs. >>>> >>>> In the 32-bit and compat cases, I cleaned this up by forcing full >>>> pt_regs for all syscalls. The performance hit doesn't really matter. >>>> >>>> I want to clean up the 64-bit case as well, but I don't want to hurt >>>> fast path performance. To do that, I want to force the syscalls >>>> that use pt_regs onto the slow path. This will enable us to make >>>> slow path syscalls be real ABI-compliant C functions. >>>> >>>> Use the new syscall entry qualification machinery for this. >>>> stub_clone is now stub_clone/ptregs. >>>> >>>> The next patch will eliminate the stubs, and we'll just have >>>> sys_clone/ptregs. >> >> [Resend after gmail web interface fail] >> >> I've got an idea on how to do this without the duplicate syscall table. >> >> ptregs_foo: >> leaq sys_foo(%rip), %rax >> jmp stub_ptregs_64 >> >> stub_ptregs_64: >> testl $TS_EXTRAREGS, <current->ti_status> >> jnz 1f >> SAVE_EXTRA_REGS >> call *%rax >> RESTORE_EXTRA_REGS >> ret >> 1: >> call *%rax >> ret >> >> This makes sure that the extra regs don't get saved a second time if >> coming in from the slow path, but preserves the fast path if not >> tracing. > > I think there's value in having the entries in the table be genuine C > ABI-compliant function pointers. In your example, it only barely > works -- you can call them from C only if you have TS_EXTRAREGS set > appropriately -- -otherwise you crash and burn. That will break the > rest of the series. I'm working on a full patch. It will set the flag (renamed TS_SLOWPATH) in do_syscall_64(), which is the only place these functions can get called from C code. Your changes already have it set up so that the slow path saved these registers before calling any C code. Where else do you expect them to be called from? > We could adjust it a bit and check whether we're in C land (by > checking rsp for ts) and jump into the slow path if we aren't, but I'm > not sure this is a huge win. It does save some rodata space by > avoiding duplicating the table. The syscall table is huge. 545*8 bytes, over a full page. Duplicating it for just a few different entries is wasteful. -- Brian Gerst -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Ingo Molnar <mingo@kernel.org> |
|---|---|
| Date | 2015-12-08 20:00 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDvEu-60F-25@gated-at.bofh.it> |
| In reply to | #1286450 |
* Brian Gerst <brgerst@gmail.com> wrote: > > We could adjust it a bit and check whether we're in C land (by checking rsp > > for ts) and jump into the slow path if we aren't, but I'm not sure this is a > > huge win. It does save some rodata space by avoiding duplicating the table. > > The syscall table is huge. 545*8 bytes, over a full page. Duplicating it for > just a few different entries is wasteful. Note that what matters more is cache footprint, not pure size: 1K of RAM overhead for something as fundamental as system calls is trivial cost. So the questions to ask are along these lines: - what is the typical locality of access (do syscall numbers cluster in time and space) - how frequently would the two tables be accessed (is one accessed less frequently than the other?) - subsequently how does the effective cache footprint change with the duplication? it might still end up not being worth it - but it's not the RAM cost that is the main factor IMHO. Thanks, Ingo -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-08 23:00 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDysG-7MA-1@gated-at.bofh.it> |
| In reply to | #1286777 |
On Tue, Dec 8, 2015 at 10:56 AM, Ingo Molnar <mingo@kernel.org> wrote: > > * Brian Gerst <brgerst@gmail.com> wrote: > >> > We could adjust it a bit and check whether we're in C land (by checking rsp >> > for ts) and jump into the slow path if we aren't, but I'm not sure this is a >> > huge win. It does save some rodata space by avoiding duplicating the table. >> >> The syscall table is huge. 545*8 bytes, over a full page. Duplicating it for >> just a few different entries is wasteful. > > Note that what matters more is cache footprint, not pure size: 1K of RAM overhead > for something as fundamental as system calls is trivial cost. > > So the questions to ask are along these lines: > > - what is the typical locality of access (do syscall numbers cluster in time and > space) > I suspect that they do. Web servers will call send over and over, for example. > - how frequently would the two tables be accessed (is one accessed less > frequently than the other?) On setups that don't bail right away, the fast path table gets hit most of the time. On setups that do bail right away (context tracking on, for example), we exclusively use the slow path table. > > - subsequently how does the effective cache footprint change with the > duplication? In the worst case (repeatedly forking, for example, but I doubt we care about that case), the duplication adds one extra cacheline. > > it might still end up not being worth it - but it's not the RAM cost that is the > main factor IMHO. Agreed. One option: borrow the high bit to indicate "needs ptregs". This adds a branch to both the fast path and the slow path, but it avoids the cache hit. Brian's approach gets the best of all worlds except that, if I understand it right, it's a bit fragile. --Andy -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-08 02:00 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDeNj-3D4-3@gated-at.bofh.it> |
| In reply to | #1285988 |
On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote:
> 64-bit syscalls currently have an optimization in which they are
> called with partial pt_regs. A small handful require full pt_regs.
>
> In the 32-bit and compat cases, I cleaned this up by forcing full
> pt_regs for all syscalls. The performance hit doesn't really matter.
>
> I want to clean up the 64-bit case as well, but I don't want to hurt
> fast path performance. To do that, I want to force the syscalls
> that use pt_regs onto the slow path. This will enable us to make
> slow path syscalls be real ABI-compliant C functions.
>
> Use the new syscall entry qualification machinery for this.
> stub_clone is now stub_clone/ptregs.
>
> The next patch will eliminate the stubs, and we'll just have
> sys_clone/ptregs.
I've got an idea on how to do this without the duplicate syscall table.
ptregs_foo:
leaq sys_foo(%rip), %rax
jmp stub_ptregs_64
stub_ptregs_64:
testl $TS_EXTRAREGS, <current->ti_status>
jnz 1f
SAVE_EXTRA_REGS
call *%rax
RESTORE_EXTRA_REGS
ret
1:
call *%rax
--
Brian Gerst
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-09 05:50 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDERs-3xo-13@gated-at.bofh.it> |
| In reply to | #1285988 |
On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote:
> 64-bit syscalls currently have an optimization in which they are
> called with partial pt_regs. A small handful require full pt_regs.
>
> In the 32-bit and compat cases, I cleaned this up by forcing full
> pt_regs for all syscalls. The performance hit doesn't really matter.
>
> I want to clean up the 64-bit case as well, but I don't want to hurt
> fast path performance. To do that, I want to force the syscalls
> that use pt_regs onto the slow path. This will enable us to make
> slow path syscalls be real ABI-compliant C functions.
>
> Use the new syscall entry qualification machinery for this.
> stub_clone is now stub_clone/ptregs.
>
> The next patch will eliminate the stubs, and we'll just have
> sys_clone/ptregs.
>
> Signed-off-by: Andy Lutomirski <luto@kernel.org>
Fails to boot, bisected to this patch:
[ 32.675319] kernel BUG at kernel/auditsc.c:1504!
[ 32.675325] invalid opcode: 0000 [#65] SMP
[ 32.675328] Modules linked in:
[ 32.675333] CPU: 1 PID: 216 Comm: systemd-cgroups Tainted: G D
4.3.0-rc4+ #7
[ 32.675336] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011
[ 32.675339] task: ffff880000075340 ti: ffff880036520000 task.ti:
ffff880036520000
[ 32.675350] RIP: 0010:[<ffffffff8113d9ed>] [<ffffffff8113d9ed>]
__audit_syscall_entry+0xcd/0xf0
[ 32.675353] RSP: 0018:ffff880036523ef0 EFLAGS: 00010202
[ 32.675355] RAX: 000000000000000c RBX: ffff8800797b3000 RCX: 00007ffef8504e88
[ 32.675357] RDX: 000056172f37cfd0 RSI: 0000000000000000 RDI: 000000000000000c
[ 32.675359] RBP: ffff880036523f00 R08: 0000000000000001 R09: ffff880000075340
[ 32.675361] R10: 0000000000000000 R11: 0000000000000001 R12: 0000000000000000
[ 32.675363] R13: 00000000c000003e R14: 0000000000000001 R15: 0000000000001000
[ 32.675380] FS: 00007f02b4ff48c0(0000) GS:ffff88007fc80000(0000)
knlGS:0000000000000000
[ 32.675383] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b
[ 32.675385] CR2: 00007f93d47ea0e0 CR3: 0000000036aa9000 CR4: 00000000000006e0
[ 32.675391] Stack:
[ 32.675396] ffff880036523f58 0000000000000000 ffff880036523f10
ffffffff8100321b
[ 32.675401] ffff880036523f48 ffffffff81003ad0 000056172f374040
00007f93d45c9990
[ 32.675404] 0000000000000001 0000000000000001 0000000000001000
000000000000000a
[ 32.675405] Call Trace:
[ 32.675414] [<ffffffff8100321b>] do_audit_syscall_entry+0x4b/0x70
[ 32.675420] [<ffffffff81003ad0>] syscall_trace_enter_phase2+0x110/0x1d0
[ 32.675425] [<ffffffff81761d94>] tracesys+0x3a/0x96
[ 32.675464] Code: 00 00 00 00 e8 a5 e0 fc ff c7 43 04 01 00 00 00
48 89 43 18 48 89 53 20 44 89 63 0c c7 83 94 02 00 00 00 00 00 00 5b
41 5c 5d c3 <0f> 0b 48 c7 43 50 00 00 00 00 48 c7 c2 60 b4 c5 81 48 89
de 4c
[ 32.675469] RIP [<ffffffff8113d9ed>] __audit_syscall_entry+0xcd/0xf0
[ 32.675471] RSP <ffff880036523ef0>
--
Brian Gerst
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-09 06:50 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDFNw-4bT-3@gated-at.bofh.it> |
| In reply to | #1287106 |
On Tue, Dec 8, 2015 at 8:43 PM, Brian Gerst <brgerst@gmail.com> wrote: > On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote: >> 64-bit syscalls currently have an optimization in which they are >> called with partial pt_regs. A small handful require full pt_regs. >> >> In the 32-bit and compat cases, I cleaned this up by forcing full >> pt_regs for all syscalls. The performance hit doesn't really matter. >> >> I want to clean up the 64-bit case as well, but I don't want to hurt >> fast path performance. To do that, I want to force the syscalls >> that use pt_regs onto the slow path. This will enable us to make >> slow path syscalls be real ABI-compliant C functions. >> >> Use the new syscall entry qualification machinery for this. >> stub_clone is now stub_clone/ptregs. >> >> The next patch will eliminate the stubs, and we'll just have >> sys_clone/ptregs. >> >> Signed-off-by: Andy Lutomirski <luto@kernel.org> > > Fails to boot, bisected to this patch: > [ 32.675319] kernel BUG at kernel/auditsc.c:1504! > [ 32.675325] invalid opcode: 0000 [#65] SMP > [ 32.675328] Modules linked in: > [ 32.675333] CPU: 1 PID: 216 Comm: systemd-cgroups Tainted: G D > 4.3.0-rc4+ #7 > [ 32.675336] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011 > [ 32.675339] task: ffff880000075340 ti: ffff880036520000 task.ti: > ffff880036520000 > [ 32.675350] RIP: 0010:[<ffffffff8113d9ed>] [<ffffffff8113d9ed>] > __audit_syscall_entry+0xcd/0xf0 > [ 32.675353] RSP: 0018:ffff880036523ef0 EFLAGS: 00010202 > [ 32.675355] RAX: 000000000000000c RBX: ffff8800797b3000 RCX: 00007ffef8504e88 > [ 32.675357] RDX: 000056172f37cfd0 RSI: 0000000000000000 RDI: 000000000000000c > [ 32.675359] RBP: ffff880036523f00 R08: 0000000000000001 R09: ffff880000075340 > [ 32.675361] R10: 0000000000000000 R11: 0000000000000001 R12: 0000000000000000 > [ 32.675363] R13: 00000000c000003e R14: 0000000000000001 R15: 0000000000001000 > [ 32.675380] FS: 00007f02b4ff48c0(0000) GS:ffff88007fc80000(0000) > knlGS:0000000000000000 > [ 32.675383] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b > [ 32.675385] CR2: 00007f93d47ea0e0 CR3: 0000000036aa9000 CR4: 00000000000006e0 > [ 32.675391] Stack: > [ 32.675396] ffff880036523f58 0000000000000000 ffff880036523f10 > ffffffff8100321b > [ 32.675401] ffff880036523f48 ffffffff81003ad0 000056172f374040 > 00007f93d45c9990 > [ 32.675404] 0000000000000001 0000000000000001 0000000000001000 > 000000000000000a > [ 32.675405] Call Trace: > [ 32.675414] [<ffffffff8100321b>] do_audit_syscall_entry+0x4b/0x70 > [ 32.675420] [<ffffffff81003ad0>] syscall_trace_enter_phase2+0x110/0x1d0 > [ 32.675425] [<ffffffff81761d94>] tracesys+0x3a/0x96 > [ 32.675464] Code: 00 00 00 00 e8 a5 e0 fc ff c7 43 04 01 00 00 00 > 48 89 43 18 48 89 53 20 44 89 63 0c c7 83 94 02 00 00 00 00 00 00 5b > 41 5c 5d c3 <0f> 0b 48 c7 43 50 00 00 00 00 48 c7 c2 60 b4 c5 81 48 89 > de 4c > [ 32.675469] RIP [<ffffffff8113d9ed>] __audit_syscall_entry+0xcd/0xf0 > [ 32.675471] RSP <ffff880036523ef0> I'm not reproducing this, even with audit manually enabled. Can you send a .config? --Andy -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-09 07:30 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDGqd-4EB-15@gated-at.bofh.it> |
| In reply to | #1287128 |
On Tue, Dec 8, 2015 at 9:45 PM, Andy Lutomirski <luto@amacapital.net> wrote: > On Tue, Dec 8, 2015 at 8:43 PM, Brian Gerst <brgerst@gmail.com> wrote: >> On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote: >>> 64-bit syscalls currently have an optimization in which they are >>> called with partial pt_regs. A small handful require full pt_regs. >>> >>> In the 32-bit and compat cases, I cleaned this up by forcing full >>> pt_regs for all syscalls. The performance hit doesn't really matter. >>> >>> I want to clean up the 64-bit case as well, but I don't want to hurt >>> fast path performance. To do that, I want to force the syscalls >>> that use pt_regs onto the slow path. This will enable us to make >>> slow path syscalls be real ABI-compliant C functions. >>> >>> Use the new syscall entry qualification machinery for this. >>> stub_clone is now stub_clone/ptregs. >>> >>> The next patch will eliminate the stubs, and we'll just have >>> sys_clone/ptregs. >>> >>> Signed-off-by: Andy Lutomirski <luto@kernel.org> >> >> Fails to boot, bisected to this patch: >> [ 32.675319] kernel BUG at kernel/auditsc.c:1504! >> [ 32.675325] invalid opcode: 0000 [#65] SMP >> [ 32.675328] Modules linked in: >> [ 32.675333] CPU: 1 PID: 216 Comm: systemd-cgroups Tainted: G D >> 4.3.0-rc4+ #7 >> [ 32.675336] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011 >> [ 32.675339] task: ffff880000075340 ti: ffff880036520000 task.ti: >> ffff880036520000 >> [ 32.675350] RIP: 0010:[<ffffffff8113d9ed>] [<ffffffff8113d9ed>] >> __audit_syscall_entry+0xcd/0xf0 >> [ 32.675353] RSP: 0018:ffff880036523ef0 EFLAGS: 00010202 >> [ 32.675355] RAX: 000000000000000c RBX: ffff8800797b3000 RCX: 00007ffef8504e88 >> [ 32.675357] RDX: 000056172f37cfd0 RSI: 0000000000000000 RDI: 000000000000000c >> [ 32.675359] RBP: ffff880036523f00 R08: 0000000000000001 R09: ffff880000075340 >> [ 32.675361] R10: 0000000000000000 R11: 0000000000000001 R12: 0000000000000000 >> [ 32.675363] R13: 00000000c000003e R14: 0000000000000001 R15: 0000000000001000 >> [ 32.675380] FS: 00007f02b4ff48c0(0000) GS:ffff88007fc80000(0000) >> knlGS:0000000000000000 >> [ 32.675383] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b >> [ 32.675385] CR2: 00007f93d47ea0e0 CR3: 0000000036aa9000 CR4: 00000000000006e0 >> [ 32.675391] Stack: >> [ 32.675396] ffff880036523f58 0000000000000000 ffff880036523f10 >> ffffffff8100321b >> [ 32.675401] ffff880036523f48 ffffffff81003ad0 000056172f374040 >> 00007f93d45c9990 >> [ 32.675404] 0000000000000001 0000000000000001 0000000000001000 >> 000000000000000a >> [ 32.675405] Call Trace: >> [ 32.675414] [<ffffffff8100321b>] do_audit_syscall_entry+0x4b/0x70 >> [ 32.675420] [<ffffffff81003ad0>] syscall_trace_enter_phase2+0x110/0x1d0 >> [ 32.675425] [<ffffffff81761d94>] tracesys+0x3a/0x96 >> [ 32.675464] Code: 00 00 00 00 e8 a5 e0 fc ff c7 43 04 01 00 00 00 >> 48 89 43 18 48 89 53 20 44 89 63 0c c7 83 94 02 00 00 00 00 00 00 5b >> 41 5c 5d c3 <0f> 0b 48 c7 43 50 00 00 00 00 48 c7 c2 60 b4 c5 81 48 89 >> de 4c >> [ 32.675469] RIP [<ffffffff8113d9ed>] __audit_syscall_entry+0xcd/0xf0 >> [ 32.675471] RSP <ffff880036523ef0> > > I'm not reproducing this, even with audit manually enabled. Can you > send a .config? Never mind, I found the bug by inspection. I'll send a fixed up series tomorrow. Can you send the boot failure you got with the full series applied, though? I think that the bug I found is only triggerable part-way through the series -- I think I inadvertently fixed it later on. --Andy -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-09 14:00 +0100 |
| Subject | Re: [PATCH 07/12] x86/entry/64: Always run ptregs-using syscalls on the slow path |
| Message-ID | <qDMvD-51-1@gated-at.bofh.it> |
| In reply to | #1287143 |
On Wed, Dec 9, 2015 at 1:21 AM, Andy Lutomirski <luto@amacapital.net> wrote: > On Tue, Dec 8, 2015 at 9:45 PM, Andy Lutomirski <luto@amacapital.net> wrote: >> On Tue, Dec 8, 2015 at 8:43 PM, Brian Gerst <brgerst@gmail.com> wrote: >>> On Mon, Dec 7, 2015 at 4:51 PM, Andy Lutomirski <luto@kernel.org> wrote: >>>> 64-bit syscalls currently have an optimization in which they are >>>> called with partial pt_regs. A small handful require full pt_regs. >>>> >>>> In the 32-bit and compat cases, I cleaned this up by forcing full >>>> pt_regs for all syscalls. The performance hit doesn't really matter. >>>> >>>> I want to clean up the 64-bit case as well, but I don't want to hurt >>>> fast path performance. To do that, I want to force the syscalls >>>> that use pt_regs onto the slow path. This will enable us to make >>>> slow path syscalls be real ABI-compliant C functions. >>>> >>>> Use the new syscall entry qualification machinery for this. >>>> stub_clone is now stub_clone/ptregs. >>>> >>>> The next patch will eliminate the stubs, and we'll just have >>>> sys_clone/ptregs. >>>> >>>> Signed-off-by: Andy Lutomirski <luto@kernel.org> >>> >>> Fails to boot, bisected to this patch: >>> [ 32.675319] kernel BUG at kernel/auditsc.c:1504! >>> [ 32.675325] invalid opcode: 0000 [#65] SMP >>> [ 32.675328] Modules linked in: >>> [ 32.675333] CPU: 1 PID: 216 Comm: systemd-cgroups Tainted: G D >>> 4.3.0-rc4+ #7 >>> [ 32.675336] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011 >>> [ 32.675339] task: ffff880000075340 ti: ffff880036520000 task.ti: >>> ffff880036520000 >>> [ 32.675350] RIP: 0010:[<ffffffff8113d9ed>] [<ffffffff8113d9ed>] >>> __audit_syscall_entry+0xcd/0xf0 >>> [ 32.675353] RSP: 0018:ffff880036523ef0 EFLAGS: 00010202 >>> [ 32.675355] RAX: 000000000000000c RBX: ffff8800797b3000 RCX: 00007ffef8504e88 >>> [ 32.675357] RDX: 000056172f37cfd0 RSI: 0000000000000000 RDI: 000000000000000c >>> [ 32.675359] RBP: ffff880036523f00 R08: 0000000000000001 R09: ffff880000075340 >>> [ 32.675361] R10: 0000000000000000 R11: 0000000000000001 R12: 0000000000000000 >>> [ 32.675363] R13: 00000000c000003e R14: 0000000000000001 R15: 0000000000001000 >>> [ 32.675380] FS: 00007f02b4ff48c0(0000) GS:ffff88007fc80000(0000) >>> knlGS:0000000000000000 >>> [ 32.675383] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b >>> [ 32.675385] CR2: 00007f93d47ea0e0 CR3: 0000000036aa9000 CR4: 00000000000006e0 >>> [ 32.675391] Stack: >>> [ 32.675396] ffff880036523f58 0000000000000000 ffff880036523f10 >>> ffffffff8100321b >>> [ 32.675401] ffff880036523f48 ffffffff81003ad0 000056172f374040 >>> 00007f93d45c9990 >>> [ 32.675404] 0000000000000001 0000000000000001 0000000000001000 >>> 000000000000000a >>> [ 32.675405] Call Trace: >>> [ 32.675414] [<ffffffff8100321b>] do_audit_syscall_entry+0x4b/0x70 >>> [ 32.675420] [<ffffffff81003ad0>] syscall_trace_enter_phase2+0x110/0x1d0 >>> [ 32.675425] [<ffffffff81761d94>] tracesys+0x3a/0x96 >>> [ 32.675464] Code: 00 00 00 00 e8 a5 e0 fc ff c7 43 04 01 00 00 00 >>> 48 89 43 18 48 89 53 20 44 89 63 0c c7 83 94 02 00 00 00 00 00 00 5b >>> 41 5c 5d c3 <0f> 0b 48 c7 43 50 00 00 00 00 48 c7 c2 60 b4 c5 81 48 89 >>> de 4c >>> [ 32.675469] RIP [<ffffffff8113d9ed>] __audit_syscall_entry+0xcd/0xf0 >>> [ 32.675471] RSP <ffff880036523ef0> >> >> I'm not reproducing this, even with audit manually enabled. Can you >> send a .config? > > Never mind, I found the bug by inspection. I'll send a fixed up > series tomorrow. > > Can you send the boot failure you got with the full series applied, > though? I think that the bug I found is only triggerable part-way > through the series -- I think I inadvertently fixed it later on. I can't reproduce it now. It was a hang, or I just didn't get the oops displayed on the screen. Could have been somethng unrelated. -- Brian Gerst -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-09 14:10 +0100 |
| Subject | [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qDMFk-nF-13@gated-at.bofh.it> |
| In reply to | #1287143 |
Instead of using a duplicate syscall table for the fast path, create stubs for
the syscalls that need pt_regs that save the extra registers if a flag for the
slow path is not set.
Signed-off-by: Brian Gerst <brgerst@gmail.com>
To: Andy Lutomirski <luto@amacapital.net>
Cc: Andy Lutomirski <luto@kernel.org>
Cc: the arch/x86 maintainers <x86@kernel.org>
Cc: Linux Kernel Mailing List <linux-kernel@vger.kernel.org>
Cc: Borislav Petkov <bp@alien8.de>
Cc: Frédéric Weisbecker <fweisbec@gmail.com>
Cc: Denys Vlasenko <dvlasenk@redhat.com>
Cc: Linus Torvalds <torvalds@linux-foundation.org>
---
Applies on top of Andy's syscall cleanup series.
arch/x86/entry/calling.h | 32 ++++++++++++++++----------------
arch/x86/entry/common.c | 4 ++++
arch/x86/entry/entry_64.S | 36 +++++++++++++++++++++++++++++-------
arch/x86/entry/syscall_64.c | 25 +++++--------------------
arch/x86/include/asm/thread_info.h | 1 +
5 files changed, 55 insertions(+), 43 deletions(-)
diff --git a/arch/x86/entry/calling.h b/arch/x86/entry/calling.h
index e32206e..7c58bd2 100644
--- a/arch/x86/entry/calling.h
+++ b/arch/x86/entry/calling.h
@@ -129,22 +129,22 @@ For 32-bit we have the following conventions - kernel is built with
SAVE_C_REGS_HELPER 0, 0, 0, 1, 0
.endm
- .macro SAVE_EXTRA_REGS offset=0
- movq %r15, 0*8+\offset(%rsp)
- movq %r14, 1*8+\offset(%rsp)
- movq %r13, 2*8+\offset(%rsp)
- movq %r12, 3*8+\offset(%rsp)
- movq %rbp, 4*8+\offset(%rsp)
- movq %rbx, 5*8+\offset(%rsp)
- .endm
-
- .macro RESTORE_EXTRA_REGS offset=0
- movq 0*8+\offset(%rsp), %r15
- movq 1*8+\offset(%rsp), %r14
- movq 2*8+\offset(%rsp), %r13
- movq 3*8+\offset(%rsp), %r12
- movq 4*8+\offset(%rsp), %rbp
- movq 5*8+\offset(%rsp), %rbx
+ .macro SAVE_EXTRA_REGS offset=0 base=rsp
+ movq %r15, 0*8+\offset(%\base)
+ movq %r14, 1*8+\offset(%\base)
+ movq %r13, 2*8+\offset(%\base)
+ movq %r12, 3*8+\offset(%\base)
+ movq %rbp, 4*8+\offset(%\base)
+ movq %rbx, 5*8+\offset(%\base)
+ .endm
+
+ .macro RESTORE_EXTRA_REGS offset=0 base=rsp
+ movq 0*8+\offset(%\base), %r15
+ movq 1*8+\offset(%\base), %r14
+ movq 2*8+\offset(%\base), %r13
+ movq 3*8+\offset(%\base), %r12
+ movq 4*8+\offset(%\base), %rbp
+ movq 5*8+\offset(%\base), %rbx
.endm
.macro ZERO_EXTRA_REGS
diff --git a/arch/x86/entry/common.c b/arch/x86/entry/common.c
index 016ac47..4381aca 100644
--- a/arch/x86/entry/common.c
+++ b/arch/x86/entry/common.c
@@ -342,6 +342,8 @@ __visible void do_syscall_64(struct pt_regs *regs)
struct thread_info *ti = pt_regs_to_thread_info(regs);
unsigned long nr = regs->orig_ax;
+ ti->status |= TS_SLOWPATH;
+
enter_from_user_mode();
local_irq_enable();
@@ -360,6 +362,8 @@ __visible void do_syscall_64(struct pt_regs *regs)
}
syscall_return_slowpath(regs);
+
+ ti->status &= ~TS_SLOWPATH;
}
#endif
diff --git a/arch/x86/entry/entry_64.S b/arch/x86/entry/entry_64.S
index 1ab5362..5852ec6 100644
--- a/arch/x86/entry/entry_64.S
+++ b/arch/x86/entry/entry_64.S
@@ -188,7 +188,7 @@ entry_SYSCALL_64_fastpath:
#endif
ja 1f /* return -ENOSYS (already in pt_regs->ax) */
movq %r10, %rcx
- call *sys_call_table_fastpath_64(, %rax, 8)
+ call *sys_call_table(, %rax, 8)
movq %rax, RAX(%rsp)
1:
@@ -306,15 +306,37 @@ END(entry_SYSCALL_64)
ENTRY(stub_ptregs_64)
/*
- * Syscalls marked as needing ptregs that go through the fast path
- * land here. We transfer to the slow path.
+ * Syscalls marked as needing ptregs land here.
+ * If we are on the fast path, we need to save the extra regs.
+ * If we are on the slow path, the extra regs are already saved.
*/
- DISABLE_INTERRUPTS(CLBR_NONE)
- TRACE_IRQS_OFF
- addq $8, %rsp
- jmp entry_SYSCALL64_slow_path
+ movq PER_CPU_VAR(cpu_current_top_of_stack), %r10
+ testl $TS_SLOWPATH, ASM_THREAD_INFO(TI_status, %r10, 0)
+ jnz 1f
+ subq $SIZEOF_PTREGS, %r10
+ SAVE_EXTRA_REGS base=r10
+ movq %r10, %rbx
+ call *%rax
+ movq %rbx, %r10
+ RESTORE_EXTRA_REGS base=r10
+ ret
+1:
+ jmp *%rax
END(stub_ptregs_64)
+.macro ptregs_stub func
+ENTRY(ptregs_\func)
+ leaq \func(%rip), %rax
+ jmp stub_ptregs_64
+END(ptregs_\func)
+.endm
+
+#define __SYSCALL_64_QUAL_(sym)
+#define __SYSCALL_64_QUAL_ptregs(sym) ptregs_stub sym
+
+#define __SYSCALL_64(nr, sym, qual) __SYSCALL_64_QUAL_##qual(sym)
+#include <asm/syscalls_64.h>
+
/*
* A newly forked process directly context switches into this address.
*
diff --git a/arch/x86/entry/syscall_64.c b/arch/x86/entry/syscall_64.c
index 601745c..9dbc5ab 100644
--- a/arch/x86/entry/syscall_64.c
+++ b/arch/x86/entry/syscall_64.c
@@ -6,11 +6,14 @@
#include <asm/asm-offsets.h>
#include <asm/syscall.h>
-#define __SYSCALL_64(nr, sym, qual) extern asmlinkage long sym(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long) ;
+#define __SYSCALL_64_QUAL_(sym) sym
+#define __SYSCALL_64_QUAL_ptregs(sym) ptregs_##sym
+
+#define __SYSCALL_64(nr, sym, qual) extern asmlinkage long __SYSCALL_64_QUAL_##qual(sym)(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long);
#include <asm/syscalls_64.h>
#undef __SYSCALL_64
-#define __SYSCALL_64(nr, sym, qual) [nr] = sym,
+#define __SYSCALL_64(nr, sym, qual) [nr] = __SYSCALL_64_QUAL_##qual(sym),
extern long sys_ni_syscall(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long);
@@ -22,21 +25,3 @@ asmlinkage const sys_call_ptr_t sys_call_table[__NR_syscall_max+1] = {
[0 ... __NR_syscall_max] = &sys_ni_syscall,
#include <asm/syscalls_64.h>
};
-
-#undef __SYSCALL_64
-
-extern long stub_ptregs_64(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long);
-
-#define __SYSCALL_64_QUAL_(nr, sym) [nr] = sym,
-#define __SYSCALL_64_QUAL_ptregs(nr, sym) [nr] = stub_ptregs_64,
-
-#define __SYSCALL_64(nr, sym, qual) __SYSCALL_64_QUAL_##qual(nr, sym)
-
-asmlinkage const sys_call_ptr_t sys_call_table_fastpath_64[__NR_syscall_max+1] = {
- /*
- * Smells like a compiler bug -- it doesn't work
- * when the & below is removed.
- */
- [0 ... __NR_syscall_max] = &sys_ni_syscall,
-#include <asm/syscalls_64.h>
-};
diff --git a/arch/x86/include/asm/thread_info.h b/arch/x86/include/asm/thread_info.h
index ae210d6..358e3a9 100644
--- a/arch/x86/include/asm/thread_info.h
+++ b/arch/x86/include/asm/thread_info.h
@@ -229,6 +229,7 @@ static inline unsigned long current_stack_pointer(void)
* ever touches our thread-synchronous status, so we don't
* have to worry about atomic accesses.
*/
+#define TS_SLOWPATH 0x0001 /* syscall slowpath (64BIT) */
#define TS_COMPAT 0x0002 /* 32bit syscall active (64BIT)*/
#define TS_RESTORE_SIGMASK 0x0008 /* restore signal mask in do_signal() */
--
2.5.0
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-09 20:00 +0100 |
| Subject | Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qDS82-3Fq-17@gated-at.bofh.it> |
| In reply to | #1287479 |
On Wed, Dec 9, 2015 at 5:02 AM, Brian Gerst <brgerst@gmail.com> wrote: > Instead of using a duplicate syscall table for the fast path, create stubs for > the syscalls that need pt_regs that save the extra registers if a flag for the > slow path is not set. > > Signed-off-by: Brian Gerst <brgerst@gmail.com> > To: Andy Lutomirski <luto@amacapital.net> > Cc: Andy Lutomirski <luto@kernel.org> > Cc: the arch/x86 maintainers <x86@kernel.org> > Cc: Linux Kernel Mailing List <linux-kernel@vger.kernel.org> > Cc: Borislav Petkov <bp@alien8.de> > Cc: Frédéric Weisbecker <fweisbec@gmail.com> > Cc: Denys Vlasenko <dvlasenk@redhat.com> > Cc: Linus Torvalds <torvalds@linux-foundation.org> > --- > > Applies on top of Andy's syscall cleanup series. A couple questions: > @@ -306,15 +306,37 @@ END(entry_SYSCALL_64) > > ENTRY(stub_ptregs_64) > /* > - * Syscalls marked as needing ptregs that go through the fast path > - * land here. We transfer to the slow path. > + * Syscalls marked as needing ptregs land here. > + * If we are on the fast path, we need to save the extra regs. > + * If we are on the slow path, the extra regs are already saved. > */ > - DISABLE_INTERRUPTS(CLBR_NONE) > - TRACE_IRQS_OFF > - addq $8, %rsp > - jmp entry_SYSCALL64_slow_path > + movq PER_CPU_VAR(cpu_current_top_of_stack), %r10 > + testl $TS_SLOWPATH, ASM_THREAD_INFO(TI_status, %r10, 0) > + jnz 1f OK (but see below), but why not do: addq $8, %rsp jmp entry_SYSCALL64_slow_path here instead of the stack munging below? > + subq $SIZEOF_PTREGS, %r10 > + SAVE_EXTRA_REGS base=r10 > + movq %r10, %rbx > + call *%rax > + movq %rbx, %r10 > + RESTORE_EXTRA_REGS base=r10 > + ret > +1: > + jmp *%rax > END(stub_ptregs_64) Also, can we not get away with keying off rip or rsp instead of ti->status? That should be faster and less magical IMO. --Andy -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-09 22:10 +0100 |
| Subject | Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qDU9R-5bQ-19@gated-at.bofh.it> |
| In reply to | #1287740 |
On Wed, Dec 9, 2015 at 1:53 PM, Andy Lutomirski <luto@amacapital.net> wrote:
> On Wed, Dec 9, 2015 at 5:02 AM, Brian Gerst <brgerst@gmail.com> wrote:
>> Instead of using a duplicate syscall table for the fast path, create stubs for
>> the syscalls that need pt_regs that save the extra registers if a flag for the
>> slow path is not set.
>>
>> Signed-off-by: Brian Gerst <brgerst@gmail.com>
>> To: Andy Lutomirski <luto@amacapital.net>
>> Cc: Andy Lutomirski <luto@kernel.org>
>> Cc: the arch/x86 maintainers <x86@kernel.org>
>> Cc: Linux Kernel Mailing List <linux-kernel@vger.kernel.org>
>> Cc: Borislav Petkov <bp@alien8.de>
>> Cc: Frédéric Weisbecker <fweisbec@gmail.com>
>> Cc: Denys Vlasenko <dvlasenk@redhat.com>
>> Cc: Linus Torvalds <torvalds@linux-foundation.org>
>> ---
>>
>> Applies on top of Andy's syscall cleanup series.
>
> A couple questions:
>
>> @@ -306,15 +306,37 @@ END(entry_SYSCALL_64)
>>
>> ENTRY(stub_ptregs_64)
>> /*
>> - * Syscalls marked as needing ptregs that go through the fast path
>> - * land here. We transfer to the slow path.
>> + * Syscalls marked as needing ptregs land here.
>> + * If we are on the fast path, we need to save the extra regs.
>> + * If we are on the slow path, the extra regs are already saved.
>> */
>> - DISABLE_INTERRUPTS(CLBR_NONE)
>> - TRACE_IRQS_OFF
>> - addq $8, %rsp
>> - jmp entry_SYSCALL64_slow_path
>> + movq PER_CPU_VAR(cpu_current_top_of_stack), %r10
>> + testl $TS_SLOWPATH, ASM_THREAD_INFO(TI_status, %r10, 0)
>> + jnz 1f
>
> OK (but see below), but why not do:
>
> addq $8, %rsp
> jmp entry_SYSCALL64_slow_path
I've always been adverse to doing things like that because it breaks
call/return branch prediction.
Also, are there any side effects to calling enter_from_user_mode()
more than once?
> here instead of the stack munging below?
>
>> + subq $SIZEOF_PTREGS, %r10
>> + SAVE_EXTRA_REGS base=r10
>> + movq %r10, %rbx
>> + call *%rax
>> + movq %rbx, %r10
>> + RESTORE_EXTRA_REGS base=r10
>> + ret
>> +1:
>> + jmp *%rax
>> END(stub_ptregs_64)
After some thought, that can be simplified. It's only executed on the
fast path, so pt_regs is at 8(%rsp).
> Also, can we not get away with keying off rip or rsp instead of
> ti->status? That should be faster and less magical IMO.
Checking if the return address is the instruction after the fast path
dispatch would work.
Simplified version:
ENTRY(stub_ptregs_64)
cmpl $fast_path_return, (%rsp)
jne 1f
SAVE_EXTRA_REGS offset=8
call *%rax
RESTORE_EXTRA_REGS offset=8
ret
1:
jmp *%rax
END(stub_ptregs_64)
--
Brian Gerst
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-09 22:20 +0100 |
| Subject | Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qDUjx-5eV-19@gated-at.bofh.it> |
| In reply to | #1287858 |
On Wed, Dec 9, 2015 at 1:08 PM, Brian Gerst <brgerst@gmail.com> wrote: > On Wed, Dec 9, 2015 at 1:53 PM, Andy Lutomirski <luto@amacapital.net> wrote: >> On Wed, Dec 9, 2015 at 5:02 AM, Brian Gerst <brgerst@gmail.com> wrote: >>> Instead of using a duplicate syscall table for the fast path, create stubs for >>> the syscalls that need pt_regs that save the extra registers if a flag for the >>> slow path is not set. >>> >>> Signed-off-by: Brian Gerst <brgerst@gmail.com> >>> To: Andy Lutomirski <luto@amacapital.net> >>> Cc: Andy Lutomirski <luto@kernel.org> >>> Cc: the arch/x86 maintainers <x86@kernel.org> >>> Cc: Linux Kernel Mailing List <linux-kernel@vger.kernel.org> >>> Cc: Borislav Petkov <bp@alien8.de> >>> Cc: Frédéric Weisbecker <fweisbec@gmail.com> >>> Cc: Denys Vlasenko <dvlasenk@redhat.com> >>> Cc: Linus Torvalds <torvalds@linux-foundation.org> >>> --- >>> >>> Applies on top of Andy's syscall cleanup series. >> >> A couple questions: >> >>> @@ -306,15 +306,37 @@ END(entry_SYSCALL_64) >>> >>> ENTRY(stub_ptregs_64) >>> /* >>> - * Syscalls marked as needing ptregs that go through the fast path >>> - * land here. We transfer to the slow path. >>> + * Syscalls marked as needing ptregs land here. >>> + * If we are on the fast path, we need to save the extra regs. >>> + * If we are on the slow path, the extra regs are already saved. >>> */ >>> - DISABLE_INTERRUPTS(CLBR_NONE) >>> - TRACE_IRQS_OFF >>> - addq $8, %rsp >>> - jmp entry_SYSCALL64_slow_path >>> + movq PER_CPU_VAR(cpu_current_top_of_stack), %r10 >>> + testl $TS_SLOWPATH, ASM_THREAD_INFO(TI_status, %r10, 0) >>> + jnz 1f >> >> OK (but see below), but why not do: >> >> addq $8, %rsp >> jmp entry_SYSCALL64_slow_path > > I've always been adverse to doing things like that because it breaks > call/return branch prediction. I'd agree with you there except that the syscalls in question really don't matter for performance enough that we should worry about a handful of cycles from a return misprediction. We're still avoiding IRET regardless (to the extent possible), and that was always the major factor. > Also, are there any side effects to calling enter_from_user_mode() > more than once? A warning that invariants are broken if you have an appropriately configured kernel. > >> here instead of the stack munging below? >> >>> + subq $SIZEOF_PTREGS, %r10 >>> + SAVE_EXTRA_REGS base=r10 >>> + movq %r10, %rbx >>> + call *%rax >>> + movq %rbx, %r10 >>> + RESTORE_EXTRA_REGS base=r10 >>> + ret >>> +1: >>> + jmp *%rax >>> END(stub_ptregs_64) > > After some thought, that can be simplified. It's only executed on the > fast path, so pt_regs is at 8(%rsp). > >> Also, can we not get away with keying off rip or rsp instead of >> ti->status? That should be faster and less magical IMO. > > Checking if the return address is the instruction after the fast path > dispatch would work. > > Simplified version: > ENTRY(stub_ptregs_64) > cmpl $fast_path_return, (%rsp) Does that instruction actually work the way you want it to? (Does it link?) I think you might need to use leaq the way I did in my patch. > jne 1f > SAVE_EXTRA_REGS offset=8 > call *%rax > RESTORE_EXTRA_REGS offset=8 > ret > 1: > jmp *%rax > END(stub_ptregs_64) This'll work, I think, but I still think I prefer keeping as much complexity as possible in the slow path. I could be convinced otherwise, though -- this variant is reasonably clean. --Andy -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-10 01:00 +0100 |
| Subject | Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qDWOm-6Hc-21@gated-at.bofh.it> |
| In reply to | #1287871 |
On Wed, Dec 9, 2015 at 1:15 PM, Andy Lutomirski <luto@amacapital.net> wrote: > On Wed, Dec 9, 2015 at 1:08 PM, Brian Gerst <brgerst@gmail.com> wrote: >> Simplified version: >> ENTRY(stub_ptregs_64) >> cmpl $fast_path_return, (%rsp) > > Does that instruction actually work the way you want it to? (Does it > link?) I think you might need to use leaq the way I did in my patch. > >> jne 1f >> SAVE_EXTRA_REGS offset=8 >> call *%rax >> RESTORE_EXTRA_REGS offset=8 >> ret >> 1: >> jmp *%rax >> END(stub_ptregs_64) > > This'll work, I think, but I still think I prefer keeping as much > complexity as possible in the slow path. I could be convinced > otherwise, though -- this variant is reasonably clean. On further reflection, there's at least one functional difference. With my variant, modifying pt_regs from sys_foo/ptregs is safe. In your variant, it's unsafe unless force_iret() is called. I don't know whether we care. --Andy -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Brian Gerst <brgerst@gmail.com> |
|---|---|
| Date | 2015-12-10 06:50 +0100 |
| Subject | Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qE2h5-1SS-9@gated-at.bofh.it> |
| In reply to | #1288067 |
On Wed, Dec 9, 2015 at 6:50 PM, Andy Lutomirski <luto@amacapital.net> wrote: > On Wed, Dec 9, 2015 at 1:15 PM, Andy Lutomirski <luto@amacapital.net> wrote: >> On Wed, Dec 9, 2015 at 1:08 PM, Brian Gerst <brgerst@gmail.com> wrote: >>> Simplified version: >>> ENTRY(stub_ptregs_64) >>> cmpl $fast_path_return, (%rsp) >> >> Does that instruction actually work the way you want it to? (Does it >> link?) I think you might need to use leaq the way I did in my patch. It should have been cmpq. leaq isn't necessary, since immediates are sign-extended to 64-bit. >>> jne 1f >>> SAVE_EXTRA_REGS offset=8 >>> call *%rax >>> RESTORE_EXTRA_REGS offset=8 >>> ret >>> 1: >>> jmp *%rax >>> END(stub_ptregs_64) >> >> This'll work, I think, but I still think I prefer keeping as much >> complexity as possible in the slow path. I could be convinced >> otherwise, though -- this variant is reasonably clean. > > On further reflection, there's at least one functional difference. > With my variant, modifying pt_regs from sys_foo/ptregs is safe. In > your variant, it's unsafe unless force_iret() is called. I don't know > whether we care. I can go either way at this point. My main concern was getting rid of the duplicate table. -- Brian Gerst -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@amacapital.net> |
|---|---|
| Date | 2015-12-10 07:00 +0100 |
| Subject | Re: [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qE2qK-1W9-3@gated-at.bofh.it> |
| In reply to | #1288212 |
On Wed, Dec 9, 2015 at 9:42 PM, Brian Gerst <brgerst@gmail.com> wrote: > On Wed, Dec 9, 2015 at 6:50 PM, Andy Lutomirski <luto@amacapital.net> wrote: >> On Wed, Dec 9, 2015 at 1:15 PM, Andy Lutomirski <luto@amacapital.net> wrote: >>> On Wed, Dec 9, 2015 at 1:08 PM, Brian Gerst <brgerst@gmail.com> wrote: >>>> Simplified version: >>>> ENTRY(stub_ptregs_64) >>>> cmpl $fast_path_return, (%rsp) >>> >>> Does that instruction actually work the way you want it to? (Does it >>> link?) I think you might need to use leaq the way I did in my patch. > > It should have been cmpq. leaq isn't necessary, since immediates are > sign-extended to 64-bit. Right, I always forget that they're sign-extended and not zero-extended. I folded that bit in to my queue. > >>>> jne 1f >>>> SAVE_EXTRA_REGS offset=8 >>>> call *%rax >>>> RESTORE_EXTRA_REGS offset=8 >>>> ret >>>> 1: >>>> jmp *%rax >>>> END(stub_ptregs_64) >>> >>> This'll work, I think, but I still think I prefer keeping as much >>> complexity as possible in the slow path. I could be convinced >>> otherwise, though -- this variant is reasonably clean. >> >> On further reflection, there's at least one functional difference. >> With my variant, modifying pt_regs from sys_foo/ptregs is safe. In >> your variant, it's unsafe unless force_iret() is called. I don't know >> whether we care. > > I can go either way at this point. My main concern was getting rid of > the duplicate table. Agreed. I'll sleep on it, and maybe someone else has some reason to prefer one approach over the other. --Andy -- Andy Lutomirski AMA Capital Management, LLC -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [next] | [standalone]
| From | Andy Lutomirski <luto@kernel.org> |
|---|---|
| Date | 2015-12-09 20:40 +0100 |
| Subject | [PATCH] x86/entry/64: Remove duplicate syscall table for fast path |
| Message-ID | <qDSKK-49e-5@gated-at.bofh.it> |
| In reply to | #1287479 |
Instead of using a duplicate syscall table for the fast path, create
stubs for the syscalls that need pt_regs that dispatch based on the
call site.
I think that this is very likely to introduce a mis-predicted branch
in all such syscalls. I think that's fine -- all of them are
already very slow.
Heavily based on a patch from Brian Gerst [1].
[1] http://lkml.kernel.org/g/1449666173-15366-1-git-send-email-brgerst@gmail.com
Signed-off-by: Brian Gerst <brgerst@gmail.com>
Cc: the arch/x86 maintainers <x86@kernel.org>
Cc: Linux Kernel Mailing List <linux-kernel@vger.kernel.org>
Cc: Borislav Petkov <bp@alien8.de>
Cc: Frédéric Weisbecker <fweisbec@gmail.com>
Cc: Denys Vlasenko <dvlasenk@redhat.com>
Cc: Linus Torvalds <torvalds@linux-foundation.org>
Signed-off-by: Andy Lutomirski <luto@kernel.org>
---
Brian, here's a counter-proposal. It's derived from your patch, but it works
differently.
If people like this, I'll send a new version of the whole series that includes
it at the end.
arch/x86/entry/entry_64.S | 49 ++++++++++++++++++++++++++++++++++++++-------
arch/x86/entry/syscall_64.c | 25 +++++------------------
2 files changed, 47 insertions(+), 27 deletions(-)
diff --git a/arch/x86/entry/entry_64.S b/arch/x86/entry/entry_64.S
index 1ab5362f241d..16779b52419e 100644
--- a/arch/x86/entry/entry_64.S
+++ b/arch/x86/entry/entry_64.S
@@ -188,7 +188,15 @@ entry_SYSCALL_64_fastpath:
#endif
ja 1f /* return -ENOSYS (already in pt_regs->ax) */
movq %r10, %rcx
- call *sys_call_table_fastpath_64(, %rax, 8)
+
+ /*
+ * This call instruction is handled specially in stub_ptregs_64.
+ * It might end up jumping to the slow path. If it jumps, rax and
+ * r11 are clobbered.
+ */
+ call *sys_call_table(, %rax, 8)
+.Lentry_SYSCALL_64_after_fastpath_call:
+
movq %rax, RAX(%rsp)
1:
@@ -306,15 +314,42 @@ END(entry_SYSCALL_64)
ENTRY(stub_ptregs_64)
/*
- * Syscalls marked as needing ptregs that go through the fast path
- * land here. We transfer to the slow path.
+ * Syscalls marked as needing ptregs land here.
+ * If we are on the fast path, we need to save the extra regs.
+ * If we are on the slow path, the extra regs are already saved.
+ *
+ * RAX stores a pointer to the C function implementing the syscall.
+ *
+ * We can safely clobber RAX (clobbered by return value regardless)
+ * and R11 (owned by callee and never stores an argument) regardless
+ * of which path we take.
*/
- DISABLE_INTERRUPTS(CLBR_NONE)
- TRACE_IRQS_OFF
- addq $8, %rsp
- jmp entry_SYSCALL64_slow_path
+ leaq .Lentry_SYSCALL_64_after_fastpath_call(%rip), %r11
+ cmpq %r11, (%rsp)
+ jne 1f
+
+ /* Called from fast path -- pop return address and jump to slow path */
+ popq %rax
+ jmp entry_SYSCALL64_slow_path /* called from fast path */
+
+1:
+ /* Called from C */
+ jmp *%rax /* called from C */
END(stub_ptregs_64)
+.macro ptregs_stub func
+ENTRY(ptregs_\func)
+ leaq \func(%rip), %rax
+ jmp stub_ptregs_64
+END(ptregs_\func)
+.endm
+
+/* Instantiate ptregs_stub for each ptregs-using syscall */
+#define __SYSCALL_64_QUAL_(sym)
+#define __SYSCALL_64_QUAL_ptregs(sym) ptregs_stub sym
+#define __SYSCALL_64(nr, sym, qual) __SYSCALL_64_QUAL_##qual(sym)
+#include <asm/syscalls_64.h>
+
/*
* A newly forked process directly context switches into this address.
*
diff --git a/arch/x86/entry/syscall_64.c b/arch/x86/entry/syscall_64.c
index 601745c667ce..9dbc5abb6162 100644
--- a/arch/x86/entry/syscall_64.c
+++ b/arch/x86/entry/syscall_64.c
@@ -6,11 +6,14 @@
#include <asm/asm-offsets.h>
#include <asm/syscall.h>
-#define __SYSCALL_64(nr, sym, qual) extern asmlinkage long sym(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long) ;
+#define __SYSCALL_64_QUAL_(sym) sym
+#define __SYSCALL_64_QUAL_ptregs(sym) ptregs_##sym
+
+#define __SYSCALL_64(nr, sym, qual) extern asmlinkage long __SYSCALL_64_QUAL_##qual(sym)(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long);
#include <asm/syscalls_64.h>
#undef __SYSCALL_64
-#define __SYSCALL_64(nr, sym, qual) [nr] = sym,
+#define __SYSCALL_64(nr, sym, qual) [nr] = __SYSCALL_64_QUAL_##qual(sym),
extern long sys_ni_syscall(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long);
@@ -22,21 +25,3 @@ asmlinkage const sys_call_ptr_t sys_call_table[__NR_syscall_max+1] = {
[0 ... __NR_syscall_max] = &sys_ni_syscall,
#include <asm/syscalls_64.h>
};
-
-#undef __SYSCALL_64
-
-extern long stub_ptregs_64(unsigned long, unsigned long, unsigned long, unsigned long, unsigned long, unsigned long);
-
-#define __SYSCALL_64_QUAL_(nr, sym) [nr] = sym,
-#define __SYSCALL_64_QUAL_ptregs(nr, sym) [nr] = stub_ptregs_64,
-
-#define __SYSCALL_64(nr, sym, qual) __SYSCALL_64_QUAL_##qual(nr, sym)
-
-asmlinkage const sys_call_ptr_t sys_call_table_fastpath_64[__NR_syscall_max+1] = {
- /*
- * Smells like a compiler bug -- it doesn't work
- * when the & below is removed.
- */
- [0 ... __NR_syscall_max] = &sys_ni_syscall,
-#include <asm/syscalls_64.h>
-};
--
2.5.0
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
[toc] | [prev] | [standalone]
Back to top | Article view | linux.kernel
csiph-web