|
Joerg Roedel |
23603d |
From: David Woodhouse <dwmw@amazon.co.uk>
|
|
Joerg Roedel |
23603d |
Date: Wed, 7 Oct 2020 13:20:42 +0100
|
|
Joerg Roedel |
23603d |
Subject: [PATCH 1/5] x86/apic: Fix x2apic enablement without interrupt
|
|
Joerg Roedel |
23603d |
remapping
|
|
Joerg Roedel |
23603d |
Patch-mainline: Never, upstream uses different implementation
|
|
Joerg Roedel |
23603d |
References: bsc#1181001, jsc#ECO-3191
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
Currently, Linux as a hypervisor guest will enable x2apic only if there
|
|
Joerg Roedel |
23603d |
are no CPUs present at boot time with an APIC ID above 255.
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
Hotplugging a CPU later with a higher APIC ID would result in a CPU
|
|
Joerg Roedel |
23603d |
which cannot be targeted by external interrupts.
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
Add a filter in x2apic_apic_id_valid() which can be used to prevent
|
|
Joerg Roedel |
23603d |
such CPUs from coming online, and allow x2apic to be enabled even if
|
|
Joerg Roedel |
23603d |
they are present at boot time.
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
Fixes: ce69a784504 ("x86/apic: Enable x2APIC without interrupt remapping under KVM")
|
|
Joerg Roedel |
23603d |
Signed-off-by: David Woodhouse <dwmw@amazon.co.uk>
|
|
Joerg Roedel |
23603d |
Acked-by: Joerg Roedel <jroedel@suse.de>
|
|
Joerg Roedel |
23603d |
---
|
|
Joerg Roedel |
23603d |
arch/x86/include/asm/apic.h | 1 +
|
|
Joerg Roedel |
23603d |
arch/x86/include/asm/x2apic.h | 5 +++++
|
|
Joerg Roedel |
23603d |
arch/x86/kernel/apic/apic.c | 14 ++++++++------
|
|
Joerg Roedel |
23603d |
arch/x86/kernel/apic/x2apic_phys.c | 6 ++++++
|
|
Joerg Roedel |
23603d |
4 files changed, 20 insertions(+), 6 deletions(-)
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
--- a/arch/x86/include/asm/apic.h
|
|
Joerg Roedel |
23603d |
+++ b/arch/x86/include/asm/apic.h
|
|
Joerg Roedel |
23603d |
@@ -235,6 +235,7 @@ static inline u64 native_x2apic_icr_read
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
extern int x2apic_mode;
|
|
Joerg Roedel |
23603d |
extern int x2apic_phys;
|
|
Joerg Roedel |
23603d |
+extern void __init x2apic_set_max_apicid(u32 apicid);
|
|
Joerg Roedel |
23603d |
extern void __init check_x2apic(void);
|
|
Joerg Roedel |
23603d |
extern void x2apic_setup(void);
|
|
Joerg Roedel |
23603d |
static inline int x2apic_enabled(void)
|
|
Joerg Roedel |
23603d |
--- a/arch/x86/include/asm/x2apic.h
|
|
Joerg Roedel |
23603d |
+++ b/arch/x86/include/asm/x2apic.h
|
|
Joerg Roedel |
23603d |
@@ -9,8 +9,13 @@
|
|
Joerg Roedel |
23603d |
#include <asm/ipi.h>
|
|
Joerg Roedel |
23603d |
#include <linux/cpumask.h>
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
+extern u32 x2apic_max_apicid;
|
|
Joerg Roedel |
23603d |
+
|
|
Joerg Roedel |
23603d |
static int x2apic_apic_id_valid(int apicid)
|
|
Joerg Roedel |
23603d |
{
|
|
Joerg Roedel |
23603d |
+ if (x2apic_max_apicid && apicid > x2apic_max_apicid)
|
|
Joerg Roedel |
23603d |
+ return 0;
|
|
Joerg Roedel |
23603d |
+
|
|
Joerg Roedel |
23603d |
return 1;
|
|
Joerg Roedel |
23603d |
}
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
--- a/arch/x86/kernel/apic/apic.c
|
|
Joerg Roedel |
23603d |
+++ b/arch/x86/kernel/apic/apic.c
|
|
Joerg Roedel |
23603d |
@@ -1580,20 +1580,22 @@ static __init void try_to_enable_x2apic(
|
|
Joerg Roedel |
23603d |
return;
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
if (remap_mode != IRQ_REMAP_X2APIC_MODE) {
|
|
Joerg Roedel |
23603d |
- /* IR is required if there is APIC ID > 255 even when running
|
|
Joerg Roedel |
23603d |
- * under KVM
|
|
Joerg Roedel |
23603d |
+ /*
|
|
Joerg Roedel |
23603d |
+ * Using X2APIC without IR is not architecturally supported
|
|
Joerg Roedel |
23603d |
+ * on bare metal but may be supported in guests.
|
|
Joerg Roedel |
23603d |
*/
|
|
Joerg Roedel |
23603d |
- if (max_physical_apicid > 255 ||
|
|
Joerg Roedel |
23603d |
- !x86_init.hyper.x2apic_available()) {
|
|
Joerg Roedel |
23603d |
+ if (!x86_init.hyper.x2apic_available()) {
|
|
Joerg Roedel |
23603d |
pr_info("x2apic: IRQ remapping doesn't support X2APIC mode\n");
|
|
Joerg Roedel |
23603d |
x2apic_disable();
|
|
Joerg Roedel |
23603d |
return;
|
|
Joerg Roedel |
23603d |
}
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
/*
|
|
Joerg Roedel |
23603d |
- * without IR all CPUs can be addressed by IOAPIC/MSI
|
|
Joerg Roedel |
23603d |
- * only in physical mode
|
|
Joerg Roedel |
23603d |
+ * Without IR, all CPUs can be addressed by IOAPIC/MSI only
|
|
Joerg Roedel |
23603d |
+ * in physical mode, and CPUs with an APIC ID that cannnot
|
|
Joerg Roedel |
23603d |
+ * be addressed must not be brought online.
|
|
Joerg Roedel |
23603d |
*/
|
|
Joerg Roedel |
23603d |
+ x2apic_set_max_apicid(255);
|
|
Joerg Roedel |
23603d |
x2apic_phys = 1;
|
|
Joerg Roedel |
23603d |
}
|
|
Joerg Roedel |
23603d |
x2apic_enable();
|
|
Joerg Roedel |
23603d |
--- a/arch/x86/kernel/apic/x2apic_phys.c
|
|
Joerg Roedel |
23603d |
+++ b/arch/x86/kernel/apic/x2apic_phys.c
|
|
Joerg Roedel |
23603d |
@@ -11,6 +11,12 @@
|
|
Joerg Roedel |
23603d |
int x2apic_phys;
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
static struct apic apic_x2apic_phys;
|
|
Joerg Roedel |
23603d |
+u32 x2apic_max_apicid;
|
|
Joerg Roedel |
23603d |
+
|
|
Joerg Roedel |
23603d |
+void __init x2apic_set_max_apicid(u32 apicid)
|
|
Joerg Roedel |
23603d |
+{
|
|
Joerg Roedel |
23603d |
+ x2apic_max_apicid = apicid;
|
|
Joerg Roedel |
23603d |
+}
|
|
Joerg Roedel |
23603d |
|
|
Joerg Roedel |
23603d |
static int set_x2apic_phys_mode(char *arg)
|
|
Joerg Roedel |
23603d |
{
|