Add in the 1st version of ECP.
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@2832 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
@@ -0,0 +1,154 @@
|
||||
/*++
|
||||
|
||||
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:
|
||||
|
||||
Debug.c
|
||||
|
||||
Abstract:
|
||||
|
||||
Support for Debug primatives.
|
||||
|
||||
--*/
|
||||
|
||||
#include "Tiano.h"
|
||||
#include "EfiRuntimeLib.h"
|
||||
#include EFI_GUID_DEFINITION (StatusCodeCallerId)
|
||||
#include EFI_GUID_DEFINITION (StatusCodeDataTypeId)
|
||||
|
||||
#define EFI_STATUS_CODE_DATA_MAX_SIZE64 (EFI_STATUS_CODE_DATA_MAX_SIZE / 8)
|
||||
|
||||
VOID
|
||||
EfiDebugAssert (
|
||||
IN CHAR8 *FileName,
|
||||
IN INTN LineNumber,
|
||||
IN CHAR8 *Description
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Worker function for ASSERT (). If Error Logging hub is loaded log ASSERT
|
||||
information. If Error Logging hub is not loaded BREAKPOINT ().
|
||||
|
||||
Arguments:
|
||||
|
||||
FileName - File name of failing routine.
|
||||
|
||||
LineNumber - Line number of failing ASSERT ().
|
||||
|
||||
Description - Description, usually the assertion,
|
||||
|
||||
Returns:
|
||||
|
||||
None
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT64 Buffer[EFI_STATUS_CODE_DATA_MAX_SIZE64];
|
||||
|
||||
EfiDebugAssertWorker (FileName, LineNumber, Description, sizeof (Buffer), Buffer);
|
||||
|
||||
EfiReportStatusCode (
|
||||
(EFI_ERROR_CODE | EFI_ERROR_UNRECOVERED),
|
||||
(EFI_SOFTWARE_DXE_RT_DRIVER | EFI_SW_EC_ILLEGAL_SOFTWARE_STATE),
|
||||
0,
|
||||
&gEfiCallerIdGuid,
|
||||
(EFI_STATUS_CODE_DATA *) Buffer
|
||||
);
|
||||
|
||||
//
|
||||
// Put break point in module that contained the error.
|
||||
//
|
||||
EFI_BREAKPOINT ();
|
||||
}
|
||||
|
||||
VOID
|
||||
EfiDebugVPrint (
|
||||
IN UINTN ErrorLevel,
|
||||
IN CHAR8 *Format,
|
||||
IN VA_LIST Marker
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Worker function for DEBUG (). If Error Logging hub is loaded log ASSERT
|
||||
information. If Error Logging hub is not loaded do nothing.
|
||||
|
||||
Arguments:
|
||||
|
||||
ErrorLevel - If error level is set do the debug print.
|
||||
|
||||
Format - String to use for the print, followed by Print arguments.
|
||||
|
||||
Marker - VarArgs
|
||||
|
||||
Returns:
|
||||
|
||||
None
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT64 Buffer[EFI_STATUS_CODE_DATA_MAX_SIZE64];
|
||||
|
||||
if (!(gRtErrorLevel & ErrorLevel)) {
|
||||
return ;
|
||||
}
|
||||
|
||||
EfiDebugVPrintWorker (ErrorLevel, Format, Marker, sizeof (Buffer), Buffer);
|
||||
|
||||
EfiReportStatusCode (
|
||||
EFI_DEBUG_CODE,
|
||||
(EFI_SOFTWARE_DXE_RT_DRIVER | EFI_DC_UNSPECIFIED),
|
||||
(UINT32) ErrorLevel,
|
||||
&gEfiCallerIdGuid,
|
||||
(EFI_STATUS_CODE_DATA *) Buffer
|
||||
);
|
||||
|
||||
return ;
|
||||
}
|
||||
|
||||
VOID
|
||||
EfiDebugPrint (
|
||||
IN UINTN ErrorLevel,
|
||||
IN CHAR8 *Format,
|
||||
...
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Worker function for DEBUG (). If Error Logging hub is loaded log ASSERT
|
||||
information. If Error Logging hub is not loaded do nothing.
|
||||
|
||||
We use UINT64 buffers due to IPF alignment concerns.
|
||||
|
||||
Arguments:
|
||||
|
||||
ErrorLevel - If error level is set do the debug print.
|
||||
|
||||
Format - String to use for the print, followed by Print arguments.
|
||||
|
||||
... - VAR args for Format
|
||||
|
||||
Returns:
|
||||
|
||||
None
|
||||
|
||||
--*/
|
||||
{
|
||||
VA_LIST Marker;
|
||||
|
||||
VA_START (Marker, Format);
|
||||
EfiDebugVPrint (ErrorLevel, Format, Marker);
|
||||
VA_END (Marker);
|
||||
}
|
@@ -0,0 +1,316 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2007, 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_GUID_DEFINITION (StatusCodeCallerId)
|
||||
#include EFI_ARCH_PROTOCOL_DEFINITION (StatusCode)
|
||||
|
||||
//
|
||||
// Driver Lib Module Globals
|
||||
//
|
||||
static EFI_RUNTIME_SERVICES *mRT;
|
||||
static EFI_EVENT mRuntimeNotifyEvent = NULL;
|
||||
static BOOLEAN mRuntimeLibInitialized = FALSE;
|
||||
static BOOLEAN mEfiGoneVirtual = FALSE;
|
||||
|
||||
//
|
||||
// Runtime Global, but you should use the Lib functions
|
||||
//
|
||||
BOOLEAN mEfiAtRuntime = FALSE;
|
||||
|
||||
#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);
|
||||
}
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
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
|
||||
|
||||
//
|
||||
// Register our ExitBootServices () notify function
|
||||
//
|
||||
Status = gBS->CreateEvent (
|
||||
EFI_EVENT_SIGNAL_EXIT_BOOT_SERVICES,
|
||||
EFI_TPL_NOTIFY,
|
||||
RuntimeDriverExitBootServices,
|
||||
NULL,
|
||||
&mRuntimeNotifyEvent
|
||||
);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
//
|
||||
// To NOT register SetVirtualAddressMap () notify function,
|
||||
// because we do not know how to trigger it without our EBC driver.
|
||||
//
|
||||
|
||||
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);
|
||||
}
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
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
|
||||
|
||||
--*/
|
||||
{
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
//
|
||||
// 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
|
||||
|
||||
--*/
|
||||
{
|
||||
return EFI_SUCCESS;
|
||||
}
|
@@ -0,0 +1,79 @@
|
||||
#/*++
|
||||
#
|
||||
# Copyright (c) 2004 - 2007, 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:
|
||||
#
|
||||
# EfiRuntimeLib.inf
|
||||
#
|
||||
# Abstract:
|
||||
#
|
||||
# Component description file for the EFI runtime library.
|
||||
#
|
||||
#--*/
|
||||
|
||||
[defines]
|
||||
BASE_NAME = EfiRuntimeLib
|
||||
COMPONENT_TYPE = LIBRARY
|
||||
|
||||
[sources.common]
|
||||
Debug.c
|
||||
Event.c
|
||||
Io.c
|
||||
LibGlobals.c
|
||||
GetImage.c
|
||||
RtDevicePath.c
|
||||
|
||||
[sources.ia32]
|
||||
Ia32\RuntimeLib.c
|
||||
Ia32\IoLib.c
|
||||
Ia32\Lock.c
|
||||
Ia32\PlatformIoLib.c
|
||||
Ia32\Fvb.c
|
||||
|
||||
[sources.x64]
|
||||
x64\RuntimeLib.c
|
||||
x64\IoLib.c
|
||||
x64\Lock.c
|
||||
x64\PlatformIoLib.c
|
||||
x64\Fvb.c
|
||||
|
||||
[sources.ipf]
|
||||
Ipf\RuntimeLib.c
|
||||
Ipf\Lock.c
|
||||
Ipf\Fvb.c
|
||||
Ipf\EsalLib.s
|
||||
Ipf\IpfCpuCache.s
|
||||
|
||||
[sources.ebc]
|
||||
Ebc\RuntimeLib.c
|
||||
|
||||
[includes.common]
|
||||
$(EDK_SOURCE)\Foundation
|
||||
$(EDK_SOURCE)\Foundation\Framework
|
||||
$(EDK_SOURCE)\Foundation\Efi
|
||||
$(EDK_SOURCE)\Foundation\Include
|
||||
$(EDK_SOURCE)\Foundation\Efi\Include
|
||||
$(EDK_SOURCE)\Foundation\Framework\Include
|
||||
$(EDK_SOURCE)\Foundation\Include\IndustryStandard
|
||||
$(EDK_SOURCE)\Foundation\Core\Dxe
|
||||
$(EDK_SOURCE)\Foundation\Library\Dxe\Include
|
||||
|
||||
[libraries.common]
|
||||
EdkGuidLib
|
||||
EdkProtocolLib
|
||||
EdkFrameworkProtocolLib
|
||||
EfiGuidLib
|
||||
EfiProtocolLib
|
||||
ArchProtocolLib
|
||||
EfiCommonLib
|
||||
|
||||
[nmake.common]
|
||||
|
@@ -0,0 +1,353 @@
|
||||
/*++
|
||||
|
||||
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:
|
||||
|
||||
Event.c
|
||||
|
||||
Abstract:
|
||||
|
||||
Support for Event lib fucntions.
|
||||
|
||||
--*/
|
||||
|
||||
#include "Tiano.h"
|
||||
#include "EfiRuntimeLib.h"
|
||||
|
||||
EFI_EVENT
|
||||
RtEfiLibCreateProtocolNotifyEvent (
|
||||
IN EFI_GUID *ProtocolGuid,
|
||||
IN EFI_TPL NotifyTpl,
|
||||
IN EFI_EVENT_NOTIFY NotifyFunction,
|
||||
IN VOID *NotifyContext,
|
||||
OUT VOID **Registration
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Create a protocol notification event and return it.
|
||||
|
||||
Arguments:
|
||||
|
||||
ProtocolGuid - Protocol to register notification event on.
|
||||
|
||||
NotifyTpl - Maximum TPL to single the NotifyFunction.
|
||||
|
||||
NotifyFunction - EFI notification routine.
|
||||
|
||||
NotifyContext - Context passed into Event when it is created.
|
||||
|
||||
Registration - Registration key returned from RegisterProtocolNotify().
|
||||
|
||||
Returns:
|
||||
|
||||
The EFI_EVENT that has been registered to be signaled when a ProtocolGuid
|
||||
is added to the system.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_EVENT Event;
|
||||
|
||||
//
|
||||
// Create the event
|
||||
//
|
||||
Status = gBS->CreateEvent (
|
||||
EFI_EVENT_NOTIFY_SIGNAL,
|
||||
NotifyTpl,
|
||||
NotifyFunction,
|
||||
NotifyContext,
|
||||
&Event
|
||||
);
|
||||
ASSERT (!EFI_ERROR (Status));
|
||||
|
||||
//
|
||||
// Register for protocol notifactions on this event
|
||||
//
|
||||
Status = gBS->RegisterProtocolNotify (
|
||||
ProtocolGuid,
|
||||
Event,
|
||||
Registration
|
||||
);
|
||||
|
||||
ASSERT (!EFI_ERROR (Status));
|
||||
|
||||
//
|
||||
// Kick the event so we will perform an initial pass of
|
||||
// current installed drivers
|
||||
//
|
||||
gBS->SignalEvent (Event);
|
||||
return Event;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
EfiLibGetSystemConfigurationTable (
|
||||
IN EFI_GUID *TableGuid,
|
||||
IN OUT VOID **Table
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Return the EFI 1.0 System Tabl entry with TableGuid
|
||||
|
||||
Arguments:
|
||||
|
||||
TableGuid - Name of entry to return in the system table
|
||||
Table - Pointer in EFI system table associated with TableGuid
|
||||
|
||||
Returns:
|
||||
|
||||
EFI_SUCCESS - Table returned;
|
||||
EFI_NOT_FOUND - TableGuid not in EFI system table
|
||||
|
||||
--*/
|
||||
{
|
||||
UINTN Index;
|
||||
|
||||
for (Index = 0; Index < gST->NumberOfTableEntries; Index++) {
|
||||
if (EfiCompareGuid (TableGuid, &(gST->ConfigurationTable[Index].VendorGuid))) {
|
||||
*Table = gST->ConfigurationTable[Index].VendorTable;
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
EfiConvertList (
|
||||
IN UINTN DebugDisposition,
|
||||
IN OUT EFI_LIST_ENTRY *ListHead
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Conver the standard Lib double linked list to a virtual mapping.
|
||||
|
||||
Arguments:
|
||||
|
||||
DebugDisposition - Argument to EfiConvertPointer (EFI 1.0 API)
|
||||
|
||||
ListHead - Head of linked list to convert
|
||||
|
||||
Returns:
|
||||
|
||||
EFI_SUCCESS
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_LIST_ENTRY *Link;
|
||||
EFI_LIST_ENTRY *NextLink;
|
||||
|
||||
//
|
||||
// Convert all the ForwardLink & BackLink pointers in the list
|
||||
//
|
||||
Link = ListHead;
|
||||
do {
|
||||
NextLink = Link->ForwardLink;
|
||||
|
||||
EfiConvertPointer (
|
||||
Link->ForwardLink == ListHead ? DebugDisposition : 0,
|
||||
(VOID **) &Link->ForwardLink
|
||||
);
|
||||
|
||||
EfiConvertPointer (
|
||||
Link->BackLink == ListHead ? DebugDisposition : 0,
|
||||
(VOID **) &Link->BackLink
|
||||
);
|
||||
|
||||
Link = NextLink;
|
||||
} while (Link != ListHead);
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
#if (EFI_SPECIFICATION_VERSION >= 0x00020000)
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
EFIAPI
|
||||
EventNotifySignalAllNullEvent (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
{
|
||||
//
|
||||
// This null event is a size efficent way to enusre that
|
||||
// EFI_EVENT_NOTIFY_SIGNAL_ALL is error checked correctly.
|
||||
// EFI_EVENT_NOTIFY_SIGNAL_ALL is now mapped into
|
||||
// CreateEventEx() and this function is used to make the
|
||||
// old error checking in CreateEvent() for Tiano extensions
|
||||
// function.
|
||||
//
|
||||
return;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
RtEfiCreateEventLegacyBoot (
|
||||
IN EFI_TPL NotifyTpl,
|
||||
IN EFI_EVENT_NOTIFY NotifyFunction,
|
||||
IN VOID *NotifyContext,
|
||||
OUT EFI_EVENT *LegacyBootEvent
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Create a Legacy Boot Event.
|
||||
Tiano extended the CreateEvent Type enum to add a legacy boot event type.
|
||||
This was bad as Tiano did not own the enum. In UEFI 2.0 CreateEventEx was
|
||||
added and now it's possible to not voilate the UEFI specification by
|
||||
declaring a GUID for the legacy boot event class. This library supports
|
||||
the R8.5/EFI 1.10 form and R8.6/UEFI 2.0 form and allows common code to
|
||||
work both ways.
|
||||
|
||||
Arguments:
|
||||
LegacyBootEvent Returns the EFI event returned from gBS->CreateEvent(Ex)
|
||||
|
||||
Returns:
|
||||
EFI_SUCCESS Event was created.
|
||||
Other Event was not created.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINT32 EventType;
|
||||
EFI_EVENT_NOTIFY WorkerNotifyFunction;
|
||||
|
||||
#if (EFI_SPECIFICATION_VERSION < 0x00020000)
|
||||
|
||||
if (NotifyFunction == NULL) {
|
||||
EventType = EFI_EVENT_SIGNAL_LEGACY_BOOT | EFI_EVENT_NOTIFY_SIGNAL_ALL;
|
||||
} else {
|
||||
EventType = EFI_EVENT_SIGNAL_LEGACY_BOOT;
|
||||
}
|
||||
WorkerNotifyFunction = NotifyFunction;
|
||||
|
||||
//
|
||||
// prior to UEFI 2.0 use Tiano extension to EFI
|
||||
//
|
||||
Status = gBS->CreateEvent (
|
||||
EventType,
|
||||
NotifyTpl,
|
||||
WorkerNotifyFunction,
|
||||
NotifyContext,
|
||||
LegacyBootEvent
|
||||
);
|
||||
#else
|
||||
|
||||
EventType = EFI_EVENT_NOTIFY_SIGNAL;
|
||||
if (NotifyFunction == NULL) {
|
||||
//
|
||||
// CreatEventEx will check NotifyFunction is NULL or not
|
||||
//
|
||||
WorkerNotifyFunction = EventNotifySignalAllNullEvent;
|
||||
} else {
|
||||
WorkerNotifyFunction = NotifyFunction;
|
||||
}
|
||||
|
||||
//
|
||||
// For UEFI 2.0 and the future use an Event Group
|
||||
//
|
||||
Status = gBS->CreateEventEx (
|
||||
EventType,
|
||||
NotifyTpl,
|
||||
WorkerNotifyFunction,
|
||||
NotifyContext,
|
||||
&gEfiEventLegacyBootGuid,
|
||||
LegacyBootEvent
|
||||
);
|
||||
#endif
|
||||
return Status;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
RtEfiCreateEventReadyToBoot (
|
||||
IN EFI_TPL NotifyTpl,
|
||||
IN EFI_EVENT_NOTIFY NotifyFunction,
|
||||
IN VOID *NotifyContext,
|
||||
OUT EFI_EVENT *ReadyToBootEvent
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Create a Read to Boot Event.
|
||||
|
||||
Tiano extended the CreateEvent Type enum to add a ready to boot event type.
|
||||
This was bad as Tiano did not own the enum. In UEFI 2.0 CreateEventEx was
|
||||
added and now it's possible to not voilate the UEFI specification and use
|
||||
the ready to boot event class defined in UEFI 2.0. This library supports
|
||||
the R8.5/EFI 1.10 form and R8.6/UEFI 2.0 form and allows common code to
|
||||
work both ways.
|
||||
|
||||
Arguments:
|
||||
ReadyToBootEvent Returns the EFI event returned from gBS->CreateEvent(Ex)
|
||||
|
||||
Return:
|
||||
EFI_SUCCESS - Event was created.
|
||||
Other - Event was not created.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINT32 EventType;
|
||||
EFI_EVENT_NOTIFY WorkerNotifyFunction;
|
||||
|
||||
#if (EFI_SPECIFICATION_VERSION < 0x00020000)
|
||||
|
||||
if (NotifyFunction == NULL) {
|
||||
EventType = EFI_EVENT_SIGNAL_READY_TO_BOOT | EFI_EVENT_NOTIFY_SIGNAL_ALL;
|
||||
} else {
|
||||
EventType = EFI_EVENT_SIGNAL_READY_TO_BOOT;
|
||||
}
|
||||
WorkerNotifyFunction = NotifyFunction;
|
||||
|
||||
//
|
||||
// prior to UEFI 2.0 use Tiano extension to EFI
|
||||
//
|
||||
Status = gBS->CreateEvent (
|
||||
EventType,
|
||||
NotifyTpl,
|
||||
WorkerNotifyFunction,
|
||||
NotifyContext,
|
||||
ReadyToBootEvent
|
||||
);
|
||||
#else
|
||||
|
||||
EventType = EFI_EVENT_NOTIFY_SIGNAL;
|
||||
if (NotifyFunction == NULL) {
|
||||
//
|
||||
// CreatEventEx will check NotifyFunction is NULL or not
|
||||
//
|
||||
WorkerNotifyFunction = EventNotifySignalAllNullEvent;
|
||||
} else {
|
||||
WorkerNotifyFunction = NotifyFunction;
|
||||
}
|
||||
|
||||
//
|
||||
// For UEFI 2.0 and the future use an Event Group
|
||||
//
|
||||
Status = gBS->CreateEventEx (
|
||||
EventType,
|
||||
NotifyTpl,
|
||||
WorkerNotifyFunction,
|
||||
NotifyContext,
|
||||
&gEfiEventReadyToBootGuid,
|
||||
ReadyToBootEvent
|
||||
);
|
||||
#endif
|
||||
return Status;
|
||||
}
|
@@ -0,0 +1,221 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2006 - 2007, 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:
|
||||
|
||||
GetImage.c
|
||||
|
||||
Abstract:
|
||||
|
||||
Image data extraction support for common use.
|
||||
|
||||
--*/
|
||||
|
||||
#include "Tiano.h"
|
||||
#include "EfiRuntimeLib.h"
|
||||
#include "EfiImageFormat.h"
|
||||
|
||||
#include EFI_PROTOCOL_CONSUMER (LoadedImage)
|
||||
|
||||
EFI_STATUS
|
||||
GetImageFromFv (
|
||||
#if (PI_SPECIFICATION_VERSION < 0x00010000)
|
||||
IN EFI_FIRMWARE_VOLUME_PROTOCOL *Fv,
|
||||
#else
|
||||
IN EFI_FIRMWARE_VOLUME2_PROTOCOL *Fv,
|
||||
#endif
|
||||
IN EFI_GUID *NameGuid,
|
||||
IN EFI_SECTION_TYPE SectionType,
|
||||
OUT VOID **Buffer,
|
||||
OUT UINTN *Size
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_FV_FILETYPE FileType;
|
||||
EFI_FV_FILE_ATTRIBUTES Attributes;
|
||||
UINT32 AuthenticationStatus;
|
||||
|
||||
//
|
||||
// Read desired section content in NameGuid file
|
||||
//
|
||||
*Buffer = NULL;
|
||||
*Size = 0;
|
||||
Status = Fv->ReadSection (
|
||||
Fv,
|
||||
NameGuid,
|
||||
SectionType,
|
||||
0,
|
||||
Buffer,
|
||||
Size,
|
||||
&AuthenticationStatus
|
||||
);
|
||||
|
||||
if (EFI_ERROR (Status) && (SectionType == EFI_SECTION_TE)) {
|
||||
//
|
||||
// Try reading PE32 section, since the TE section does not exist
|
||||
//
|
||||
*Buffer = NULL;
|
||||
*Size = 0;
|
||||
Status = Fv->ReadSection (
|
||||
Fv,
|
||||
NameGuid,
|
||||
EFI_SECTION_PE32,
|
||||
0,
|
||||
Buffer,
|
||||
Size,
|
||||
&AuthenticationStatus
|
||||
);
|
||||
}
|
||||
|
||||
if (EFI_ERROR (Status) &&
|
||||
((SectionType == EFI_SECTION_TE) || (SectionType == EFI_SECTION_PE32))) {
|
||||
//
|
||||
// Try reading raw file, since the desired section does not exist
|
||||
//
|
||||
*Buffer = NULL;
|
||||
*Size = 0;
|
||||
Status = Fv->ReadFile (
|
||||
Fv,
|
||||
NameGuid,
|
||||
Buffer,
|
||||
Size,
|
||||
&FileType,
|
||||
&Attributes,
|
||||
&AuthenticationStatus
|
||||
);
|
||||
}
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
GetImage (
|
||||
IN EFI_GUID *NameGuid,
|
||||
IN EFI_SECTION_TYPE SectionType,
|
||||
OUT VOID **Buffer,
|
||||
OUT UINTN *Size
|
||||
)
|
||||
{
|
||||
return GetImageEx (NULL, NameGuid, SectionType, Buffer, Size, FALSE);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
GetImageEx (
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_GUID *NameGuid,
|
||||
IN EFI_SECTION_TYPE SectionType,
|
||||
OUT VOID **Buffer,
|
||||
OUT UINTN *Size,
|
||||
BOOLEAN WithinImageFv
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_HANDLE *HandleBuffer;
|
||||
UINTN HandleCount;
|
||||
UINTN Index;
|
||||
EFI_LOADED_IMAGE_PROTOCOL *LoadedImage;
|
||||
#if (PI_SPECIFICATION_VERSION < 0x00010000)
|
||||
EFI_FIRMWARE_VOLUME_PROTOCOL *ImageFv;
|
||||
EFI_FIRMWARE_VOLUME_PROTOCOL *Fv;
|
||||
#else
|
||||
EFI_FIRMWARE_VOLUME2_PROTOCOL *ImageFv;
|
||||
EFI_FIRMWARE_VOLUME2_PROTOCOL *Fv;
|
||||
#endif
|
||||
|
||||
if (ImageHandle == NULL && WithinImageFv) {
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
Status = EFI_NOT_FOUND;
|
||||
ImageFv = NULL;
|
||||
if (ImageHandle != NULL) {
|
||||
Status = gBS->HandleProtocol (
|
||||
ImageHandle,
|
||||
&gEfiLoadedImageProtocolGuid,
|
||||
&LoadedImage
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return Status;
|
||||
}
|
||||
Status = gBS->HandleProtocol (
|
||||
LoadedImage->DeviceHandle,
|
||||
#if (PI_SPECIFICATION_VERSION < 0x00010000)
|
||||
&gEfiFirmwareVolumeProtocolGuid,
|
||||
#else
|
||||
&gEfiFirmwareVolume2ProtocolGuid,
|
||||
#endif
|
||||
&ImageFv
|
||||
);
|
||||
if (!EFI_ERROR (Status)) {
|
||||
Status = GetImageFromFv (ImageFv, NameGuid, SectionType, Buffer, Size);
|
||||
}
|
||||
}
|
||||
|
||||
if (Status == EFI_SUCCESS || WithinImageFv) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
Status = gBS->LocateHandleBuffer (
|
||||
ByProtocol,
|
||||
#if (PI_SPECIFICATION_VERSION < 0x00010000)
|
||||
&gEfiFirmwareVolumeProtocolGuid,
|
||||
#else
|
||||
&gEfiFirmwareVolume2ProtocolGuid,
|
||||
#endif
|
||||
NULL,
|
||||
&HandleCount,
|
||||
&HandleBuffer
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
//
|
||||
// Find desired image in all Fvs
|
||||
//
|
||||
for (Index = 0; Index < HandleCount; ++Index) {
|
||||
Status = gBS->HandleProtocol (
|
||||
HandleBuffer[Index],
|
||||
#if (PI_SPECIFICATION_VERSION < 0x00010000)
|
||||
&gEfiFirmwareVolumeProtocolGuid,
|
||||
#else
|
||||
&gEfiFirmwareVolume2ProtocolGuid,
|
||||
#endif
|
||||
(VOID**)&Fv
|
||||
);
|
||||
|
||||
if (EFI_ERROR (Status)) {
|
||||
gBS->FreePool(HandleBuffer);
|
||||
return Status;
|
||||
}
|
||||
|
||||
if (ImageFv != NULL && Fv == ImageFv) {
|
||||
continue;
|
||||
}
|
||||
|
||||
Status = GetImageFromFv (Fv, NameGuid, SectionType, Buffer, Size);
|
||||
|
||||
if (!EFI_ERROR (Status)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
gBS->FreePool(HandleBuffer);
|
||||
|
||||
//
|
||||
// Not found image
|
||||
//
|
||||
if (Index == HandleCount) {
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
@@ -0,0 +1,339 @@
|
||||
/*++
|
||||
|
||||
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:
|
||||
|
||||
Io.c
|
||||
|
||||
Abstract:
|
||||
|
||||
Light weight lib functions that wrape IoRead (), IoWrite, MemRead (),
|
||||
and MemWrite ().
|
||||
|
||||
--*/
|
||||
|
||||
#include "Tiano.h"
|
||||
#include "EfiRuntimeLib.h"
|
||||
|
||||
UINT8
|
||||
IoRead8 (
|
||||
IN UINT64 Address
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a one byte IO read
|
||||
|
||||
Arguments:
|
||||
Address - IO address to read
|
||||
|
||||
Returns:
|
||||
Data read
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT8 Buffer;
|
||||
|
||||
EfiIoRead (EfiCpuIoWidthUint8, Address, 1, &Buffer);
|
||||
return Buffer;
|
||||
}
|
||||
|
||||
UINT16
|
||||
IoRead16 (
|
||||
IN UINT64 Address
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a two byte IO read
|
||||
|
||||
Arguments:
|
||||
Address - IO address to read
|
||||
|
||||
Returns:
|
||||
Data read
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT16 Buffer;
|
||||
|
||||
EfiIoRead (EfiCpuIoWidthUint16, Address, 1, &Buffer);
|
||||
return Buffer;
|
||||
}
|
||||
|
||||
UINT32
|
||||
IoRead32 (
|
||||
IN UINT64 Address
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a four byte IO read
|
||||
|
||||
Arguments:
|
||||
Address - IO address to read
|
||||
|
||||
Returns:
|
||||
Data read
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT32 Buffer;
|
||||
|
||||
EfiIoRead (EfiCpuIoWidthUint32, Address, 1, &Buffer);
|
||||
return Buffer;
|
||||
}
|
||||
|
||||
VOID
|
||||
IoWrite8 (
|
||||
IN UINT64 Address,
|
||||
IN UINT8 Data
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a one byte IO write
|
||||
|
||||
Arguments:
|
||||
Address - IO address to write
|
||||
Data - Data to write to Address
|
||||
|
||||
Returns:
|
||||
NONE
|
||||
|
||||
--*/
|
||||
{
|
||||
EfiIoWrite (EfiCpuIoWidthUint8, Address, 1, &Data);
|
||||
}
|
||||
|
||||
VOID
|
||||
IoWrite16 (
|
||||
IN UINT64 Address,
|
||||
IN UINT16 Data
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a two byte IO write
|
||||
|
||||
Arguments:
|
||||
Address - IO address to write
|
||||
Data - Data to write to Address
|
||||
|
||||
Returns:
|
||||
NONE
|
||||
|
||||
--*/
|
||||
{
|
||||
EfiIoWrite (EfiCpuIoWidthUint16, Address, 1, &Data);
|
||||
}
|
||||
|
||||
VOID
|
||||
IoWrite32 (
|
||||
IN UINT64 Address,
|
||||
IN UINT32 Data
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a four byte IO write
|
||||
|
||||
Arguments:
|
||||
Address - IO address to write
|
||||
Data - Data to write to Address
|
||||
|
||||
Returns:
|
||||
NONE
|
||||
|
||||
--*/
|
||||
{
|
||||
EfiIoWrite (EfiCpuIoWidthUint32, Address, 1, &Data);
|
||||
}
|
||||
|
||||
UINT8
|
||||
MemRead8 (
|
||||
IN UINT64 Address
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a one byte Memory mapped IO read
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to read
|
||||
|
||||
Returns:
|
||||
Data read
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT8 Buffer;
|
||||
|
||||
EfiMemRead (EfiCpuIoWidthUint8, Address, 1, &Buffer);
|
||||
return Buffer;
|
||||
}
|
||||
|
||||
UINT16
|
||||
MemRead16 (
|
||||
IN UINT64 Address
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a two byte Memory mapped IO read
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to read
|
||||
|
||||
Returns:
|
||||
Data read
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT16 Buffer;
|
||||
|
||||
EfiMemRead (EfiCpuIoWidthUint16, Address, 1, &Buffer);
|
||||
return Buffer;
|
||||
}
|
||||
|
||||
UINT32
|
||||
MemRead32 (
|
||||
IN UINT64 Address
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a four byte Memory mapped IO read
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to read
|
||||
|
||||
Returns:
|
||||
Data read
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT32 Buffer;
|
||||
|
||||
EfiMemRead (EfiCpuIoWidthUint32, Address, 1, &Buffer);
|
||||
return Buffer;
|
||||
}
|
||||
|
||||
UINT64
|
||||
MemRead64 (
|
||||
IN UINT64 Address
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a eight byte Memory mapped IO read
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to read
|
||||
|
||||
Returns:
|
||||
Data read
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT64 Buffer;
|
||||
|
||||
EfiMemRead (EfiCpuIoWidthUint64, Address, 1, &Buffer);
|
||||
return Buffer;
|
||||
}
|
||||
|
||||
VOID
|
||||
MemWrite8 (
|
||||
IN UINT64 Address,
|
||||
IN UINT8 Data
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a one byte Memory mapped IO write
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to write
|
||||
Data - Data to write to Address
|
||||
|
||||
Returns:
|
||||
NONE
|
||||
|
||||
--*/
|
||||
{
|
||||
EfiMemWrite (EfiCpuIoWidthUint8, Address, 1, &Data);
|
||||
}
|
||||
|
||||
VOID
|
||||
MemWrite16 (
|
||||
IN UINT64 Address,
|
||||
IN UINT16 Data
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a two byte Memory mapped IO write
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to write
|
||||
Data - Data to write to Address
|
||||
|
||||
Returns:
|
||||
NONE
|
||||
|
||||
--*/
|
||||
{
|
||||
EfiMemWrite (EfiCpuIoWidthUint16, Address, 1, &Data);
|
||||
}
|
||||
|
||||
VOID
|
||||
MemWrite32 (
|
||||
IN UINT64 Address,
|
||||
IN UINT32 Data
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a four byte Memory mapped IO write
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to write
|
||||
Data - Data to write to Address
|
||||
|
||||
Returns:
|
||||
NONE
|
||||
|
||||
--*/
|
||||
{
|
||||
EfiMemWrite (EfiCpuIoWidthUint32, Address, 1, &Data);
|
||||
}
|
||||
|
||||
VOID
|
||||
MemWrite64 (
|
||||
IN UINT64 Address,
|
||||
IN UINT64 Data
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Do a eight byte Memory mapped IO write
|
||||
|
||||
Arguments:
|
||||
Address - Memory mapped IO address to write
|
||||
Data - Data to write to Address
|
||||
|
||||
Returns:
|
||||
NONE
|
||||
|
||||
--*/
|
||||
{
|
||||
EfiMemWrite (EfiCpuIoWidthUint64, Address, 1, &Data);
|
||||
}
|
@@ -0,0 +1,149 @@
|
||||
//++
|
||||
// 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:
|
||||
//
|
||||
// EsalLib.s
|
||||
//
|
||||
// Abstract:
|
||||
//
|
||||
//
|
||||
// Revision History:
|
||||
//
|
||||
//--
|
||||
|
||||
.file "EsalLib.s"
|
||||
|
||||
#include "IpfMacro.i"
|
||||
|
||||
//
|
||||
// Exports
|
||||
//
|
||||
.global GetEsalEntryPoint
|
||||
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
//++
|
||||
// GetEsalEntryPoint
|
||||
//
|
||||
// Return Esal global and PSR register.
|
||||
//
|
||||
// On Entry :
|
||||
//
|
||||
//
|
||||
// Return Value:
|
||||
// r8 = EFI_SAL_SUCCESS
|
||||
// r9 = Physical Plabel
|
||||
// r10 = Virtual Plabel
|
||||
// r11 = psr
|
||||
//
|
||||
// As per static calling conventions.
|
||||
//
|
||||
//--
|
||||
//---------------------------------------------------------------------------
|
||||
PROCEDURE_ENTRY (GetEsalEntryPoint)
|
||||
|
||||
NESTED_SETUP (0,8,0,0)
|
||||
|
||||
EsalCalcStart:
|
||||
mov r8 = ip;;
|
||||
add r8 = (EsalEntryPoint - EsalCalcStart), r8;;
|
||||
mov r9 = r8;;
|
||||
add r10 = 0x10, r8;;
|
||||
mov r11 = psr;;
|
||||
mov r8 = r0;;
|
||||
|
||||
NESTED_RETURN
|
||||
|
||||
PROCEDURE_EXIT (GetEsalEntryPoint)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
//++
|
||||
// SetEsalPhysicalEntryPoint
|
||||
//
|
||||
// Set the dispatcher entry point
|
||||
//
|
||||
// On Entry:
|
||||
// in0 = Physical address of Esal Dispatcher
|
||||
// in1 = Physical GP
|
||||
//
|
||||
// Return Value:
|
||||
// r8 = EFI_SAL_SUCCESS
|
||||
//
|
||||
// As per static calling conventions.
|
||||
//
|
||||
//--
|
||||
//---------------------------------------------------------------------------
|
||||
PROCEDURE_ENTRY (SetEsalPhysicalEntryPoint)
|
||||
|
||||
NESTED_SETUP (2,8,0,0)
|
||||
|
||||
EsalCalcStart1:
|
||||
mov r8 = ip;;
|
||||
add r8 = (EsalEntryPoint - EsalCalcStart1), r8;;
|
||||
st8 [r8] = in0;;
|
||||
add r8 = 0x08, r8;;
|
||||
st8 [r8] = in1;;
|
||||
mov r8 = r0;;
|
||||
|
||||
NESTED_RETURN
|
||||
|
||||
PROCEDURE_EXIT (SetEsalPhysicalEntryPoint)
|
||||
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
//++
|
||||
// SetEsalVirtualEntryPoint
|
||||
//
|
||||
// Register physical address of Esal globals.
|
||||
//
|
||||
// On Entry :
|
||||
// in0 = Virtual address of Esal Dispatcher
|
||||
// in1 = Virtual GP
|
||||
//
|
||||
// Return Value:
|
||||
// r8 = EFI_SAL_ERROR
|
||||
//
|
||||
// As per static calling conventions.
|
||||
//
|
||||
//--
|
||||
//---------------------------------------------------------------------------
|
||||
PROCEDURE_ENTRY (SetEsalVirtualEntryPoint)
|
||||
|
||||
NESTED_SETUP (2,8,0,0)
|
||||
|
||||
EsalCalcStart2:
|
||||
mov r8 = ip;;
|
||||
add r8 = (EsalEntryPoint - EsalCalcStart2), r8;;
|
||||
add r8 = 0x10, r8;;
|
||||
st8 [r8] = in0;;
|
||||
add r8 = 0x08, r8;;
|
||||
st8 [r8] = in1;;
|
||||
mov r8 = r0;;
|
||||
|
||||
NESTED_RETURN
|
||||
|
||||
PROCEDURE_EXIT (SetEsalVirtualEntryPoint)
|
||||
|
||||
|
||||
|
||||
|
||||
.align 32
|
||||
EsalEntryPoint:
|
||||
data8 0 // Physical Entry
|
||||
data8 0 // GP
|
||||
data8 0 // Virtual Entry
|
||||
data8 0 // GP
|
||||
|
||||
|
@@ -0,0 +1,334 @@
|
||||
/*++
|
||||
|
||||
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:
|
||||
|
||||
Fvb.c
|
||||
|
||||
Abstract:
|
||||
|
||||
Light weight lib to support Tiano Firmware Volume Block
|
||||
protocol abstraction at runtime.
|
||||
|
||||
All these functions convert EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID
|
||||
class function to the Runtime Lib function. There is a 1 to 1 mapping.
|
||||
|
||||
If you are using any of these lib functions.you must first call FvbInitialize ().
|
||||
|
||||
--*/
|
||||
|
||||
#include "Tiano.h"
|
||||
#include "EfiRuntimeLib.h"
|
||||
#include EFI_PROTOCOL_DEFINITION (ExtendedSalGuid)
|
||||
#include "SalApi.h"
|
||||
|
||||
EFI_STATUS
|
||||
EfiFvbInitialize (
|
||||
VOID
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Initialize globals and register Fvb Protocol notification function.
|
||||
|
||||
Arguments:
|
||||
None
|
||||
|
||||
Returns:
|
||||
EFI_SUCCESS
|
||||
|
||||
--*/
|
||||
{
|
||||
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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (&Guid, Read, Instance, Lba, Offset, (UINT64) NumBytes, (UINT64) Buffer, 0, 0).Status;
|
||||
}
|
||||
|
||||
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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (&Guid, Write, Instance, Lba, Offset, (UINT64) NumBytes, (UINT64) Buffer, 0, 0).Status;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
EfiFvbEraseBlock (
|
||||
IN UINTN Instance,
|
||||
IN UINTN 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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (&Guid, EraseBlock, Instance, Lba, 0, 0, 0, 0, 0).Status;
|
||||
}
|
||||
|
||||
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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (&Guid, SetVolumeAttributes, Instance, (UINT64) Attributes, 0, 0, 0, 0, 0).Status;
|
||||
}
|
||||
|
||||
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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (&Guid, SetVolumeAttributes, Instance, (UINT64) Attributes, 0, 0, 0, 0, 0).Status;
|
||||
}
|
||||
|
||||
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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (&Guid, GetPhysicalAddress, Instance, (UINT64) BaseAddress, 0, 0, 0, 0, 0).Status;
|
||||
}
|
||||
|
||||
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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (
|
||||
&Guid,
|
||||
GetBlockSize,
|
||||
Instance,
|
||||
Lba,
|
||||
(UINT64) BlockSize,
|
||||
(UINT64) NumOfBlocks,
|
||||
0,
|
||||
0,
|
||||
0
|
||||
).Status;
|
||||
}
|
||||
|
||||
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_GUID Guid = EFI_EXTENDED_SAL_FV_BLOCK_SERVICES_PROTOCOL_GUID;
|
||||
|
||||
return EfiCallEsalService (
|
||||
&Guid,
|
||||
EraseCustomBlockRange,
|
||||
Instance,
|
||||
StartLba,
|
||||
OffsetStartLba,
|
||||
LastLba,
|
||||
OffsetLastLba,
|
||||
0,
|
||||
0
|
||||
).Status;
|
||||
}
|
||||
EFI_STATUS
|
||||
EfiFvbShutdown (
|
||||
VOID
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Release resources allocated in EfiFvbInitialize.
|
||||
|
||||
Arguments:
|
||||
None
|
||||
|
||||
Returns:
|
||||
EFI_SUCCESS
|
||||
|
||||
--*/
|
||||
{
|
||||
return EFI_SUCCESS;
|
||||
}
|
@@ -0,0 +1,88 @@
|
||||
//++
|
||||
// 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:
|
||||
//
|
||||
// IpfCpuCache.s
|
||||
//
|
||||
// Abstract:
|
||||
//
|
||||
// Contains Misc assembly procedures to support IPF CPU AP.
|
||||
//
|
||||
// Revision History:
|
||||
//
|
||||
//--
|
||||
|
||||
.file "IpfCpuCache.s"
|
||||
|
||||
#include "IpfMacro.i"
|
||||
#include "IpfDefines.h"
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
//++
|
||||
// Flush Cache
|
||||
//
|
||||
// Arguments :
|
||||
|
||||
// Input = in0 = Starting Address to Flush.
|
||||
// Input = in1 = Length in bytes.
|
||||
// Input = b0 = return branch register.
|
||||
// On Entry :
|
||||
//
|
||||
// Return Value:
|
||||
//
|
||||
// VOID
|
||||
// SalFlushCache (
|
||||
// IN UINT64 BaseToFlush,
|
||||
// IN UINT64 LengthToFlush
|
||||
// );
|
||||
//
|
||||
//--
|
||||
//---------------------------------------------------------------------------
|
||||
PROCEDURE_ENTRY (SalFlushCache)
|
||||
|
||||
NESTED_SETUP (5,8,0,0)
|
||||
|
||||
mov loc2 = ar.lc
|
||||
|
||||
mov loc3 = in0 // Start address.
|
||||
mov loc4 = in1;; // Length in bytes.
|
||||
|
||||
cmp.eq p6,p7 = loc4, r0;; // If Length is zero then don't flush any cache
|
||||
(p6) br.spnt.many DoneFlushingC;;
|
||||
|
||||
add loc4 = loc4,loc3
|
||||
mov loc5 = 1;;
|
||||
sub loc4 = loc4, loc5 ;; // the End address to flush
|
||||
|
||||
dep loc3 = r0,loc3,0,5
|
||||
dep loc4 = r0,loc4,0,5;;
|
||||
shr loc3 = loc3,5
|
||||
shr loc4 = loc4,5;; // 32 byte cache line
|
||||
|
||||
sub loc4 = loc4,loc3;; // total flush count, It should be add 1 but
|
||||
// the br.cloop will first execute one time
|
||||
mov loc3 = in0
|
||||
mov loc5 = 32
|
||||
mov ar.lc = loc4;;
|
||||
|
||||
StillFlushingC:
|
||||
fc loc3;;
|
||||
sync.i;;
|
||||
srlz.i;;
|
||||
add loc3 = loc5,loc3;;
|
||||
br.cloop.sptk.few StillFlushingC;;
|
||||
|
||||
DoneFlushingC:
|
||||
mov ar.lc = loc2
|
||||
NESTED_RETURN
|
||||
|
||||
PROCEDURE_EXIT (SalFlushCache)
|
||||
|
@@ -0,0 +1,170 @@
|
||||
/*++
|
||||
|
||||
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. These primitives may be implemented
|
||||
as Esal calls but since these result in small code that us position
|
||||
independent, we can use lib functions. ESAL calls have a significant
|
||||
software overhead and too deep nesting is bad for the stack.
|
||||
|
||||
--*/
|
||||
|
||||
#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. There is
|
||||
no concept of TPL at runtime hence priority is
|
||||
ignored.
|
||||
|
||||
Arguments:
|
||||
|
||||
Lock - The EFI_LOCK structure to initialize
|
||||
|
||||
Priority - Ignored
|
||||
|
||||
|
||||
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. For now,
|
||||
only allow one level of nesting.
|
||||
|
||||
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:
|
||||
|
||||
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.
|
||||
|
||||
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);
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,37 @@
|
||||
/*++
|
||||
|
||||
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:
|
||||
|
||||
LibGlobals.c
|
||||
|
||||
Abstract:
|
||||
|
||||
Lib Globals
|
||||
|
||||
gBS - Pointer to the EFI Boot Services Table
|
||||
gST - Pointer to EFI System Table
|
||||
gRtErrorLevel - Error level used with DEBUG () macro
|
||||
|
||||
--*/
|
||||
|
||||
#include "Tiano.h"
|
||||
#include "EfiRuntimeLib.h"
|
||||
#include EFI_GUID_DEFINITION (StatusCodeCallerId)
|
||||
#include EFI_GUID_DEFINITION (StatusCodeDataTypeId)
|
||||
|
||||
//
|
||||
// Lib globals that can ONLY be used at BootServices time!
|
||||
//
|
||||
EFI_BOOT_SERVICES *gBS;
|
||||
EFI_SYSTEM_TABLE *gST;
|
||||
EFI_DXE_SERVICES *gDS = NULL;
|
||||
UINTN gRtErrorLevel = EFI_DBUG_MASK | EFI_D_LOAD;
|
@@ -0,0 +1,705 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2006 - 2007, 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:
|
||||
|
||||
RtDevicePath.c
|
||||
|
||||
Abstract:
|
||||
|
||||
Device Path services. The thing to remember is device paths are built out of
|
||||
nodes. The device path is terminated by an end node that is length
|
||||
sizeof(EFI_DEVICE_PATH_PROTOCOL). That would be why there is sizeof(EFI_DEVICE_PATH_PROTOCOL)
|
||||
all over this file.
|
||||
|
||||
The only place where multi-instance device paths are supported is in
|
||||
environment varibles. Multi-instance device paths should never be placed
|
||||
on a Handle.
|
||||
|
||||
--*/
|
||||
|
||||
#include "Tiano.h"
|
||||
#include "EfiRuntimeLib.h"
|
||||
#include "RtDevicePath.h"
|
||||
#include EFI_GUID_DEFINITION (FrameworkDevicePath)
|
||||
#include EFI_PROTOCOL_DEFINITION (DevicePath)
|
||||
|
||||
STATIC
|
||||
VOID *
|
||||
InternalAllocatePool (
|
||||
IN UINTN AllocationSize
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Allocate BootServicesData pool.
|
||||
|
||||
Arguments:
|
||||
|
||||
AllocationSize - The size to allocate
|
||||
|
||||
Returns:
|
||||
|
||||
Pointer of the buffer allocated.
|
||||
|
||||
--*/
|
||||
{
|
||||
VOID *Memory;
|
||||
|
||||
Memory = NULL;
|
||||
gBS->AllocatePool (EfiBootServicesData, AllocationSize, &Memory);
|
||||
return Memory;
|
||||
}
|
||||
|
||||
STATIC
|
||||
VOID *
|
||||
InternalAllocateCopyPool (
|
||||
IN UINTN AllocationSize,
|
||||
IN VOID *Buffer
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Allocate BootServicesData pool and use a buffer provided by
|
||||
caller to fill it.
|
||||
|
||||
Arguments:
|
||||
|
||||
AllocationSize - The size to allocate
|
||||
|
||||
Buffer - Buffer that will be filled into the buffer allocated
|
||||
|
||||
Returns:
|
||||
|
||||
Pointer of the buffer allocated.
|
||||
|
||||
--*/
|
||||
{
|
||||
VOID *Memory;
|
||||
|
||||
Memory = NULL;
|
||||
gBS->AllocatePool (EfiBootServicesData, AllocationSize, &Memory);
|
||||
if (Memory != NULL) {
|
||||
gBS->CopyMem (Memory, Buffer, AllocationSize);
|
||||
}
|
||||
|
||||
return Memory;
|
||||
}
|
||||
|
||||
STATIC
|
||||
VOID *
|
||||
InternalAllocateZeroPool (
|
||||
IN UINTN AllocationSize
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Allocate BootServicesData pool and zero it.
|
||||
|
||||
Arguments:
|
||||
|
||||
AllocationSize - The size to allocate
|
||||
|
||||
Returns:
|
||||
|
||||
Pointer of the buffer allocated.
|
||||
|
||||
--*/
|
||||
{
|
||||
VOID *Memory;
|
||||
|
||||
Memory = InternalAllocatePool (AllocationSize);
|
||||
if (Memory != NULL) {
|
||||
gBS->SetMem (Memory, AllocationSize, 0);
|
||||
}
|
||||
|
||||
return Memory;
|
||||
}
|
||||
|
||||
EFI_DEVICE_PATH_PROTOCOL *
|
||||
RtEfiDevicePathInstance (
|
||||
IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath,
|
||||
OUT UINTN *Size
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Function retrieves the next device path instance from a device path data structure.
|
||||
|
||||
Arguments:
|
||||
DevicePath - A pointer to a device path data structure.
|
||||
|
||||
Size - A pointer to the size of a device path instance in bytes.
|
||||
|
||||
Returns:
|
||||
|
||||
This function returns a pointer to the current device path instance.
|
||||
In addition, it returns the size in bytes of the current device path instance in Size,
|
||||
and a pointer to the next device path instance in DevicePath.
|
||||
If there are no more device path instances in DevicePath, then DevicePath will be set to NULL.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevPath;
|
||||
EFI_DEVICE_PATH_PROTOCOL *ReturnValue;
|
||||
UINT8 Temp;
|
||||
|
||||
if (*DevicePath == NULL) {
|
||||
if (Size != NULL) {
|
||||
*Size = 0;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//
|
||||
// Find the end of the device path instance
|
||||
//
|
||||
DevPath = *DevicePath;
|
||||
while (!IsDevicePathEndType (DevPath)) {
|
||||
DevPath = NextDevicePathNode (DevPath);
|
||||
}
|
||||
|
||||
//
|
||||
// Compute the size of the device path instance
|
||||
//
|
||||
if (Size != NULL) {
|
||||
*Size = ((UINTN) DevPath - (UINTN) (*DevicePath)) + sizeof (EFI_DEVICE_PATH_PROTOCOL);
|
||||
}
|
||||
|
||||
//
|
||||
// Make a copy and return the device path instance
|
||||
//
|
||||
Temp = DevPath->SubType;
|
||||
DevPath->SubType = END_ENTIRE_DEVICE_PATH_SUBTYPE;
|
||||
ReturnValue = RtEfiDuplicateDevicePath (*DevicePath);
|
||||
DevPath->SubType = Temp;
|
||||
|
||||
//
|
||||
// If DevPath is the end of an entire device path, then another instance
|
||||
// does not follow, so *DevicePath is set to NULL.
|
||||
//
|
||||
if (DevicePathSubType (DevPath) == END_ENTIRE_DEVICE_PATH_SUBTYPE) {
|
||||
*DevicePath = NULL;
|
||||
} else {
|
||||
*DevicePath = NextDevicePathNode (DevPath);
|
||||
}
|
||||
|
||||
return ReturnValue;
|
||||
}
|
||||
|
||||
BOOLEAN
|
||||
RtEfiIsDevicePathMultiInstance (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *DevicePath
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Return TRUE is this is a multi instance device path.
|
||||
|
||||
Arguments:
|
||||
DevicePath - A pointer to a device path data structure.
|
||||
|
||||
|
||||
Returns:
|
||||
TRUE - If DevicePath is multi instance. FALSE - If DevicePath is not multi
|
||||
instance.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_DEVICE_PATH_PROTOCOL *Node;
|
||||
|
||||
if (DevicePath == NULL) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
Node = DevicePath;
|
||||
while (!EfiIsDevicePathEnd (Node)) {
|
||||
if (EfiIsDevicePathEndInstance (Node)) {
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
Node = EfiNextDevicePathNode (Node);
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
UINTN
|
||||
RtEfiDevicePathSize (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *DevicePath
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Calculate the space size of a device path.
|
||||
|
||||
Arguments:
|
||||
|
||||
DevicePath - A specified device path
|
||||
|
||||
Returns:
|
||||
|
||||
The size.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_DEVICE_PATH_PROTOCOL *Start;
|
||||
|
||||
if (DevicePath == NULL) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
//
|
||||
// Search for the end of the device path structure
|
||||
//
|
||||
Start = DevicePath;
|
||||
while (!EfiIsDevicePathEnd (DevicePath)) {
|
||||
DevicePath = EfiNextDevicePathNode (DevicePath);
|
||||
}
|
||||
|
||||
//
|
||||
// Compute the size and add back in the size of the end device path structure
|
||||
//
|
||||
return ((UINTN) DevicePath - (UINTN) Start) + sizeof (EFI_DEVICE_PATH_PROTOCOL);
|
||||
}
|
||||
|
||||
EFI_DEVICE_PATH_PROTOCOL *
|
||||
RtEfiDevicePathFromHandle (
|
||||
IN EFI_HANDLE Handle
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Get the device path protocol interface installed on a specified handle.
|
||||
|
||||
Arguments:
|
||||
|
||||
Handle - a specified handle
|
||||
|
||||
Returns:
|
||||
|
||||
The device path protocol interface installed on that handle.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
|
||||
|
||||
DevicePath = NULL;
|
||||
gBS->HandleProtocol (
|
||||
Handle,
|
||||
&gEfiDevicePathProtocolGuid,
|
||||
(VOID *) &DevicePath
|
||||
);
|
||||
return DevicePath;
|
||||
}
|
||||
|
||||
EFI_DEVICE_PATH_PROTOCOL *
|
||||
RtEfiDuplicateDevicePath (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *DevicePath
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Duplicate a device path structure.
|
||||
|
||||
Arguments:
|
||||
|
||||
DevicePath - The device path to duplicated.
|
||||
|
||||
Returns:
|
||||
|
||||
The duplicated device path.
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
|
||||
UINTN Size;
|
||||
|
||||
if (DevicePath == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//
|
||||
// Compute the size
|
||||
//
|
||||
Size = RtEfiDevicePathSize (DevicePath);
|
||||
if (Size == 0) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//
|
||||
// Allocate space for duplicate device path
|
||||
//
|
||||
NewDevicePath = InternalAllocateCopyPool (Size, DevicePath);
|
||||
|
||||
return NewDevicePath;
|
||||
}
|
||||
|
||||
EFI_DEVICE_PATH_PROTOCOL *
|
||||
RtEfiAppendDevicePath (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *Src1,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *Src2
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Function is used to append a Src1 and Src2 together.
|
||||
|
||||
Arguments:
|
||||
Src1 - A pointer to a device path data structure.
|
||||
|
||||
Src2 - A pointer to a device path data structure.
|
||||
|
||||
Returns:
|
||||
|
||||
A pointer to the new device path is returned.
|
||||
NULL is returned if space for the new device path could not be allocated from pool.
|
||||
It is up to the caller to free the memory used by Src1 and Src2 if they are no longer needed.
|
||||
|
||||
--*/
|
||||
{
|
||||
UINTN Size;
|
||||
UINTN Size1;
|
||||
UINTN Size2;
|
||||
EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
|
||||
EFI_DEVICE_PATH_PROTOCOL *SecondDevicePath;
|
||||
|
||||
//
|
||||
// If there's only 1 path, just duplicate it
|
||||
//
|
||||
if (!Src1) {
|
||||
ASSERT (!IsDevicePathUnpacked (Src2));
|
||||
return RtEfiDuplicateDevicePath (Src2);
|
||||
}
|
||||
|
||||
if (!Src2) {
|
||||
ASSERT (!IsDevicePathUnpacked (Src1));
|
||||
return RtEfiDuplicateDevicePath (Src1);
|
||||
}
|
||||
|
||||
//
|
||||
// Allocate space for the combined device path. It only has one end node of
|
||||
// length EFI_DEVICE_PATH_PROTOCOL
|
||||
//
|
||||
Size1 = RtEfiDevicePathSize (Src1);
|
||||
Size2 = RtEfiDevicePathSize (Src2);
|
||||
Size = Size1 + Size2 - sizeof (EFI_DEVICE_PATH_PROTOCOL);
|
||||
|
||||
NewDevicePath = InternalAllocateCopyPool (Size, Src1);
|
||||
|
||||
if (NewDevicePath != NULL) {
|
||||
|
||||
//
|
||||
// Over write Src1 EndNode and do the copy
|
||||
//
|
||||
SecondDevicePath = (EFI_DEVICE_PATH_PROTOCOL *) ((CHAR8 *) NewDevicePath + (Size1 - sizeof (EFI_DEVICE_PATH_PROTOCOL)));
|
||||
EfiCopyMem (SecondDevicePath, Src2, Size2);
|
||||
}
|
||||
|
||||
return NewDevicePath;
|
||||
}
|
||||
|
||||
EFI_DEVICE_PATH_PROTOCOL *
|
||||
RtEfiAppendDevicePathNode (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *Src1,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *Node
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
Function is used to append a device path node to the end of another device path.
|
||||
|
||||
Arguments:
|
||||
Src1 - A pointer to a device path data structure.
|
||||
|
||||
Node - A pointer to a device path data structure.
|
||||
|
||||
Returns:
|
||||
This function returns a pointer to the new device path.
|
||||
If there is not enough temporary pool memory available to complete this function,
|
||||
then NULL is returned.
|
||||
|
||||
|
||||
--*/
|
||||
{
|
||||
EFI_DEVICE_PATH_PROTOCOL *Temp;
|
||||
EFI_DEVICE_PATH_PROTOCOL *NextNode;
|
||||
EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
|
||||
UINTN NodeLength;
|
||||
|
||||
//
|
||||
// Build a Node that has a terminator on it
|
||||
//
|
||||
NodeLength = DevicePathNodeLength (Node);
|
||||
|
||||
Temp = InternalAllocateCopyPool (NodeLength + sizeof (EFI_DEVICE_PATH_PROTOCOL), Node);
|
||||
if (Temp == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//
|
||||
// Add and end device path node to convert Node to device path
|
||||
//
|
||||
NextNode = NextDevicePathNode (Temp);
|
||||
SetDevicePathEndNode (NextNode);
|
||||
|
||||
//
|
||||
// Append device paths
|
||||
//
|
||||
NewDevicePath = RtEfiAppendDevicePath (Src1, Temp);
|
||||
gBS->FreePool (Temp);
|
||||
return NewDevicePath;
|
||||
}
|
||||
|
||||
EFI_DEVICE_PATH_PROTOCOL *
|
||||
RtEfiFileDevicePath (
|
||||
IN EFI_HANDLE Device OPTIONAL,
|
||||
IN CHAR16 *FileName
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
This function allocates a device path for a file and appends it to an existiong
|
||||
device path.
|
||||
|
||||
Arguments:
|
||||
Device - A pointer to a device handle.
|
||||
|
||||
FileName - A pointer to a Null-terminated Unicodestring.
|
||||
|
||||
Returns:
|
||||
A device path contain the file name.
|
||||
|
||||
--*/
|
||||
{
|
||||
UINTN Size;
|
||||
FILEPATH_DEVICE_PATH *FilePath;
|
||||
EFI_DEVICE_PATH_PROTOCOL *Eop;
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
|
||||
|
||||
for (Size = 0; FileName[Size] != 0; Size++)
|
||||
;
|
||||
Size = (Size + 1) * 2;
|
||||
|
||||
FilePath = InternalAllocateZeroPool (Size + SIZE_OF_FILEPATH_DEVICE_PATH + sizeof (EFI_DEVICE_PATH_PROTOCOL));
|
||||
|
||||
DevicePath = NULL;
|
||||
|
||||
if (FilePath != NULL) {
|
||||
|
||||
//
|
||||
// Build a file path
|
||||
//
|
||||
FilePath->Header.Type = MEDIA_DEVICE_PATH;
|
||||
FilePath->Header.SubType = MEDIA_FILEPATH_DP;
|
||||
SetDevicePathNodeLength (&FilePath->Header, Size + SIZE_OF_FILEPATH_DEVICE_PATH);
|
||||
EfiCopyMem (FilePath->PathName, FileName, Size);
|
||||
Eop = NextDevicePathNode (&FilePath->Header);
|
||||
SetDevicePathEndNode (Eop);
|
||||
|
||||
//
|
||||
// Append file path to device's device path
|
||||
//
|
||||
|
||||
DevicePath = (EFI_DEVICE_PATH_PROTOCOL *) FilePath;
|
||||
if (Device != NULL) {
|
||||
DevicePath = RtEfiAppendDevicePath (
|
||||
RtEfiDevicePathFromHandle (Device),
|
||||
DevicePath
|
||||
);
|
||||
|
||||
gBS->FreePool (FilePath);
|
||||
}
|
||||
}
|
||||
|
||||
return DevicePath;
|
||||
}
|
||||
|
||||
EFI_DEVICE_PATH_PROTOCOL *
|
||||
RtEfiAppendDevicePathInstance (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *Src,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *Instance
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Append a device path instance to another.
|
||||
|
||||
Arguments:
|
||||
|
||||
Src - The device path instance to be appended with.
|
||||
Instance - The device path instance appending the other.
|
||||
|
||||
Returns:
|
||||
|
||||
The contaction of these two.
|
||||
|
||||
--*/
|
||||
{
|
||||
UINT8 *Ptr;
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevPath;
|
||||
UINTN SrcSize;
|
||||
UINTN InstanceSize;
|
||||
|
||||
if (Src == NULL) {
|
||||
return RtEfiDuplicateDevicePath (Instance);
|
||||
}
|
||||
|
||||
SrcSize = RtEfiDevicePathSize (Src);
|
||||
InstanceSize = RtEfiDevicePathSize (Instance);
|
||||
|
||||
Ptr = InternalAllocateCopyPool (SrcSize + InstanceSize, Src);
|
||||
if (Ptr != NULL) {
|
||||
|
||||
DevPath = (EFI_DEVICE_PATH_PROTOCOL *) Ptr;
|
||||
|
||||
while (!IsDevicePathEnd (DevPath)) {
|
||||
DevPath = NextDevicePathNode (DevPath);
|
||||
}
|
||||
//
|
||||
// Convert the End to an End Instance, since we are
|
||||
// appending another instacne after this one its a good
|
||||
// idea.
|
||||
//
|
||||
DevPath->SubType = END_INSTANCE_DEVICE_PATH_SUBTYPE;
|
||||
|
||||
DevPath = NextDevicePathNode (DevPath);
|
||||
EfiCopyMem (DevPath, Instance, InstanceSize);
|
||||
}
|
||||
|
||||
return (EFI_DEVICE_PATH_PROTOCOL *) Ptr;
|
||||
}
|
||||
|
||||
VOID
|
||||
EFIAPI
|
||||
RtEfiInitializeFwVolDevicepathNode (
|
||||
IN MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvDevicePathNode,
|
||||
IN EFI_GUID *NameGuid
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Initialize a Firmware Volume (FV) Media Device Path node.
|
||||
|
||||
Tiano extended the EFI 1.10 device path nodes. Tiano does not own this enum
|
||||
so as we move to UEFI 2.0 support we must use a mechanism that conforms with
|
||||
the UEFI 2.0 specification to define the FV device path. An UEFI GUIDed
|
||||
device path is defined for PIWG extensions of device path. If the code
|
||||
is compiled to conform with the UEFI 2.0 specification use the new device path
|
||||
else use the old form for backwards compatability.
|
||||
|
||||
Arguments:
|
||||
|
||||
FvDevicePathNode - Pointer to a FV device path node to initialize
|
||||
NameGuid - FV file name to use in FvDevicePathNode
|
||||
|
||||
Returns:
|
||||
|
||||
None
|
||||
|
||||
--*/
|
||||
{
|
||||
#if (EFI_SPECIFICATION_VERSION != 0x00020000)
|
||||
//
|
||||
// Use old Device Path
|
||||
//
|
||||
FvDevicePathNode->Header.Type = MEDIA_DEVICE_PATH;
|
||||
FvDevicePathNode->Header.SubType = MEDIA_FV_FILEPATH_DP;
|
||||
SetDevicePathNodeLength (&FvDevicePathNode->Header, sizeof (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH));
|
||||
|
||||
#else
|
||||
//
|
||||
// Use the new Device path that does not conflict with the UEFI 2.0
|
||||
//
|
||||
FvDevicePathNode->Piwg.Header.Type = MEDIA_DEVICE_PATH;
|
||||
FvDevicePathNode->Piwg.Header.SubType = MEDIA_VENDOR_DP;
|
||||
SetDevicePathNodeLength (&FvDevicePathNode->Piwg.Header, sizeof (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH));
|
||||
|
||||
//
|
||||
// Add the GUID for generic PIWG device paths
|
||||
//
|
||||
EfiCopyMem (&FvDevicePathNode->Piwg.PiwgSpecificDevicePath, &gEfiFrameworkDevicePathGuid, sizeof(EFI_GUID));
|
||||
|
||||
//
|
||||
// Add in the FW Vol File Path PIWG defined inforation
|
||||
//
|
||||
FvDevicePathNode->Piwg.Type = PIWG_MEDIA_FW_VOL_FILEPATH_DEVICE_PATH_TYPE;
|
||||
|
||||
#endif
|
||||
EfiCopyMem (&FvDevicePathNode->NameGuid, NameGuid, sizeof(EFI_GUID));
|
||||
}
|
||||
|
||||
EFI_GUID *
|
||||
EFIAPI
|
||||
RtEfiGetNameGuidFromFwVolDevicePathNode (
|
||||
IN MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvDevicePathNode
|
||||
)
|
||||
/*++
|
||||
|
||||
Routine Description:
|
||||
|
||||
Check to see if the Firmware Volume (FV) Media Device Path is valid.
|
||||
|
||||
Tiano extended the EFI 1.10 device path nodes. Tiano does not own this enum
|
||||
so as we move to UEFI 2.0 support we must use a mechanism that conforms with
|
||||
the UEFI 2.0 specification to define the FV device path. An UEFI GUIDed
|
||||
device path is defined for PIWG extensions of device path. If the code
|
||||
is compiled to conform with the UEFI 2.0 specification use the new device path
|
||||
else use the old form for backwards compatability. The return value to this
|
||||
function points to a location in FvDevicePathNode and it does not allocate
|
||||
new memory for the GUID pointer that is returned.
|
||||
|
||||
Arguments:
|
||||
|
||||
FvDevicePathNode - Pointer to FV device path to check
|
||||
|
||||
Returns:
|
||||
|
||||
NULL - FvDevicePathNode is not valid.
|
||||
Other - FvDevicePathNode is valid and pointer to NameGuid was returned.
|
||||
|
||||
--*/
|
||||
{
|
||||
#if (EFI_SPECIFICATION_VERSION != 0x00020000)
|
||||
//
|
||||
// Use old Device Path
|
||||
//
|
||||
if (DevicePathType (&FvDevicePathNode->Header) == MEDIA_DEVICE_PATH &&
|
||||
DevicePathSubType (&FvDevicePathNode->Header) == MEDIA_FV_FILEPATH_DP) {
|
||||
return &FvDevicePathNode->NameGuid;
|
||||
}
|
||||
|
||||
#else
|
||||
//
|
||||
// Use the new Device path that does not conflict with the UEFI 2.0
|
||||
//
|
||||
if (DevicePathType (&FvDevicePathNode->Piwg.Header) == MEDIA_DEVICE_PATH &&
|
||||
DevicePathSubType (&FvDevicePathNode->Piwg.Header) == MEDIA_VENDOR_DP) {
|
||||
if (EfiCompareGuid (&gEfiFrameworkDevicePathGuid, &FvDevicePathNode->Piwg.PiwgSpecificDevicePath)) {
|
||||
if (FvDevicePathNode->Piwg.Type == PIWG_MEDIA_FW_VOL_FILEPATH_DEVICE_PATH_TYPE) {
|
||||
return &FvDevicePathNode->NameGuid;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return NULL;
|
||||
}
|
||||
|
@@ -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
|
||||
);
|
||||
}
|
@@ -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);
|
||||
}
|
@@ -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);
|
||||
}
|
||||
}
|
@@ -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);
|
||||
}
|
||||
}
|
@@ -0,0 +1,842 @@
|
||||
/*++
|
||||
|
||||
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<63><65>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<6F><72>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<6F><72>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<72><6D>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) {
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
Status = gStatusCode->ReportStatusCode (CodeType, Value, Instance, CallerId, Data);
|
||||
#else
|
||||
if (mRT == NULL) {
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
//
|
||||
// Check whether EFI_RUNTIME_SERVICES has Tiano Extension
|
||||
//
|
||||
Status = EFI_UNSUPPORTED;
|
||||
if (mRT->Hdr.Revision == EFI_SPECIFICATION_VERSION &&
|
||||
mRT->Hdr.HeaderSize == sizeof (EFI_RUNTIME_SERVICES) &&
|
||||
mRT->ReportStatusCode != NULL) {
|
||||
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
|
||||
|
||||
--*/
|
||||
{
|
||||
return EFI_SUCCESS;
|
||||
}
|
@@ -0,0 +1,620 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2005 - 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
|
||||
);
|
||||
}
|
@@ -0,0 +1,130 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2005, 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);
|
||||
}
|
@@ -0,0 +1,177 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2005, 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);
|
||||
}
|
||||
}
|
@@ -0,0 +1,409 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2005 - 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 = 0;
|
||||
|
||||
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);
|
||||
}
|
||||
}
|
@@ -0,0 +1,843 @@
|
||||
/*++
|
||||
|
||||
Copyright (c) 2005 - 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<63><65>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<6F><72>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<6F><72>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<72><6D>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) {
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
Status = gStatusCode->ReportStatusCode (CodeType, Value, Instance, CallerId, Data);
|
||||
#else
|
||||
if (mRT == NULL) {
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
//
|
||||
// Check whether EFI_RUNTIME_SERVICES has Tiano Extension
|
||||
//
|
||||
Status = EFI_UNSUPPORTED;
|
||||
if (mRT->Hdr.Revision == EFI_SPECIFICATION_VERSION &&
|
||||
mRT->Hdr.HeaderSize == sizeof (EFI_RUNTIME_SERVICES) &&
|
||||
mRT->ReportStatusCode != NULL) {
|
||||
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
|
||||
|
||||
--*/
|
||||
{
|
||||
return EFI_SUCCESS;
|
||||
}
|
Reference in New Issue
Block a user