diff options
author | Marc Jones <marcj303@gmail.com> | 2017-05-15 18:55:11 -0600 |
---|---|---|
committer | Martin Roth <martinroth@google.com> | 2017-06-26 00:46:18 +0000 |
commit | 1587dc8a2b4ddfe110cd0239c6506a320cccac96 (patch) | |
tree | ab9b3b3ae63461e9fa8caf4c3fe4410f78f664c3 /src/soc/amd/common | |
parent | 21cde8b83227fa324f246672b1e2d58408ea6bf8 (diff) | |
download | coreboot-1587dc8a2b4ddfe110cd0239c6506a320cccac96.tar.xz |
soc/amd/stoneyridge: Add northbridge support
Copy northbridge files from northbridge/amd/pi/00670F00
to soc/amd/stoneyridge and soc/amd/common.
Changes:
- update chip_ops and device_ops
- remove multi-node support
- clean up Kconfig and Makefile
Change-Id: Ie86b4d744900f23502068517ece5bcea6c128993
Signed-off-by: Marc Jones <marcj303@gmail.com>
Reviewed-on: https://review.coreboot.org/19724
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
Reviewed-by: Martin Roth <martinroth@google.com>
Diffstat (limited to 'src/soc/amd/common')
-rw-r--r-- | src/soc/amd/common/BiosCallOuts.h | 65 | ||||
-rw-r--r-- | src/soc/amd/common/Makefile.inc | 4 | ||||
-rw-r--r-- | src/soc/amd/common/agesawrapper.c | 416 | ||||
-rw-r--r-- | src/soc/amd/common/agesawrapper.h | 63 | ||||
-rw-r--r-- | src/soc/amd/common/agesawrapper_call.h | 58 | ||||
-rw-r--r-- | src/soc/amd/common/amd_late_init.c | 4 | ||||
-rw-r--r-- | src/soc/amd/common/def_callouts.c | 141 | ||||
-rw-r--r-- | src/soc/amd/common/dimmSpd.h | 25 |
8 files changed, 774 insertions, 2 deletions
diff --git a/src/soc/amd/common/BiosCallOuts.h b/src/soc/amd/common/BiosCallOuts.h new file mode 100644 index 0000000000..ac953cac56 --- /dev/null +++ b/src/soc/amd/common/BiosCallOuts.h @@ -0,0 +1,65 @@ +/* + * This file is part of the coreboot project. + * + * Copyright (C) 2011,2012 Advanced Micro Devices, Inc. + * Copyright (C) 2013 Sage Electronic Engineering, LLC + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef CALLOUTS_AMD_AGESA_H +#define CALLOUTS_AMD_AGESA_H + +#include <Porting.h> +#include <AGESA.h> + +#define BIOS_HEAP_START_ADDRESS 0x010000000 +#define BIOS_HEAP_SIZE 0x30000 +#define BSP_STACK_BASE_ADDR 0x30000 + +typedef struct _BIOS_HEAP_MANAGER { + UINT32 StartOfAllocatedNodes; + UINT32 StartOfFreedNodes; +} BIOS_HEAP_MANAGER; + +typedef struct _BIOS_BUFFER_NODE { + UINT32 BufferHandle; + UINT32 BufferSize; + UINT32 NextNodeOffset; +} BIOS_BUFFER_NODE; + +UINT32 GetHeapBase(AMD_CONFIG_PARAMS *StdHeader); +void EmptyHeap(void); + +AGESA_STATUS agesa_AllocateBuffer (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_DeallocateBuffer (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_LocateBuffer (UINT32 Func, UINT32 Data, VOID *ConfigPtr); + +AGESA_STATUS agesa_NoopUnsupported (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_NoopSuccess (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_EmptyIdsInitData (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_Reset (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_RunFuncOnAp (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_GfxGetVbiosImage(UINT32 Func, UINT32 FchData, VOID *ConfigPrt); + +AGESA_STATUS agesa_ReadSpd (UINT32 Func, UINT32 Data, VOID *ConfigPtr); +AGESA_STATUS agesa_ReadSpd_from_cbfs(UINT32 Func, UINT32 Data, VOID *ConfigPtr); + +AGESA_STATUS GetBiosCallout (UINT32 Func, UINT32 Data, VOID *ConfigPtr); + +typedef struct { + UINT32 CalloutName; + CALLOUT_ENTRY CalloutPtr; +} BIOS_CALLOUT_STRUCT; + +extern const BIOS_CALLOUT_STRUCT BiosCallouts[]; +extern const int BiosCalloutsLen; + +#endif /* CALLOUTS_AMD_AGESA_H */ diff --git a/src/soc/amd/common/Makefile.inc b/src/soc/amd/common/Makefile.inc index 1a4927efaa..9d4588d079 100644 --- a/src/soc/amd/common/Makefile.inc +++ b/src/soc/amd/common/Makefile.inc @@ -2,10 +2,14 @@ ifeq ($(CONFIG_SOC_AMD_COMMON),y) cpu_incs-y += $(src)/soc/amd/common/cache_as_ram.inc +romstage-y += agesawrapper.c +romstage-y += def_callouts.c romstage-y += heapmanager.c +ramstage-y += agesawrapper.c ramstage-y += amd_late_init.c ramstage-y += amd_pci_util.c +ramstage-y += def_callouts.c ramstage-y += heapmanager.c ramstage-$(CONFIG_SPI_FLASH) += spi.c diff --git a/src/soc/amd/common/agesawrapper.c b/src/soc/amd/common/agesawrapper.c new file mode 100644 index 0000000000..b7c19cb72a --- /dev/null +++ b/src/soc/amd/common/agesawrapper.c @@ -0,0 +1,416 @@ +/* + * This file is part of the coreboot project. + * + * Copyright (C) 2012 - 2014 Advanced Micro Devices, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <AGESA.h> +#include <cbfs.h> +#include <cbmem.h> +#include <delay.h> +#include <cpu/x86/mtrr.h> +#include <cpuRegisters.h> +#include <FchPlatform.h> +#include <heapManager.h> +#include <agesawrapper.h> +#include <BiosCallOuts.h> + +void __attribute__((weak)) OemPostParams(AMD_POST_PARAMS *PostParams) {} + +#define FILECODE UNASSIGNED_FILE_FILECODE + +#ifndef __PRE_RAM__ +/* ACPI table pointers returned by AmdInitLate */ +static void *DmiTable = NULL; +static void *AcpiPstate = NULL; +static void *AcpiSrat = NULL; +static void *AcpiSlit = NULL; + +static void *AcpiWheaMce = NULL; +static void *AcpiWheaCmc = NULL; +static void *AcpiAlib = NULL; +static void *AcpiIvrs = NULL; +static void *AcpiCrat = NULL; +#endif /* #ifndef __PRE_RAM__ */ + +AGESA_STATUS agesawrapper_amdinitreset(void) +{ + AGESA_STATUS status; + AMD_INTERFACE_PARAMS AmdParamStruct; + AMD_RESET_PARAMS AmdResetParams; + + LibAmdMemFill (&AmdParamStruct, + 0, + sizeof(AMD_INTERFACE_PARAMS), + &(AmdParamStruct.StdHeader)); + + LibAmdMemFill (&AmdResetParams, + 0, + sizeof(AMD_RESET_PARAMS), + &(AmdResetParams.StdHeader)); + + AmdParamStruct.AgesaFunctionName = AMD_INIT_RESET; + AmdParamStruct.AllocationMethod = ByHost; + AmdParamStruct.NewStructSize = sizeof(AMD_RESET_PARAMS); + AmdParamStruct.NewStructPtr = &AmdResetParams; + AmdParamStruct.StdHeader.AltImageBasePtr = 0; + AmdParamStruct.StdHeader.CalloutPtr = &GetBiosCallout; + AmdParamStruct.StdHeader.Func = 0; + AmdParamStruct.StdHeader.ImageBasePtr = 0; + AmdCreateStruct (&AmdParamStruct); + + AmdResetParams.FchInterface.Xhci0Enable = IS_ENABLED(CONFIG_STONEYRIDGE_XHCI_ENABLE); + + AmdResetParams.FchInterface.SataEnable = !((CONFIG_STONEYRIDGE_SATA_MODE == 0) || (CONFIG_STONEYRIDGE_SATA_MODE == 3)); + AmdResetParams.FchInterface.IdeEnable = (CONFIG_STONEYRIDGE_SATA_MODE == 0) || (CONFIG_STONEYRIDGE_SATA_MODE == 3); + + status = AmdInitReset(&AmdResetParams); + if (status != AGESA_SUCCESS) agesawrapper_amdreadeventlog(AmdParamStruct.StdHeader.HeapStatus); + AmdReleaseStruct (&AmdParamStruct); + return status; +} + +AGESA_STATUS agesawrapper_amdinitearly(void) +{ + AGESA_STATUS status; + AMD_INTERFACE_PARAMS AmdParamStruct; + AMD_EARLY_PARAMS *AmdEarlyParamsPtr; + + LibAmdMemFill (&AmdParamStruct, + 0, + sizeof(AMD_INTERFACE_PARAMS), + &(AmdParamStruct.StdHeader)); + + AmdParamStruct.AgesaFunctionName = AMD_INIT_EARLY; + AmdParamStruct.AllocationMethod = PreMemHeap; + AmdParamStruct.StdHeader.AltImageBasePtr = 0; + AmdParamStruct.StdHeader.CalloutPtr = &GetBiosCallout; + AmdParamStruct.StdHeader.Func = 0; + AmdParamStruct.StdHeader.ImageBasePtr = 0; + AmdCreateStruct (&AmdParamStruct); + + AmdEarlyParamsPtr = (AMD_EARLY_PARAMS *)AmdParamStruct.NewStructPtr; + OemCustomizeInitEarly (AmdEarlyParamsPtr); + + AmdEarlyParamsPtr->GnbConfig.PsppPolicy = PsppDisabled; + status = AmdInitEarly ((AMD_EARLY_PARAMS *)AmdParamStruct.NewStructPtr); + + if (status != AGESA_SUCCESS) agesawrapper_amdreadeventlog(AmdParamStruct.StdHeader.HeapStatus); + AmdReleaseStruct (&AmdParamStruct); + + return status; +} + +AGESA_STATUS agesawrapper_amdinitpost(void) +{ + AGESA_STATUS status; + AMD_INTERFACE_PARAMS AmdParamStruct; + AMD_POST_PARAMS *PostParams; + + LibAmdMemFill (&AmdParamStruct, + 0, + sizeof(AMD_INTERFACE_PARAMS), + &(AmdParamStruct.StdHeader)); + + AmdParamStruct.AgesaFunctionName = AMD_INIT_POST; + AmdParamStruct.AllocationMethod = PreMemHeap; + AmdParamStruct.StdHeader.AltImageBasePtr = NULL; + AmdParamStruct.StdHeader.CalloutPtr = &GetBiosCallout; + AmdParamStruct.StdHeader.Func = 0; + AmdParamStruct.StdHeader.ImageBasePtr = 0; + + AmdCreateStruct (&AmdParamStruct); + PostParams = (AMD_POST_PARAMS *)AmdParamStruct.NewStructPtr; + + // Do not use IS_ENABLED here. CONFIG_GFXUMA should always have a value. Allow + // the compiler to flag the error if CONFIG_GFXUMA is not set. + PostParams->MemConfig.UmaMode = CONFIG_GFXUMA ? UMA_AUTO : UMA_NONE; + PostParams->MemConfig.UmaSize = 0; + PostParams->MemConfig.BottomIo = (UINT16) + (CONFIG_BOTTOMIO_POSITION >> 24); + + OemPostParams(PostParams); + + status = AmdInitPost (PostParams); + + /* If UMA is enabled we currently have it below TOP_MEM as well. + * UMA may or may not be cacheable, so Sub4GCacheTop could be + * higher than UmaBase. With UMA_NONE we see UmaBase==0. */ + if (PostParams->MemConfig.UmaBase) + backup_top_of_low_cacheable(PostParams->MemConfig.UmaBase << 16); + else + backup_top_of_low_cacheable(PostParams->MemConfig.Sub4GCacheTop); + + + printk( + BIOS_SPEW, + "setup_uma_memory: umamode %s\n", + (PostParams->MemConfig.UmaMode == UMA_AUTO) ? "UMA_AUTO" : + (PostParams->MemConfig.UmaMode == UMA_SPECIFIED) ? "UMA_SPECIFIED" : + (PostParams->MemConfig.UmaMode == UMA_NONE) ? "UMA_NONE" : + "unknown" + ); + printk( + BIOS_SPEW, + "setup_uma_memory: syslimit 0x%08llX, bottomio 0x%08lx\n", + (unsigned long long)(PostParams->MemConfig.SysLimit) << 16, + (unsigned long)(PostParams->MemConfig.BottomIo) << 16 + ); + printk( + BIOS_SPEW, + "setup_uma_memory: uma size %luMB, uma start 0x%08lx\n", + (unsigned long)(PostParams->MemConfig.UmaSize) >> (20 - 16), + (unsigned long)(PostParams->MemConfig.UmaBase) << 16 + ); + + if (status != AGESA_SUCCESS) agesawrapper_amdreadeventlog(PostParams->StdHeader.HeapStatus); + AmdReleaseStruct (&AmdParamStruct); + /* Initialize heap space */ + EmptyHeap(); + + return status; +} + +AGESA_STATUS agesawrapper_amdinitenv(void) +{ + AGESA_STATUS status; + AMD_INTERFACE_PARAMS AmdParamStruct; + AMD_ENV_PARAMS *EnvParam; + + LibAmdMemFill (&AmdParamStruct, + 0, + sizeof(AMD_INTERFACE_PARAMS), + &(AmdParamStruct.StdHeader)); + + AmdParamStruct.AgesaFunctionName = AMD_INIT_ENV; + AmdParamStruct.AllocationMethod = PostMemDram; + AmdParamStruct.StdHeader.AltImageBasePtr = 0; + AmdParamStruct.StdHeader.CalloutPtr = &GetBiosCallout; + AmdParamStruct.StdHeader.Func = 0; + AmdParamStruct.StdHeader.ImageBasePtr = 0; + status = AmdCreateStruct (&AmdParamStruct); + EnvParam = (AMD_ENV_PARAMS *)AmdParamStruct.NewStructPtr; + + EnvParam->FchInterface.AzaliaController = AzEnable; + EnvParam->FchInterface.SataClass = CONFIG_STONEYRIDGE_SATA_MODE; + EnvParam->FchInterface.SataEnable = !((CONFIG_STONEYRIDGE_SATA_MODE == 0) || (CONFIG_STONEYRIDGE_SATA_MODE == 3)); + EnvParam->FchInterface.IdeEnable = (CONFIG_STONEYRIDGE_SATA_MODE == 0) || (CONFIG_STONEYRIDGE_SATA_MODE == 3); + EnvParam->FchInterface.SataIdeMode = (CONFIG_STONEYRIDGE_SATA_MODE == 3); + EnvParam->GnbEnvConfiguration.IommuSupport = FALSE; + + status = AmdInitEnv (EnvParam); + if (status != AGESA_SUCCESS) agesawrapper_amdreadeventlog(EnvParam->StdHeader.HeapStatus); + /* Initialize Subordinate Bus Number and Secondary Bus Number + * In platform BIOS this address is allocated by PCI enumeration code + Modify D1F0x18 + */ + + return status; +} + +#ifndef __PRE_RAM__ +VOID* agesawrapper_getlateinitptr (int pick) +{ + switch (pick) { + case PICK_DMI: + return DmiTable; + case PICK_PSTATE: + return AcpiPstate; + case PICK_SRAT: + return AcpiSrat; + case PICK_SLIT: + return AcpiSlit; + case PICK_WHEA_MCE: + return AcpiWheaMce; + case PICK_WHEA_CMC: + return AcpiWheaCmc; + case PICK_ALIB: + return AcpiAlib; + case PICK_IVRS: + return AcpiIvrs; + case PICK_CRAT: + return AcpiCrat; + default: + return NULL; + } +} +#endif /* #ifndef __PRE_RAM__ */ + +AGESA_STATUS agesawrapper_amdinitmid(void) +{ + AGESA_STATUS status; + AMD_INTERFACE_PARAMS AmdParamStruct; + AMD_MID_PARAMS *MidParam; + + /* Enable MMIO on AMD CPU Address Map Controller */ + amd_initcpuio (); + + LibAmdMemFill (&AmdParamStruct, + 0, + sizeof(AMD_INTERFACE_PARAMS), + &(AmdParamStruct.StdHeader)); + + AmdParamStruct.AgesaFunctionName = AMD_INIT_MID; + AmdParamStruct.AllocationMethod = PostMemDram; + AmdParamStruct.StdHeader.AltImageBasePtr = 0; + AmdParamStruct.StdHeader.CalloutPtr = &GetBiosCallout; + AmdParamStruct.StdHeader.Func = 0; + AmdParamStruct.StdHeader.ImageBasePtr = 0; + + AmdCreateStruct (&AmdParamStruct); + MidParam = (AMD_MID_PARAMS *)AmdParamStruct.NewStructPtr; + + MidParam->GnbMidConfiguration.iGpuVgaMode = 0;/* 0 iGpuVgaAdapter, 1 iGpuVgaNonAdapter; */ + MidParam->GnbMidConfiguration.GnbIoapicAddress = 0xFEC20000; + + MidParam->FchInterface.AzaliaController = AzEnable; + MidParam->FchInterface.SataClass = CONFIG_STONEYRIDGE_SATA_MODE; + MidParam->FchInterface.SataEnable = !((CONFIG_STONEYRIDGE_SATA_MODE == 0) || (CONFIG_STONEYRIDGE_SATA_MODE == 3)); + MidParam->FchInterface.IdeEnable = (CONFIG_STONEYRIDGE_SATA_MODE == 0) || (CONFIG_STONEYRIDGE_SATA_MODE == 3); + MidParam->FchInterface.SataIdeMode = (CONFIG_STONEYRIDGE_SATA_MODE == 3); + + status = AmdInitMid ((AMD_MID_PARAMS *)AmdParamStruct.NewStructPtr); + if (status != AGESA_SUCCESS) agesawrapper_amdreadeventlog(AmdParamStruct.StdHeader.HeapStatus); + AmdReleaseStruct (&AmdParamStruct); + + return status; +} + +#ifndef __PRE_RAM__ +AGESA_STATUS agesawrapper_amdinitlate(void) +{ + AGESA_STATUS Status; + AMD_INTERFACE_PARAMS AmdParamStruct; + AMD_LATE_PARAMS *AmdLateParams; + + LibAmdMemFill (&AmdParamStruct, + 0, + sizeof(AMD_INTERFACE_PARAMS), + &(AmdParamStruct.StdHeader)); + + AmdParamStruct.AgesaFunctionName = AMD_INIT_LATE; + AmdParamStruct.AllocationMethod = PostMemDram; + AmdParamStruct.StdHeader.AltImageBasePtr = 0; + AmdParamStruct.StdHeader.CalloutPtr = &GetBiosCallout; + AmdParamStruct.StdHeader.HeapStatus = HEAP_SYSTEM_MEM; + AmdParamStruct.StdHeader.Func = 0; + AmdParamStruct.StdHeader.ImageBasePtr = 0; + + /* NOTE: if not call amdcreatestruct, the initializer(AmdInitLateInitializer) would not be called */ + AmdCreateStruct(&AmdParamStruct); + AmdLateParams = (AMD_LATE_PARAMS *)AmdParamStruct.NewStructPtr; + Status = AmdInitLate(AmdLateParams); + if (Status != AGESA_SUCCESS) { + agesawrapper_amdreadeventlog(AmdLateParams->StdHeader.HeapStatus); + ASSERT(Status == AGESA_SUCCESS); + } + + DmiTable = AmdLateParams->DmiTable; + AcpiPstate = AmdLateParams->AcpiPState; + + AcpiWheaMce = AmdLateParams->AcpiWheaMce; + AcpiWheaCmc = AmdLateParams->AcpiWheaCmc; + AcpiAlib = AmdLateParams->AcpiAlib; + AcpiIvrs = AmdLateParams->AcpiIvrs; + AcpiCrat = AmdLateParams->AcpiCrat; + + printk(BIOS_DEBUG, "DmiTable:%x, AcpiPstatein: %x, AcpiSrat:%x," + "AcpiSlit:%x, Mce:%x, Cmc:%x," + "Alib:%x, AcpiIvrs:%x in %s\n", + (unsigned int)DmiTable, (unsigned int)AcpiPstate, (unsigned int)AcpiSrat, + (unsigned int)AcpiSlit, (unsigned int)AcpiWheaMce, (unsigned int)AcpiWheaCmc, + (unsigned int)AcpiAlib, (unsigned int)AcpiIvrs, __func__); + + /* AmdReleaseStruct (&AmdParamStruct); */ + return Status; +} +#endif /* #ifndef __PRE_RAM__ */ + +AGESA_STATUS agesawrapper_amdlaterunaptask ( + UINT32 Func, + UINT32 Data, + VOID *ConfigPtr + ) +{ + AGESA_STATUS Status; + AP_EXE_PARAMS ApExeParams; + + LibAmdMemFill (&ApExeParams, + 0, + sizeof(AP_EXE_PARAMS), + &(ApExeParams.StdHeader)); + + ApExeParams.StdHeader.AltImageBasePtr = 0; + ApExeParams.StdHeader.CalloutPtr = &GetBiosCallout; + ApExeParams.StdHeader.Func = 0; + ApExeParams.StdHeader.ImageBasePtr = 0; + ApExeParams.FunctionNumber = Func; + ApExeParams.RelatedDataBlock = ConfigPtr; + + Status = AmdLateRunApTask (&ApExeParams); + if (Status != AGESA_SUCCESS) { + /* agesawrapper_amdreadeventlog(); */ + ASSERT(Status == AGESA_SUCCESS); + } + + return Status; +} + +AGESA_STATUS agesawrapper_amdreadeventlog (UINT8 HeapStatus) +{ + AGESA_STATUS Status; + EVENT_PARAMS AmdEventParams; + + LibAmdMemFill (&AmdEventParams, + 0, + sizeof(EVENT_PARAMS), + &(AmdEventParams.StdHeader)); + + AmdEventParams.StdHeader.AltImageBasePtr = 0; + AmdEventParams.StdHeader.CalloutPtr = &GetBiosCallout; + AmdEventParams.StdHeader.Func = 0; + AmdEventParams.StdHeader.ImageBasePtr = 0; + AmdEventParams.StdHeader.HeapStatus = HeapStatus; + Status = AmdReadEventLog (&AmdEventParams); + while (AmdEventParams.EventClass != 0) { + printk(BIOS_DEBUG,"\nEventLog: EventClass = %x, EventInfo = %x.\n", (unsigned int)AmdEventParams.EventClass,(unsigned int)AmdEventParams.EventInfo); + printk(BIOS_DEBUG," Param1 = %x, Param2 = %x.\n",(unsigned int)AmdEventParams.DataParam1, (unsigned int)AmdEventParams.DataParam2); + printk(BIOS_DEBUG," Param3 = %x, Param4 = %x.\n",(unsigned int)AmdEventParams.DataParam3, (unsigned int)AmdEventParams.DataParam4); + Status = AmdReadEventLog (&AmdEventParams); + } + + return Status; +} + +const void *agesawrapper_locate_module (const CHAR8 name[8]) +{ + const void* agesa; + const AMD_IMAGE_HEADER* image; + const AMD_MODULE_HEADER* module; + size_t file_size; + + if (IS_ENABLED(CONFIG_VBOOT)) { + /* Use phys. location in flash and prevent vboot from searching cbmem */ + agesa = (void *)CONFIG_AGESA_BINARY_PI_LOCATION; + file_size = 0x100000; + } else { + agesa = cbfs_boot_map_with_leak((const char *)CONFIG_CBFS_AGESA_NAME, + CBFS_TYPE_RAW, &file_size); + } + + if (!agesa) + return NULL; + image = LibAmdLocateImage(agesa, agesa + file_size - 1, 4096, name); + module = (AMD_MODULE_HEADER*)image->ModuleInfoOffset; + + return module; +} diff --git a/src/soc/amd/common/agesawrapper.h b/src/soc/amd/common/agesawrapper.h new file mode 100644 index 0000000000..b7f60ad3f0 --- /dev/null +++ b/src/soc/amd/common/agesawrapper.h @@ -0,0 +1,63 @@ +/* + * This file is part of the coreboot project. + * + * Copyright (C) 2012 Advanced Micro Devices, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef _AGESAWRAPPER_H_ +#define _AGESAWRAPPER_H_ + +#include <stdint.h> +#include <Porting.h> +#include <AGESA.h> + +/* TODO: Add a kconfig option to name the AGESA ROM file in CBFS */ +#ifndef CONFIG_CBFS_AGESA_NAME +#define CONFIG_CBFS_AGESA_NAME "AGESA" +#endif + +enum { + PICK_DMI, /* DMI Interface */ + PICK_PSTATE, /* Acpi Pstate SSDT Table */ + PICK_SRAT, /* SRAT Table */ + PICK_SLIT, /* SLIT Table */ + PICK_WHEA_MCE, /* WHEA MCE table */ + PICK_WHEA_CMC, /* WHEA CMV table */ + PICK_ALIB, /* SACPI SSDT table with ALIB implementation */ + PICK_IVRS, /* IOMMU ACPI IVRS(I/O Virtualization Reporting Structure) table */ + PICK_CRAT, +}; + +AGESA_STATUS agesawrapper_amdinitreset(void); +AGESA_STATUS agesawrapper_amdinitearly(void); +AGESA_STATUS agesawrapper_amdinitenv(void); +AGESA_STATUS agesawrapper_amdinitlate(void); +AGESA_STATUS agesawrapper_amdinitpost(void); +AGESA_STATUS agesawrapper_amdinitmid(void); +AGESA_STATUS agesawrapper_amdreadeventlog(UINT8 HeapStatus); +void *agesawrapper_getlateinitptr(int pick); +AGESA_STATUS agesawrapper_amdlaterunaptask(UINT32 Func, UINT32 Data, void *ConfigPtr); +AGESA_STATUS agesawrapper_amdS3Save(void); +AGESA_STATUS agesawrapper_amdinitresume(void); +AGESA_STATUS agesawrapper_amds3laterestore(void); + +AGESA_STATUS agesawrapper_fchs3earlyrestore(void); +AGESA_STATUS agesawrapper_fchs3laterestore(void); + +VOID OemCustomizeInitEarly (IN OUT AMD_EARLY_PARAMS *InitEarly); +VOID amd_initcpuio(void); +VOID amd_initmmio(void); +const void *agesawrapper_locate_module (const CHAR8 name[8]); + +void OemPostParams(AMD_POST_PARAMS *PostParams); + +#endif /* _AGESAWRAPPER_H_ */ diff --git a/src/soc/amd/common/agesawrapper_call.h b/src/soc/amd/common/agesawrapper_call.h new file mode 100644 index 0000000000..925a4240c0 --- /dev/null +++ b/src/soc/amd/common/agesawrapper_call.h @@ -0,0 +1,58 @@ +/* + * This file is part of the coreboot project. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef _AGESAWRAPPER_CALL_H_ +#define _AGESAWRAPPER_CALL_H_ + +#include <stdint.h> +#include <console/console.h> +#include <AGESA.h> + +/* + * Possible AGESA_STATUS values: + * + * 0x0 = AGESA_SUCCESS + * 0x1 = AGESA_UNSUPPORTED + * 0x2 = AGESA_BOUNDS_CHK + * 0x3 = AGESA_ALERT + * 0x4 = AGESA_WARNING + * 0x5 = AGESA_ERROR + * 0x6 = AGESA_CRITICAL + * 0x7 = AGESA_FATAL + */ +static const char * decodeAGESA_STATUS(AGESA_STATUS sret) +{ + const char* statusStrings[] = { "AGESA_SUCCESS", "AGESA_UNSUPPORTED", + "AGESA_BOUNDS_CHK", "AGESA_ALERT", + "AGESA_WARNING", "AGESA_ERROR", + "AGESA_CRITICAL", "AGESA_FATAL" + }; + if (sret > 7) return "unknown"; /* Non-AGESA error code */ + return statusStrings[sret]; +} + +static inline u32 do_agesawrapper(AGESA_STATUS (*func)(void), const char *name) +{ + AGESA_STATUS ret; + printk(BIOS_DEBUG, "agesawrapper_%s() entry\n", name); + ret = func(); + printk(BIOS_DEBUG, "agesawrapper_%s() returned %s\n", + name, decodeAGESA_STATUS(ret)); + return (u32)ret; +} + +#define AGESAWRAPPER(func) do_agesawrapper(agesawrapper_ ## func, #func) + +#define AGESAWRAPPER_PRE_CONSOLE(func) agesawrapper_ ## func() + +#endif diff --git a/src/soc/amd/common/amd_late_init.c b/src/soc/amd/common/amd_late_init.c index d9a5b43743..3aee23ca7e 100644 --- a/src/soc/amd/common/amd_late_init.c +++ b/src/soc/amd/common/amd_late_init.c @@ -20,8 +20,8 @@ #include <device/pci_def.h> #include <device/pci_ops.h> -#include <northbridge/amd/pi/agesawrapper.h> -#include <northbridge/amd/pi/agesawrapper_call.h> +#include <agesawrapper.h> +#include <agesawrapper_call.h> static void agesawrapper_post_device(void *unused) { diff --git a/src/soc/amd/common/def_callouts.c b/src/soc/amd/common/def_callouts.c new file mode 100644 index 0000000000..52b502c023 --- /dev/null +++ b/src/soc/amd/common/def_callouts.c @@ -0,0 +1,141 @@ +/* + * This file is part of the coreboot project. + * + * Copyright (C) 2011 Advanced Micro Devices, Inc. + * Copyright (C) 2013 Sage Electronic Engineering, LLC + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <cbfs.h> +#include <spd_bin.h> + +#include <AGESA.h> +#include <amdlib.h> +#include <Ids.h> +#include <agesawrapper.h> +#include <BiosCallOuts.h> +#include <dimmSpd.h> + +AGESA_STATUS GetBiosCallout (UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + UINTN i; + + for (i = 0; i < BiosCalloutsLen; i++) { + if (BiosCallouts[i].CalloutName == Func) + break; + } + if (i >= BiosCalloutsLen) + return AGESA_UNSUPPORTED; + + return BiosCallouts[i].CalloutPtr (Func, Data, ConfigPtr); +} + +AGESA_STATUS agesa_NoopUnsupported (UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + return AGESA_UNSUPPORTED; +} + +AGESA_STATUS agesa_NoopSuccess (UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + return AGESA_SUCCESS; +} + +AGESA_STATUS agesa_EmptyIdsInitData (UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + IDS_NV_ITEM *IdsPtr = ((IDS_CALLOUT_STRUCT *) ConfigPtr)->IdsNvPtr; + if (Data == IDS_CALLOUT_INIT) + IdsPtr[0].IdsNvValue = IdsPtr[0].IdsNvId = 0xffff; + return AGESA_SUCCESS; +} + +AGESA_STATUS agesa_Reset (UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + AGESA_STATUS Status; + UINT8 Value; + UINTN ResetType; + AMD_CONFIG_PARAMS *StdHeader; + + ResetType = Data; + StdHeader = ConfigPtr; + + // + // Perform the RESET based upon the ResetType. In case of + // WARM_RESET_WHENVER and COLD_RESET_WHENEVER, the request will go to + // AmdResetManager. During the critical condition, where reset is required + // immediately, the reset will be invoked directly by writing 0x04 to port + // 0xCF9 (Reset Port). + // + switch (ResetType) { + case WARM_RESET_WHENEVER: + case COLD_RESET_WHENEVER: + break; + + case WARM_RESET_IMMEDIATELY: + case COLD_RESET_IMMEDIATELY: + Value = 0x06; + LibAmdIoWrite (AccessWidth8, 0xCf9, &Value, StdHeader); + break; + + default: + break; + } + + Status = 0; + return Status; +} + +AGESA_STATUS agesa_RunFuncOnAp (UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + AGESA_STATUS Status; + + Status = agesawrapper_amdlaterunaptask (Func, Data, ConfigPtr); + return Status; +} + +AGESA_STATUS agesa_GfxGetVbiosImage(UINT32 Func, UINT32 FchData, VOID *ConfigPrt) +{ + GFX_VBIOS_IMAGE_INFO *pVbiosImageInfo = (GFX_VBIOS_IMAGE_INFO *)ConfigPrt; + pVbiosImageInfo->ImagePtr = cbfs_boot_map_with_leak( + "pci"CONFIG_VGA_BIOS_ID".rom", + CBFS_TYPE_OPTIONROM, NULL); + printk(BIOS_DEBUG, "agesa_GfxGetVbiosImage: IMGptr=%p\n", pVbiosImageInfo->ImagePtr); + return (pVbiosImageInfo->ImagePtr ? AGESA_SUCCESS : AGESA_WARNING); +} + +AGESA_STATUS agesa_ReadSpd (UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + AGESA_STATUS Status = AGESA_UNSUPPORTED; +#ifdef __PRE_RAM__ + Status = AmdMemoryReadSPD (Func, Data, ConfigPtr); +#endif + return Status; +} + +AGESA_STATUS agesa_ReadSpd_from_cbfs(UINT32 Func, UINT32 Data, VOID *ConfigPtr) +{ + AGESA_STATUS Status = AGESA_UNSUPPORTED; +#ifdef __PRE_RAM__ + AGESA_READ_SPD_PARAMS *info = ConfigPtr; + if (info->MemChannelId > 0) + return AGESA_UNSUPPORTED; + if (info->SocketId != 0) + return AGESA_UNSUPPORTED; + if (info->DimmId != 0) + return AGESA_UNSUPPORTED; + + /* Read index 0, first SPD_SIZE bytes of spd.bin file. */ + if (read_ddr3_spd_from_cbfs((u8*)info->Buffer, 0) < 0) + die("No SPD data\n"); + + Status = AGESA_SUCCESS; +#endif + return Status; +} diff --git a/src/soc/amd/common/dimmSpd.h b/src/soc/amd/common/dimmSpd.h new file mode 100644 index 0000000000..1ad45469e2 --- /dev/null +++ b/src/soc/amd/common/dimmSpd.h @@ -0,0 +1,25 @@ +/* + * This file is part of the coreboot project. + * + * Copyright (C) 2012 Advanced Micro Devices, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef _DIMMSPD_H_ +#define _DIMMSPD_H_ + +AGESA_STATUS +AmdMemoryReadSPD (IN UINT32 Func, IN UINT32 Data, IN OUT AGESA_READ_SPD_PARAMS *SpdData); + +int hudson_readSpd(int spdAddress, char *buf, size_t len); +int smbus_readSpd(int spdAddress, char *buf, size_t len); + +#endif |