diff options
author | David Kaplan <david.kaplan@amd.com> | 2025-09-15 08:47:04 -0500 |
---|---|---|
committer | Borislav Petkov (AMD) <bp@alien8.de> | 2025-09-16 12:59:55 +0200 |
commit | 30ef245c6f5a6842d60308590cf26d0ae836fbf0 (patch) | |
tree | 65ce3a3541644f217ebb68bfcc526c9b48587abb /arch/x86/kernel/cpu/bugs.c | |
parent | 440d20154add24082eb43305f85288a756a5cc56 (diff) |
x86/bugs: Fix spectre_v2 forcing
There were two oddities with spectre_v2 command line options.
First, any option other than 'off' or 'auto' would force spectre_v2
mitigations even if the CPU (hypothetically) wasn't vulnerable to spectre_v2.
That was inconsistent with all the other bugs where mitigations are ignored
unless an explicit 'force' option is specified.
Second, even though spectre_v2 mitigations would be enabled in these cases,
the X86_BUG_SPECTRE_V2 bit wasn't set. This is again inconsistent with the
forcing behavior of other bugs and arguably incorrect as it doesn't make sense
to enable a mitigation if the X86_BUG bit isn't set.
Fix both issues by only forcing spectre_v2 mitigations when the
'spectre_v2=on' option is specified (which was already called
SPECTRE_V2_CMD_FORCE) and setting the relevant X86_BUG_* bits in that case.
This also allows for simplifying bhi_update_mitigation() because
spectre_v2_cmd will now always be SPECTRE_V2_CMD_NONE if the CPU is immune to
spectre_v2.
Signed-off-by: David Kaplan <david.kaplan@amd.com>
Signed-off-by: Borislav Petkov (AMD) <bp@alien8.de>
Link: https://lore.kernel.org/20250915134706.3201818-1-david.kaplan@amd.com
Diffstat (limited to 'arch/x86/kernel/cpu/bugs.c')
-rw-r--r-- | arch/x86/kernel/cpu/bugs.c | 36 |
1 files changed, 18 insertions, 18 deletions
diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index f28a7383b88b..145f8777aa32 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -2057,29 +2057,32 @@ static int __init spectre_v2_parse_cmdline(char *str) if (nospectre_v2) return 0; - if (!strcmp(str, "off")) + if (!strcmp(str, "off")) { spectre_v2_cmd = SPECTRE_V2_CMD_NONE; - else if (!strcmp(str, "on")) + } else if (!strcmp(str, "on")) { spectre_v2_cmd = SPECTRE_V2_CMD_FORCE; - else if (!strcmp(str, "retpoline")) + setup_force_cpu_bug(X86_BUG_SPECTRE_V2); + setup_force_cpu_bug(X86_BUG_SPECTRE_V2_USER); + } else if (!strcmp(str, "retpoline")) { spectre_v2_cmd = SPECTRE_V2_CMD_RETPOLINE; - else if (!strcmp(str, "retpoline,amd") || - !strcmp(str, "retpoline,lfence")) + } else if (!strcmp(str, "retpoline,amd") || + !strcmp(str, "retpoline,lfence")) { spectre_v2_cmd = SPECTRE_V2_CMD_RETPOLINE_LFENCE; - else if (!strcmp(str, "retpoline,generic")) + } else if (!strcmp(str, "retpoline,generic")) { spectre_v2_cmd = SPECTRE_V2_CMD_RETPOLINE_GENERIC; - else if (!strcmp(str, "eibrs")) + } else if (!strcmp(str, "eibrs")) { spectre_v2_cmd = SPECTRE_V2_CMD_EIBRS; - else if (!strcmp(str, "eibrs,lfence")) + } else if (!strcmp(str, "eibrs,lfence")) { spectre_v2_cmd = SPECTRE_V2_CMD_EIBRS_LFENCE; - else if (!strcmp(str, "eibrs,retpoline")) + } else if (!strcmp(str, "eibrs,retpoline")) { spectre_v2_cmd = SPECTRE_V2_CMD_EIBRS_RETPOLINE; - else if (!strcmp(str, "auto")) + } else if (!strcmp(str, "auto")) { spectre_v2_cmd = SPECTRE_V2_CMD_AUTO; - else if (!strcmp(str, "ibrs")) + } else if (!strcmp(str, "ibrs")) { spectre_v2_cmd = SPECTRE_V2_CMD_IBRS; - else + } else { pr_err("Ignoring unknown spectre_v2 option (%s).", str); + } return 0; } @@ -2232,10 +2235,6 @@ static void __init bhi_update_mitigation(void) { if (spectre_v2_cmd == SPECTRE_V2_CMD_NONE) bhi_mitigation = BHI_MITIGATION_OFF; - - if (!boot_cpu_has_bug(X86_BUG_SPECTRE_V2) && - spectre_v2_cmd == SPECTRE_V2_CMD_AUTO) - bhi_mitigation = BHI_MITIGATION_OFF; } static void __init bhi_apply_mitigation(void) @@ -2316,9 +2315,10 @@ static void __init spectre_v2_select_mitigation(void) spectre_v2_cmd = SPECTRE_V2_CMD_AUTO; } - if (!boot_cpu_has_bug(X86_BUG_SPECTRE_V2) && - (spectre_v2_cmd == SPECTRE_V2_CMD_NONE || spectre_v2_cmd == SPECTRE_V2_CMD_AUTO)) + if (!boot_cpu_has_bug(X86_BUG_SPECTRE_V2)) { + spectre_v2_cmd = SPECTRE_V2_CMD_NONE; return; + } switch (spectre_v2_cmd) { case SPECTRE_V2_CMD_NONE: |