diff options
Diffstat (limited to 'EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32')
5 files changed, 2171 insertions, 0 deletions
diff --git a/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/Fvb.c b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/Fvb.c new file mode 100644 index 0000000..1cf85c0 --- /dev/null +++ b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/Fvb.c @@ -0,0 +1,617 @@ +/*++ + +Copyright (c) 2004 - 2006, Intel Corporation +All rights reserved. This program and the accompanying materials +are licensed and made available under the terms and conditions of the BSD License +which accompanies this distribution. The full text of the license may be found at +http://opensource.org/licenses/bsd-license.php + +THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +Module Name: + + Fvb.c + +Abstract: + + Firmware Volume Block Protocol Runtime Abstraction + + mFvbEntry is an array of Handle Fvb pairs. The Fvb Lib Instance matches the + index in the mFvbEntry array. This should be the same sequence as the FVB's + were described in the HOB. We have to remember the handle so we can tell if + the protocol has been reinstalled and it needs updateing. + + If you are using any of these lib functions.you must first call FvbInitialize (). + +Key: + FVB - Firmware Volume Block + +--*/ + +#include "Tiano.h" +#include "EfiRuntimeLib.h" +#include EFI_PROTOCOL_DEFINITION (FirmwareVolumeBlock) +#include EFI_PROTOCOL_DEFINITION (FvbExtension) + +// +// Lib will ASSERT if more FVB devices than this are added to the system. +// +UINTN mFvbCount; +VOID *mFvbRegistration; +VOID *mFvbExtRegistration; +static EFI_EVENT mEfiFvbVirtualNotifyEvent; +BOOLEAN gEfiFvbInitialized = FALSE; +EFI_EVENT mFvbEvent; + +BOOLEAN +IsMemoryRuntime ( + IN VOID *Address + ) +/*++ + +Routine Description: + Check whether an address is runtime memory or not. + +Arguments: + + Address - The Address being checked. + +Returns: + TRUE - The address is runtime memory. + FALSE - The address is not runtime memory. + +--*/ +{ + EFI_STATUS Status; + UINT8 TmpMemoryMap[1]; + UINTN MapKey; + UINTN DescriptorSize; + UINT32 DescriptorVersion; + UINTN MemoryMapSize; + EFI_MEMORY_DESCRIPTOR *MemoryMap; + EFI_MEMORY_DESCRIPTOR *MemoryMapPtr; + BOOLEAN IsRuntime; + UINTN Index; + + IsRuntime = FALSE; + + // + // Get System MemoryMapSize + // + MemoryMapSize = 1; + Status = gBS->GetMemoryMap ( + &MemoryMapSize, + (EFI_MEMORY_DESCRIPTOR *)TmpMemoryMap, + &MapKey, + &DescriptorSize, + &DescriptorVersion + ); + ASSERT (Status == EFI_BUFFER_TOO_SMALL); + // + // Enlarge space here, because we will allocate pool now. + // + MemoryMapSize += EFI_PAGE_SIZE; + Status = gBS->AllocatePool ( + EfiBootServicesData, + MemoryMapSize, + (VOID**)&MemoryMap + ); + ASSERT_EFI_ERROR (Status); + + // + // Get System MemoryMap + // + Status = gBS->GetMemoryMap ( + &MemoryMapSize, + MemoryMap, + &MapKey, + &DescriptorSize, + &DescriptorVersion + ); + ASSERT_EFI_ERROR (Status); + + MemoryMapPtr = MemoryMap; + // + // Search the request Address + // + for (Index = 0; Index < (MemoryMapSize / DescriptorSize); Index++) { + if (((EFI_PHYSICAL_ADDRESS)(UINTN)Address >= MemoryMap->PhysicalStart) && + ((EFI_PHYSICAL_ADDRESS)(UINTN)Address < MemoryMap->PhysicalStart + + LShiftU64 (MemoryMap->NumberOfPages, EFI_PAGE_SHIFT))) { + // + // Found it + // + if (MemoryMap->Attribute & EFI_MEMORY_RUNTIME) { + IsRuntime = TRUE; + } + break; + } + // + // Get next item + // + MemoryMap = (EFI_MEMORY_DESCRIPTOR *)((UINTN)MemoryMap + DescriptorSize); + } + + // + // Done + // + gBS->FreePool (MemoryMapPtr); + + return IsRuntime; +} + +VOID +EFIAPI +FvbNotificationFunction ( + IN EFI_EVENT Event, + IN VOID *Context + ) +/*++ + +Routine Description: + Update mFvbEntry. Add new entry, or update existing entry if Fvb protocol is + reinstalled. + +Arguments: + + Event - The Event that is being processed + + Context - Event Context + +Returns: + None + +--*/ +{ + EFI_STATUS Status; + UINTN BufferSize; + EFI_HANDLE Handle; + UINTN Index; + UINTN UpdateIndex; + EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL *Fvb; + EFI_FVB_EXTENSION_PROTOCOL *FvbExtension; + + while (TRUE) { + BufferSize = sizeof (Handle); + Status = gBS->LocateHandle ( + ByRegisterNotify, + &gEfiFirmwareVolumeBlockProtocolGuid, + mFvbRegistration, + &BufferSize, + &Handle + ); + if (EFI_ERROR (Status)) { + // + // Exit Path of While Loop.... + // + break; + } + + UpdateIndex = MAX_FVB_COUNT; + for (Index = 0; Index < mFvbCount; Index++) { + if (mFvbEntry[Index].Handle == Handle) { + // + // If the handle is already in the table just update the protocol + // + UpdateIndex = Index; + break; + } + } + + if (UpdateIndex == MAX_FVB_COUNT) { + // + // Use the next free slot for a new entry + // + UpdateIndex = mFvbCount; + } + // + // The array does not have enough entries + // + ASSERT (UpdateIndex < MAX_FVB_COUNT); + + // + // Get the interface pointer and if it's ours, skip it. + // We check Runtime here, because it has no reason to register + // a boot time FVB protocol. + // + Status = gBS->HandleProtocol (Handle, &gEfiFirmwareVolumeBlockProtocolGuid, &Fvb); + ASSERT_EFI_ERROR (Status); + if (IsMemoryRuntime (Fvb)) { + // + // Increase mFvbCount if we need to add a new entry + // + if (UpdateIndex == mFvbCount) { + mFvbCount++; + } + mFvbEntry[UpdateIndex].Handle = Handle; + mFvbEntry[UpdateIndex].Fvb = Fvb; + mFvbEntry[UpdateIndex].FvbExtension = NULL; + + Status = gBS->HandleProtocol (Handle, &gEfiFvbExtensionProtocolGuid, &FvbExtension); + if ((Status == EFI_SUCCESS) && IsMemoryRuntime (FvbExtension)) { + mFvbEntry[UpdateIndex].FvbExtension = FvbExtension; + } + } + } +} + +EFI_STATUS +EfiFvbInitialize ( + VOID + ) +/*++ + +Routine Description: + Initialize globals and register Fvb Protocol notification function. + +Arguments: + None + +Returns: + EFI_SUCCESS - Fvb is successfully initialized + others - Fail to initialize + +--*/ +{ + UINTN Status; + mFvbCount = 0; + + Status = gBS->AllocatePool ( + EfiRuntimeServicesData, + (UINTN) sizeof (FVB_ENTRY) * MAX_FVB_COUNT, + (VOID *) &mFvbEntry + ); + + if (EFI_ERROR (Status)) { + return Status; + } + + EfiZeroMem (mFvbEntry, sizeof (FVB_ENTRY) * MAX_FVB_COUNT); + + mFvbEvent = RtEfiLibCreateProtocolNotifyEvent ( + &gEfiFirmwareVolumeBlockProtocolGuid, + EFI_TPL_CALLBACK, + FvbNotificationFunction, + NULL, + &mFvbRegistration + ); + + // + // Register SetVirtualAddressMap () notify function + // + // Status = gBS->CreateEvent ( + // EFI_EVENT_SIGNAL_VIRTUAL_ADDRESS_CHANGE, + // EFI_TPL_NOTIFY, + // EfiRuntimeLibFvbVirtualNotifyEvent, + // NULL, + // &mEfiFvbVirtualNotifyEvent + // ); + // ASSERT_EFI_ERROR (Status); + // + gEfiFvbInitialized = TRUE; + + return EFI_SUCCESS; +} + +EFI_STATUS +EfiFvbShutdown ( + VOID + ) +/*++ + +Routine Description: + Release resources allocated in EfiFvbInitialize. + +Arguments: + None + +Returns: + EFI_SUCCESS + +--*/ +{ + gBS->FreePool ((VOID *) mFvbEntry); + gBS->CloseEvent (mFvbEvent); + gEfiFvbInitialized = FALSE; + return EFI_SUCCESS; +} + +// +// The following functions wrap Fvb protocol in the Runtime Lib functions. +// The Instance translates into Fvb instance. The Fvb order defined by HOBs and +// thus the sequence of FVB protocol addition define Instance. +// +// EfiFvbInitialize () must be called before any of the following functions +// must be called. +// + +EFI_STATUS +EfiFvbReadBlock ( + IN UINTN Instance, + IN EFI_LBA Lba, + IN UINTN Offset, + IN OUT UINTN *NumBytes, + IN UINT8 *Buffer + ) +/*++ + +Routine Description: + Reads specified number of bytes into a buffer from the specified block + +Arguments: + Instance - The FV instance to be read from + Lba - The logical block address to be read from + Offset - Offset into the block at which to begin reading + NumBytes - Pointer that on input contains the total size of + the buffer. On output, it contains the total number + of bytes read + Buffer - Pointer to a caller allocated buffer that will be + used to hold the data read + +Returns: + + Status code + + EFI_INVALID_PARAMETER - invalid parameter + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + return mFvbEntry[Instance].Fvb->Read (mFvbEntry[Instance].Fvb, Lba, Offset, NumBytes, Buffer); +} + +EFI_STATUS +EfiFvbWriteBlock ( + IN UINTN Instance, + IN EFI_LBA Lba, + IN UINTN Offset, + IN OUT UINTN *NumBytes, + IN UINT8 *Buffer + ) +/*++ + +Routine Description: + Writes specified number of bytes from the input buffer to the block + +Arguments: + Instance - The FV instance to be written to + Lba - The starting logical block index to write to + Offset - Offset into the block at which to begin writing + NumBytes - Pointer that on input contains the total size of + the buffer. On output, it contains the total number + of bytes actually written + Buffer - Pointer to a caller allocated buffer that contains + the source for the write + +Returns: + + Status code + + EFI_INVALID_PARAMETER - invalid parameter + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + return mFvbEntry[Instance].Fvb->Write (mFvbEntry[Instance].Fvb, Lba, Offset, NumBytes, Buffer); +} + +EFI_STATUS +EfiFvbEraseBlock ( + IN UINTN Instance, + IN EFI_LBA Lba + ) +/*++ + +Routine Description: + Erases and initializes a firmware volume block + +Arguments: + Instance - The FV instance to be erased + Lba - The logical block index to be erased + +Returns: + + Status code + + EFI_INVALID_PARAMETER - invalid parameter + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + return mFvbEntry[Instance].Fvb->EraseBlocks (mFvbEntry[Instance].Fvb, Lba, -1); +} + +EFI_STATUS +EfiFvbGetVolumeAttributes ( + IN UINTN Instance, + OUT EFI_FVB_ATTRIBUTES *Attributes + ) +/*++ + +Routine Description: + Retrieves attributes, insures positive polarity of attribute bits, returns + resulting attributes in output parameter + +Arguments: + Instance - The FV instance whose attributes is going to be + returned + Attributes - Output buffer which contains attributes + +Returns: + Status code + + EFI_INVALID_PARAMETER - invalid parameter + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + return mFvbEntry[Instance].Fvb->GetVolumeAttributes (mFvbEntry[Instance].Fvb, Attributes); +} + +EFI_STATUS +EfiFvbSetVolumeAttributes ( + IN UINTN Instance, + IN EFI_FVB_ATTRIBUTES Attributes + ) +/*++ + +Routine Description: + Modifies the current settings of the firmware volume according to the + input parameter, and returns the new setting of the volume + +Arguments: + Instance - The FV instance whose attributes is going to be + modified + Attributes - On input, it is a pointer to EFI_FVB_ATTRIBUTES + containing the desired firmware volume settings. + On successful return, it contains the new settings + of the firmware volume + +Returns: + Status code + + EFI_INVALID_PARAMETER - invalid parameter + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + return mFvbEntry[Instance].Fvb->SetVolumeAttributes (mFvbEntry[Instance].Fvb, &Attributes); +} + +EFI_STATUS +EfiFvbGetPhysicalAddress ( + IN UINTN Instance, + OUT EFI_PHYSICAL_ADDRESS *BaseAddress + ) +/*++ + +Routine Description: + Retrieves the physical address of a memory mapped FV + +Arguments: + Instance - The FV instance whose base address is going to be + returned + BaseAddress - Pointer to a caller allocated EFI_PHYSICAL_ADDRESS + that on successful return, contains the base address + of the firmware volume. + +Returns: + + Status code + + EFI_INVALID_PARAMETER - invalid parameter + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + return mFvbEntry[Instance].Fvb->GetPhysicalAddress (mFvbEntry[Instance].Fvb, BaseAddress); +} + +EFI_STATUS +EfiFvbGetBlockSize ( + IN UINTN Instance, + IN EFI_LBA Lba, + OUT UINTN *BlockSize, + OUT UINTN *NumOfBlocks + ) +/*++ + +Routine Description: + Retrieve the size of a logical block + +Arguments: + Instance - The FV instance whose block size is going to be + returned + Lba - Indicates which block to return the size for. + BlockSize - A pointer to a caller allocated UINTN in which + the size of the block is returned + NumOfBlocks - a pointer to a caller allocated UINTN in which the + number of consecutive blocks starting with Lba is + returned. All blocks in this range have a size of + BlockSize + +Returns: + EFI_SUCCESS - The firmware volume was read successfully and + contents are in Buffer + + EFI_INVALID_PARAMETER - invalid parameter + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + return mFvbEntry[Instance].Fvb->GetBlockSize (mFvbEntry[Instance].Fvb, Lba, BlockSize, NumOfBlocks); +} + +EFI_STATUS +EfiFvbEraseCustomBlockRange ( + IN UINTN Instance, + IN EFI_LBA StartLba, + IN UINTN OffsetStartLba, + IN EFI_LBA LastLba, + IN UINTN OffsetLastLba + ) +/*++ + +Routine Description: + Erases and initializes a specified range of a firmware volume + +Arguments: + Instance - The FV instance to be erased + StartLba - The starting logical block index to be erased + OffsetStartLba - Offset into the starting block at which to + begin erasing + LastLba - The last logical block index to be erased + OffsetLastLba - Offset into the last block at which to end erasing + +Returns: + + Status code + + EFI_INVALID_PARAMETER - invalid parameter + + EFI_UNSUPPORTED - not support + +--*/ +{ + if (Instance >= mFvbCount) { + return EFI_INVALID_PARAMETER; + } + + if (!(mFvbEntry[Instance].FvbExtension)) { + return EFI_UNSUPPORTED; + } + + if (!(mFvbEntry[Instance].FvbExtension->EraseFvbCustomBlock)) { + return EFI_UNSUPPORTED; + } + + return mFvbEntry[Instance].FvbExtension->EraseFvbCustomBlock ( + mFvbEntry[Instance].FvbExtension, + StartLba, + OffsetStartLba, + LastLba, + OffsetLastLba + ); +} diff --git a/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/IoLib.c b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/IoLib.c new file mode 100644 index 0000000..ad65bae --- /dev/null +++ b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/IoLib.c @@ -0,0 +1,130 @@ +/*++ + +Copyright (c) 2004, Intel Corporation +All rights reserved. This program and the accompanying materials +are licensed and made available under the terms and conditions of the BSD License +which accompanies this distribution. The full text of the license may be found at +http://opensource.org/licenses/bsd-license.php + +THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +Module Name: + + IoLib.c + +Abstract: + + Light weight lib to support Tiano drivers. + +--*/ + +#include "Tiano.h" +#include "EfiRuntimeLib.h" +#include EFI_PROTOCOL_DEFINITION (CpuIo) + +extern EFI_CPU_IO_PROTOCOL *gCpuIo; + +EFI_STATUS +EfiIoRead ( + IN EFI_CPU_IO_PROTOCOL_WIDTH Width, + IN UINT64 Address, + IN UINTN Count, + IN OUT VOID *Buffer + ) +/*++ + +Routine Description: + Perform an IO read into Buffer. + +Arguments: + Width - Width of read transaction, and repeat operation to use + Address - IO address to read + Count - Number of times to read the IO address. + Buffer - Buffer to read data into. size is Width * Count + +Returns: + BugBug: Check with Mike to see if I can find this #define some ware else + +--*/ +{ + return gCpuIo->Io.Read (gCpuIo, Width, Address, Count, Buffer); +} + +EFI_STATUS +EfiIoWrite ( + IN EFI_CPU_IO_PROTOCOL_WIDTH Width, + IN UINT64 Address, + IN UINTN Count, + IN OUT VOID *Buffer + ) +/*++ + +Routine Description: + Perform an IO write into Buffer. + +Arguments: + Width - Width of write transaction, and repeat operation to use + Address - IO address to write + Count - Number of times to write the IO address. + Buffer - Buffer to write data from. size is Width * Count + +Returns: + BugBug: Check with Mike to see if I can find this #define some ware else + +--*/ +{ + return gCpuIo->Io.Write (gCpuIo, Width, Address, Count, Buffer); +} + +EFI_STATUS +EfiMemRead ( + IN EFI_CPU_IO_PROTOCOL_WIDTH Width, + IN UINT64 Address, + IN UINTN Count, + IN OUT VOID *Buffer + ) +/*++ + +Routine Description: + Perform a Memory mapped IO read into Buffer. + +Arguments: + Width - Width of each read transaction. + Address - Memory mapped IO address to read + Count - Number of Width quanta to read + Buffer - Buffer to read data into. size is Width * Count + +Returns: + BugBug: Check with Mike to see if I can find this #define some ware else + +--*/ +{ + return gCpuIo->Mem.Read (gCpuIo, Width, Address, Count, Buffer); +} + +EFI_STATUS +EfiMemWrite ( + IN EFI_CPU_IO_PROTOCOL_WIDTH Width, + IN UINT64 Address, + IN UINTN Count, + IN OUT VOID *Buffer + ) +/*++ + +Routine Description: + Perform a memory mapped IO write into Buffer. + +Arguments: + Width - Width of write transaction, and repeat operation to use + Address - IO address to write + Count - Number of times to write the IO address. + Buffer - Buffer to write data from. size is Width * Count + +Returns: + BugBug: Check with Mike to see if I can find this #define some ware else + +--*/ +{ + return gCpuIo->Mem.Write (gCpuIo, Width, Address, Count, Buffer); +} diff --git a/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/Lock.c b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/Lock.c new file mode 100644 index 0000000..596da27 --- /dev/null +++ b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/Lock.c @@ -0,0 +1,177 @@ +/*++ + +Copyright (c) 2004, Intel Corporation +All rights reserved. This program and the accompanying materials +are licensed and made available under the terms and conditions of the BSD License +which accompanies this distribution. The full text of the license may be found at +http://opensource.org/licenses/bsd-license.php + +THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +Module Name: + + Lock.c + +Abstract: + + Support for locking lib services. + +--*/ + +#include "Tiano.h" +#include "EfiDriverLib.h" + +extern +BOOLEAN +EfiAtRuntime ( + VOID + ); + +VOID +EfiInitializeLock ( + IN OUT EFI_LOCK *Lock, + IN EFI_TPL Priority + ) +/*++ + +Routine Description: + + Initialize a basic mutual exclusion lock. Each lock + provides mutual exclusion access at it's task priority + level. Since there is no-premption (at any TPL) or + multiprocessor support, acquiring the lock only consists + of raising to the locks TPL. + + Note on a check build ASSERT()s are used to ensure proper + lock usage. + +Arguments: + + Lock - The EFI_LOCK structure to initialize + + Priority - The task priority level of the lock + + +Returns: + + An initialized Efi Lock structure. + +--*/ +{ + Lock->Tpl = Priority; + Lock->OwnerTpl = 0; + Lock->Lock = 0; +} + +EFI_STATUS +EfiAcquireLockOrFail ( + IN EFI_LOCK *Lock + ) +/*++ + +Routine Description: + + Initialize a basic mutual exclusion lock. Each lock + provides mutual exclusion access at it's task priority + level. Since there is no-premption (at any TPL) or + multiprocessor support, acquiring the lock only consists + of raising to the locks TPL. + +Arguments: + + Lock - The EFI_LOCK structure to initialize + +Returns: + + EFI_SUCCESS - Lock Owned. + EFI_ACCESS_DENIED - Reentrant Lock Acquisition, Lock not Owned. + +--*/ +{ + if (Lock->Lock != 0) { + // + // Lock is already owned, so bail out + // + return EFI_ACCESS_DENIED; + } + + if (!EfiAtRuntime ()) { + // + // The check is just debug code for core inplementation. It must + // always be true in a driver + // + Lock->OwnerTpl = gBS->RaiseTPL (Lock->Tpl); + } + + Lock->Lock += 1; + return EFI_SUCCESS; +} + +VOID +EfiAcquireLock ( + IN EFI_LOCK *Lock + ) +/*++ + +Routine Description: + + Raising to the task priority level of the mutual exclusion + lock, and then acquires ownership of the lock. + +Arguments: + + Lock - The lock to acquire + +Returns: + + Lock owned + +--*/ +{ + EFI_STATUS Status; + + Status = EfiAcquireLockOrFail (Lock); + + // + // Lock was already locked. + // + ASSERT_EFI_ERROR (Status); +} + +VOID +EfiReleaseLock ( + IN EFI_LOCK *Lock + ) +/*++ + +Routine Description: + + Releases ownership of the mutual exclusion lock, and + restores the previous task priority level. + +Arguments: + + Lock - The lock to release + +Returns: + + Lock unowned + +--*/ +{ + EFI_TPL Tpl; + + Tpl = Lock->OwnerTpl; + + ASSERT (Lock->Lock == 1); + Lock->Lock -= 1; + + if (!EfiAtRuntime ()) { + // + // The check is just debug code for core inplementation. It must + // always be true in a driver + // + gBS->RestoreTPL (Tpl); + } +} diff --git a/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/PlatformIoLib.c b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/PlatformIoLib.c new file mode 100644 index 0000000..d06d0ea --- /dev/null +++ b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/PlatformIoLib.c @@ -0,0 +1,407 @@ +/*++ + +Copyright (c) 2004 - 2006, Intel Corporation +All rights reserved. This program and the accompanying materials +are licensed and made available under the terms and conditions of the BSD License +which accompanies this distribution. The full text of the license may be found at +http://opensource.org/licenses/bsd-license.php + +THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +Module Name: + + PlatformIoLib.c + +Abstract: + +--*/ + +#include "Tiano.h" +#include "EfiRuntimeLib.h" +#include EFI_PROTOCOL_DEFINITION (CpuIo) + +#define PCI_CONFIG_INDEX_PORT 0xcf8 +#define PCI_CONFIG_DATA_PORT 0xcfc +#define REFRESH_CYCLE_TOGGLE_BIT 0x10 + +UINT32 +GetPciAddress ( + UINT8 Segment, + UINT8 Bus, + UINT8 DevFunc, + UINT8 Register + ) +/*++ + +Routine Description: + Constructs PCI Address 32 bits + +Arguments: + Segment - PCI Segment ACPI _SEG + Bus - PCI Bus + DevFunc - PCI Device(7:3) and Func(2:0) + Register - PCI config space register + +Returns: + PciAddress to be written to Config Port + +--*/ +{ + UINT32 Data; + + Data = (((UINT32) Segment) << 24); + Data |= (((UINT32) Bus) << 16); + Data |= (((UINT32) DevFunc) << 8); + Data |= (UINT32) Register; + + return Data; + +} + +UINT8 +PciRead8 ( + UINT8 Segment, + UINT8 Bus, + UINT8 DevFunc, + UINT8 Register + ) +/*++ + +Routine Description: + Perform an one byte PCI config cycle read + +Arguments: + Segment - PCI Segment ACPI _SEG + Bus - PCI Bus + DevFunc - PCI Device(7:3) and Func(2:0) + Register - PCI config space register + +Returns: + Data read from PCI config space + +--*/ +{ + EFI_STATUS Status; + UINT32 PciAddress; + UINT32 PciAddress1; + UINT8 Data; + + PciAddress = GetPciAddress (Segment, Bus, DevFunc, Register); + // + // Set bit 31 for PCI config access + // + PciAddress1 = PciAddress; + PciAddress = ((PciAddress & 0xFFFFFFFC) | (0x80000000)); + + Status = EfiIoWrite (EfiCpuIoWidthUint32, PCI_CONFIG_INDEX_PORT, 1, &PciAddress); + + if (EFI_ERROR (Status)) { + return 0; + } + + EfiIoRead (EfiCpuIoWidthUint8, (PCI_CONFIG_DATA_PORT + (PciAddress1 & 0x3)), 1, &Data); + + return Data; +} + +UINT16 +PciRead16 ( + UINT8 Segment, + UINT8 Bus, + UINT8 DevFunc, + UINT8 Register + ) +/*++ + +Routine Description: + Perform an two byte PCI config cycle read + +Arguments: + Segment - PCI Segment ACPI _SEG + Bus - PCI Bus + DevFunc - PCI Device(7:3) and Func(2:0) + Register - PCI config space register + +Returns: + Data read from PCI config space + +--*/ +{ + EFI_STATUS Status; + UINT32 PciAddress; + UINT32 PciAddress1; + UINT16 Data; + + PciAddress = GetPciAddress (Segment, Bus, DevFunc, Register); + // + // Set bit 31 for PCI config access + // + PciAddress1 = PciAddress; + PciAddress = ((PciAddress & 0xFFFFFFFC) | (0x80000000)); + + Status = EfiIoWrite (EfiCpuIoWidthUint32, PCI_CONFIG_INDEX_PORT, 1, &PciAddress); + + if (EFI_ERROR (Status)) { + return 0; + } + + EfiIoRead (EfiCpuIoWidthUint16, (PCI_CONFIG_DATA_PORT + (PciAddress1 & 0x3)), 1, &Data); + + return Data; +} + +UINT32 +PciRead32 ( + UINT8 Segment, + UINT8 Bus, + UINT8 DevFunc, + UINT8 Register + ) +/*++ + +Routine Description: + Perform an four byte PCI config cycle read + +Arguments: + Segment - PCI Segment ACPI _SEG + Bus - PCI Bus + DevFunc - PCI Device(7:3) and Func(2:0) + Register - PCI config space register + +Returns: + Data read from PCI config space + +--*/ +{ + EFI_STATUS Status; + UINT32 PciAddress; + UINT32 PciAddress1; + UINT32 Data; + + PciAddress = GetPciAddress (Segment, Bus, DevFunc, Register); + // + // Set bit 31 for PCI config access + // + PciAddress1 = PciAddress; + PciAddress = ((PciAddress & 0xFFFFFFFC) | (0x80000000)); + + Status = EfiIoWrite (EfiCpuIoWidthUint32, PCI_CONFIG_INDEX_PORT, 1, &PciAddress); + + if (EFI_ERROR (Status)) { + return 0; + } + + EfiIoRead (EfiCpuIoWidthUint32, (PCI_CONFIG_DATA_PORT + (PciAddress1 & 0x3)), 1, &Data); + + return Data; +} + +VOID +PciWrite8 ( + UINT8 Segment, + UINT8 Bus, + UINT8 DevFunc, + UINT8 Register, + UINT8 Data + ) +/*++ + +Routine Description: + Perform an one byte PCI config cycle write + +Arguments: + Segment - PCI Segment ACPI _SEG + Bus - PCI Bus + DevFunc - PCI Device(7:3) and Func(2:0) + Register - PCI config space register + Data - Data to write + +Returns: + NONE + +--*/ +{ + EFI_STATUS Status; + UINT32 PciAddress; + UINT32 PciAddress1; + + PciAddress = GetPciAddress (Segment, Bus, DevFunc, Register); + // + // Set bit 31 for PCI config access + // + PciAddress1 = PciAddress; + PciAddress = ((PciAddress & 0xFFFFFFFC) | (0x80000000)); + + Status = EfiIoWrite (EfiCpuIoWidthUint32, PCI_CONFIG_INDEX_PORT, 1, &PciAddress); + + if (EFI_ERROR (Status)) { + return ; + } + + EfiIoWrite (EfiCpuIoWidthUint8, (PCI_CONFIG_DATA_PORT + (PciAddress1 & 0x3)), 1, &Data); +} + +VOID +PciWrite16 ( + UINT8 Segment, + UINT8 Bus, + UINT8 DevFunc, + UINT8 Register, + UINT16 Data + ) +/*++ + +Routine Description: + Perform an two byte PCI config cycle write + +Arguments: + Segment - PCI Segment ACPI _SEG + Bus - PCI Bus + DevFunc - PCI Device(7:3) and Func(2:0) + Register - PCI config space register + Data - Data to write + +Returns: + NONE + +--*/ +{ + EFI_STATUS Status; + UINT32 PciAddress; + UINT32 PciAddress1; + + PciAddress = GetPciAddress (Segment, Bus, DevFunc, Register); + // + // Set bit 31 for PCI config access + // + PciAddress1 = PciAddress; + PciAddress = ((PciAddress & 0xFFFFFFFC) | (0x80000000)); + + Status = EfiIoWrite (EfiCpuIoWidthUint32, PCI_CONFIG_INDEX_PORT, 1, &PciAddress); + + if (EFI_ERROR (Status)) { + return ; + } + + EfiIoWrite (EfiCpuIoWidthUint16, (PCI_CONFIG_DATA_PORT + (PciAddress1 & 0x3)), 1, &Data); +} + +VOID +PciWrite32 ( + UINT8 Segment, + UINT8 Bus, + UINT8 DevFunc, + UINT8 Register, + UINT32 Data + ) +/*++ + +Routine Description: + Perform an four byte PCI config cycle write + +Arguments: + Segment - PCI Segment ACPI _SEG + Bus - PCI Bus + DevFunc - PCI Device(7:3) and Func(2:0) + Register - PCI config space register + Data - Data to write + +Returns: + NONE + +--*/ +{ + EFI_STATUS Status; + UINT32 PciAddress; + UINT32 PciAddress1; + + PciAddress = GetPciAddress (Segment, Bus, DevFunc, Register); + // + // Set bit 31 for PCI config access + // + PciAddress1 = PciAddress; + PciAddress = ((PciAddress & 0xFFFFFFFC) | (0x80000000)); + + Status = EfiIoWrite (EfiCpuIoWidthUint32, PCI_CONFIG_INDEX_PORT, 1, &PciAddress); + + if (EFI_ERROR (Status)) { + return ; + } + + EfiIoWrite (EfiCpuIoWidthUint32, (PCI_CONFIG_DATA_PORT + (PciAddress1 & 0x3)), 1, &Data); +} +// +// Delay Primative +// +VOID +EfiStall ( + IN UINTN Microseconds + ) +/*++ + +Routine Description: + Delay for at least the request number of microseconds + +Arguments: + Microseconds - Number of microseconds to delay. + +Returns: + NONE + +--*/ +{ + UINT8 Data; + UINT8 InitialState; + UINTN CycleIterations; + + CycleIterations = 0; + Data = 0; + InitialState = 0; + + if (EfiAtRuntime ()) { + // + // The time-source is 30 us granular, so calibrate the timing loop + // based on this baseline + // Error is possible 30us. + // + CycleIterations = (Microseconds - 1) / 30 + 1; + + // + // Use the DMA Refresh timer in port 0x61. Cheap but effective. + // The only issue is that the granularity is 30us, and we want to + // guarantee "at least" one full transition to avoid races. + // + // + // _____________/----------\__________/-------- + // + // |<--15us-->|<--15us-->| + // + // --------------------------------------------------> Time (us) + // + while (CycleIterations--) { + EfiIoRead (EfiCpuIoWidthUint8, 0x61, 1, &Data); + Data &= REFRESH_CYCLE_TOGGLE_BIT; + InitialState = Data; + + // + // Capture first transition (strictly less than one period) + // + while (InitialState == Data) { + EfiIoRead (EfiCpuIoWidthUint8, 0x61, 1, &Data); + Data &= REFRESH_CYCLE_TOGGLE_BIT; + } + + InitialState = Data; + // + // Capture next transition (guarantee at least one full pulse) + // + while (InitialState == Data) { + EfiIoRead (EfiCpuIoWidthUint8, 0x61, 1, &Data); + Data &= REFRESH_CYCLE_TOGGLE_BIT; + } + } + } else { + gBS->Stall (Microseconds); + } +} diff --git a/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/RuntimeLib.c b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/RuntimeLib.c new file mode 100644 index 0000000..e73095b --- /dev/null +++ b/EDK/Foundation/Library/RuntimeDxe/EfiRuntimeLib/ia32/RuntimeLib.c @@ -0,0 +1,840 @@ +/*++ + +Copyright (c) 2004 - 2006, Intel Corporation +All rights reserved. This program and the accompanying materials +are licensed and made available under the terms and conditions of the BSD License +which accompanies this distribution. The full text of the license may be found at +http://opensource.org/licenses/bsd-license.php + +THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +Module Name: + + RuntimeLib.c + +Abstract: + + Light weight lib to support Tiano drivers. + +--*/ + +#include "Tiano.h" +#include "EfiRuntimeLib.h" +#include EFI_PROTOCOL_DEFINITION (CpuIo) +#include EFI_PROTOCOL_DEFINITION (FirmwareVolumeBlock) +#include EFI_GUID_DEFINITION (StatusCodeCallerId) +#include EFI_ARCH_PROTOCOL_DEFINITION (StatusCode) + +// +// Driver Lib Module Globals +// +static EFI_RUNTIME_SERVICES *mRT; +static EFI_EVENT mRuntimeNotifyEvent = NULL; +static EFI_EVENT mEfiVirtualNotifyEvent = NULL; +static BOOLEAN mRuntimeLibInitialized = FALSE; +static BOOLEAN mEfiGoneVirtual = FALSE; + +// +// Runtime Global, but you should use the Lib functions +// +EFI_CPU_IO_PROTOCOL *gCpuIo; +BOOLEAN mEfiAtRuntime = FALSE; +FVB_ENTRY *mFvbEntry; + +#if (EFI_SPECIFICATION_VERSION >= 0x00020000) +static EFI_STATUS_CODE_PROTOCOL *gStatusCode = NULL; +#endif + +EFI_STATUS +EfiConvertPointer ( + IN UINTN DebugDisposition, + IN OUT VOID *Address + ) +/*++ + +Routine Description: + + Determines the new virtual address that is to be used on subsequent memory accesses. + +Arguments: + + DebugDisposition - Supplies type information for the pointer being converted. + Address - A pointer to a pointer that is to be fixed to be the value needed + for the new virtual address mappings being applied. + +Returns: + + Status code + +--*/ +{ + return mRT->ConvertPointer (DebugDisposition, Address); +} + +EFI_STATUS +EfiConvertInternalPointer ( + IN OUT VOID *Address + ) +/*++ + +Routine Description: + + Call EfiConvertPointer() to convert internal pointer. + +Arguments: + + Address - A pointer to a pointer that is to be fixed to be the value needed + for the new virtual address mappings being applied. + +Returns: + + Status code + +--*/ +{ + return EfiConvertPointer (EFI_INTERNAL_POINTER, Address); +} + +VOID +EFIAPI +EfiRuntimeLibFvbVirtualNotifyEvent ( + IN EFI_EVENT Event, + IN VOID *Context + ) +/*++ + +Routine Description: + + Convert all pointers in mFvbEntry after ExitBootServices. + +Arguments: + + Event - The Event that is being processed + + Context - Event Context + +Returns: + + None + +--*/ +{ + UINTN Index; + if (mFvbEntry != NULL) { + for (Index = 0; Index < MAX_FVB_COUNT; Index++) { + if (NULL != mFvbEntry[Index].Fvb) { + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb->GetBlockSize); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb->GetPhysicalAddress); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb->GetVolumeAttributes); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb->SetVolumeAttributes); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb->Read); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb->Write); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb->EraseBlocks); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].Fvb); + } + + if (NULL != mFvbEntry[Index].FvbExtension) { + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].FvbExtension->EraseFvbCustomBlock); + EfiConvertInternalPointer ((VOID **) &mFvbEntry[Index].FvbExtension); + } + } + + EfiConvertInternalPointer ((VOID **) &mFvbEntry); + } +} + +VOID +EFIAPI +RuntimeDriverExitBootServices ( + IN EFI_EVENT Event, + IN VOID *Context + ) +/*++ + +Routine Description: + + Set AtRuntime flag as TRUE after ExitBootServices + +Arguments: + + Event - The Event that is being processed + + Context - Event Context + +Returns: + + None + +--*/ +{ + mEfiAtRuntime = TRUE; +} + +extern BOOLEAN gEfiFvbInitialized; + +VOID +EFIAPI +EfiRuntimeLibVirtualNotifyEvent ( + IN EFI_EVENT Event, + IN VOID *Context + ) +/*++ + +Routine Description: + + 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. + +Arguments: + + Event - The Event that is being processed + + Context - Event Context + +Returns: + + None + +--*/ +{ + EFI_EVENT_NOTIFY ChildNotifyEventHandler; + + if (Context != NULL) { + ChildNotifyEventHandler = (EFI_EVENT_NOTIFY) (UINTN) Context; + ChildNotifyEventHandler (Event, NULL); + } + + if (gEfiFvbInitialized) { + EfiRuntimeLibFvbVirtualNotifyEvent (Event, Context); + } + // + // Update global for Runtime Services Table and IO + // + EfiConvertInternalPointer ((VOID **) &gCpuIo); +#if (EFI_SPECIFICATION_VERSION >= 0x00020000) + if (gStatusCode != NULL) { + EfiConvertInternalPointer ((VOID **) &gStatusCode->ReportStatusCode); + EfiConvertInternalPointer ((VOID **) &gStatusCode); + } +#endif + EfiConvertInternalPointer ((VOID **) &mRT); + + // + // Clear out BootService globals + // + gBS = NULL; + gST = NULL; + mEfiGoneVirtual = TRUE; +} + +EFI_STATUS +EfiInitializeRuntimeDriverLib ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable, + IN EFI_EVENT_NOTIFY GoVirtualChildEvent + ) +/*++ + +Routine Description: + + Intialize runtime Driver Lib if it has not yet been initialized. + +Arguments: + + ImageHandle - The firmware allocated handle for the EFI image. + + SystemTable - A pointer to the EFI System Table. + + GoVirtualChildEvent - Caller can register a virtual notification event. + +Returns: + + EFI_STATUS always returns EFI_SUCCESS except EFI_ALREADY_STARTED if already started. + +--*/ +{ + EFI_STATUS Status; + + if (mRuntimeLibInitialized) { + return EFI_ALREADY_STARTED; + } + + mRuntimeLibInitialized = TRUE; + + gST = SystemTable; + ASSERT (gST != NULL); + + gBS = SystemTable->BootServices; + ASSERT (gBS != NULL); + mRT = SystemTable->RuntimeServices; + ASSERT (mRT != NULL); + + Status = EfiLibGetSystemConfigurationTable (&gEfiDxeServicesTableGuid, (VOID **) &gDS); + ASSERT_EFI_ERROR (Status); + +#if (EFI_SPECIFICATION_VERSION >= 0x00020000) + Status = gBS->LocateProtocol (&gEfiStatusCodeRuntimeProtocolGuid, NULL, (VOID **)&gStatusCode); + if (EFI_ERROR (Status)) { + gStatusCode = NULL; + } +#endif + + Status = gBS->LocateProtocol (&gEfiCpuIoProtocolGuid, NULL, &gCpuIo); + if (EFI_ERROR (Status)) { + gCpuIo = NULL; + } + + // + // Register our ExitBootServices () notify function + // + Status = gBS->CreateEvent ( + EFI_EVENT_SIGNAL_EXIT_BOOT_SERVICES, + EFI_TPL_NOTIFY, + RuntimeDriverExitBootServices, + NULL, + &mRuntimeNotifyEvent + ); + ASSERT_EFI_ERROR (Status); + + // + // Register SetVirtualAddressMap () notify function + // + Status = gBS->CreateEvent ( + EFI_EVENT_SIGNAL_VIRTUAL_ADDRESS_CHANGE, + EFI_TPL_NOTIFY, + EfiRuntimeLibVirtualNotifyEvent, + (VOID *) (UINTN) GoVirtualChildEvent, + &mEfiVirtualNotifyEvent + ); + ASSERT_EFI_ERROR (Status); + + return EFI_SUCCESS; +} + +EFI_STATUS +EfiShutdownRuntimeDriverLib ( + VOID + ) +/*++ + +Routine Description: + + This routine will free some resources which have been allocated in + EfiInitializeRuntimeDriverLib(). If a runtime driver exits with an error, + it must call this routine to free the allocated resource before the exiting. + +Arguments: + + None + +Returns: + + EFI_SUCCESS - Shotdown the Runtime Driver Lib successfully + EFI_UNSUPPORTED - Runtime Driver lib was not initialized at all + +--*/ +{ + EFI_STATUS Status; + + if (!mRuntimeLibInitialized) { + // + // You must call EfiInitializeRuntimeDriverLib() first + // + return EFI_UNSUPPORTED; + } + + mRuntimeLibInitialized = FALSE; + + // + // Close our ExitBootServices () notify function + // + if (mRuntimeNotifyEvent != NULL) { + Status = gBS->CloseEvent (mRuntimeNotifyEvent); + ASSERT_EFI_ERROR (Status); + } + + // + // Close SetVirtualAddressMap () notify function + // + if (mEfiVirtualNotifyEvent != NULL) { + Status = gBS->CloseEvent (mEfiVirtualNotifyEvent); + ASSERT_EFI_ERROR (Status); + } + + return EFI_SUCCESS; +} + +EFI_STATUS +EfiInitializeSmmDriverLib ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +/*++ + +Routine Description: + + Intialize runtime Driver Lib if it has not yet been initialized. + +Arguments: + + ImageHandle - The firmware allocated handle for the EFI image. + + SystemTable - A pointer to the EFI System Table. + +Returns: + + EFI_STATUS always returns EFI_SUCCESS except EFI_ALREADY_STARTED if already started. + +--*/ +{ + EFI_STATUS Status; + + if (mRuntimeLibInitialized) { + return EFI_ALREADY_STARTED; + } + + mRuntimeLibInitialized = TRUE; + + gST = SystemTable; + ASSERT (gST != NULL); + + gBS = SystemTable->BootServices; + ASSERT (gBS != NULL); + mRT = SystemTable->RuntimeServices; + ASSERT (mRT != NULL); + +#if (EFI_SPECIFICATION_VERSION >= 0x00020000) + Status = gBS->LocateProtocol (&gEfiStatusCodeRuntimeProtocolGuid, NULL, (VOID **)&gStatusCode); + if (EFI_ERROR (Status)) { + gStatusCode = NULL; + } +#endif + + Status = gBS->LocateProtocol (&gEfiCpuIoProtocolGuid, NULL, &gCpuIo); + if (EFI_ERROR (Status)) { + gCpuIo = NULL; + } + + return EFI_SUCCESS; +} + +BOOLEAN +EfiAtRuntime ( + VOID + ) +/*++ + +Routine Description: + Return TRUE if ExitBootServices () has been called + +Arguments: + NONE + +Returns: + TRUE - If ExitBootServices () has been called + +--*/ +{ + return mEfiAtRuntime; +} + +BOOLEAN +EfiGoneVirtual ( + VOID + ) +/*++ + +Routine Description: + Return TRUE if SetVirtualAddressMap () has been called + +Arguments: + NONE + +Returns: + TRUE - If SetVirtualAddressMap () has been called + +--*/ +{ + return mEfiGoneVirtual; +} +// +// The following functions hide the mRT local global from the call to +// runtime service in the EFI system table. +// +EFI_STATUS +EfiGetTime ( + OUT EFI_TIME *Time, + OUT EFI_TIME_CAPABILITIES *Capabilities + ) +/*++ + +Routine Description: + + Returns the current time and date information, and the time-keeping + capabilities of the hardware platform. + +Arguments: + + Time - A pointer to storage to receive a snapshot of the current time. + Capabilities - An optional pointer to a buffer to receive the real time clock device¡¯s + capabilities. + +Returns: + + Status code + +--*/ +{ + return mRT->GetTime (Time, Capabilities); +} + +EFI_STATUS +EfiSetTime ( + IN EFI_TIME *Time + ) +/*++ + +Routine Description: + + Sets the current local time and date information. + +Arguments: + + Time - A pointer to the current time. + +Returns: + + Status code + +--*/ +{ + return mRT->SetTime (Time); +} + +EFI_STATUS +EfiGetWakeupTime ( + OUT BOOLEAN *Enabled, + OUT BOOLEAN *Pending, + OUT EFI_TIME *Time + ) +/*++ + +Routine Description: + + Returns the current wakeup alarm clock setting. + +Arguments: + + Enabled - Indicates if the alarm is currently enabled or disabled. + Pending - Indicates if the alarm signal is pending and requires acknowledgement. + Time - The current alarm setting. + +Returns: + + Status code + +--*/ +{ + return mRT->GetWakeupTime (Enabled, Pending, Time); +} + +EFI_STATUS +EfiSetWakeupTime ( + IN BOOLEAN Enable, + IN EFI_TIME *Time + ) +/*++ + +Routine Description: + + Sets the system wakeup alarm clock time. + +Arguments: + + Enable - Enable or disable the wakeup alarm. + Time - If Enable is TRUE, the time to set the wakeup alarm for. + If Enable is FALSE, then this parameter is optional, and may be NULL. + +Returns: + + Status code + +--*/ +{ + return mRT->SetWakeupTime (Enable, Time); +} + +EFI_STATUS +EfiGetVariable ( + IN CHAR16 *VariableName, + IN EFI_GUID * VendorGuid, + OUT UINT32 *Attributes OPTIONAL, + IN OUT UINTN *DataSize, + OUT VOID *Data + ) +/*++ + +Routine Description: + + Returns the value of a variable. + +Arguments: + + VariableName - A Null-terminated Unicode string that is the name of the + vendor¡¯s variable. + VendorGuid - A unique identifier for the vendor. + Attributes - If not NULL, a pointer to the memory location to return the + attributes bitmask for the variable. + DataSize - On input, the size in bytes of the return Data buffer. + On output the size of data returned in Data. + Data - The buffer to return the contents of the variable. + +Returns: + + Status code + +--*/ +{ + return mRT->GetVariable (VariableName, VendorGuid, Attributes, DataSize, Data); +} + +EFI_STATUS +EfiGetNextVariableName ( + IN OUT UINTN *VariableNameSize, + IN OUT CHAR16 *VariableName, + IN OUT EFI_GUID *VendorGuid + ) +/*++ + +Routine Description: + + Enumerates the current variable names. + +Arguments: + + VariableNameSize - The size of the VariableName buffer. + VariableName - On input, supplies the last VariableName that was returned + by GetNextVariableName(). + On output, returns the Nullterminated Unicode string of the + current variable. + VendorGuid - On input, supplies the last VendorGuid that was returned by + GetNextVariableName(). + On output, returns the VendorGuid of the current variable. + +Returns: + + Status code + +--*/ +{ + return mRT->GetNextVariableName (VariableNameSize, VariableName, VendorGuid); +} + +EFI_STATUS +EfiSetVariable ( + IN CHAR16 *VariableName, + IN EFI_GUID *VendorGuid, + IN UINT32 Attributes, + IN UINTN DataSize, + IN VOID *Data + ) +/*++ + +Routine Description: + + Sets the value of a variable. + +Arguments: + + VariableName - A Null-terminated Unicode string that is the name of the + vendor¡¯s variable. + VendorGuid - A unique identifier for the vendor. + Attributes - Attributes bitmask to set for the variable. + DataSize - The size in bytes of the Data buffer. + Data - The contents for the variable. + +Returns: + + Status code + +--*/ +{ + return mRT->SetVariable (VariableName, VendorGuid, Attributes, DataSize, Data); +} + + +#if (EFI_SPECIFICATION_VERSION >= 0x00020000) + +EFI_STATUS +EfiQueryVariableInfo ( + IN UINT32 Attributes, + OUT UINT64 *MaximumVariableStorageSize, + OUT UINT64 *RemainingVariableStorageSize, + OUT UINT64 *MaximumVariableSize + ) + +/*++ + +Routine Description: + + This code returns information about the EFI variables. + +Arguments: + + Attributes Attributes bitmask to specify the type of variables + on which to return information. + MaximumVariableStorageSize Pointer to the maximum size of the storage space available + for the EFI variables associated with the attributes specified. + RemainingVariableStorageSize Pointer to the remaining size of the storage space available + for the EFI variables associated with the attributes specified. + MaximumVariableSize Pointer to the maximum size of the individual EFI variables + associated with the attributes specified. + +Returns: + + Status code + +--*/ +{ + return mRT->QueryVariableInfo (Attributes, MaximumVariableStorageSize, RemainingVariableStorageSize, MaximumVariableSize); +} + +#endif + +EFI_STATUS +EfiGetNextHighMonotonicCount ( + OUT UINT32 *HighCount + ) +/*++ + +Routine Description: + + Returns the next high 32 bits of the platform¡¯s monotonic counter. + +Arguments: + + HighCount - Pointer to returned value. + +Returns: + + Status code + +--*/ +{ + return mRT->GetNextHighMonotonicCount (HighCount); +} + +VOID +EfiResetSystem ( + IN EFI_RESET_TYPE ResetType, + IN EFI_STATUS ResetStatus, + IN UINTN DataSize, + IN CHAR16 *ResetData + ) +/*++ + +Routine Description: + + Resets the entire platform. + +Arguments: + + ResetType - The type of reset to perform. + ResetStatus - The status code for the reset. + DataSize - The size, in bytes, of ResetData. + ResetData - A data buffer that includes a Null-terminated Unicode string, optionally + followed by additional binary data. + +Returns: + + None + +--*/ +{ + mRT->ResetSystem (ResetType, ResetStatus, DataSize, ResetData); +} + +EFI_STATUS +EfiReportStatusCode ( + IN EFI_STATUS_CODE_TYPE CodeType, + IN EFI_STATUS_CODE_VALUE Value, + IN UINT32 Instance, + IN EFI_GUID * CallerId, + IN EFI_STATUS_CODE_DATA * Data OPTIONAL + ) +/*++ + +Routine Description: + + Status Code reporter + +Arguments: + + CodeType - Type of Status Code. + + Value - Value to output for Status Code. + + Instance - Instance Number of this status code. + + CallerId - ID of the caller of this status code. + + Data - Optional data associated with this status code. + +Returns: + + Status code + +--*/ +{ + EFI_STATUS Status; + +#if (EFI_SPECIFICATION_VERSION >= 0x00020000) + if (gStatusCode == NULL) { + if (EfiAtRuntime ()) { + return EFI_UNSUPPORTED; + } + Status = gBS->LocateProtocol (&gEfiStatusCodeRuntimeProtocolGuid, NULL, (VOID **)&gStatusCode); + if (EFI_ERROR (Status) || gStatusCode == NULL) { + return EFI_UNSUPPORTED; + } + } + Status = gStatusCode->ReportStatusCode (CodeType, Value, Instance, CallerId, Data); +#else + Status = mRT->ReportStatusCode (CodeType, Value, Instance, CallerId, Data); +#endif + return Status; +} +// +// Cache Flush Routine. +// +EFI_STATUS +EfiCpuFlushCache ( + IN EFI_PHYSICAL_ADDRESS Start, + IN UINT64 Length + ) +/*++ + +Routine Description: + + Flush cache with specified range. + +Arguments: + + Start - Start address + Length - Length in bytes + +Returns: + + Status code + + EFI_SUCCESS - success + +--*/ +{ + __asm { + wbinvd + } + return EFI_SUCCESS; +} |