cpu/amd: Add common helpers for TSEG and SMM
Change-Id: I73174766980e0405e7b8efd4f059bb400c0c0a25 Signed-off-by: Arthur Heymans <arthur@aheymans.xyz> Reviewed-on: https://review.coreboot.org/c/coreboot/+/64866 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: Felix Held <felix-coreboot@felixheld.de>
This commit is contained in:
		
				
					committed by
					
						
						Felix Held
					
				
			
			
				
	
			
			
			
						parent
						
							b00ba8c247
						
					
				
				
					commit
					7ae8fa538e
				
			@@ -3,3 +3,7 @@
 | 
				
			|||||||
subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY14) += family14
 | 
					subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY14) += family14
 | 
				
			||||||
subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY15_TN) += family15tn
 | 
					subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY15_TN) += family15tn
 | 
				
			||||||
subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY16_KB) += family16kb
 | 
					subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY16_KB) += family16kb
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					romstage-y += ../../../soc/amd/common/block/cpu/smm/smm_helper.c
 | 
				
			||||||
 | 
					postcar-y += ../../../soc/amd/common/block/cpu/smm/smm_helper.c
 | 
				
			||||||
 | 
					ramstage-y += ../../../soc/amd/common/block/cpu/smm/smm_helper.c
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,14 +1,15 @@
 | 
				
			|||||||
/* SPDX-License-Identifier: GPL-2.0-only */
 | 
					/* SPDX-License-Identifier: GPL-2.0-only */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <acpi/acpi.h>
 | 
				
			||||||
 | 
					#include <amdblocks/smm.h>
 | 
				
			||||||
#include <console/console.h>
 | 
					#include <console/console.h>
 | 
				
			||||||
#include <cpu/x86/msr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/msr.h>
 | 
					#include <cpu/amd/msr.h>
 | 
				
			||||||
#include <cpu/x86/mtrr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/mtrr.h>
 | 
					#include <cpu/amd/mtrr.h>
 | 
				
			||||||
#include <device/device.h>
 | 
					 | 
				
			||||||
#include <cpu/cpu.h>
 | 
					#include <cpu/cpu.h>
 | 
				
			||||||
#include <cpu/x86/cache.h>
 | 
					#include <cpu/x86/cache.h>
 | 
				
			||||||
#include <acpi/acpi.h>
 | 
					#include <cpu/x86/msr.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/mtrr.h>
 | 
				
			||||||
 | 
					#include <device/device.h>
 | 
				
			||||||
#include <northbridge/amd/agesa/agesa_helper.h>
 | 
					#include <northbridge/amd/agesa/agesa_helper.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void model_14_init(struct device *dev)
 | 
					static void model_14_init(struct device *dev)
 | 
				
			||||||
