x86/apic: Save the APIC virtual base address
authorThomas Gleixner <tglx@linutronix.de>
Fri, 12 May 2023 21:07:51 +0000 (23:07 +0200)
committerPeter Zijlstra <peterz@infradead.org>
Mon, 15 May 2023 11:45:03 +0000 (13:45 +0200)
For parallel CPU brinugp it's required to read the APIC ID in the low level
startup code. The virtual APIC base address is a constant because its a
fix-mapped address. Exposing that constant which is composed via macros to
assembly code is non-trivial due to header inclusion hell.

Aside of that it's constant only because of the vsyscall ABI
requirement. Once vsyscall is out of the picture the fixmap can be placed
at runtime.

Avoid header hell, stay flexible and store the address in a variable which
can be exposed to the low level startup code.

Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org>
Tested-by: Michael Kelley <mikelley@microsoft.com>
Tested-by: Oleksandr Natalenko <oleksandr@natalenko.name>
Tested-by: Helge Deller <deller@gmx.de> # parisc
Tested-by: Guilherme G. Piccoli <gpiccoli@igalia.com> # Steam Deck
Link: https://lore.kernel.org/r/20230512205257.299231005@linutronix.de
arch/x86/include/asm/smp.h
arch/x86/kernel/apic/apic.c

index 726c2a243eb077b40a9b655b3ab5c8611a8ec535..c6d5b65b7a47fb589c980f172a05213f5b7215dc 100644 (file)
@@ -196,6 +196,7 @@ extern void nmi_selftest(void);
 #endif
 
 extern unsigned int smpboot_control;
+extern unsigned long apic_mmio_base;
 
 #endif /* !__ASSEMBLY__ */
 
index e17600d3e2850d5954ad43bafd4bab8d031d9ae5..d3f6c18cd3eceace2a18712987a60fe0d6fc5070 100644 (file)
@@ -101,6 +101,9 @@ static int apic_extnmi __ro_after_init = APIC_EXTNMI_BSP;
  */
 static bool virt_ext_dest_id __ro_after_init;
 
+/* For parallel bootup. */
+unsigned long apic_mmio_base __ro_after_init;
+
 /*
  * Map cpu index to physical APIC ID
  */
@@ -2163,6 +2166,7 @@ void __init register_lapic_address(unsigned long address)
 
        if (!x2apic_mode) {
                set_fixmap_nocache(FIX_APIC_BASE, address);
+               apic_mmio_base = APIC_BASE;
                apic_printk(APIC_VERBOSE, "mapped APIC to %16lx (%16lx)\n",
                            APIC_BASE, address);
        }