AcpiS3Save could try to check PcdIdentifyMappingPageTablePtr is NULL, if it is not, it means someone else has allocate memory for page table, AcpiS3Save could re-use this memory.

Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: Elvin Li <elvin.li@intel.com>
Signed-off-by: Jiewen Yao <jiewen.yao@intel.com>

git-svn-id: https://svn.code.sf.net/p/edk2/code/trunk/edk2@15910 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
Elvin Li 2014-08-26 12:28:15 +00:00 committed by li-elvin
parent b5040e4c55
commit ac790db940
2 changed files with 66 additions and 57 deletions

View File

@ -328,68 +328,74 @@ S3CreateIdentityMappingPageTables (
VOID *Hob; VOID *Hob;
BOOLEAN Page1GSupport; BOOLEAN Page1GSupport;
Page1GSupport = FALSE; S3NvsPageTableAddress = (EFI_PHYSICAL_ADDRESS) PcdGet64 (PcdIdentifyMappingPageTablePtr);
if (PcdGetBool(PcdUse1GPageTable)) { if (S3NvsPageTableAddress != 0x0) {
AsmCpuid (0x80000000, &RegEax, NULL, NULL, NULL); return S3NvsPageTableAddress;
if (RegEax >= 0x80000001) { } else {
AsmCpuid (0x80000001, NULL, NULL, NULL, &RegEdx); Page1GSupport = FALSE;
if ((RegEdx & BIT26) != 0) { if (PcdGetBool(PcdUse1GPageTable)) {
Page1GSupport = TRUE; AsmCpuid (0x80000000, &RegEax, NULL, NULL, NULL);
if (RegEax >= 0x80000001) {
AsmCpuid (0x80000001, NULL, NULL, NULL, &RegEdx);
if ((RegEdx & BIT26) != 0) {
Page1GSupport = TRUE;
}
} }
} }
}
// //
// Get physical address bits supported. // Get physical address bits supported.
// //
Hob = GetFirstHob (EFI_HOB_TYPE_CPU); Hob = GetFirstHob (EFI_HOB_TYPE_CPU);
if (Hob != NULL) { if (Hob != NULL) {
PhysicalAddressBits = ((EFI_HOB_CPU *) Hob)->SizeOfMemorySpace; PhysicalAddressBits = ((EFI_HOB_CPU *) Hob)->SizeOfMemorySpace;
} else {
AsmCpuid (0x80000000, &RegEax, NULL, NULL, NULL);
if (RegEax >= 0x80000008) {
AsmCpuid (0x80000008, &RegEax, NULL, NULL, NULL);
PhysicalAddressBits = (UINT8) RegEax;
} else { } else {
PhysicalAddressBits = 36; AsmCpuid (0x80000000, &RegEax, NULL, NULL, NULL);
if (RegEax >= 0x80000008) {
AsmCpuid (0x80000008, &RegEax, NULL, NULL, NULL);
PhysicalAddressBits = (UINT8) RegEax;
} else {
PhysicalAddressBits = 36;
}
} }
}
// //
// IA-32e paging translates 48-bit linear addresses to 52-bit physical addresses. // IA-32e paging translates 48-bit linear addresses to 52-bit physical addresses.
// //
ASSERT (PhysicalAddressBits <= 52); ASSERT (PhysicalAddressBits <= 52);
if (PhysicalAddressBits > 48) { if (PhysicalAddressBits > 48) {
PhysicalAddressBits = 48; PhysicalAddressBits = 48;
} }
// //
// Calculate the table entries needed. // Calculate the table entries needed.
// //
if (PhysicalAddressBits <= 39 ) { if (PhysicalAddressBits <= 39 ) {
NumberOfPml4EntriesNeeded = 1; NumberOfPml4EntriesNeeded = 1;
NumberOfPdpEntriesNeeded = (UINT32)LShiftU64 (1, (PhysicalAddressBits - 30)); NumberOfPdpEntriesNeeded = (UINT32)LShiftU64 (1, (PhysicalAddressBits - 30));
} else { } else {
NumberOfPml4EntriesNeeded = (UINT32)LShiftU64 (1, (PhysicalAddressBits - 39)); NumberOfPml4EntriesNeeded = (UINT32)LShiftU64 (1, (PhysicalAddressBits - 39));
NumberOfPdpEntriesNeeded = 512; NumberOfPdpEntriesNeeded = 512;
} }
// //
// We need calculate whole page size then allocate once, because S3 restore page table does not know each page in Nvs. // We need calculate whole page size then allocate once, because S3 restore page table does not know each page in Nvs.
// //
if (!Page1GSupport) { if (!Page1GSupport) {
TotalPageTableSize = (UINTN)(1 + NumberOfPml4EntriesNeeded + NumberOfPml4EntriesNeeded * NumberOfPdpEntriesNeeded); TotalPageTableSize = (UINTN)(1 + NumberOfPml4EntriesNeeded + NumberOfPml4EntriesNeeded * NumberOfPdpEntriesNeeded);
} else { } else {
TotalPageTableSize = (UINTN)(1 + NumberOfPml4EntriesNeeded); TotalPageTableSize = (UINTN)(1 + NumberOfPml4EntriesNeeded);
} }
DEBUG ((EFI_D_ERROR, "TotalPageTableSize - %x pages\n", TotalPageTableSize)); DEBUG ((EFI_D_ERROR, "TotalPageTableSize - %x pages\n", TotalPageTableSize));
// //
// By architecture only one PageMapLevel4 exists - so lets allocate storage for it. // By architecture only one PageMapLevel4 exists - so lets allocate storage for it.
// //
S3NvsPageTableAddress = (EFI_PHYSICAL_ADDRESS)(UINTN)AllocateMemoryBelow4G (EfiReservedMemoryType, EFI_PAGES_TO_SIZE(TotalPageTableSize)); S3NvsPageTableAddress = (EFI_PHYSICAL_ADDRESS)(UINTN)AllocateMemoryBelow4G (EfiReservedMemoryType, EFI_PAGES_TO_SIZE(TotalPageTableSize));
ASSERT (S3NvsPageTableAddress != 0); ASSERT (S3NvsPageTableAddress != 0);
return S3NvsPageTableAddress; PcdSet64 (PcdIdentifyMappingPageTablePtr, S3NvsPageTableAddress);
return S3NvsPageTableAddress;
}
} else { } else {
// //
// If DXE is running 32-bit mode, no need to establish page table. // If DXE is running 32-bit mode, no need to establish page table.

View File

@ -75,6 +75,9 @@
gEfiIntelFrameworkModulePkgTokenSpaceGuid.PcdS3AcpiReservedMemorySize ## CONSUMES gEfiIntelFrameworkModulePkgTokenSpaceGuid.PcdS3AcpiReservedMemorySize ## CONSUMES
gEfiIntelFrameworkModulePkgTokenSpaceGuid.PcdS3BootScriptStackSize ## CONSUMES gEfiIntelFrameworkModulePkgTokenSpaceGuid.PcdS3BootScriptStackSize ## CONSUMES
gEfiMdeModulePkgTokenSpaceGuid.PcdUse1GPageTable gEfiMdeModulePkgTokenSpaceGuid.PcdUse1GPageTable
## SOMETIMES_CONSUMES
## SOMETIMES_PRODUCES
gEfiMdeModulePkgTokenSpaceGuid.PcdIdentifyMappingPageTablePtr
[Depex] [Depex]
# #