linux-stable/arch/x86
Tony Luck 65ac09c965 x86/cpu: Fix x86_match_cpu() to match just X86_VENDOR_INTEL
[ Upstream commit 93022482b2 ]

Code in v6.9 arch/x86/kernel/smpboot.c was changed by commit

  4db64279bc ("x86/cpu: Switch to new Intel CPU model defines") from:

  static const struct x86_cpu_id intel_cod_cpu[] = {
          X86_MATCH_INTEL_FAM6_MODEL(HASWELL_X, 0),       /* COD */
          X86_MATCH_INTEL_FAM6_MODEL(BROADWELL_X, 0),     /* COD */
          X86_MATCH_INTEL_FAM6_MODEL(ANY, 1),             /* SNC */	<--- 443
          {}
  };

  static bool match_llc(struct cpuinfo_x86 *c, struct cpuinfo_x86 *o)
  {
          const struct x86_cpu_id *id = x86_match_cpu(intel_cod_cpu);

to:

  static const struct x86_cpu_id intel_cod_cpu[] = {
           X86_MATCH_VFM(INTEL_HASWELL_X,   0),    /* COD */
           X86_MATCH_VFM(INTEL_BROADWELL_X, 0),    /* COD */
           X86_MATCH_VFM(INTEL_ANY,         1),    /* SNC */
           {}
   };

  static bool match_llc(struct cpuinfo_x86 *c, struct cpuinfo_x86 *o)
  {
          const struct x86_cpu_id *id = x86_match_cpu(intel_cod_cpu);

On an Intel CPU with SNC enabled this code previously matched the rule on line
443 to avoid printing messages about insane cache configuration.  The new code
did not match any rules.

Expanding the macros for the intel_cod_cpu[] array shows that the old is
equivalent to:

  static const struct x86_cpu_id intel_cod_cpu[] = {
  [0] = { .vendor = 0, .family = 6, .model = 0x3F, .steppings = 0, .feature = 0, .driver_data = 0 },
  [1] = { .vendor = 0, .family = 6, .model = 0x4F, .steppings = 0, .feature = 0, .driver_data = 0 },
  [2] = { .vendor = 0, .family = 6, .model = 0x00, .steppings = 0, .feature = 0, .driver_data = 1 },
  [3] = { .vendor = 0, .family = 0, .model = 0x00, .steppings = 0, .feature = 0, .driver_data = 0 }
  }

while the new code expands to:

  static const struct x86_cpu_id intel_cod_cpu[] = {
  [0] = { .vendor = 0, .family = 6, .model = 0x3F, .steppings = 0, .feature = 0, .driver_data = 0 },
  [1] = { .vendor = 0, .family = 6, .model = 0x4F, .steppings = 0, .feature = 0, .driver_data = 0 },
  [2] = { .vendor = 0, .family = 0, .model = 0x00, .steppings = 0, .feature = 0, .driver_data = 1 },
  [3] = { .vendor = 0, .family = 0, .model = 0x00, .steppings = 0, .feature = 0, .driver_data = 0 }
  }

Looking at the code for x86_match_cpu():

  const struct x86_cpu_id *x86_match_cpu(const struct x86_cpu_id *match)
  {
           const struct x86_cpu_id *m;
           struct cpuinfo_x86 *c = &boot_cpu_data;

           for (m = match;
                m->vendor | m->family | m->model | m->steppings | m->feature;
                m++) {
       		...
           }
           return NULL;

it is clear that there was no match because the ANY entry in the table (array
index 2) is now the loop termination condition (all of vendor, family, model,
steppings, and feature are zero).

So this code was working before because the "ANY" check was looking for any
Intel CPU in family 6. But fails now because the family is a wild card. So the
root cause is that x86_match_cpu() has never been able to match on a rule with
just X86_VENDOR_INTEL and all other fields set to wildcards.

Add a new flags field to struct x86_cpu_id that has a bit set to indicate that
this entry in the array is valid. Update X86_MATCH*() macros to set that bit.
Change the end-marker check in x86_match_cpu() to just check the flags field
for this bit.

Backporter notes: The commit in Fixes is really the one that is broken:
you can't have m->vendor as part of the loop termination conditional in
x86_match_cpu() because it can happen - as it has happened above
- that that whole conditional is 0 albeit vendor == 0 is a valid case
- X86_VENDOR_INTEL is 0.

However, the only case where the above happens is the SNC check added by
4db64279bc so you only need this fix if you have backported that
other commit

  4db64279bc ("x86/cpu: Switch to new Intel CPU model defines")

Fixes: 644e9cbbe3 ("Add driver auto probing for x86 features v4")
Suggested-by: Thomas Gleixner <tglx@linutronix.de>
Suggested-by: Borislav Petkov <bp@alien8.de>
Signed-off-by: Tony Luck <tony.luck@intel.com>
Signed-off-by: Borislav Petkov (AMD) <bp@alien8.de>
Cc: <stable+noautosel@kernel.org> # see above
Link: https://lore.kernel.org/r/20240517144312.GBZkdtAOuJZCvxhFbJ@fat_crate.local
Signed-off-by: Sasha Levin <sashal@kernel.org>
2024-06-27 13:49:14 +02:00
..
boot x86/boot: Don't add the EFI stub to targets, again 2024-06-21 14:38:37 +02:00
coco x86/coco: Require seeding RNG with RDRAND on CoCo systems 2024-04-10 16:36:03 +02:00
configs - The first, cleanup part of the microcode loader reorg tglx has been 2023-08-28 15:55:20 -07:00
crypto crypto: x86/sha512-avx2 - add missing vzeroupper 2024-06-12 11:11:32 +02:00
entry kbuild: unify vdso_install rules 2024-06-12 11:12:32 +02:00
events perf/x86: Fix out of range data 2024-04-17 11:19:36 +02:00
hyperv x86/hyperv: Use per cpu initial stack for vtl context 2024-03-26 18:20:06 -04:00
ia32
include x86/cpu: Fix x86_match_cpu() to match just X86_VENDOR_INTEL 2024-06-27 13:49:14 +02:00
kernel x86/cpu: Fix x86_match_cpu() to match just X86_VENDOR_INTEL 2024-06-27 13:49:14 +02:00
kvm KVM: x86: Always sync PIR to IRR prior to scanning I/O APIC routes 2024-06-27 13:49:11 +02:00
lib x86/uaccess: Fix missed zeroing of ia32 u64 get_user() range checking 2024-06-21 14:38:34 +02:00
math-emu x86/fpu: Include asm/fpu/regset.h 2023-05-18 11:56:18 -07:00
mm mm: fix race between __split_huge_pmd_locked() and GUP-fast 2024-06-16 13:47:40 +02:00
net bpf, x86: Fix PROBE_MEM runtime load check 2024-06-12 11:11:27 +02:00
pci x86/pci: Skip early E820 check for ECAM region 2024-06-12 11:13:01 +02:00
platform efi/x86: Free EFI memory map only when installing a new one. 2024-06-27 13:49:13 +02:00
power mm/treewide: replace pud_large() with pud_leaf() 2024-04-10 16:35:46 +02:00
purgatory x86/purgatory: Switch to the position-independent small code model 2024-06-12 11:11:43 +02:00
ras
realmode x86/realmode: Make stack lock work in trampoline_compat() 2023-05-30 14:11:47 +02:00
tools x86/boot: Ignore relocations in .notes sections in walk_relocs() too 2024-06-12 11:11:36 +02:00
um um: Fix the -Wmissing-prototypes warning for get_thread_reg 2024-06-12 11:12:42 +02:00
video Merge drm/drm-next into drm-misc-next 2023-07-24 15:44:47 +02:00
virt/vmx/tdx
xen xen/x86: add extra pages to unpopulated-alloc if available 2024-06-12 11:12:46 +02:00
.gitignore
Kbuild
Kconfig cpu: Ignore "mitigations" kernel parameter if CPU_MITIGATIONS=n 2024-06-12 11:11:24 +02:00
Kconfig.assembler x86/shstk: Add Kconfig option for shadow stack 2023-07-11 14:12:18 -07:00
Kconfig.cpu x86/Kconfig: Transmeta Crusoe is CPU family 5, not 6 2024-02-23 09:25:10 +01:00
Kconfig.debug x86/kconfig: Select ARCH_WANT_FRAME_POINTERS again when UNWINDER_FRAME_POINTER=y 2024-06-12 11:12:46 +02:00
Makefile kbuild: unify vdso_install rules 2024-06-12 11:12:32 +02:00
Makefile.postlink x86/build: Avoid relocation information in final vmlinux 2023-06-14 19:54:40 +02:00
Makefile.um
Makefile_32.cpu