Clean up UncachedMemoryAllocationLib to use CPU AP.
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@9960 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
@ -83,6 +83,7 @@ AddPagesToList (
|
|||||||
|
|
||||||
NewNode->Buffer = Buffer;
|
NewNode->Buffer = Buffer;
|
||||||
NewNode->Allocation = Allocation;
|
NewNode->Allocation = Allocation;
|
||||||
|
NewNode->Pages = Pages;
|
||||||
|
|
||||||
InsertTailList (&mPageList, &NewNode->Link);
|
InsertTailList (&mPageList, &NewNode->Link);
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
/** @file
|
/** @file
|
||||||
|
UncachedMemoryAllocation lib that uses DXE CPU driver to chnage cachability for
|
||||||
|
a buffer.
|
||||||
|
|
||||||
Copyright (c) 2008-2009, Apple Inc. All rights reserved.
|
Copyright (c) 2008-2010, Apple Inc. All rights reserved.
|
||||||
|
|
||||||
All rights reserved. This program and the accompanying materials
|
All rights reserved. This program and the accompanying materials
|
||||||
are licensed and made available under the terms and conditions of the BSD License
|
are licensed and made available under the terms and conditions of the BSD License
|
||||||
@ -12,63 +14,111 @@
|
|||||||
|
|
||||||
**/
|
**/
|
||||||
|
|
||||||
|
#include <Library/BaseLib.h>
|
||||||
#include <Library/BaseMemoryLib.h>
|
#include <Library/BaseMemoryLib.h>
|
||||||
|
#include <Library/MemoryAllocationLib.h>
|
||||||
#include <Library/DebugLib.h>
|
#include <Library/DebugLib.h>
|
||||||
#include <Library/UefiBootServicesTableLib.h>
|
#include <Library/UefiBootServicesTableLib.h>
|
||||||
#include <Library/UncachedMemoryAllocationLib.h>
|
#include <Library/UncachedMemoryAllocationLib.h>
|
||||||
#include <Library/PcdLib.h>
|
#include <Library/PcdLib.h>
|
||||||
#include <Library/ArmLib.h>
|
#include <Library/ArmLib.h>
|
||||||
|
#include <Library/DxeServicesTableLib.h>
|
||||||
|
|
||||||
#include <Protocol/Cpu.h>
|
#include <Protocol/Cpu.h>
|
||||||
|
|
||||||
|
VOID *
|
||||||
|
UncachedInternalAllocatePages (
|
||||||
|
IN EFI_MEMORY_TYPE MemoryType,
|
||||||
|
IN UINTN Pages
|
||||||
|
);
|
||||||
|
|
||||||
|
VOID *
|
||||||
|
UncachedInternalAllocateAlignedPages (
|
||||||
|
IN EFI_MEMORY_TYPE MemoryType,
|
||||||
|
IN UINTN Pages,
|
||||||
|
IN UINTN Alignment
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
EFI_CPU_ARCH_PROTOCOL *gDebugUncachedCpu;
|
||||||
|
|
||||||
|
//
|
||||||
|
// Assume all of memory has the same cache attributes, unless we do our magic
|
||||||
|
//
|
||||||
|
UINT64 gAttributes;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
VOID *Allocation;
|
||||||
|
UINTN Pages;
|
||||||
|
LIST_ENTRY Link;
|
||||||
|
} FREE_PAGE_NODE;
|
||||||
|
|
||||||
|
LIST_ENTRY mPageList = INITIALIZE_LIST_HEAD_VARIABLE (mPageList);
|
||||||
|
|
||||||
|
VOID
|
||||||
|
AddPagesToList (
|
||||||
|
IN VOID *Allocation,
|
||||||
|
UINTN Pages
|
||||||
|
)
|
||||||
|
{
|
||||||
|
FREE_PAGE_NODE *NewNode;
|
||||||
|
|
||||||
|
NewNode = AllocatePool (sizeof (LIST_ENTRY));
|
||||||
|
if (NewNode == NULL) {
|
||||||
|
ASSERT (FALSE);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
NewNode->Allocation = Allocation;
|
||||||
|
NewNode->Pages = Pages;
|
||||||
|
|
||||||
|
InsertTailList (&mPageList, &NewNode->Link);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
VOID
|
||||||
|
RemovePagesFromList (
|
||||||
|
OUT VOID *Allocation,
|
||||||
|
OUT UINTN *Pages
|
||||||
|
)
|
||||||
|
{
|
||||||
|
LIST_ENTRY *Link;
|
||||||
|
FREE_PAGE_NODE *OldNode;
|
||||||
|
|
||||||
|
*Pages = 0;
|
||||||
|
|
||||||
|
for (Link = mPageList.ForwardLink; Link != &mPageList; Link = Link->ForwardLink) {
|
||||||
|
OldNode = BASE_CR (Link, FREE_PAGE_NODE, Link);
|
||||||
|
if (OldNode->Allocation == Allocation) {
|
||||||
|
*Pages = OldNode->Pages;
|
||||||
|
|
||||||
|
RemoveEntryList (&OldNode->Link);
|
||||||
|
FreePool (OldNode);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
Converts a cached or uncached address to a physical address suitable for use in SoC registers.
|
||||||
|
|
||||||
|
@param VirtualAddress The pointer to convert.
|
||||||
|
|
||||||
|
@return The physical address of the supplied virtual pointer.
|
||||||
|
|
||||||
|
**/
|
||||||
EFI_PHYSICAL_ADDRESS
|
EFI_PHYSICAL_ADDRESS
|
||||||
ConvertToPhysicalAddress (
|
ConvertToPhysicalAddress (
|
||||||
IN VOID *VirtualAddress
|
IN VOID *VirtualAddress
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UINTN UncachedMemoryMask = (UINTN)PcdGet64(PcdArmUncachedMemoryMask);
|
return (EFI_PHYSICAL_ADDRESS)(UINTN)VirtualAddress;
|
||||||
UINTN PhysicalAddress;
|
|
||||||
|
|
||||||
PhysicalAddress = (UINTN)VirtualAddress & ~UncachedMemoryMask;
|
|
||||||
|
|
||||||
return (EFI_PHYSICAL_ADDRESS)PhysicalAddress;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
VOID *
|
|
||||||
ConvertToCachedAddress (
|
|
||||||
IN VOID *Address
|
|
||||||
)
|
|
||||||
{
|
|
||||||
return (VOID *)(UINTN)ConvertToPhysicalAddress(Address);
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID *
|
|
||||||
ConvertToUncachedAddress (
|
|
||||||
IN VOID *Address
|
|
||||||
)
|
|
||||||
{
|
|
||||||
UINTN UncachedMemoryMask = (UINTN)PcdGet64(PcdArmUncachedMemoryMask);
|
|
||||||
UINTN UncachedAddress;
|
|
||||||
|
|
||||||
UncachedAddress = (UINTN)Address | UncachedMemoryMask;
|
|
||||||
|
|
||||||
return (VOID *)UncachedAddress;
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID
|
|
||||||
FlushCache (
|
|
||||||
IN EFI_PHYSICAL_ADDRESS Address,
|
|
||||||
IN UINTN Size
|
|
||||||
)
|
|
||||||
{
|
|
||||||
EFI_CPU_ARCH_PROTOCOL *Cpu;
|
|
||||||
EFI_STATUS Status;
|
|
||||||
|
|
||||||
Status = gBS->LocateProtocol(&gEfiCpuArchProtocolGuid, NULL, (VOID **)&Cpu);
|
|
||||||
ASSERT_EFI_ERROR(Status);
|
|
||||||
|
|
||||||
Status = Cpu->FlushDataCache(Cpu, Address, Size, EfiCpuFlushTypeWriteBackInvalidate);
|
|
||||||
ASSERT_EFI_ERROR(Status);
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID *
|
VOID *
|
||||||
UncachedInternalAllocatePages (
|
UncachedInternalAllocatePages (
|
||||||
@ -76,26 +126,10 @@ UncachedInternalAllocatePages (
|
|||||||
IN UINTN Pages
|
IN UINTN Pages
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
EFI_STATUS Status;
|
return UncachedInternalAllocateAlignedPages (MemoryType, Pages, EFI_PAGE_SIZE);
|
||||||
EFI_PHYSICAL_ADDRESS Memory;
|
|
||||||
|
|
||||||
if (Pages == 0) {
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
Status = gBS->AllocatePages (AllocateAnyPages, MemoryType, Pages, &Memory);
|
|
||||||
if (EFI_ERROR (Status)) {
|
|
||||||
Memory = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Memory != 0) {
|
|
||||||
FlushCache(Memory, EFI_PAGES_TO_SIZE(Pages));
|
|
||||||
Memory = (EFI_PHYSICAL_ADDRESS)(UINTN)ConvertToUncachedAddress((VOID *)(UINTN)Memory);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (VOID *) (UINTN) Memory;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
VOID *
|
VOID *
|
||||||
EFIAPI
|
EFIAPI
|
||||||
UncachedAllocatePages (
|
UncachedAllocatePages (
|
||||||
@ -123,6 +157,8 @@ UncachedAllocateReservedPages (
|
|||||||
return UncachedInternalAllocatePages (EfiReservedMemoryType, Pages);
|
return UncachedInternalAllocatePages (EfiReservedMemoryType, Pages);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
VOID
|
VOID
|
||||||
EFIAPI
|
EFIAPI
|
||||||
UncachedFreePages (
|
UncachedFreePages (
|
||||||
@ -130,16 +166,11 @@ UncachedFreePages (
|
|||||||
IN UINTN Pages
|
IN UINTN Pages
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
EFI_STATUS Status;
|
UncachedFreeAlignedPages (Buffer, Pages);
|
||||||
|
return;
|
||||||
ASSERT (Pages != 0);
|
|
||||||
|
|
||||||
Buffer = ConvertToCachedAddress(Buffer);
|
|
||||||
|
|
||||||
Status = gBS->FreePages ((EFI_PHYSICAL_ADDRESS) (UINTN) Buffer, Pages);
|
|
||||||
ASSERT_EFI_ERROR (Status);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
VOID *
|
VOID *
|
||||||
UncachedInternalAllocateAlignedPages (
|
UncachedInternalAllocateAlignedPages (
|
||||||
IN EFI_MEMORY_TYPE MemoryType,
|
IN EFI_MEMORY_TYPE MemoryType,
|
||||||
@ -147,12 +178,13 @@ UncachedInternalAllocateAlignedPages (
|
|||||||
IN UINTN Alignment
|
IN UINTN Alignment
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
EFI_STATUS Status;
|
EFI_STATUS Status;
|
||||||
EFI_PHYSICAL_ADDRESS Memory;
|
EFI_PHYSICAL_ADDRESS Memory;
|
||||||
UINTN AlignedMemory;
|
EFI_PHYSICAL_ADDRESS AlignedMemory;
|
||||||
UINTN AlignmentMask;
|
UINTN AlignmentMask;
|
||||||
UINTN UnalignedPages;
|
UINTN UnalignedPages;
|
||||||
UINTN RealPages;
|
UINTN RealPages;
|
||||||
|
EFI_GCD_MEMORY_SPACE_DESCRIPTOR Descriptor;
|
||||||
|
|
||||||
//
|
//
|
||||||
// Alignment must be a power of two or zero.
|
// Alignment must be a power of two or zero.
|
||||||
@ -206,43 +238,20 @@ UncachedInternalAllocateAlignedPages (
|
|||||||
AlignedMemory = (UINTN) Memory;
|
AlignedMemory = (UINTN) Memory;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (AlignedMemory != 0) {
|
Status = gDS->GetMemorySpaceDescriptor (Memory, &Descriptor);
|
||||||
FlushCache (AlignedMemory, EFI_PAGES_TO_SIZE(Pages));
|
if (!EFI_ERROR (Status)) {
|
||||||
AlignedMemory = (UINTN)ConvertToUncachedAddress((VOID *)AlignedMemory);
|
// We are making an assumption that all of memory has the same default attributes
|
||||||
|
gAttributes = Descriptor.Attributes;
|
||||||
}
|
}
|
||||||
|
|
||||||
return (VOID *) AlignedMemory;
|
Status = gDebugUncachedCpu->SetMemoryAttributes (gDebugUncachedCpu, Memory, EFI_PAGES_TO_SIZE (Pages), EFI_MEMORY_UC);
|
||||||
|
if (EFI_ERROR (Status)) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (VOID *)(UINTN)Memory;
|
||||||
}
|
}
|
||||||
|
|
||||||
VOID *
|
|
||||||
EFIAPI
|
|
||||||
UncachedAllocateAlignedPages (
|
|
||||||
IN UINTN Pages,
|
|
||||||
IN UINTN Alignment
|
|
||||||
)
|
|
||||||
{
|
|
||||||
return UncachedInternalAllocateAlignedPages (EfiBootServicesData, Pages, Alignment);
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID *
|
|
||||||
EFIAPI
|
|
||||||
UncachedAllocateAlignedRuntimePages (
|
|
||||||
IN UINTN Pages,
|
|
||||||
IN UINTN Alignment
|
|
||||||
)
|
|
||||||
{
|
|
||||||
return UncachedInternalAllocateAlignedPages (EfiRuntimeServicesData, Pages, Alignment);
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID *
|
|
||||||
EFIAPI
|
|
||||||
UncachedAllocateAlignedReservedPages (
|
|
||||||
IN UINTN Pages,
|
|
||||||
IN UINTN Alignment
|
|
||||||
)
|
|
||||||
{
|
|
||||||
return UncachedInternalAllocateAlignedPages (EfiReservedMemoryType, Pages, Alignment);
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID
|
VOID
|
||||||
EFIAPI
|
EFIAPI
|
||||||
@ -251,16 +260,21 @@ UncachedFreeAlignedPages (
|
|||||||
IN UINTN Pages
|
IN UINTN Pages
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
EFI_STATUS Status;
|
EFI_STATUS Status;
|
||||||
|
EFI_PHYSICAL_ADDRESS Memory;
|
||||||
|
|
||||||
ASSERT (Pages != 0);
|
ASSERT (Pages != 0);
|
||||||
|
|
||||||
Buffer = ConvertToCachedAddress(Buffer);
|
Memory = (EFI_PHYSICAL_ADDRESS) (UINTN) Buffer;
|
||||||
|
Status = gDebugUncachedCpu->SetMemoryAttributes (gDebugUncachedCpu, Memory, EFI_PAGES_TO_SIZE (Pages), gAttributes);
|
||||||
|
|
||||||
Status = gBS->FreePages ((EFI_PHYSICAL_ADDRESS) (UINTN) Buffer, Pages);
|
Status = gBS->FreePages (Memory, Pages);
|
||||||
ASSERT_EFI_ERROR (Status);
|
ASSERT_EFI_ERROR (Status);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
VOID *
|
VOID *
|
||||||
UncachedInternalAllocateAlignedPool (
|
UncachedInternalAllocateAlignedPool (
|
||||||
IN EFI_MEMORY_TYPE PoolType,
|
IN EFI_MEMORY_TYPE PoolType,
|
||||||
@ -268,59 +282,23 @@ UncachedInternalAllocateAlignedPool (
|
|||||||
IN UINTN Alignment
|
IN UINTN Alignment
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
VOID *RawAddress;
|
VOID *AlignedAddress;
|
||||||
UINTN AlignedAddress;
|
|
||||||
UINTN AlignmentMask;
|
|
||||||
UINTN OverAllocationSize;
|
|
||||||
UINTN RealAllocationSize;
|
|
||||||
VOID **FreePointer;
|
|
||||||
UINTN DataCacheLineLength;
|
|
||||||
EFI_STATUS Status;
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// Alignment must be a power of two or zero.
|
// Alignment must be a power of two or zero.
|
||||||
//
|
//
|
||||||
ASSERT ((Alignment & (Alignment - 1)) == 0);
|
ASSERT ((Alignment & (Alignment - 1)) == 0);
|
||||||
|
|
||||||
DataCacheLineLength = ArmDataCacheLineLength();
|
if (Alignment < EFI_PAGE_SIZE) {
|
||||||
|
Alignment = EFI_PAGE_SIZE;
|
||||||
// Alignment must be at least cache-line aligned
|
|
||||||
if (Alignment < DataCacheLineLength) {
|
|
||||||
Alignment = DataCacheLineLength;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Alignment == 0) {
|
AlignedAddress = UncachedInternalAllocateAlignedPages (PoolType, EFI_SIZE_TO_PAGES (AllocationSize), Alignment);
|
||||||
AlignmentMask = Alignment;
|
if (AlignedAddress == NULL) {
|
||||||
} else {
|
|
||||||
AlignmentMask = Alignment - 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Calculate the extra memory size, over-allocate memory pool and get the aligned memory address.
|
|
||||||
//
|
|
||||||
OverAllocationSize = sizeof (RawAddress) + AlignmentMask;
|
|
||||||
RealAllocationSize = AllocationSize + OverAllocationSize;
|
|
||||||
//
|
|
||||||
// Make sure that AllocationSize plus OverAllocationSize does not overflow.
|
|
||||||
//
|
|
||||||
ASSERT (RealAllocationSize > AllocationSize);
|
|
||||||
|
|
||||||
Status = gBS->AllocatePool (PoolType, RealAllocationSize, &RawAddress);
|
|
||||||
if (EFI_ERROR (Status)) {
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
AlignedAddress = ((UINTN) RawAddress + OverAllocationSize) & ~AlignmentMask;
|
AddPagesToList ((VOID *)(UINTN)AlignedAddress, EFI_SIZE_TO_PAGES (AllocationSize));
|
||||||
//
|
|
||||||
// Save the original memory address just before the aligned address.
|
|
||||||
//
|
|
||||||
FreePointer = (VOID **)(AlignedAddress - sizeof (RawAddress));
|
|
||||||
*FreePointer = RawAddress;
|
|
||||||
|
|
||||||
if (AlignedAddress != 0) {
|
|
||||||
FlushCache (AlignedAddress, AllocationSize);
|
|
||||||
AlignedAddress = (UINTN)ConvertToUncachedAddress((VOID *)AlignedAddress);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (VOID *) AlignedAddress;
|
return (VOID *) AlignedAddress;
|
||||||
}
|
}
|
||||||
@ -456,23 +434,14 @@ UncachedAllocateAlignedReservedCopyPool (
|
|||||||
VOID
|
VOID
|
||||||
EFIAPI
|
EFIAPI
|
||||||
UncachedFreeAlignedPool (
|
UncachedFreeAlignedPool (
|
||||||
IN VOID *Buffer
|
IN VOID *Allocation
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
VOID *RawAddress;
|
UINTN Pages;
|
||||||
VOID **FreePointer;
|
|
||||||
EFI_STATUS Status;
|
|
||||||
|
|
||||||
Buffer = ConvertToCachedAddress(Buffer);
|
RemovePagesFromList (Allocation, &Pages);
|
||||||
|
|
||||||
//
|
UncachedFreePages (Allocation, Pages);
|
||||||
// Get the pre-saved original address in the over-allocate pool.
|
|
||||||
//
|
|
||||||
FreePointer = (VOID **)((UINTN) Buffer - sizeof (RawAddress));
|
|
||||||
RawAddress = *FreePointer;
|
|
||||||
|
|
||||||
Status = gBS->FreePool (RawAddress);
|
|
||||||
ASSERT_EFI_ERROR (Status);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
VOID *
|
VOID *
|
||||||
@ -481,8 +450,8 @@ UncachedInternalAllocatePool (
|
|||||||
IN UINTN AllocationSize
|
IN UINTN AllocationSize
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UINTN CacheLineLength = ArmDataCacheLineLength();
|
UINTN CacheLineLength = ArmDataCacheLineLength ();
|
||||||
return UncachedInternalAllocateAlignedPool(MemoryType, AllocationSize, CacheLineLength);
|
return UncachedInternalAllocateAlignedPool (MemoryType, AllocationSize, CacheLineLength);
|
||||||
}
|
}
|
||||||
|
|
||||||
VOID *
|
VOID *
|
||||||
@ -609,7 +578,7 @@ UncachedFreePool (
|
|||||||
IN VOID *Buffer
|
IN VOID *Buffer
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UncachedFreeAlignedPool(Buffer);
|
UncachedFreeAlignedPool (Buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
VOID
|
VOID
|
||||||
@ -624,3 +593,35 @@ UncachedSafeFreePool (
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
The constructor function caches the pointer of DXE Services Table.
|
||||||
|
|
||||||
|
The constructor function caches the pointer of DXE Services Table.
|
||||||
|
It will ASSERT() if that operation fails.
|
||||||
|
It will ASSERT() if the pointer of DXE Services Table is NULL.
|
||||||
|
It will always return EFI_SUCCESS.
|
||||||
|
|
||||||
|
@param ImageHandle The firmware allocated handle for the EFI image.
|
||||||
|
@param SystemTable A pointer to the EFI System Table.
|
||||||
|
|
||||||
|
@retval EFI_SUCCESS The constructor always returns EFI_SUCCESS.
|
||||||
|
|
||||||
|
**/
|
||||||
|
EFI_STATUS
|
||||||
|
EFIAPI
|
||||||
|
DebugUncachedMemoryAllocationLibConstructor (
|
||||||
|
IN EFI_HANDLE ImageHandle,
|
||||||
|
IN EFI_SYSTEM_TABLE *SystemTable
|
||||||
|
)
|
||||||
|
{
|
||||||
|
EFI_STATUS Status;
|
||||||
|
|
||||||
|
Status = gBS->LocateProtocol (&gEfiCpuArchProtocolGuid, NULL, (VOID **)&gDebugUncachedCpu);
|
||||||
|
ASSERT_EFI_ERROR(Status);
|
||||||
|
|
||||||
|
|
||||||
|
return Status;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -32,8 +32,9 @@
|
|||||||
gEfiCpuArchProtocolGuid
|
gEfiCpuArchProtocolGuid
|
||||||
|
|
||||||
[LibraryClasses]
|
[LibraryClasses]
|
||||||
|
BaseLib
|
||||||
ArmLib
|
ArmLib
|
||||||
|
MemoryAllocationLib
|
||||||
|
DxeServicesTableLib
|
||||||
|
|
||||||
[FixedPcd]
|
|
||||||
gArmTokenSpaceGuid.PcdArmUncachedMemoryMask
|
|
||||||
|
|
Reference in New Issue
Block a user