x86/speculation: Make {JMP,CALL}_NOSPEC Consistent
cover x86/speculation: Make {JMP,CALL}_NOSPEC Consistent
The 4 patches in this series make the JMP_NOSPEC and CALL_NOSPEC macros used in the kernel consistent with what is generated by the compiler.
("x86,nospec: Simplify {JMP,CALL}_NOSPEC") was merged in v6.0 and the remaining 3 patches in this series were merged in v6.15. All 4 were included in kernels v5.15+ as prerequisites for the backport of the ITS mitigations [1].
None of these patches were included in the backport of the ITS mitigations to the 5.10 kernel [2]. They all apply cleanly and are applicable to the 5.10 kernel. Thus I see no reason that they weren't applied here, unless someone can correct me?
I am sending them for inclusion in the 5.10 kernel as this kernel is still actively maintained for these kind of vulnerability mitigations and as such having these patches will unify the handling of these cases with subsequent kernel versions easing code understanding and the ease of backports in the future.
[1] https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=1ac116ce6468670eeda39345a5585df308243dca
[2] https://lore.kernel.org/stable/[email protected]/
Pawan Gupta (3):
x86/speculation: Simplify and make CALL_NOSPEC consistent x86/speculation: Add a conditional CS prefix to CALL_NOSPEC x86/speculation: Remove the extra #ifdef around CALL_NOSPEC
Peter Zijlstra (1):
x86,nospec: Simplify {JMP,CALL}_NOSPEC
arch/x86/include/asm/nospec-branch.h | 46 ++++++++++++++++++---------- 1 file changed, 30 insertions(+), 16 deletions(-)
Signature · 1 line
2.34.1
PATCH 1/4 x86,nospec: Simplify {JMP,CALL}_NOSPEC
From: Peter Zijlstra <[email protected]>
commit 09d09531a51a24635bc3331f56d92ee7092f5516 upstream.
Have {JMP,CALL}_NOSPEC generate the same code GCC does for indirect calls and rely on the objtool retpoline patching infrastructure.
There's no reason these should be alternatives while the vast bulk of compiler generated retpolines are not.
--- arch/x86/include/asm/nospec-branch.h | 24 ++++++++++++++++++------ 1 file changed, 18 insertions(+), 6 deletions(-)
arch/x86/include/asm/nospec-branch.h +18 -6
@@ -118,6 +118,19 @@#endif .endm +/* + * Equivalent to -mindirect-branch-cs-prefix; emit the 5 byte jmp/call + * to the retpoline thunk with a CS prefix when the register requires + * a RAX prefix byte to encode. Also see apply_retpolines(). + */ +.macro __CS_PREFIX reg:req + .irp rs,r8,r9,r10,r11,r12,r13,r14,r15 + .ifc \reg,\rs + .byte 0x2e + .endif + .endr +.endm +/* * JMP_NOSPEC and CALL_NOSPEC macros can be used instead of a simple * indirect jmp/call which may be susceptible to the Spectre variant 2
@@ -125,19 +138,18 @@*/ .macro JMP_NOSPEC reg:req #ifdef CONFIG_RETPOLINE - ALTERNATIVE_2 __stringify(ANNOTATE_RETPOLINE_SAFE; jmp *%\reg), \ - __stringify(jmp __x86_indirect_thunk_\reg), X86_FEATURE_RETPOLINE, \ - __stringify(lfence; ANNOTATE_RETPOLINE_SAFE; jmp *%\reg), X86_FEATURE_RETPOLINE_LFENCE + __CS_PREFIX \reg + jmp __x86_indirect_thunk_\reg #else jmp *%\reg + int3 #endif .endm .macro CALL_NOSPEC reg:req #ifdef CONFIG_RETPOLINE - ALTERNATIVE_2 __stringify(ANNOTATE_RETPOLINE_SAFE; call *%\reg), \ - __stringify(call __x86_indirect_thunk_\reg), X86_FEATURE_RETPOLINE, \ - __stringify(lfence; ANNOTATE_RETPOLINE_SAFE; call *%\reg), X86_FEATURE_RETPOLINE_LFENCE + __CS_PREFIX \reg + call __x86_indirect_thunk_\reg #else call *%\reg #endif
Signature · 1 line
2.34.1
PATCH 2/4 x86/speculation: Simplify and make CALL_NOSPEC consistent
In reply to Suraj Jitindar SinghFrom: Pawan Gupta <[email protected]>
commit cfceff8526a426948b53445c02bcb98453c7330d upstream.
CALL_NOSPEC macro is used to generate Spectre-v2 mitigation friendly indirect branches. At compile time the macro defaults to indirect branch, and at runtime those can be patched to thunk based mitigations.
This approach is opposite of what is done for the rest of the kernel, where the compile time default is to replace indirect calls with retpoline thunk calls.
Make CALL_NOSPEC consistent with the rest of the kernel, default to retpoline thunk at compile time when CONFIG_MITIGATION_RETPOLINE is enabled.
--- arch/x86/include/asm/nospec-branch.h | 15 +++++---------- 1 file changed, 5 insertions(+), 10 deletions(-)
arch/x86/include/asm/nospec-branch.h +5 -10
@@ -285,16 +285,11 @@ extern retpoline_thunk_t __x86_indirect_thunk_array[];* Inline asm uses the %V modifier which is only in newer GCC * which is ensured when CONFIG_RETPOLINE is defined. */ -# define CALL_NOSPEC \ - ALTERNATIVE_2( \ - ANNOTATE_RETPOLINE_SAFE \ - "call *%[thunk_target]\n", \ - "call __x86_indirect_thunk_%V[thunk_target]\n", \ - X86_FEATURE_RETPOLINE, \ - "lfence;\n" \ - ANNOTATE_RETPOLINE_SAFE \ - "call *%[thunk_target]\n", \ - X86_FEATURE_RETPOLINE_LFENCE) +#ifdef CONFIG_RETPOLINE +#define CALL_NOSPEC "call __x86_indirect_thunk_%V[thunk_target]\n" +#else +#define CALL_NOSPEC "call *%[thunk_target]\n" +#endif # define THUNK_TARGET (addr) [thunk_target] "r" (addr)
Signature · 1 line
2.34.1
PATCH 3/4 x86/speculation: Add a conditional CS prefix to CALL_NOSPEC
In reply to Suraj Jitindar SinghFrom: Pawan Gupta <[email protected]>
commit 052040e34c08428a5a388b85787e8531970c0c67 upstream.
Retpoline mitigation for spectre-v2 uses thunks for indirect branches. To support this mitigation compilers add a CS prefix with -mindirect-branch-cs-prefix. For an indirect branch in asm, this needs to be added manually.
CS prefix is already being added to indirect branches in asm files, but not in inline asm. Add CS prefix to CALL_NOSPEC for inline asm as well. There is no JMP_NOSPEC for inline asm.
--- arch/x86/include/asm/nospec-branch.h | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-)
arch/x86/include/asm/nospec-branch.h +15 -4
@@ -119,9 +119,8 @@ .endm /* - * Equivalent to -mindirect-branch-cs-prefix; emit the 5 byte jmp/call - * to the retpoline thunk with a CS prefix when the register requires - * a RAX prefix byte to encode. Also see apply_retpolines(). + * Emits a conditional CS prefix that is compatible with + * -mindirect-branch-cs-prefix. */ .macro __CS_PREFIX reg:req .irp rs,r8,r9,r10,r11,r12,r13,r14,r15
@@ -281,12 +280,24 @@ extern retpoline_thunk_t __x86_indirect_thunk_array[];#ifdef CONFIG_X86_64 +/* +* Emits a conditional CS prefix that is compatible with +* -mindirect-branch-cs-prefix. +*/ +#define __CS_PREFIX (reg) \ + ".irp rs,r8,r9,r10,r11,r12,r13,r14,r15\n" \ + ".ifc \\rs," reg "\n" \ + ".byte 0x2e\n" \ + ".endif\n" \ + ".endr\n" +/* * Inline asm uses the %V modifier which is only in newer GCC * which is ensured when CONFIG_RETPOLINE is defined. */ #ifdef CONFIG_RETPOLINE -#define CALL_NOSPEC "call __x86_indirect_thunk_%V[thunk_target]\n" +#define CALL_NOSPEC __CS_PREFIX("%V[thunk_target]") \ + "call __x86_indirect_thunk_%V[thunk_target]\n"#else #define CALL_NOSPEC "call *%[thunk_target]\n"#endif
Signature · 1 line
2.34.1
PATCH 4/4 x86/speculation: Remove the extra #ifdef around CALL_NOSPEC
In reply to Suraj Jitindar SinghFrom: Pawan Gupta <[email protected]>
commit c8c81458863ab686cda4fe1e603fccaae0f12460 upstream.
Commit:
010c4a461c1d ("x86/speculation: Simplify and make CALL_NOSPEC consistent")
added an #ifdef CONFIG_MITIGATION_RETPOLINE around the CALL_NOSPEC definition. This is not required as this code is already under a larger #ifdef.
Remove the extra #ifdef, no functional change.
vmlinux size remains same before and after this change:
CONFIG_MITIGATION_RETPOLINE=y:
text data bss dec hex filename 25434752 7342290 2301212 35078254 217406e vmlinux.before 25434752 7342290 2301212 35078254 217406e vmlinux.after
# CONFIG_MITIGATION_RETPOLINE is not set:
text data bss dec hex filename 22943094 6214994 1550152 30708240 1d49210 vmlinux.before 22943094 6214994 1550152 30708240 1d49210 vmlinux.after
--- arch/x86/include/asm/nospec-branch.h | 4 ---- 1 file changed, 4 deletions(-)
arch/x86/include/asm/nospec-branch.h +0 -4
@@ -295,12 +295,8 @@ extern retpoline_thunk_t __x86_indirect_thunk_array[];* Inline asm uses the %V modifier which is only in newer GCC * which is ensured when CONFIG_RETPOLINE is defined. */ -#ifdef CONFIG_RETPOLINE #define CALL_NOSPEC __CS_PREFIX("%V[thunk_target]") \ "call __x86_indirect_thunk_%V[thunk_target]\n" -#else -#define CALL_NOSPEC "call *%[thunk_target]\n" -#endif # define THUNK_TARGET (addr) [thunk_target] "r" (addr)
Signature · 1 line
2.34.1
Greg KH
maintainerQuoted 11 lines · Suraj Jitindar Singh
The 4 patches in this series make the
JMP_NOSPECandCALL_NOSPECmacros used in the kernel consistent with what is generated by the compiler.("x86,nospec: Simplify {JMP,CALL}_NOSPEC") was merged in v6.0 and the remaining 3 patches in this series were merged in v6.15. All 4 were included in kernels v5.15+ as prerequisites for the backport of the ITS mitigations [1].
None of these patches were included in the backport of the ITS mitigations to the 5.10 kernel [2]. They all apply cleanly and are applicable to the 5.10 kernel. Thus I see no reason that they weren't applied here, unless someone can correct me?
Do they actually fix anything?
Quoted 5 lines
I am sending them for inclusion in the 5.10 kernel as this kernel is still actively maintained for these kind of vulnerability mitigations and as such having these patches will unify the handling of these cases with subsequent kernel versions easing code understanding and the ease of backports in the future.
Does this actually allow this to happen? I think there are a few speculation fixes that have not been backported to this kernel tree, so why not just make this as a part of that work instead? Just adding infastructure that doesn't do anything isn't usually a good idea.
thanks,
greg k-h
Re: [PATCH 5.10 0/4] x86/speculation: Make {JMP, CALL}_NOSPEC Consistent
Quoted 26 lines · Greg KH
CAUTION: This email originated from outside of the organization. Do not click links or open attachments unless you can confirm the sender and know the content is safe.
Quoted 11 lines · Suraj Jitindar Singh
The 4 patches in this series make the
JMP_NOSPECandCALL_NOSPECmacros used
in the kernel consistent with what is generated by the compiler.("x86,nospec: Simplify {JMP,CALL}_NOSPEC") was merged in v6.0 and the remaining
3 patches in this series were merged in v6.15. All 4 were included in kernels
v5.15+ as prerequisites for the backport of the ITS mitigations [1].Quoted 7 lines
None of these patches were included in the backport of the ITS mitigations to
the 5.10 kernel [2]. They all apply cleanly and are applicable to the 5.10
kernel. Thus I see no reason that they weren't applied here, unless someone can
correct me?
Quoted 1 line
Do they actually fix anything?
They do not, no.
Quoted 11 lines
Quoted 10 lines
I am sending them for inclusion in the 5.10 kernel as this kernel is still
actively maintained for these kind of vulnerability mitigations and as such
having these patches will unify the handling of these cases with subsequent
kernel versions easing code understanding and the ease of backports in the
future.
Quoted 6 lines
Does this actually allow this to happen? I think there are a few speculation fixes that have not been backported to this kernel tree, so
why not just make this as a part of that work instead? Just adding infastructure that doesn't do anything isn't usually a good idea.
In my case at least, it does. I had to spend time working out why this code was different compared to newer stable and upstream, and determining if this required special handling - which would not have been necessary if this code was the same. Other speculation fixes don't touch this path which is why it was included in the ITS mitigation patch series for other stable versions. It does do something, any where the macros are used this does something and is then rewritten by the alternatives code.
Trying to save my own (and anyone elses) sanity for having to work out why this is different in the future in an area which does still get regularly touched for these old kernels. Understand it doesn't fit the regular stable patch mold but wanted to help in case these were just unintentionally missed in this stable stream. But I acknowledge as you point out that they are not fixing anything.
Suraj
Quoted 3 lines
thanks,
greg k-h
[email protected]
maintainerRe: [PATCH 5.10 0/4] x86/speculation: Make {JMP, CALL}_NOSPEC Consistent
Quoted 52 lines · Suraj
Quoted 20 lines · Greg KH
Quoted 11 lines · Suraj Jitindar Singh
The 4 patches in this series make the
JMP_NOSPECandCALL_NOSPECmacros used
in the kernel consistent with what is generated by the compiler.("x86,nospec: Simplify {JMP,CALL}_NOSPEC") was merged in v6.0 and the remaining
3 patches in this series were merged in v6.15. All 4 were included in kernels
v5.15+ as prerequisites for the backport of the ITS mitigations [1].Quoted 7 lines
None of these patches were included in the backport of the ITS mitigations to
the 5.10 kernel [2]. They all apply cleanly and are applicable to the 5.10
kernel. Thus I see no reason that they weren't applied here, unless someone can
correct me?Quoted 1 line
Do they actually fix anything?
They do not, no.
Quoted 11 lines
Quoted 10 lines
I am sending them for inclusion in the 5.10 kernel as this kernel is still
actively maintained for these kind of vulnerability mitigations and as such
having these patches will unify the handling of these cases with subsequent
kernel versions easing code understanding and the ease of backports in the
future.Quoted 6 lines
Does this actually allow this to happen? I think there are a few speculation fixes that have not been backported to this kernel tree, so
why not just make this as a part of that work instead? Just adding infastructure that doesn't do anything isn't usually a good idea.In my case at least, it does. I had to spend time working out why this code was different compared to newer stable and upstream, and determining if this required special handling - which would not have been necessary if this code was the same. Other speculation fixes don't touch this path which is why it was included in the ITS mitigation patch series for other stable versions. It does do something, any where the macros are used this does something and is then rewritten by the alternatives code.
Quoted 6 lines
Trying to save my own (and anyone elses) sanity for having to work out why this is different in the future in an area which does still get regularly touched for these old kernels. Understand it doesn't fit the regular stable patch mold but wanted to help in case these were just unintentionally missed in this stable stream. But I acknowledge as you point out that they are not fixing anything.
If you want to include this as part of a patch series that does add additional speculation bugfixes, as it would make that series work easier, that's great, but on its own, it wouldn't make much sense to do this for no reason.
good luck with keeping this alive, that's not an easy task.
greg k-h
Greg KH
maintainerQuoted 12 lines · Suraj Jitindar Singh
The 4 patches in this series make the
JMP_NOSPECandCALL_NOSPECmacros used in the kernel consistent with what is generated by the compiler.("x86,nospec: Simplify {JMP,CALL}_NOSPEC") was merged in v6.0 and the remaining 3 patches in this series were merged in v6.15. All 4 were included in kernels v5.15+ as prerequisites for the backport of the ITS mitigations [1].
None of these patches were included in the backport of the ITS mitigations to the 5.10 kernel [2]. They all apply cleanly and are applicable to the 5.10 kernel. Thus I see no reason that they weren't applied here, unless someone can correct me?
Quoted 5 lines
I am sending them for inclusion in the 5.10 kernel as this kernel is still actively maintained for these kind of vulnerability mitigations and as such having these patches will unify the handling of these cases with subsequent kernel versions easing code understanding and the ease of backports in the future.
Also, you only really have about 1 more year left for this kernel version, why not take the time to move any systems that are somehow still using this to a more modern kernel instead? What's preventing that from happening?
Running any x86 systems on this old kernel right now is probably not a good idea given the huge number of unfixed bugs in it...
thanks,
greg k-h
Re: [PATCH 5.10 0/4] x86/speculation: Make {JMP, CALL}_NOSPEC Consistent
Quoted 36 lines · Greg KH
CAUTION: This email originated from outside of the organization. Do not click links or open attachments unless you can confirm the sender and know the content is safe.
Quoted 19 lines · Suraj Jitindar Singh
The 4 patches in this series make the
JMP_NOSPECandCALL_NOSPECmacros used
in the kernel consistent with what is generated by the compiler.("x86,nospec: Simplify {JMP,CALL}_NOSPEC") was merged in v6.0 and the remaining
3 patches in this series were merged in v6.15. All 4 were included in kernels
v5.15+ as prerequisites for the backport of the ITS mitigations [1].None of these patches were included in the backport of the ITS mitigations to
the 5.10 kernel [2]. They all apply cleanly and are applicable to the 5.10
kernel. Thus I see no reason that they weren't applied here, unless someone can
correct me?Quoted 9 lines
I am sending them for inclusion in the 5.10 kernel as this kernel is still
actively maintained for these kind of vulnerability mitigations and as such
having these patches will unify the handling of these cases with subsequent
kernel versions easing code understanding and the ease of backports in the
future.
Quoted 4 lines
Also, you only really have about 1 more year left for this kernel version, why not take the time to move any systems that are somehow still using this to a more modern kernel instead? What's preventing that from happening?
You can lead a horse to water but you can't make it drink.
Quoted 5 lines
Running any x86 systems on this old kernel right now is probably not a
good idea given the huge number of unfixed bugs in it...
Aware of that and agree.
Suraj
Quoted 3 lines
thanks,
greg k-h
[email protected]
maintainerRe: [PATCH 5.10 0/4] x86/speculation: Make {JMP, CALL}_NOSPEC Consistent
Quoted 45 lines · Suraj
Quoted 36 lines · Greg KH
CAUTION: This email originated from outside of the organization. Do not click links or open attachments unless you can confirm the sender and know the content is safe.
Quoted 19 lines · Suraj Jitindar Singh
The 4 patches in this series make the
JMP_NOSPECandCALL_NOSPECmacros used
in the kernel consistent with what is generated by the compiler.("x86,nospec: Simplify {JMP,CALL}_NOSPEC") was merged in v6.0 and the remaining
3 patches in this series were merged in v6.15. All 4 were included in kernels
v5.15+ as prerequisites for the backport of the ITS mitigations [1].None of these patches were included in the backport of the ITS mitigations to
the 5.10 kernel [2]. They all apply cleanly and are applicable to the 5.10
kernel. Thus I see no reason that they weren't applied here, unless someone can
correct me?Quoted 9 lines
I am sending them for inclusion in the 5.10 kernel as this kernel is still
actively maintained for these kind of vulnerability mitigations and as such
having these patches will unify the handling of these cases with subsequent
kernel versions easing code understanding and the ease of backports in the
future.Quoted 4 lines
Also, you only really have about 1 more year left for this kernel version, why not take the time to move any systems that are somehow still using this to a more modern kernel instead? What's preventing that from happening?
You can lead a horse to water but you can't make it drink.
Quoted 1 line
Quoted 6 lines
Quoted 4 lines
Running any x86 systems on this old kernel right now is probably not a
good idea given the huge number of unfixed bugs in it...Aware of that and agree.
We have the tools that show just how many unfixed CVEs are in the current 5.10.y tree, doesn't that make anyone a bit nervous:
$ ./scripts/strak v5.10.244 | wc -l 1096
good luck!
greg k-h