Arthur Heymans has uploaded this change for review.

View Change

[UNTESTED]cpu/amd/agesa: Use common MRC_CACHE code to save S3 data

Most of the code is copied from soc/amd/common/block/s3/s3_resume.c

The current default MRC_CACHE FMAP region is 64K instead of 8K. One
could make this configurable in the future.

Change-Id: I0f4f36dcead52a6c550fb5e606772e0a99029872
Signed-off-by: Arthur Heymans <arthur@aheymans.xyz>
---
M src/cpu/amd/agesa/Kconfig
M src/cpu/amd/agesa/Makefile.inc
M src/drivers/amd/agesa/oem_s3.c
3 files changed, 38 insertions(+), 81 deletions(-)

git pull ssh://review.coreboot.org:29418/coreboot refs/changes/95/44295/1
diff --git a/src/cpu/amd/agesa/Kconfig b/src/cpu/amd/agesa/Kconfig
index 499cc5b..f407139 100644
--- a/src/cpu/amd/agesa/Kconfig
+++ b/src/cpu/amd/agesa/Kconfig
@@ -18,6 +18,7 @@
select SMM_ASEG
select SSE2
select ACPI_NO_SMI_GNVS
+ select CACHE_MRC_SETTINGS

if CPU_AMD_AGESA

@@ -53,14 +54,6 @@
Try to restore memory training results
from non-volatile memory.

-config S3_DATA_POS
- hex
- default 0xFFFF0000
-
-config S3_DATA_SIZE
- int
- default 8192
-
endif # CPU_AMD_AGESA

source "src/cpu/amd/agesa/family14/Kconfig"
diff --git a/src/cpu/amd/agesa/Makefile.inc b/src/cpu/amd/agesa/Makefile.inc
index 14067e1..1f9cca5 100644
--- a/src/cpu/amd/agesa/Makefile.inc
+++ b/src/cpu/amd/agesa/Makefile.inc
@@ -3,18 +3,3 @@
subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY14) += family14
subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY15_TN) += family15tn
subdirs-$(CONFIG_CPU_AMD_AGESA_FAMILY16_KB) += family16kb
-
-ifeq ($(CONFIG_HAVE_ACPI_RESUME), y)
-
-$(obj)/coreboot_s3nv.rom: $(obj)/config.h
- echo " S3 NVRAM $(CONFIG_S3_DATA_POS) (S3 storage area)"
- # force C locale, so cygwin awk doesn't try to interpret the 0xff below as UTF-8 (or worse)
- printf %d $(CONFIG_S3_DATA_SIZE) | LC_ALL=C awk '{for (i=0; i<$$1; i++) {printf "%c", 255}}' > $@.tmp
- mv $@.tmp $@
-
-cbfs-files-y += s3nv
-s3nv-file := $(obj)/coreboot_s3nv.rom
-s3nv-position := $(CONFIG_S3_DATA_POS)
-s3nv-type := raw
-
-endif # CONFIG_HAVE_ACPI_RESUME == y
diff --git a/src/drivers/amd/agesa/oem_s3.c b/src/drivers/amd/agesa/oem_s3.c
index 0b37d3e..8d32bae 100644
--- a/src/drivers/amd/agesa/oem_s3.c
+++ b/src/drivers/amd/agesa/oem_s3.c
@@ -1,41 +1,53 @@
/* SPDX-License-Identifier: GPL-2.0-only */

-#include <spi-generic.h>
-#include <spi_flash.h>
#include <string.h>
+#include <device/mmio.h>
#include <cbmem.h>
#include <console/console.h>
+#include <mrc_cache.h>
+#include <reset.h>
#include <northbridge/amd/agesa/state_machine.h>
#include <AGESA.h>
#include <northbridge/amd/agesa/agesa_helper.h>

-/* The size needs to be 4k aligned, which is the sector size of most flashes. */
-#define S3_DATA_NONVOLATILE_SIZE 0x1000
+/* Training data versioning is not supported or tracked. */
+#define DEFAULT_MRC_VERSION 0

-#if CONFIG(HAVE_ACPI_RESUME) && S3_DATA_NONVOLATILE_SIZE > CONFIG_S3_DATA_SIZE
-#error "Please increase the value of S3_DATA_SIZE"
-#endif
-
-static void get_s3nv_data(uintptr_t *pos, uintptr_t *len)
+static void __noreturn reboot_from_resume(const char *message)
{
- /* FIXME: Find file from CBFS. */
- *pos = CONFIG_S3_DATA_POS;
- *len= S3_DATA_NONVOLATILE_SIZE;
+ printk(BIOS_ERR, "%s", message);
+// set_pm1cnt_s5(); TODO??
+ board_reset();
}

