Re: [PATCH v2 7/9] x86/vdso: abstract out vdso system call internals
Uros Bizjak <[email protected]>
| Newsgroups | org.kernel.vger.linux-sgx,org.kernel.vger.linux-kernel,org.kvack.linux-mm |
|---|---|
| Message-ID | <CAFULd4aMOueG5y3K7F57ryLtt-JUhE-yfsDODC=5+bgjF_gtSw@mail.gmail.com> |
On Wed, Nov 12, 2025 at 5:38 AM H. Peter Anvin <[email protected]> wrote: > > Abstract out the calling of true system calls from the vdso into > macros. > > It has been a very long time since gcc did not allow %ebx or %ebp in > inline asm in 32-bit PIC mode; remove the corresponding hacks. > > Remove the use of memory output constraints in gettimeofday.h in favor > of "memory" clobbers. The resulting code is identical for the current > use cases, as the system call is usually a terminal fallback anyway, > and it merely complicates the macroization. > > This patch adds only a handful of more lines of code than it removes, > and in fact could be made substantially smaller by removing the macros > for the argument counts that aren't currently used, however, it seems > better to be general from the start. > > Signed-off-by: H. Peter Anvin (Intel) <[email protected]> [...] > diff --git a/arch/x86/include/asm/vdso/sys_call.h b/arch/x86/include/asm/vdso/sys_call.h > new file mode 100644 > index 000000000000..6b1fbcdcbd5c > --- /dev/null > +++ b/arch/x86/include/asm/vdso/sys_call.h > @@ -0,0 +1,119 @@ > +/* SPDX-License-Identifier: GPL-2.0 */ > +/* > + * Macros for issuing an inline system call from the vDSO. > + */ > + > +#ifndef X86_ASM_VDSO_SYS_CALL_H > +#define X86_ASM_VDSO_SYS_CALL_H > + > +#include <linux/compiler.h> > +#include <asm/cpufeatures.h> > +#include <asm/alternative.h> > + > +/* > + * Note: only three arguments are currently supported, > + * because there are no constraint letters for r10, r8, r9. The above comment does not apply when using local variables associated with a register. > + */ > +#ifdef CONFIG_X86_64 > +/* Using dummy output registers instead of clobbers avoids messing up > + user-specified clobbers. */ > +#define __sys_instr "syscall" > +#define __sys_clobber "rcx", "r11", "memory" > +#define __sys_nr(x,y) __NR_ ## x > +#define __sys_reg1 "rdi" > +#define __sys_reg2 "rsi" > +#define __sys_reg3 "rdx" > +#define __sys_reg4 "r10" > +#define __sys_reg5 "r8" > +#define __sys_reg6 "r9" > +#else > +#define __sys_instr "call __kernel_vsyscall" > +#define __sys_clobber "memory" > +#define __sys_nr(x,y) __NR_ ## x ## y > +#define __sys_reg1 "ebx" > +#define __sys_reg2 "ecx" > +#define __sys_reg3 "edx" > +#define __sys_reg4 "esi" > +#define __sys_reg5 "edi" > +#define __sys_reg6 "ebp" > +#endif [...] > +#define VDSO_SYSCALL6(name,suf32,a1,a2,a3,a4,a5,a6) \ > + ({ \ > + register long _sys_arg1 asm(__sys_reg1) = (long)(a1); \ > + register long _sys_arg2 asm(__sys_reg2) = (long)(a2); \ > + register long _sys_arg3 asm(__sys_reg3) = (long)(a3); \ > + register long _sys_arg4 asm(__sys_reg4) = (long)(a4); \ > + register long _sys_arg5 asm(__sys_reg5) = (long)(a5); \ > + register long _sys_arg6 asm(__sys_reg6) = (long)(a6); \ > + _VDSO_SYSCALL(name,suf32, \ > + "r" (_sys_arg1), "r" (_sys_arg2), \ > + "r" (_sys_arg3), "r" (_sys_arg4), \ > + "r" (_sys_arg5), "r" (_sys_arg6)); \ > + }) Unfortunately, %ebp is still special with -fno-omit-frame-pointer, so using "ebp" as _sys_arg6 on 32-bit targets will result in: error: bp cannot be used in ‘asm’ here Please see how %ebp register is handled in arch/x86/include/asm/vmware.h, vmware_hypercall_hb_out() and vmware_hypercall_hb_in(). Uros.