mirror of https://github.com/acidanthera/audk.git
ArmPlatformPkg/NorFlashDxe: Fixed driver to support UEFI Runtime mode
- Added the NOR Flash region to the Runtime UEFI Memory Mapped IO - Caught the gEfiEventVirtualAddressChangeGuid event to fixup the NOR Flash pointers Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Olivier Martin <olivier.martin@arm.com> git-svn-id: https://svn.code.sf.net/p/edk2/code/trunk/edk2@15438 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
parent
2dff0c1ab2
commit
1dbbfc176f
|
@ -20,11 +20,13 @@
|
||||||
|
|
||||||
#include "NorFlashDxe.h"
|
#include "NorFlashDxe.h"
|
||||||
|
|
||||||
|
STATIC EFI_EVENT mNorFlashVirtualAddrChangeEvent;
|
||||||
|
|
||||||
//
|
//
|
||||||
// Global variable declarations
|
// Global variable declarations
|
||||||
//
|
//
|
||||||
NOR_FLASH_INSTANCE **mNorFlashInstances;
|
NOR_FLASH_INSTANCE **mNorFlashInstances;
|
||||||
|
UINT32 mNorFlashDeviceCount;
|
||||||
|
|
||||||
NOR_FLASH_INSTANCE mNorFlashInstanceTemplate = {
|
NOR_FLASH_INSTANCE mNorFlashInstanceTemplate = {
|
||||||
NOR_FLASH_SIGNATURE, // Signature
|
NOR_FLASH_SIGNATURE, // Signature
|
||||||
|
@ -792,6 +794,50 @@ NorFlashReset (
|
||||||
return EFI_SUCCESS;
|
return EFI_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
Fixup internal data so that EFI can be call in virtual mode.
|
||||||
|
Call the passed in Child Notify event and convert any pointers in
|
||||||
|
lib to virtual mode.
|
||||||
|
|
||||||
|
@param[in] Event The Event that is being processed
|
||||||
|
@param[in] Context Event Context
|
||||||
|
**/
|
||||||
|
VOID
|
||||||
|
EFIAPI
|
||||||
|
NorFlashVirtualNotifyEvent (
|
||||||
|
IN EFI_EVENT Event,
|
||||||
|
IN VOID *Context
|
||||||
|
)
|
||||||
|
{
|
||||||
|
UINTN Index;
|
||||||
|
|
||||||
|
for (Index = 0; Index < mNorFlashDeviceCount; Index++) {
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->DeviceBaseAddress);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->RegionBaseAddress);
|
||||||
|
|
||||||
|
// Convert BlockIo protocol
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->BlockIoProtocol.FlushBlocks);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->BlockIoProtocol.ReadBlocks);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->BlockIoProtocol.Reset);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->BlockIoProtocol.WriteBlocks);
|
||||||
|
|
||||||
|
// Convert Fvb
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbProtocol.EraseBlocks);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbProtocol.GetAttributes);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbProtocol.GetBlockSize);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbProtocol.GetPhysicalAddress);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbProtocol.Read);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbProtocol.SetAttributes);
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbProtocol.Write);
|
||||||
|
|
||||||
|
if (mNorFlashInstances[Index]->FvbBuffer != NULL) {
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mNorFlashInstances[Index]->FvbBuffer);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
EFI_STATUS
|
EFI_STATUS
|
||||||
EFIAPI
|
EFIAPI
|
||||||
NorFlashInitialise (
|
NorFlashInitialise (
|
||||||
|
@ -802,7 +848,6 @@ NorFlashInitialise (
|
||||||
EFI_STATUS Status;
|
EFI_STATUS Status;
|
||||||
UINT32 Index;
|
UINT32 Index;
|
||||||
NOR_FLASH_DESCRIPTION* NorFlashDevices;
|
NOR_FLASH_DESCRIPTION* NorFlashDevices;
|
||||||
UINT32 NorFlashDeviceCount;
|
|
||||||
BOOLEAN ContainVariableStorage;
|
BOOLEAN ContainVariableStorage;
|
||||||
|
|
||||||
Status = NorFlashPlatformInitialization ();
|
Status = NorFlashPlatformInitialization ();
|
||||||
|
@ -811,15 +856,15 @@ NorFlashInitialise (
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
||||||
Status = NorFlashPlatformGetDevices (&NorFlashDevices,&NorFlashDeviceCount);
|
Status = NorFlashPlatformGetDevices (&NorFlashDevices, &mNorFlashDeviceCount);
|
||||||
if (EFI_ERROR(Status)) {
|
if (EFI_ERROR(Status)) {
|
||||||
DEBUG((EFI_D_ERROR,"NorFlashInitialise: Fail to get Nor Flash devices\n"));
|
DEBUG((EFI_D_ERROR,"NorFlashInitialise: Fail to get Nor Flash devices\n"));
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
||||||
mNorFlashInstances = AllocateRuntimePool (sizeof(NOR_FLASH_INSTANCE*) * NorFlashDeviceCount);
|
mNorFlashInstances = AllocateRuntimePool (sizeof(NOR_FLASH_INSTANCE*) * mNorFlashDeviceCount);
|
||||||
|
|
||||||
for (Index = 0; Index < NorFlashDeviceCount; Index++) {
|
for (Index = 0; Index < mNorFlashDeviceCount; Index++) {
|
||||||
// Check if this NOR Flash device contain the variable storage region
|
// Check if this NOR Flash device contain the variable storage region
|
||||||
ContainVariableStorage =
|
ContainVariableStorage =
|
||||||
(NorFlashDevices[Index].RegionBaseAddress <= PcdGet32 (PcdFlashNvStorageVariableBase)) &&
|
(NorFlashDevices[Index].RegionBaseAddress <= PcdGet32 (PcdFlashNvStorageVariableBase)) &&
|
||||||
|
@ -840,5 +885,18 @@ NorFlashInitialise (
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// Register for the virtual address change event
|
||||||
|
//
|
||||||
|
Status = gBS->CreateEventEx (
|
||||||
|
EVT_NOTIFY_SIGNAL,
|
||||||
|
TPL_NOTIFY,
|
||||||
|
NorFlashVirtualNotifyEvent,
|
||||||
|
NULL,
|
||||||
|
&gEfiEventVirtualAddressChangeGuid,
|
||||||
|
&mNorFlashVirtualAddrChangeEvent
|
||||||
|
);
|
||||||
|
ASSERT_EFI_ERROR (Status);
|
||||||
|
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,6 +19,8 @@
|
||||||
#include <Base.h>
|
#include <Base.h>
|
||||||
#include <PiDxe.h>
|
#include <PiDxe.h>
|
||||||
|
|
||||||
|
#include <Guid/EventGroup.h>
|
||||||
|
|
||||||
#include <Protocol/BlockIo.h>
|
#include <Protocol/BlockIo.h>
|
||||||
#include <Protocol/FirmwareVolumeBlock.h>
|
#include <Protocol/FirmwareVolumeBlock.h>
|
||||||
|
|
||||||
|
|
|
@ -42,10 +42,12 @@
|
||||||
UefiDriverEntryPoint
|
UefiDriverEntryPoint
|
||||||
UefiBootServicesTableLib
|
UefiBootServicesTableLib
|
||||||
UefiRuntimeLib
|
UefiRuntimeLib
|
||||||
|
DxeServicesTableLib
|
||||||
|
|
||||||
[Guids]
|
[Guids]
|
||||||
gEfiSystemNvDataFvGuid
|
gEfiSystemNvDataFvGuid
|
||||||
gEfiVariableGuid
|
gEfiVariableGuid
|
||||||
|
gEfiEventVirtualAddressChangeGuid
|
||||||
|
|
||||||
[Protocols]
|
[Protocols]
|
||||||
gEfiBlockIoProtocolGuid
|
gEfiBlockIoProtocolGuid
|
||||||
|
|
|
@ -20,6 +20,7 @@
|
||||||
#include <Library/UefiLib.h>
|
#include <Library/UefiLib.h>
|
||||||
#include <Library/BaseMemoryLib.h>
|
#include <Library/BaseMemoryLib.h>
|
||||||
#include <Library/MemoryAllocationLib.h>
|
#include <Library/MemoryAllocationLib.h>
|
||||||
|
#include <Library/DxeServicesTableLib.h>
|
||||||
#include <Library/UefiBootServicesTableLib.h>
|
#include <Library/UefiBootServicesTableLib.h>
|
||||||
|
|
||||||
#include <Guid/VariableFormat.h>
|
#include <Guid/VariableFormat.h>
|
||||||
|
@ -27,6 +28,8 @@
|
||||||
|
|
||||||
#include "NorFlashDxe.h"
|
#include "NorFlashDxe.h"
|
||||||
|
|
||||||
|
STATIC EFI_EVENT mFvbVirtualAddrChangeEvent;
|
||||||
|
STATIC UINTN mFlashNvStorageVariableBase;
|
||||||
|
|
||||||
///
|
///
|
||||||
/// The Firmware Volume Block Protocol is the low-level interface
|
/// The Firmware Volume Block Protocol is the low-level interface
|
||||||
|
@ -301,7 +304,7 @@ FvbGetPhysicalAddress (
|
||||||
|
|
||||||
ASSERT(Address != NULL);
|
ASSERT(Address != NULL);
|
||||||
|
|
||||||
*Address = PcdGet32 (PcdFlashNvStorageVariableBase);
|
*Address = mFlashNvStorageVariableBase;
|
||||||
return EFI_SUCCESS;
|
return EFI_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -745,6 +748,25 @@ EXIT:
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
Fixup internal data so that EFI can be call in virtual mode.
|
||||||
|
Call the passed in Child Notify event and convert any pointers in
|
||||||
|
lib to virtual mode.
|
||||||
|
|
||||||
|
@param[in] Event The Event that is being processed
|
||||||
|
@param[in] Context Event Context
|
||||||
|
**/
|
||||||
|
VOID
|
||||||
|
EFIAPI
|
||||||
|
FvbVirtualNotifyEvent (
|
||||||
|
IN EFI_EVENT Event,
|
||||||
|
IN VOID *Context
|
||||||
|
)
|
||||||
|
{
|
||||||
|
EfiConvertPointer (0x0, (VOID**)&mFlashNvStorageVariableBase);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
EFI_STATUS
|
EFI_STATUS
|
||||||
EFIAPI
|
EFIAPI
|
||||||
NorFlashFvbInitialize (
|
NorFlashFvbInitialize (
|
||||||
|
@ -754,10 +776,12 @@ NorFlashFvbInitialize (
|
||||||
EFI_STATUS Status;
|
EFI_STATUS Status;
|
||||||
UINT32 FvbNumLba;
|
UINT32 FvbNumLba;
|
||||||
EFI_BOOT_MODE BootMode;
|
EFI_BOOT_MODE BootMode;
|
||||||
|
UINTN RuntimeMmioRegionSize;
|
||||||
|
|
||||||
DEBUG((DEBUG_BLKIO,"NorFlashFvbInitialize\n"));
|
DEBUG((DEBUG_BLKIO,"NorFlashFvbInitialize\n"));
|
||||||
|
|
||||||
Instance->Initialized = TRUE;
|
Instance->Initialized = TRUE;
|
||||||
|
mFlashNvStorageVariableBase = FixedPcdGet32 (PcdFlashNvStorageVariableBase);
|
||||||
|
|
||||||
// Set the index of the first LBA for the FVB
|
// Set the index of the first LBA for the FVB
|
||||||
Instance->StartLba = (PcdGet32 (PcdFlashNvStorageVariableBase) - Instance->RegionBaseAddress) / Instance->Media.BlockSize;
|
Instance->StartLba = (PcdGet32 (PcdFlashNvStorageVariableBase) - Instance->RegionBaseAddress) / Instance->Media.BlockSize;
|
||||||
|
@ -789,5 +813,41 @@ NorFlashFvbInitialize (
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// Declare the Non-Volatile storage as EFI_MEMORY_RUNTIME
|
||||||
|
//
|
||||||
|
|
||||||
|
// Note: all the NOR Flash region needs to be reserved into the UEFI Runtime memory;
|
||||||
|
// even if we only use the small block region at the top of the NOR Flash.
|
||||||
|
// The reason is when the NOR Flash memory is set into program mode, the command
|
||||||
|
// is written as the base of the flash region (ie: Instance->DeviceBaseAddress)
|
||||||
|
RuntimeMmioRegionSize = (Instance->RegionBaseAddress - Instance->DeviceBaseAddress) + Instance->Size;
|
||||||
|
|
||||||
|
Status = gDS->AddMemorySpace (
|
||||||
|
EfiGcdMemoryTypeMemoryMappedIo,
|
||||||
|
Instance->DeviceBaseAddress, RuntimeMmioRegionSize,
|
||||||
|
EFI_MEMORY_UC | EFI_MEMORY_RUNTIME
|
||||||
|
);
|
||||||
|
ASSERT_EFI_ERROR (Status);
|
||||||
|
|
||||||
|
Status = gDS->SetMemorySpaceAttributes (
|
||||||
|
Instance->DeviceBaseAddress, RuntimeMmioRegionSize,
|
||||||
|
EFI_MEMORY_UC | EFI_MEMORY_RUNTIME);
|
||||||
|
ASSERT_EFI_ERROR (Status);
|
||||||
|
|
||||||
|
//
|
||||||
|
// Register for the virtual address change event
|
||||||
|
//
|
||||||
|
Status = gBS->CreateEventEx (
|
||||||
|
EVT_NOTIFY_SIGNAL,
|
||||||
|
TPL_NOTIFY,
|
||||||
|
FvbVirtualNotifyEvent,
|
||||||
|
NULL,
|
||||||
|
&gEfiEventVirtualAddressChangeGuid,
|
||||||
|
&mFvbVirtualAddrChangeEvent
|
||||||
|
);
|
||||||
|
ASSERT_EFI_ERROR (Status);
|
||||||
|
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue