[RFC][PATCH 32/34] x86/cpu/amd: Move memory encryption detection

From: Dave Hansen
Date: Thu Feb 22 2024 - 13:50:23 EST



From: Dave Hansen <dave.hansen@xxxxxxxxxxxxxxx>

Right now the AMD memory encryption detection code is run on every CPU
despite it operating on 'bsp_addr_config' and doing setup_clear_cpu_cap()
which only affects 'boot_cpu_data'.

Move it to bsp_init_amd() where it belongs and change its name to match.

Signed-off-by: Dave Hansen <dave.hansen@xxxxxxxxxxxxxxx>
---

b/arch/x86/kernel/cpu/amd.c | 110 ++++++++++++++++++++++----------------------
1 file changed, 55 insertions(+), 55 deletions(-)

diff -puN arch/x86/kernel/cpu/amd.c~early_init_amd-__init arch/x86/kernel/cpu/amd.c
--- a/arch/x86/kernel/cpu/amd.c~early_init_amd-__init 2024-02-22 10:09:04.201071279 -0800
+++ b/arch/x86/kernel/cpu/amd.c 2024-02-22 10:09:04.201071279 -0800
@@ -468,8 +468,62 @@ static void early_init_amd_mc(struct cpu
#endif
}

-static void bsp_init_amd(struct cpuinfo_x86 *c)
+static void bsp_detect_mem_encrypt(struct cpuinfo_x86 *c)
{
+ u64 msr;
+
+ /*
+ * BIOS support is required for SME and SEV.
+ * For SME: If BIOS has enabled SME then adjust x86_phys_bits by
+ * the SME physical address space reduction value.
+ * If BIOS has not enabled SME then don't advertise the
+ * SME feature (set in scattered.c).
+ * If the kernel has not enabled SME via any means then
+ * don't advertise the SME feature.
+ * For SEV: If BIOS has not enabled SEV then don't advertise the
+ * SEV and SEV_ES feature (set in scattered.c).
+ *
+ * In all cases, since support for SME and SEV requires long mode,
+ * don't advertise the feature under CONFIG_X86_32.
+ */
+ if (cpu_has(c, X86_FEATURE_SME) || cpu_has(c, X86_FEATURE_SEV)) {
+ /* Check if memory encryption is enabled */
+ rdmsrl(MSR_AMD64_SYSCFG, msr);
+ if (!(msr & MSR_AMD64_SYSCFG_MEM_ENCRYPT))
+ goto clear_all;
+
+ /*
+ * Always adjust physical address bits. Even though this
+ * will be a value above 32-bits this is still done for
+ * CONFIG_X86_32 so that accurate values are reported.
+ */
+ bsp_addr_config.phys_addr_reduction_bits =
+ (cpuid_ebx(0x8000001f) >> 6) & 0x3f;
+
+ if (IS_ENABLED(CONFIG_X86_32))
+ goto clear_all;
+
+ if (!sme_me_mask)
+ setup_clear_cpu_cap(X86_FEATURE_SME);
+
+ rdmsrl(MSR_K7_HWCR, msr);
+ if (!(msr & MSR_K7_HWCR_SMMLOCK))
+ goto clear_sev;
+
+ return;
+
+clear_all:
+ setup_clear_cpu_cap(X86_FEATURE_SME);
+clear_sev:
+ setup_clear_cpu_cap(X86_FEATURE_SEV);
+ setup_clear_cpu_cap(X86_FEATURE_SEV_ES);
+ }
+}
+
+static void __init bsp_init_amd(struct cpuinfo_x86 *c)
+{
+ bsp_detect_mem_encrypt(c);
+
if (cpu_has(c, X86_FEATURE_CONSTANT_TSC)) {

if (c->x86 > 0x10 ||
@@ -593,58 +647,6 @@ warn:
WARN_ONCE(1, "Family 0x%x, model: 0x%x??\n", c->x86, c->x86_model);
}

-static void early_detect_mem_encrypt(struct cpuinfo_x86 *c)
-{
- u64 msr;
-
- /*
- * BIOS support is required for SME and SEV.
- * For SME: If BIOS has enabled SME then adjust x86_phys_bits by
- * the SME physical address space reduction value.
- * If BIOS has not enabled SME then don't advertise the
- * SME feature (set in scattered.c).
- * If the kernel has not enabled SME via any means then
- * don't advertise the SME feature.
- * For SEV: If BIOS has not enabled SEV then don't advertise the
- * SEV and SEV_ES feature (set in scattered.c).
- *
- * In all cases, since support for SME and SEV requires long mode,
- * don't advertise the feature under CONFIG_X86_32.
- */
- if (cpu_has(c, X86_FEATURE_SME) || cpu_has(c, X86_FEATURE_SEV)) {
- /* Check if memory encryption is enabled */
- rdmsrl(MSR_AMD64_SYSCFG, msr);
- if (!(msr & MSR_AMD64_SYSCFG_MEM_ENCRYPT))
- goto clear_all;
-
- /*
- * Always adjust physical address bits. Even though this
- * will be a value above 32-bits this is still done for
- * CONFIG_X86_32 so that accurate values are reported.
- */
- bsp_addr_config.phys_addr_reduction_bits =
- (cpuid_ebx(0x8000001f) >> 6) & 0x3f;
-
- if (IS_ENABLED(CONFIG_X86_32))
- goto clear_all;
-
- if (!sme_me_mask)
- setup_clear_cpu_cap(X86_FEATURE_SME);
-
- rdmsrl(MSR_K7_HWCR, msr);
- if (!(msr & MSR_K7_HWCR_SMMLOCK))
- goto clear_sev;
-
- return;
-
-clear_all:
- setup_clear_cpu_cap(X86_FEATURE_SME);
-clear_sev:
- setup_clear_cpu_cap(X86_FEATURE_SEV);
- setup_clear_cpu_cap(X86_FEATURE_SEV_ES);
- }
-}
-
static void early_init_amd(struct cpuinfo_x86 *c)
{
u64 value;
@@ -715,8 +717,6 @@ static void early_init_amd(struct cpuinf
if (c->x86 == 0x16 && c->x86_model <= 0xf)
msr_set_bit(MSR_AMD64_LS_CFG, 15);

- early_detect_mem_encrypt(c);
-
/* Re-enable TopologyExtensions if switched off by BIOS */
if (c->x86 == 0x15 &&
(c->x86_model >= 0x10 && c->x86_model <= 0x6f) &&
_