diff options
Diffstat (limited to 'src/soc/amd')
-rw-r--r-- | src/soc/amd/stoneyridge/Kconfig | 2 | ||||
-rw-r--r-- | src/soc/amd/stoneyridge/chip.c | 18 | ||||
-rw-r--r-- | src/soc/amd/stoneyridge/northbridge.c | 8 | ||||
-rw-r--r-- | src/soc/amd/stoneyridge/romstage.c | 72 |
4 files changed, 60 insertions, 40 deletions
diff --git a/src/soc/amd/stoneyridge/Kconfig b/src/soc/amd/stoneyridge/Kconfig index 79755239d8..8bf577c72f 100644 --- a/src/soc/amd/stoneyridge/Kconfig +++ b/src/soc/amd/stoneyridge/Kconfig @@ -50,7 +50,7 @@ config CPU_SPECIFIC_OPTIONS select SOC_AMD_COMMON_BLOCK_PI select SOC_AMD_COMMON_BLOCK_PSP select SOC_AMD_COMMON_BLOCK_CAR - select SOC_AMD_COMMON_BLOCK_S3 + select SOC_AMD_COMMON_BLOCK_S3 if HAVE_ACPI_RESUME select C_ENVIRONMENT_BOOTBLOCK select BOOTBLOCK_CONSOLE select BOOT_DEVICE_SUPPORTS_WRITES if BOOT_DEVICE_SPI_FLASH diff --git a/src/soc/amd/stoneyridge/chip.c b/src/soc/amd/stoneyridge/chip.c index d3a8bc4044..f5efcfd96f 100644 --- a/src/soc/amd/stoneyridge/chip.c +++ b/src/soc/amd/stoneyridge/chip.c @@ -21,6 +21,7 @@ #include <device/device.h> #include <device/pci.h> #include <drivers/i2c/designware/dw_i2c.h> +#include <romstage_handoff.h> #include <soc/cpu.h> #include <soc/northbridge.h> #include <soc/pci_devs.h> @@ -110,12 +111,19 @@ struct chip_operations soc_amd_stoneyridge_ops = { static void earliest_ramstage(void *unused) { - post_code(0x46); - if (IS_ENABLED(CONFIG_SOC_AMD_PSP_SELECTABLE_SMU_FW)) - psp_load_named_blob(MBOX_BIOS_CMD_SMU_FW2, "smu_fw2"); + if (!romstage_handoff_is_resume()) { + post_code(0x46); + if (IS_ENABLED(CONFIG_SOC_AMD_PSP_SELECTABLE_SMU_FW)) + psp_load_named_blob(MBOX_BIOS_CMD_SMU_FW2, "smu_fw2"); - post_code(0x47); - do_agesawrapper(agesawrapper_amdinitenv, "amdinitenv"); + post_code(0x47); + do_agesawrapper(agesawrapper_amdinitenv, "amdinitenv"); + } else { + /* Complete the initial system restoration */ + post_code(0x46); + do_agesawrapper(agesawrapper_amds3laterestore, + "amds3laterestore"); + } } BOOT_STATE_INIT_ENTRY(BS_PRE_DEVICE, BS_ON_ENTRY, earliest_ramstage, NULL); diff --git a/src/soc/amd/stoneyridge/northbridge.c b/src/soc/amd/stoneyridge/northbridge.c index 9d2823f329..2449077313 100644 --- a/src/soc/amd/stoneyridge/northbridge.c +++ b/src/soc/amd/stoneyridge/northbridge.c @@ -28,6 +28,7 @@ #include <device/device.h> #include <device/pci.h> #include <device/pci_ids.h> +#include <romstage_handoff.h> #include <amdblocks/agesawrapper.h> #include <amdblocks/agesawrapper_call.h> #include <agesa_headers.h> @@ -425,14 +426,9 @@ void domain_read_resources(device_t dev) void domain_enable_resources(device_t dev) { - if (acpi_is_wakeup_s3()) - do_agesawrapper(agesawrapper_fchs3laterestore, - "fchs3laterestore"); - /* Must be called after PCI enumeration and resource allocation */ - else + if (!romstage_handoff_is_resume()) do_agesawrapper(agesawrapper_amdinitmid, "amdinitmid"); - printk(BIOS_DEBUG, " ader - leaving domain_enable_resources.\n"); } void domain_set_resources(device_t dev) diff --git a/src/soc/amd/stoneyridge/romstage.c b/src/soc/amd/stoneyridge/romstage.c index 24d62895eb..490fd9ee9c 100644 --- a/src/soc/amd/stoneyridge/romstage.c +++ b/src/soc/amd/stoneyridge/romstage.c @@ -15,6 +15,7 @@ */ #include <arch/cpu.h> +#include <arch/acpi.h> #include <cpu/x86/msr.h> #include <cpu/x86/mtrr.h> #include <cpu/amd/mtrr.h> @@ -24,6 +25,7 @@ #include <device/device.h> #include <chip.h> #include <program_loading.h> +#include <romstage_handoff.h> #include <amdblocks/agesawrapper.h> #include <amdblocks/agesawrapper_call.h> #include <soc/northbridge.h> @@ -40,45 +42,59 @@ asmlinkage void car_stage_entry(void) msr_t base, mask; msr_t mtrr_cap = rdmsr(MTRR_CAP_MSR); int vmtrrs = mtrr_cap.lo & MTRR_CAP_VCNT; + int s3_resume = acpi_s3_resume_allowed() && acpi_is_wakeup_s3(); int i; console_init(); - post_code(0x40); - do_agesawrapper(agesawrapper_amdinitpost, "amdinitpost"); - - post_code(0x41); - /* - * TODO: This is a hack to work around current AGESA behavior. AGESA - * needs to change to reflect that coreboot owns the MTRRs. - * - * After setting up DRAM, AGESA also completes the configuration of the - * MTRRs, setting regions to WB. Anything written to memory between - * now and and when CAR is dismantled will be in cache and lost. For - * now, set the regions UC to ensure the writes get to DRAM. - */ - for (i = 0 ; i < vmtrrs ; i++) { - base = rdmsr(MTRR_PHYS_BASE(i)); - mask = rdmsr(MTRR_PHYS_MASK(i)); - if (!(mask.lo & MTRR_PHYS_MASK_VALID)) - continue; - - if ((base.lo & 0x7) == MTRR_TYPE_WRBACK) { - base.lo &= ~0x7; - base.lo |= MTRR_TYPE_UNCACHEABLE; - wrmsr(MTRR_PHYS_BASE(i), base); + if (!s3_resume) { + post_code(0x40); + do_agesawrapper(agesawrapper_amdinitpost, "amdinitpost"); + + post_code(0x41); + /* + * TODO: This is a hack to work around current AGESA behavior. + * AGESA needs to change to reflect that coreboot owns + * the MTRRs. + * + * After setting up DRAM, AGESA also completes the configuration + * of the MTRRs, setting regions to WB. Anything written to + * memory between now and and when CAR is dismantled will be + * in cache and lost. For now, set the regions UC to ensure + * the writes get to DRAM. + */ + for (i = 0 ; i < vmtrrs ; i++) { + base = rdmsr(MTRR_PHYS_BASE(i)); + mask = rdmsr(MTRR_PHYS_MASK(i)); + if (!(mask.lo & MTRR_PHYS_MASK_VALID)) + continue; + + if ((base.lo & 0x7) == MTRR_TYPE_WRBACK) { + base.lo &= ~0x7; + base.lo |= MTRR_TYPE_UNCACHEABLE; + wrmsr(MTRR_PHYS_BASE(i), base); + } } + /* Disable WB from to region 4GB-TOM2. */ + msr_t sys_cfg = rdmsr(SYSCFG_MSR); + sys_cfg.lo &= ~SYSCFG_MSR_TOM2WB; + wrmsr(SYSCFG_MSR, sys_cfg); + } else { + printk(BIOS_INFO, "S3 detected\n"); + post_code(0x60); + do_agesawrapper(agesawrapper_amdinitresume, "amdinitresume"); + + post_code(0x61); } - /* Disable WB from to region 4GB-TOM2. */ - msr_t sys_cfg = rdmsr(SYSCFG_MSR); - sys_cfg.lo &= ~SYSCFG_MSR_TOM2WB; - wrmsr(SYSCFG_MSR, sys_cfg); post_code(0x42); psp_notify_dram(); post_code(0x43); - cbmem_initialize_empty(); + if (cbmem_recovery(s3_resume)) + printk(BIOS_CRIT, "Failed to recover cbmem\n"); + if (romstage_handoff_init(s3_resume)) + printk(BIOS_ERR, "Failed to set romstage handoff data\n"); post_code(0x44); if (postcar_frame_init(&pcf, 1 * KiB)) |