@@ -76,9 +77,7 @@ static void model_14_init(struct device *dev)
 | 
				
			|||||||
	wrmsr(NB_CFG_MSR, msr);
 | 
						wrmsr(NB_CFG_MSR, msr);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	/* Write protect SMM space with SMMLOCK. */
 | 
						/* Write protect SMM space with SMMLOCK. */
 | 
				
			||||||
	msr = rdmsr(HWCR_MSR);
 | 
						lock_smm();
 | 
				
			||||||
	msr.lo |= (1 << 0);
 | 
					 | 
				
			||||||
	wrmsr(HWCR_MSR, msr);
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct device_operations cpu_dev_ops = {
 | 
					static struct device_operations cpu_dev_ops = {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,15 +1,16 @@
 | 
				
			|||||||
/* SPDX-License-Identifier: GPL-2.0-only */
 | 
					/* SPDX-License-Identifier: GPL-2.0-only */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <acpi/acpi.h>
 | 
				
			||||||
 | 
					#include <amdblocks/smm.h>
 | 
				
			||||||
#include <console/console.h>
 | 
					#include <console/console.h>
 | 
				
			||||||
#include <cpu/x86/msr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/msr.h>
 | 
					#include <cpu/amd/msr.h>
 | 
				
			||||||
#include <cpu/x86/mtrr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/mtrr.h>
 | 
					#include <cpu/amd/mtrr.h>
 | 
				
			||||||
#include <cpu/x86/smm.h>
 | 
					 | 
				
			||||||
#include <device/device.h>
 | 
					 | 
				
			||||||
#include <cpu/cpu.h>
 | 
					#include <cpu/cpu.h>
 | 
				
			||||||
#include <cpu/x86/cache.h>
 | 
					#include <cpu/x86/cache.h>
 | 
				
			||||||
#include <acpi/acpi.h>
 | 
					#include <cpu/x86/msr.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/mtrr.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/smm.h>
 | 
				
			||||||
 | 
					#include <device/device.h>
 | 
				
			||||||
#include <northbridge/amd/agesa/agesa_helper.h>
 | 
					#include <northbridge/amd/agesa/agesa_helper.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void model_15_init(struct device *dev)
 | 
					static void model_15_init(struct device *dev)
 | 
				
			||||||
@@ -93,9 +94,7 @@ static void model_15_init(struct device *dev)
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	/* Write protect SMM space with SMMLOCK. */
 | 
						/* Write protect SMM space with SMMLOCK. */
 | 
				
			||||||
	msr = rdmsr(HWCR_MSR);
 | 
						lock_smm();
 | 
				
			||||||
	msr.lo |= (1 << 0);
 | 
					 | 
				
			||||||
	wrmsr(HWCR_MSR, msr);
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct device_operations cpu_dev_ops = {
 | 
					static struct device_operations cpu_dev_ops = {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,14 +1,15 @@
 | 
				
			|||||||
/* SPDX-License-Identifier: GPL-2.0-only */
 | 
					/* SPDX-License-Identifier: GPL-2.0-only */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <acpi/acpi.h>
 | 
				
			||||||
 | 
					#include <amdblocks/smm.h>
 | 
				
			||||||
#include <console/console.h>
 | 
					#include <console/console.h>
 | 
				
			||||||
#include <cpu/x86/msr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/msr.h>
 | 
					#include <cpu/amd/msr.h>
 | 
				
			||||||
#include <cpu/x86/mtrr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/mtrr.h>
 | 
					#include <cpu/amd/mtrr.h>
 | 
				
			||||||
#include <device/device.h>
 | 
					 | 
				
			||||||
#include <cpu/cpu.h>
 | 
					#include <cpu/cpu.h>
 | 
				
			||||||
#include <cpu/x86/cache.h>
 | 
					#include <cpu/x86/cache.h>
 | 
				
			||||||
#include <acpi/acpi.h>
 | 
					#include <cpu/x86/msr.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/mtrr.h>
 | 
				
			||||||
 | 
					#include <device/device.h>
 | 
				
			||||||
#include <northbridge/amd/agesa/agesa_helper.h>
 | 
					#include <northbridge/amd/agesa/agesa_helper.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void model_16_init(struct device *dev)
 | 
					static void model_16_init(struct device *dev)
 | 
				
			||||||
@@ -76,9 +77,7 @@ static void model_16_init(struct device *dev)
 | 
				
			|||||||
	wrmsr(NB_CFG_MSR, msr);
 | 
						wrmsr(NB_CFG_MSR, msr);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	/* Write protect SMM space with SMMLOCK. */
 | 
						/* Write protect SMM space with SMMLOCK. */
 | 
				
			||||||
	msr = rdmsr(HWCR_MSR);
 | 
						lock_smm();
 | 
				
			||||||
	msr.lo |= (1 << 0);
 | 
					 | 
				
			||||||
	wrmsr(HWCR_MSR, msr);
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct device_operations cpu_dev_ops = {
 | 
					static struct device_operations cpu_dev_ops = {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,16 +1,17 @@
 | 
				
			|||||||
/* SPDX-License-Identifier: GPL-2.0-only */
 | 
					/* SPDX-License-Identifier: GPL-2.0-only */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <amdblocks/smm.h>
 | 
				
			||||||
#include <commonlib/helpers.h>
 | 
					#include <commonlib/helpers.h>
 | 
				
			||||||
#include <console/console.h>
 | 
					#include <console/console.h>
 | 
				
			||||||
#include <cpu/amd/microcode.h>
 | 
					#include <cpu/amd/microcode.h>
 | 
				
			||||||
#include <cpu/x86/msr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/msr.h>
 | 
					#include <cpu/amd/msr.h>
 | 
				
			||||||
#include <cpu/x86/mtrr.h>
 | 
					 | 
				
			||||||
#include <cpu/amd/mtrr.h>
 | 
					#include <cpu/amd/mtrr.h>
 | 
				
			||||||
#include <device/device.h>
 | 
					 | 
				
			||||||
#include <device/pci.h>
 | 
					 | 
				
			||||||
#include <cpu/cpu.h>
 | 
					#include <cpu/cpu.h>
 | 
				
			||||||
#include <cpu/x86/cache.h>
 | 
					#include <cpu/x86/cache.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/msr.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/mtrr.h>
 | 
				
			||||||
 | 
					#include <device/device.h>
 | 
				
			||||||
 | 
					#include <device/pci.h>
 | 
				
			||||||
#include <smp/node.h>
 | 
					#include <smp/node.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void model_16_init(struct device *dev)
 | 
					static void model_16_init(struct device *dev)
 | 
				
			||||||
@@ -44,9 +45,7 @@ static void model_16_init(struct device *dev)
 | 
				
			|||||||
	wrmsr(NB_CFG_MSR, msr);
 | 
						wrmsr(NB_CFG_MSR, msr);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	/* Write protect SMM space with SMMLOCK. */
 | 
						/* Write protect SMM space with SMMLOCK. */
 | 
				
			||||||
	msr = rdmsr(HWCR_MSR);
 | 
						lock_smm();
 | 
				
			||||||
	msr.lo |= (1 << 0);
 | 
					 | 
				
			||||||
	wrmsr(HWCR_MSR, msr);
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
	amd_update_microcode_from_cbfs();
 | 
						amd_update_microcode_from_cbfs();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,3 +1,7 @@
 | 
				
			|||||||
# SPDX-License-Identifier: GPL-2.0-only
 | 
					# SPDX-License-Identifier: GPL-2.0-only
 | 
				
			||||||
 | 
					
 | 
				
			||||||
subdirs-$(CONFIG_CPU_AMD_PI_00730F01) += 00730F01
 | 
					subdirs-$(CONFIG_CPU_AMD_PI_00730F01) += 00730F01
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					romstage-y += ../../../soc/amd/common/block/cpu/smm/smm_helper.c
 | 
				
			||||||
 | 
					postcar-y += ../../../soc/amd/common/block/cpu/smm/smm_helper.c
 | 
				
			||||||
 | 
					ramstage-y += ../../../soc/amd/common/block/cpu/smm/smm_helper.c
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,31 +1,25 @@
 | 
				
			|||||||
/* SPDX-License-Identifier: GPL-2.0-only */
 | 
					/* SPDX-License-Identifier: GPL-2.0-only */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include <acpi/acpi.h>
 | 
					#include <acpi/acpi.h>
 | 
				
			||||||
#include <cpu/x86/mp.h>
 | 
					#include <amdblocks/acpi.h>
 | 
				
			||||||
#include <cpu/x86/msr.h>
 | 
					#include <amdblocks/smm.h>
 | 
				
			||||||
#include <cpu/amd/msr.h>
 | 
					 | 
				
			||||||
#include <bootstate.h>
 | 
					#include <bootstate.h>
 | 
				
			||||||
#include <console/console.h>
 | 
					#include <console/console.h>
 | 
				
			||||||
#include <amdblocks/acpi.h>
 | 
					#include <cpu/amd/msr.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/mp.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/msr.h>
 | 
				
			||||||
#include <types.h>
 | 
					#include <types.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void per_core_finalize(void *unused)
 | 
					static void per_core_finalize(void *unused)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	msr_t hwcr, mask;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	/* Finalize SMM settings */
 | 
						/* Finalize SMM settings */
 | 
				
			||||||
	hwcr = rdmsr(HWCR_MSR);
 | 
						if (is_smm_locked()) /* Skip if already locked, avoid GPF */
 | 
				
			||||||
	if (hwcr.lo & SMM_LOCK) /* Skip if already locked, avoid GPF */
 | 
					 | 
				
			||||||
		return;
 | 
							return;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if (CONFIG(HAVE_SMI_HANDLER)) {
 | 
						if (CONFIG(HAVE_SMI_HANDLER))
 | 
				
			||||||
		mask = rdmsr(SMM_MASK_MSR);
 | 
							tseg_valid();
 | 
				
			||||||
		mask.lo |= SMM_TSEG_VALID;
 | 
					 | 
				
			||||||
		wrmsr(SMM_MASK_MSR, mask);
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
	hwcr.lo |= SMM_LOCK;
 | 
						lock_smm();
 | 
				
			||||||
	wrmsr(HWCR_MSR, hwcr);
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void finalize_cores(void)
 | 
					static void finalize_cores(void)
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,9 +1,12 @@
 | 
				
			|||||||
/* SPDX-License-Identifier: GPL-2.0-only */
 | 
					/* SPDX-License-Identifier: GPL-2.0-only */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include <amdblocks/smm.h>
 | 
					 | 
				
			||||||
#include <console/console.h>
 | 
					#include <console/console.h>
 | 
				
			||||||
#include <cpu/x86/msr.h>
 | 
					#include <cpu/amd/amd64_save_state.h>
 | 
				
			||||||
#include <cpu/amd/msr.h>
 | 
					#include <cpu/amd/msr.h>
 | 
				
			||||||
 | 
					#include <amdblocks/smm.h>
 | 
				
			||||||
 | 
					#include <cpu/cpu.h>
 | 
				
			||||||
 | 
					#include <cpu/x86/msr.h>
 | 
				
			||||||
 | 
					#include <stdint.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/*
 | 
					/*
 | 
				
			||||||
 * For data stored in TSEG, ensure TValid is clear so R/W access can reach
 | 
					 * For data stored in TSEG, ensure TValid is clear so R/W access can reach
 | 
				
			||||||
@@ -26,3 +29,24 @@ void clear_tvalid(void)
 | 
				
			|||||||
	mask.lo &= ~SMM_TSEG_VALID;
 | 
						mask.lo &= ~SMM_TSEG_VALID;
 | 
				
			||||||
	wrmsr(SMM_MASK_MSR, mask);
 | 
						wrmsr(SMM_MASK_MSR, mask);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void tseg_valid(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						msr_t mask = rdmsr(SMM_MASK_MSR);
 | 
				
			||||||
 | 
						mask.lo |= SMM_TSEG_VALID;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						wrmsr(SMM_MASK_MSR, mask);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					bool is_smm_locked(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						msr_t hwcr = rdmsr(HWCR_MSR);
 | 
				
			||||||
 | 
						return hwcr.lo & SMM_LOCK ? true : false;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void lock_smm(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						msr_t hwcr = rdmsr(HWCR_MSR);
 | 
				
			||||||
 | 
						hwcr.lo |= SMM_LOCK;
 | 
				
			||||||
 | 
						wrmsr(HWCR_MSR, hwcr);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -12,6 +12,9 @@ void *get_smi_source_handler(int source);
 | 
				
			|||||||
void handle_smi_gsmi(void);
 | 
					void handle_smi_gsmi(void);
 | 
				
			||||||
void handle_smi_store(void);
 | 
					void handle_smi_store(void);
 | 
				
			||||||
void clear_tvalid(void);
 | 
					void clear_tvalid(void);
 | 
				
			||||||
 | 
					void tseg_valid(void);
 | 
				
			||||||
 | 
					bool is_smm_locked(void);
 | 
				
			||||||
 | 
					void lock_smm(void);
 | 
				
			||||||
/* See SMITYPE_* for list possible of events. GEVENTS are handled with mainboard_smi_gpi. */
 | 
					/* See SMITYPE_* for list possible of events. GEVENTS are handled with mainboard_smi_gpi. */
 | 
				
			||||||
void mainboard_handle_smi(int event);
 | 
					void mainboard_handle_smi(int event);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user