AGESA_STATUS OemInitResume(AMD_S3_PARAMS *dataBlock)
{
- uintptr_t pos, size;
- get_s3nv_data(&pos, &size);
+ void *base;
+ size_t size;
+ int i;
+ uint32_t erased = 0xffffffff;
+ struct region_device rdev;

- u32 len = *(u32*)pos;
+ if (mrc_cache_get_current(MRC_TRAINING_DATA, DEFAULT_MRC_VERSION,
+ &rdev))
+ reboot_from_resume("mrc_cache_get_current error, rebooting.\n");

- /* Test for uninitialized s3nv data in SPI. */
- if (len == 0 || len == (u32)-1ULL)
- return AGESA_FATAL;
+ base = rdev_mmap_full(&rdev);
+ size = region_device_sz(&rdev);
+ if (!base || !size)
+ reboot_from_resume("Error: S3 NV data not found, rebooting.\n");

- dataBlock->NvStorageSize = len;
- dataBlock->NvStorage = (void *) (pos + sizeof(u32));
+ /* Read 16 bytes to infer if the NV has been erased from flash. */
+ for (i = 0; i < 4; i++)
+ erased &= read32((uint32_t *)base + i);
+ if (erased == 0xffffffff)
+ reboot_from_resume("Error: S3 NV data invalid, rebooting.\n");
+
+ dataBlock->NvStorage = base;
+ dataBlock->NvStorageSize = size;
+ printk(BIOS_SPEW, "S3 NV data @%p, 0x%0zx bytes\n",
+ dataBlock->NvStorage, (size_t)dataBlock->NvStorageSize);
+
return AGESA_SUCCESS;
}

@@ -56,44 +68,13 @@
return AGESA_SUCCESS;
}

-#if ENV_RAMSTAGE
-
-static int spi_SaveS3info(u32 pos, u32 size, u8 *buf, u32 len)
-{
-#if CONFIG(SPI_FLASH)
- struct spi_flash flash;
-
- spi_init();
- if (spi_flash_probe(0, 0, &flash))
- return -1;
-
- spi_flash_volatile_group_begin(&flash);
-
- spi_flash_erase(&flash, pos, size);
- spi_flash_write(&flash, pos, sizeof(len), &len);
- spi_flash_write(&flash, pos + sizeof(len), len, buf);
-
- spi_flash_volatile_group_end(&flash);
- return 0;
-#else
- return -1;
-#endif
-}
-
AGESA_STATUS OemS3Save(AMD_S3_PARAMS *dataBlock)
{
- uintptr_t pos, size;
-
- /* To be consumed in AmdInitResume. */
- get_s3nv_data(&pos, &size);
- if (size && dataBlock->NvStorageSize)
- spi_SaveS3info(pos, size, dataBlock->NvStorage,
- dataBlock->NvStorageSize);
- else
- printk(BIOS_EMERG,
- "Error: Cannot store memory training results in SPI.\n"
- "Error: S3 resume will not be possible.\n"
- );
+ if (mrc_cache_stash_data(MRC_TRAINING_DATA, DEFAULT_MRC_VERSION,
+ dataBlock->NvStorage, dataBlock->NvStorageSize) < 0) {
+ printk(BIOS_ERR, "Failed to stash MRC data\n");
+ return AGESA_CRITICAL;
+ }

/* To be consumed in AmdS3LateRestore. */
char *heap = cbmem_add(CBMEM_ID_RESUME_SCRATCH, HIGH_MEMORY_SCRATCH);
@@ -107,5 +88,3 @@

return AGESA_SUCCESS;
}
-
-#endif /* ENV_RAMSTAGE */

To view, visit change 44295. To unsubscribe, or for help writing mail filters, visit settings.

Gerrit-Project: coreboot
Gerrit-Branch: master
Gerrit-Change-Id: I0f4f36dcead52a6c550fb5e606772e0a99029872
Gerrit-Change-Number: 44295
Gerrit-PatchSet: 1
Gerrit-Owner: Arthur Heymans <arthur@aheymans.xyz>
Gerrit-Reviewer: Martin Roth <martinroth@google.com>
Gerrit-Reviewer: Patrick Georgi <pgeorgi@google.com>
Gerrit-MessageType: newchange