linux/arch
Otavio Pontes 369428a646 x86/microcode: Check for offline CPUs before requesting new microcode
[ Upstream commit 7189b3c11903667808029ec9766a6e96de5012a5 ]

Currently, the late microcode loading mechanism checks whether any CPUs
are offlined, and, in such a case, aborts the load attempt.

However, this must be done before the kernel caches new microcode from
the filesystem. Otherwise, when offlined CPUs are onlined later, those
cores are going to be updated through the CPU hotplug notifier callback
with the new microcode, while CPUs previously onine will continue to run
with the older microcode.

For example:

Turn off one core (2 threads):

  echo 0 > /sys/devices/system/cpu/cpu3/online
  echo 0 > /sys/devices/system/cpu/cpu1/online

Install the ucode fails because a primary SMT thread is offline:

  cp intel-ucode/06-8e-09 /lib/firmware/intel-ucode/
  echo 1 > /sys/devices/system/cpu/microcode/reload
  bash: echo: write error: Invalid argument

Turn the core back on

  echo 1 > /sys/devices/system/cpu/cpu3/online
  echo 1 > /sys/devices/system/cpu/cpu1/online
  cat /proc/cpuinfo |grep microcode
  microcode : 0x30
  microcode : 0xde
  microcode : 0x30
  microcode : 0xde

The rationale for why the update is aborted when at least one primary
thread is offline is because even if that thread is soft-offlined
and idle, it will still have to participate in broadcasted MCE's
synchronization dance or enter SMM, and in both examples it will execute
instructions so it better have the same microcode revision as the other
cores.

 [ bp: Heavily edit and extend commit message with the reasoning behind all
   this. ]

Fixes: 30ec26da99 ("x86/microcode: Do not upload microcode if CPUs are offline")
Signed-off-by: Otavio Pontes <otavio.pontes@intel.com>
Signed-off-by: Borislav Petkov <bp@suse.de>
Reviewed-by: Tony Luck <tony.luck@intel.com>
Acked-by: Ashok Raj <ashok.raj@intel.com>
Link: https://lkml.kernel.org/r/20210319165515.9240-2-otavio.pontes@intel.com
Signed-off-by: Sasha Levin <sashal@kernel.org>
2021-05-14 09:44:17 +02:00
..
alpha alpha: fix annotation of io{read,write}{16,32}be() 2020-08-26 10:40:58 +02:00
arc arc: kernel: Return -EFAULT if copy_to_user() fails 2021-04-21 12:56:13 +02:00
arm ARM: dts: exynos: correct PMIC interrupt trigger level on Snow 2021-05-14 09:44:16 +02:00
arm64 arm64: dts: renesas: r8a77980: Fix vin4-7 endpoint binding 2021-05-14 09:44:17 +02:00
c6x
csky csky: change a Kconfig symbol name to fix e1000 build error 2021-04-28 13:19:16 +02:00
h8300 h8300: fix PREEMPTION build, TI_PRE_COUNT undefined 2021-02-17 10:35:18 +01:00
hexagon
ia64 ia64: fix discontig.c section mismatches 2021-04-28 13:19:16 +02:00
m68k m68k: q40: Fix info-leak in rtc_ioctl 2020-10-01 13:17:12 +02:00
microblaze
mips MIPS: pci-rt2880: fix slot 0 configuration 2021-05-14 09:44:12 +02:00
nds32 nds32: flush_dcache_page: use page_mapping_file to avoid races with swapoff 2021-04-14 08:24:10 +02:00
nios2
openrisc openrisc: Fix issue with get_user for 64-bit values 2020-11-01 12:01:06 +01:00
parisc parisc: avoid a warning on u8 cast for cmpxchg on u8 pointers 2021-04-14 08:24:11 +02:00
powerpc powerpc: fix EDEADLOCK redefinition error in uapi/asm/errno.h 2021-05-11 14:04:15 +02:00
riscv riscv: Fix spelling mistake "SPARSEMEM" to "SPARSMEM" 2021-04-21 12:56:16 +02:00
s390 KVM: s390: split kvm_s390_real_to_abs 2021-05-14 09:44:15 +02:00
sh sh: dma: fix kconfig dependency for G2_DMA 2021-01-27 11:47:52 +01:00
sparc sparc64: Fix opcode filtering in handling of no fault loads 2021-03-30 14:35:22 +02:00
um um: mm: check more comprehensively for stub changes 2021-03-04 10:26:50 +01:00
unicore32
x86 x86/microcode: Check for offline CPUs before requesting new microcode 2021-05-14 09:44:17 +02:00
xtensa xtensa: move coprocessor_flush to the .text section 2021-04-07 14:47:42 +02:00
.gitignore
Kconfig Revert: "ring-buffer: Remove HAVE_64BIT_ALIGNED_ACCESS" 2020-12-30 11:51:47 +01:00