xref: /aosp_15_r20/external/coreboot/src/soc/amd/common/block/cpu/smm/smi_handler.c (revision b9411a12aaaa7e1e6a6fb7c5e057f44ee179a49c)
1 /* SPDX-License-Identifier: GPL-2.0-or-later */
2 
3 #include <amdblocks/acpimmio.h>
4 #include <console/console.h>
5 #include <amdblocks/smi.h>
6 #include <amdblocks/smm.h>
7 #include <cpu/x86/smm.h>
8 #include <soc/smi.h>
9 
mainboard_handle_smi(int event)10 __weak void mainboard_handle_smi(int event)
11 {
12 	printk(BIOS_WARNING, "SMI event %d is missing handler\n", event);
13 }
14 
process_smi_sources(uint32_t reg)15 static void process_smi_sources(uint32_t reg)
16 {
17 	const uint32_t status = smi_read32(reg);
18 	int bit_zero = 32 / sizeof(uint32_t) * (reg - SMI_REG_SMISTS0);
19 	void (*source_handler)(void);
20 	int i;
21 
22 	for (i = 0 ; i < 32 ; i++) {
23 		if (status & (1 << i)) {
24 			source_handler = get_smi_source_handler(i + bit_zero);
25 			if (source_handler)
26 				source_handler();
27 			else if (reg != SMI_REG_SMISTS0 || (status & GEVENT_MASK) == 0)
28 				mainboard_handle_smi(i + bit_zero);
29 		}
30 	}
31 
32 	if (reg == SMI_REG_SMISTS0)
33 		if (status & GEVENT_MASK)
34 			/* Gevent[23:0] are assumed to be mainboard-specific */
35 			mainboard_smi_gpi(status & GEVENT_MASK);
36 
37 	/* Clear all events in this register */
38 	smi_write32(reg, status);
39 }
40 
southbridge_smi_handler(void)41 void southbridge_smi_handler(void)
42 {
43 	const uint16_t smi_src = smi_read16(SMI_REG_POINTER);
44 
45 	if (smi_src & SMI_STATUS_SRC_SCI) {
46 		printk(BIOS_WARNING, "Ignoring SCI SMI: %#x\n", smi_read32(SMI_SCI_STATUS));
47 
48 		/* Clear events to prevent re-entering SMI if event isn't handled */
49 		clear_smi_sci_status();
50 	}
51 	if (smi_src & SMI_STATUS_SRC_0)
52 		process_smi_sources(SMI_REG_SMISTS0);
53 	if (smi_src & SMI_STATUS_SRC_1)
54 		process_smi_sources(SMI_REG_SMISTS1);
55 	if (smi_src & SMI_STATUS_SRC_2)
56 		process_smi_sources(SMI_REG_SMISTS2);
57 	if (smi_src & SMI_STATUS_SRC_3)
58 		process_smi_sources(SMI_REG_SMISTS3);
59 	if (smi_src & SMI_STATUS_SRC_4)
60 		process_smi_sources(SMI_REG_SMISTS4);
61 }
62