Fix for 'ShowMemoryResources' command with BIOS having PMTT Rev: 0x1 table.
The helper function used to retrieve the DDR phyical size looks at
only PMTT Rev: 0x2 table. Updated the function to also parse PMTT 0X1
table to get the DDR size thus maintaining backwards comptability.
Fixes
@@ -8846,12 +8846,10 @@ GetDDRPhysicalSize(
)
{
EFI_STATUS ReturnCode = EFI_LOAD_ERROR;
+ TABLE_HEADER *pTable = NULL;
+ DIMM_INFO *pDimmInfo = NULL;
UINT64 TotalDDRMemorySize = 0;
UINT16 Index = 0;
- ParsedPmttHeader *pPmttHead;
- UINT32 DDRModulesNum;
- PMTT_MODULE_INFO **ppDDRModules;
- DIMM_INFO *pDimmInfo = NULL;
NVDIMM_ENTRY();
@@ -8861,11 +8859,50 @@ GetDDRPhysicalSize(
goto Finish;
}
+ ReturnCode = GetAcpiPMTT(NULL, (VOID *)&pTable);
+ if (EFI_ERROR(ReturnCode)) {
+ NVDIMM_DBG("Unable to retrieve PMTT table.");
+ goto Finish;
+ }
+
+ if (IS_ACPI_REV_MAJ_0_MIN_1(pTable->Revision)) {
+ PMTT_TABLE *pPMTT = (PMTT_TABLE *)pTable;
+ PMTT_COMMON_HEADER *pCommonHeader = NULL;
+ PMTT_MODULE *pModule = NULL;
+ UINT64 Offset = 0;
+
+ Offset = sizeof(pPMTT->Header) + sizeof(pPMTT->Reserved);
+ //Iterate through the table and look for DDR Modules
+ while (Offset < pPMTT->Header.Length) {
+ pCommonHeader = (PMTT_COMMON_HEADER *)(((UINT8 *)pPMTT) + Offset);
+ if (pCommonHeader->Type == PMTT_TYPE_SOCKET) {
+ Offset += sizeof(PMTT_SOCKET) + PMTT_COMMON_HDR_LEN;
+ }
+ else if (pCommonHeader->Type == PMTT_TYPE_iMC) {
+ Offset += sizeof(PMTT_iMC) + PMTT_COMMON_HDR_LEN;
+ }
+ else if (pCommonHeader->Type == PMTT_TYPE_MODULE) {
+ pModule = (PMTT_MODULE *)(((UINT8 *)pPMTT) + Offset + PMTT_COMMON_HDR_LEN);
+ if (pModule->SmbiosHandle != PMTT_INVALID_SMBIOS_HANDLE) {
+ if (!(pCommonHeader->Flags & PMTT_DDR_DCPM_FLAG) && (pModule->SizeOfDimm > 0)) {
+ TotalDDRMemorySize += MIB_TO_BYTES(pModule->SizeOfDimm);
+ }
+ }
+ Offset += sizeof(PMTT_MODULE) + PMTT_COMMON_HDR_LEN;
+ }
+ }
+ }
+ else if (IS_ACPI_REV_MAJ_0_MIN_2(pTable->Revision)) {
+ ParsedPmttHeader *pPmttHead = NULL;
+ UINT32 DDRModulesNum;
+ PMTT_MODULE_INFO **ppDDRModules = NULL;
+
pPmttHead = gNvmDimmData->PMEMDev.pPmttHead;
if (NULL == pPmttHead) {
NVDIMM_DBG("Pmtt head not found.");
goto Finish;
}
+
// Get list of DIMM modules from PMTT
DDRModulesNum = pPmttHead->DDRModulesNum;
ppDDRModules = pPmttHead->ppDDRModules;
@@ -8889,6 +8926,7 @@ GetDDRPhysicalSize(
// Get dimm capacity and add it to the total
TotalDDRMemorySize += pDimmInfo->CapacityFromSmbios;
}
+ }
// Set total to the result output
*pResult = TotalDDRMemorySize;
@@ -8897,6 +8935,7 @@ GetDDRPhysicalSize(
Finish:
FREE_POOL_SAFE(pDimmInfo);
+ FREE_POOL_SAFE(pTable);
NVDIMM_EXIT_I64(ReturnCode);
return ReturnCode;
}
