From aac79e0b8f4777f8a912ccdfc483755b7a4da52c Mon Sep 17 00:00:00 2001 From: Zheng Bao Date: Wed, 10 Jun 2020 11:04:36 +0800 Subject: x86/lapic: Set EXTINT on BSP only MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit When Linux is booted, the kernel reports "do_IRQ: 1.55 No irq handler for vector" So far it comes with payloads SeaBIOS and depthcharge, not with Grub. We assume Grub does something to avoid this problem. AMD bug tracker system (JIRA PLAT-21393) says the APs can not be set EXTINT delivery mode. In Intel 64 and IA-32 Architectures Software Developer’s Manual volume 3A, see chapter 10.5.1 Local Vector Table, it says: "The APIC architecture supports only one ExtINT source in a system, usually contained in the compatibility bridge. Only one processor in the system should have an LVT entry configured to use the ExtINT delivery mode." Tested on mandolin (Picasso) board, the error in dmesg is gone. The bug 153677727 has two parts. 1. Soft lockup 2. do_IRQ 1.55. The soft lockup issued has been fixed by https://review.coreboot.org/c/coreboot/+/41128 BUG=b:153677727 TEST=mandolin Change-Id: I2956dcaad87cc1466deeca703748de33390b7603 Signed-off-by: Zheng Bao Signed-off-by: Zheng Bao Reviewed-on: https://review.coreboot.org/c/coreboot/+/42219 Reviewed-by: Felix Held Reviewed-by: Paul Menzel Tested-by: build bot (Jenkins) --- src/cpu/x86/lapic/lapic.c | 26 +++++++++++--------------- 1 file changed, 11 insertions(+), 15 deletions(-) (limited to 'src') diff --git a/src/cpu/x86/lapic/lapic.c b/src/cpu/x86/lapic/lapic.c index f0a6cd7f46..653c3b2e40 100644 --- a/src/cpu/x86/lapic/lapic.c +++ b/src/cpu/x86/lapic/lapic.c @@ -2,16 +2,11 @@ #include #include +#include void do_lapic_init(void) { - /* this is so interrupts work. This is very limited scope -- - * linux will do better later, we hope ... - */ - /* this is the first way we learned to do it. It fails on real SMP - * stuff. So we have to do things differently ... - * see the Intel mp1.4 spec, page A-3 - */ + uint32_t lvt0_val; printk(BIOS_INFO, "Setting up local APIC...\n"); @@ -28,15 +23,16 @@ void do_lapic_init(void) lapic_write_around(LAPIC_SPIV, (lapic_read_around(LAPIC_SPIV) & ~(LAPIC_VECTOR_MASK)) | LAPIC_SPIV_ENABLE); - lapic_write_around(LAPIC_LVT0, - (lapic_read_around(LAPIC_LVT0) & - ~(LAPIC_LVT_MASKED | LAPIC_LVT_LEVEL_TRIGGER | + + lvt0_val = (lapic_read_around(LAPIC_LVT0) & + ~(LAPIC_LVT_MASKED | LAPIC_LVT_LEVEL_TRIGGER | LAPIC_LVT_REMOTE_IRR | LAPIC_INPUT_POLARITY | - LAPIC_SEND_PENDING | LAPIC_LVT_RESERVED_1 | - LAPIC_DELIVERY_MODE_MASK)) - | (LAPIC_LVT_REMOTE_IRR | LAPIC_SEND_PENDING | - LAPIC_DELIVERY_MODE_EXTINT) - ); + LAPIC_SEND_PENDING | LAPIC_LVT_RESERVED_1)) | + (LAPIC_LVT_REMOTE_IRR | LAPIC_SEND_PENDING); + if (boot_cpu()) + lvt0_val = SET_LAPIC_DELIVERY_MODE(lvt0_val, LAPIC_MODE_EXINT); + lapic_write_around(LAPIC_LVT0, lvt0_val); + lapic_write_around(LAPIC_LVT1, (lapic_read_around(LAPIC_LVT1) & ~(LAPIC_LVT_MASKED | LAPIC_LVT_LEVEL_TRIGGER | -- cgit v1.2.3