mirror of
https://github.com/acidanthera/audk.git
synced 2025-07-31 01:24:12 +02:00
MdeModulePkg/AcpiTableDxe: use pool allocations when possible
On AArch64 systems, page based allocations for memory types that are relevant to the OS are rounded up to 64 KB multiples. This wastes some space in the ACPI table memory allocator, since it uses page based allocations in order to be able to place the ACPI tables low in memory. Since the latter requirement does not exist on AArch64, switch to pool allocations for all ACPI tables except the root tables if the active allocation policy permits them to be anywhere in memory. The root tables will be handled in a subsequent patch. Signed-off-by: Ard Biesheuvel <ard.biesheuvel@arm.com> Reviewed-by: Liming Gao <gaoliming@byosoft.com.cn>
This commit is contained in:
parent
8cadcaa13d
commit
0e0ae47da6
@ -68,8 +68,8 @@ FindTableByBuffer (
|
|||||||
|
|
||||||
while (CurrentLink != StartLink) {
|
while (CurrentLink != StartLink) {
|
||||||
CurrentTableList = EFI_ACPI_TABLE_LIST_FROM_LINK (CurrentLink);
|
CurrentTableList = EFI_ACPI_TABLE_LIST_FROM_LINK (CurrentLink);
|
||||||
if (((UINTN)CurrentTableList->PageAddress <= (UINTN)Buffer) &&
|
if (((UINTN)CurrentTableList->Table <= (UINTN)Buffer) &&
|
||||||
((UINTN)CurrentTableList->PageAddress + EFI_PAGES_TO_SIZE(CurrentTableList->NumberOfPages) > (UINTN)Buffer)) {
|
((UINTN)CurrentTableList->Table + CurrentTableList->TableSize > (UINTN)Buffer)) {
|
||||||
//
|
//
|
||||||
// Good! Found Table.
|
// Good! Found Table.
|
||||||
//
|
//
|
||||||
|
@ -55,18 +55,21 @@
|
|||||||
// Link is the linked list data.
|
// Link is the linked list data.
|
||||||
// Version is the versions of the ACPI tables that this table belongs in.
|
// Version is the versions of the ACPI tables that this table belongs in.
|
||||||
// Table is a pointer to the table.
|
// Table is a pointer to the table.
|
||||||
// PageAddress is the address of the pages allocated for the table.
|
// TableSize is the size of the table
|
||||||
// NumberOfPages is the number of pages allocated at PageAddress.
|
|
||||||
// Handle is used to identify a particular table.
|
// Handle is used to identify a particular table.
|
||||||
|
// PoolAllocation carries the allocation type:
|
||||||
|
// FALSE: Table points to EFI_SIZE_TO_PAGES(TableSize) pages allocated using
|
||||||
|
// gBS->AllocatePages ()
|
||||||
|
// TRUE: Table points to TableSize bytes allocated using gBS->AllocatePool ()
|
||||||
//
|
//
|
||||||
typedef struct {
|
typedef struct {
|
||||||
UINT32 Signature;
|
UINT32 Signature;
|
||||||
LIST_ENTRY Link;
|
LIST_ENTRY Link;
|
||||||
EFI_ACPI_TABLE_VERSION Version;
|
EFI_ACPI_TABLE_VERSION Version;
|
||||||
EFI_ACPI_COMMON_HEADER *Table;
|
EFI_ACPI_COMMON_HEADER *Table;
|
||||||
EFI_PHYSICAL_ADDRESS PageAddress;
|
UINTN TableSize;
|
||||||
UINTN NumberOfPages;
|
|
||||||
UINTN Handle;
|
UINTN Handle;
|
||||||
|
BOOLEAN PoolAllocation;
|
||||||
} EFI_ACPI_TABLE_LIST;
|
} EFI_ACPI_TABLE_LIST;
|
||||||
|
|
||||||
//
|
//
|
||||||
|
@ -428,6 +428,26 @@ ReallocateAcpiTableBuffer (
|
|||||||
return EFI_SUCCESS;
|
return EFI_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
Free the memory associated with the provided EFI_ACPI_TABLE_LIST instance.
|
||||||
|
|
||||||
|
@param TableEntry EFI_ACPI_TABLE_LIST instance pointer
|
||||||
|
|
||||||
|
**/
|
||||||
|
STATIC
|
||||||
|
VOID
|
||||||
|
FreeTableMemory (
|
||||||
|
EFI_ACPI_TABLE_LIST *TableEntry
|
||||||
|
)
|
||||||
|
{
|
||||||
|
if (TableEntry->PoolAllocation) {
|
||||||
|
gBS->FreePool (TableEntry->Table);
|
||||||
|
} else {
|
||||||
|
gBS->FreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)TableEntry->Table,
|
||||||
|
EFI_SIZE_TO_PAGES (TableEntry->TableSize));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
This function adds an ACPI table to the table list. It will detect FACS and
|
This function adds an ACPI table to the table list. It will detect FACS and
|
||||||
allocate the correct type of memory and properly align the table.
|
allocate the correct type of memory and properly align the table.
|
||||||
@ -454,14 +474,15 @@ AddTableToList (
|
|||||||
OUT UINTN *Handle
|
OUT UINTN *Handle
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
EFI_STATUS Status;
|
EFI_STATUS Status;
|
||||||
EFI_ACPI_TABLE_LIST *CurrentTableList;
|
EFI_ACPI_TABLE_LIST *CurrentTableList;
|
||||||
UINT32 CurrentTableSignature;
|
UINT32 CurrentTableSignature;
|
||||||
UINT32 CurrentTableSize;
|
UINT32 CurrentTableSize;
|
||||||
UINT32 *CurrentRsdtEntry;
|
UINT32 *CurrentRsdtEntry;
|
||||||
VOID *CurrentXsdtEntry;
|
VOID *CurrentXsdtEntry;
|
||||||
UINT64 Buffer64;
|
EFI_PHYSICAL_ADDRESS AllocPhysAddress;
|
||||||
BOOLEAN AddToRsdt;
|
UINT64 Buffer64;
|
||||||
|
BOOLEAN AddToRsdt;
|
||||||
|
|
||||||
//
|
//
|
||||||
// Check for invalid input parameters
|
// Check for invalid input parameters
|
||||||
@ -496,8 +517,9 @@ AddTableToList (
|
|||||||
// There is no architectural reason these should be below 4GB, it is purely
|
// There is no architectural reason these should be below 4GB, it is purely
|
||||||
// for convenience of implementation that we force memory below 4GB.
|
// for convenience of implementation that we force memory below 4GB.
|
||||||
//
|
//
|
||||||
CurrentTableList->PageAddress = 0xFFFFFFFF;
|
AllocPhysAddress = 0xFFFFFFFF;
|
||||||
CurrentTableList->NumberOfPages = EFI_SIZE_TO_PAGES (CurrentTableSize);
|
CurrentTableList->TableSize = CurrentTableSize;
|
||||||
|
CurrentTableList->PoolAllocation = FALSE;
|
||||||
|
|
||||||
//
|
//
|
||||||
// Allocation memory type depends on the type of the table
|
// Allocation memory type depends on the type of the table
|
||||||
@ -518,9 +540,21 @@ AddTableToList (
|
|||||||
Status = gBS->AllocatePages (
|
Status = gBS->AllocatePages (
|
||||||
AllocateMaxAddress,
|
AllocateMaxAddress,
|
||||||
EfiACPIMemoryNVS,
|
EfiACPIMemoryNVS,
|
||||||
CurrentTableList->NumberOfPages,
|
EFI_SIZE_TO_PAGES (CurrentTableList->TableSize),
|
||||||
&CurrentTableList->PageAddress
|
&AllocPhysAddress
|
||||||
);
|
);
|
||||||
|
} else if (mAcpiTableAllocType == AllocateAnyPages) {
|
||||||
|
//
|
||||||
|
// If there is no allocation limit, there is also no need to use page
|
||||||
|
// based allocations for ACPI tables, which may be wasteful on platforms
|
||||||
|
// such as AArch64 that allocate multiples of 64 KB
|
||||||
|
//
|
||||||
|
Status = gBS->AllocatePool (
|
||||||
|
EfiACPIReclaimMemory,
|
||||||
|
CurrentTableList->TableSize,
|
||||||
|
(VOID **)&CurrentTableList->Table
|
||||||
|
);
|
||||||
|
CurrentTableList->PoolAllocation = TRUE;
|
||||||
} else {
|
} else {
|
||||||
//
|
//
|
||||||
// All other tables are ACPI reclaim memory, no alignment requirements.
|
// All other tables are ACPI reclaim memory, no alignment requirements.
|
||||||
@ -528,9 +562,10 @@ AddTableToList (
|
|||||||
Status = gBS->AllocatePages (
|
Status = gBS->AllocatePages (
|
||||||
mAcpiTableAllocType,
|
mAcpiTableAllocType,
|
||||||
EfiACPIReclaimMemory,
|
EfiACPIReclaimMemory,
|
||||||
CurrentTableList->NumberOfPages,
|
EFI_SIZE_TO_PAGES (CurrentTableList->TableSize),
|
||||||
&CurrentTableList->PageAddress
|
&AllocPhysAddress
|
||||||
);
|
);
|
||||||
|
CurrentTableList->Table = (EFI_ACPI_COMMON_HEADER *)(UINTN)AllocPhysAddress;
|
||||||
}
|
}
|
||||||
//
|
//
|
||||||
// Check return value from memory alloc.
|
// Check return value from memory alloc.
|
||||||
@ -539,10 +574,10 @@ AddTableToList (
|
|||||||
gBS->FreePool (CurrentTableList);
|
gBS->FreePool (CurrentTableList);
|
||||||
return EFI_OUT_OF_RESOURCES;
|
return EFI_OUT_OF_RESOURCES;
|
||||||
}
|
}
|
||||||
//
|
|
||||||
// Update the table pointer with the allocated memory start
|
if (!CurrentTableList->PoolAllocation) {
|
||||||
//
|
CurrentTableList->Table = (EFI_ACPI_COMMON_HEADER *)(UINTN)AllocPhysAddress;
|
||||||
CurrentTableList->Table = (EFI_ACPI_COMMON_HEADER *) (UINTN) CurrentTableList->PageAddress;
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// Initialize the table contents
|
// Initialize the table contents
|
||||||
@ -575,7 +610,7 @@ AddTableToList (
|
|||||||
if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Fadt1 != NULL) ||
|
if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Fadt1 != NULL) ||
|
||||||
((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Fadt3 != NULL)
|
((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Fadt3 != NULL)
|
||||||
) {
|
) {
|
||||||
gBS->FreePages (CurrentTableList->PageAddress, CurrentTableList->NumberOfPages);
|
FreeTableMemory (CurrentTableList);
|
||||||
gBS->FreePool (CurrentTableList);
|
gBS->FreePool (CurrentTableList);
|
||||||
return EFI_ACCESS_DENIED;
|
return EFI_ACCESS_DENIED;
|
||||||
}
|
}
|
||||||
@ -729,7 +764,7 @@ AddTableToList (
|
|||||||
if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Facs1 != NULL) ||
|
if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Facs1 != NULL) ||
|
||||||
((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Facs3 != NULL)
|
((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Facs3 != NULL)
|
||||||
) {
|
) {
|
||||||
gBS->FreePages (CurrentTableList->PageAddress, CurrentTableList->NumberOfPages);
|
FreeTableMemory (CurrentTableList);
|
||||||
gBS->FreePool (CurrentTableList);
|
gBS->FreePool (CurrentTableList);
|
||||||
return EFI_ACCESS_DENIED;
|
return EFI_ACCESS_DENIED;
|
||||||
}
|
}
|
||||||
@ -813,7 +848,7 @@ AddTableToList (
|
|||||||
if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Dsdt1 != NULL) ||
|
if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Dsdt1 != NULL) ||
|
||||||
((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Dsdt3 != NULL)
|
((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Dsdt3 != NULL)
|
||||||
) {
|
) {
|
||||||
gBS->FreePages (CurrentTableList->PageAddress, CurrentTableList->NumberOfPages);
|
FreeTableMemory (CurrentTableList);
|
||||||
gBS->FreePool (CurrentTableList);
|
gBS->FreePool (CurrentTableList);
|
||||||
return EFI_ACCESS_DENIED;
|
return EFI_ACCESS_DENIED;
|
||||||
}
|
}
|
||||||
@ -1449,7 +1484,7 @@ DeleteTable (
|
|||||||
//
|
//
|
||||||
// Free the Table
|
// Free the Table
|
||||||
//
|
//
|
||||||
gBS->FreePages (Table->PageAddress, Table->NumberOfPages);
|
FreeTableMemory (Table);
|
||||||
RemoveEntryList (&(Table->Link));
|
RemoveEntryList (&(Table->Link));
|
||||||
gBS->FreePool (Table);
|
gBS->FreePool (Table);
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user