summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/x86/include/asm/apic.h2
-rw-r--r--arch/x86/kernel/acpi/boot.c3
-rw-r--r--arch/x86/kernel/apic/apic.c19
3 files changed, 23 insertions, 1 deletions
diff --git a/arch/x86/include/asm/apic.h b/arch/x86/include/asm/apic.h
index 9362a3aae927..ef40e4acd7c2 100644
--- a/arch/x86/include/asm/apic.h
+++ b/arch/x86/include/asm/apic.h
@@ -504,8 +504,10 @@ extern int default_check_phys_apicid_present(int phys_apicid);
#ifdef CONFIG_SMP
bool apic_id_is_primary_thread(unsigned int id);
+bool apic_id_disabled(unsigned int id);
#else
static inline bool apic_id_is_primary_thread(unsigned int id) { return false; }
+static inline bool apic_id_disabled(unsigned int id) { return false; }
#endif
extern void irq_enter(void);
diff --git a/arch/x86/kernel/acpi/boot.c b/arch/x86/kernel/acpi/boot.c
index 3b20607d581b..db4c118a7e4d 100644
--- a/arch/x86/kernel/acpi/boot.c
+++ b/arch/x86/kernel/acpi/boot.c
@@ -181,7 +181,8 @@ static int acpi_register_lapic(int id, u32 acpiid, u8 enabled)
}
if (!enabled) {
- ++disabled_cpus;
+ if (!apic_id_disabled(id))
+ ++disabled_cpus;
return -EINVAL;
}
diff --git a/arch/x86/kernel/apic/apic.c b/arch/x86/kernel/apic/apic.c
index 8703caa9d6db..b86091add294 100644
--- a/arch/x86/kernel/apic/apic.c
+++ b/arch/x86/kernel/apic/apic.c
@@ -2204,6 +2204,16 @@ bool apic_id_is_primary_thread(unsigned int apicid)
return !(apicid & mask);
}
+/**
+ * apic_id_disabled - Check whether APIC ID is disabled via SMT control
+ * @id: APIC ID to check
+ */
+bool apic_id_disabled(unsigned int id)
+{
+ return (cpu_smt_control == CPU_SMT_FORCE_DISABLED &&
+ !apic_id_is_primary_thread(id));
+}
+
/*
* Should use this API to allocate logical CPU IDs to keep nr_logical_cpuids
* and cpuid_to_apicid[] synchronized.
@@ -2299,6 +2309,15 @@ int generic_processor_info(int apicid, int version)
return -EINVAL;
}
+ /*
+ * If SMT is force disabled and the APIC ID belongs to
+ * a secondary thread, ignore it.
+ */
+ if (apic_id_disabled(apicid)) {
+ pr_info_once("Ignoring secondary SMT threads\n");
+ return -EINVAL;
+ }
+
if (apicid == boot_cpu_physical_apicid) {
/*
* x86_bios_cpu_apicid is required to have processors listed