diff options
Diffstat (limited to 'MdeModulePkg/Core/Dxe/DxeMain/DxeProtocolNotify.c')
| -rw-r--r-- | MdeModulePkg/Core/Dxe/DxeMain/DxeProtocolNotify.c | 558 |
1 files changed, 279 insertions, 279 deletions
diff --git a/MdeModulePkg/Core/Dxe/DxeMain/DxeProtocolNotify.c b/MdeModulePkg/Core/Dxe/DxeMain/DxeProtocolNotify.c index 3fe02940ed..62c7bda96d 100644 --- a/MdeModulePkg/Core/Dxe/DxeMain/DxeProtocolNotify.c +++ b/MdeModulePkg/Core/Dxe/DxeMain/DxeProtocolNotify.c @@ -1,279 +1,279 @@ -/** @file
- This file deals with Architecture Protocol (AP) registration in
- the Dxe Core. The mArchProtocols[] array represents a list of
- events that represent the Architectural Protocols.
-
-Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
-SPDX-License-Identifier: BSD-2-Clause-Patent
-
-**/
-
-#include "DxeMain.h"
-
-//
-// DXE Core Global Variables for all of the Architectural Protocols.
-// If a protocol is installed mArchProtocols[].Present will be TRUE.
-//
-// CoreNotifyOnArchProtocolInstallation () fills in mArchProtocols[].Event
-// and mArchProtocols[].Registration as it creates events for every array
-// entry.
-//
-EFI_CORE_PROTOCOL_NOTIFY_ENTRY mArchProtocols[] = {
- { &gEfiSecurityArchProtocolGuid, (VOID **)&gSecurity, NULL, NULL, FALSE },
- { &gEfiCpuArchProtocolGuid, (VOID **)&gCpu, NULL, NULL, FALSE },
- { &gEfiMetronomeArchProtocolGuid, (VOID **)&gMetronome, NULL, NULL, FALSE },
- { &gEfiTimerArchProtocolGuid, (VOID **)&gTimer, NULL, NULL, FALSE },
- { &gEfiBdsArchProtocolGuid, (VOID **)&gBds, NULL, NULL, FALSE },
- { &gEfiWatchdogTimerArchProtocolGuid, (VOID **)&gWatchdogTimer, NULL, NULL, FALSE },
- { &gEfiRuntimeArchProtocolGuid, (VOID **)&gRuntime, NULL, NULL, FALSE },
- { &gEfiVariableArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE },
- { &gEfiVariableWriteArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE },
- { &gEfiCapsuleArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE },
- { &gEfiMonotonicCounterArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE },
- { &gEfiResetArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE },
- { &gEfiRealTimeClockArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE },
- { NULL, (VOID **)NULL, NULL, NULL, FALSE }
-};
-
-//
-// Optional protocols that the DXE Core will use if they are present
-//
-EFI_CORE_PROTOCOL_NOTIFY_ENTRY mOptionalProtocols[] = {
- { &gEfiSecurity2ArchProtocolGuid, (VOID **)&gSecurity2, NULL, NULL, FALSE },
- { &gEfiSmmBase2ProtocolGuid, (VOID **)&gSmmBase2, NULL, NULL, FALSE },
- { NULL, (VOID **)NULL, NULL, NULL, FALSE }
-};
-
-//
-// Following is needed to display missing architectural protocols in debug builds
-//
-typedef struct {
- EFI_GUID *ProtocolGuid;
- CHAR8 *GuidString;
-} GUID_TO_STRING_PROTOCOL_ENTRY;
-
-GLOBAL_REMOVE_IF_UNREFERENCED CONST GUID_TO_STRING_PROTOCOL_ENTRY mMissingProtocols[] = {
- { &gEfiSecurityArchProtocolGuid, "Security" },
- { &gEfiCpuArchProtocolGuid, "CPU" },
- { &gEfiMetronomeArchProtocolGuid, "Metronome" },
- { &gEfiTimerArchProtocolGuid, "Timer" },
- { &gEfiBdsArchProtocolGuid, "Bds" },
- { &gEfiWatchdogTimerArchProtocolGuid, "Watchdog Timer" },
- { &gEfiRuntimeArchProtocolGuid, "Runtime" },
- { &gEfiVariableArchProtocolGuid, "Variable" },
- { &gEfiVariableWriteArchProtocolGuid, "Variable Write" },
- { &gEfiCapsuleArchProtocolGuid, "Capsule" },
- { &gEfiMonotonicCounterArchProtocolGuid, "Monotonic Counter" },
- { &gEfiResetArchProtocolGuid, "Reset" },
- { &gEfiRealTimeClockArchProtocolGuid, "Real Time Clock" },
- { NULL, "" }
-};
-
-/**
- Return TRUE if all AP services are available.
-
- @retval EFI_SUCCESS All AP services are available
- @retval EFI_NOT_FOUND At least one AP service is not available
-
-**/
-EFI_STATUS
-CoreAllEfiServicesAvailable (
- VOID
- )
-{
- EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry;
-
- for (Entry = mArchProtocols; Entry->ProtocolGuid != NULL; Entry++) {
- if (!Entry->Present) {
- return EFI_NOT_FOUND;
- }
- }
-
- return EFI_SUCCESS;
-}
-
-/**
- Notification event handler registered by CoreNotifyOnArchProtocolInstallation ().
- This notify function is registered for every architectural protocol. This handler
- updates mArchProtocol[] array entry with protocol instance data and sets it's
- present flag to TRUE. If any constructor is required it is executed. The EFI
- System Table headers are updated.
-
- @param Event The Event that is being processed, not used.
- @param Context Event Context, not used.
-
-**/
-VOID
-EFIAPI
-GenericProtocolNotify (
- IN EFI_EVENT Event,
- IN VOID *Context
- )
-{
- EFI_STATUS Status;
- EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry;
- VOID *Protocol;
- LIST_ENTRY *Link;
- LIST_ENTRY TempLinkNode;
-
- Protocol = NULL;
-
- //
- // Get Entry from Context
- //
- Entry = (EFI_CORE_PROTOCOL_NOTIFY_ENTRY *)Context;
-
- //
- // See if the expected protocol is present in the handle database
- //
- Status = CoreLocateProtocol (Entry->ProtocolGuid, Entry->Registration, &Protocol);
- if (EFI_ERROR (Status)) {
- return;
- }
-
- //
- // Mark the protocol as present
- //
- Entry->Present = TRUE;
-
- //
- // Update protocol global variable if one exists. Entry->Protocol points to a global variable
- // if one exists in the DXE core for this Architectural Protocol
- //
- if (Entry->Protocol != NULL) {
- *(Entry->Protocol) = Protocol;
- }
-
- //
- // Do special operations for Architectural Protocols
- //
-
- if (CompareGuid (Entry->ProtocolGuid, &gEfiTimerArchProtocolGuid)) {
- //
- // Register the Core timer tick handler with the Timer AP
- //
- gTimer->RegisterHandler (gTimer, CoreTimerTick);
- }
-
- if (CompareGuid (Entry->ProtocolGuid, &gEfiRuntimeArchProtocolGuid)) {
- //
- // When runtime architectural protocol is available, updates CRC32 in the Debug Table
- //
- CoreUpdateDebugTableCrc32 ();
-
- //
- // Update the Runtime Architectural protocol with the template that the core was
- // using so there would not need to be a dependency on the Runtime AP
- //
-
- //
- // Copy all the registered Image to new gRuntime protocol
- //
- for (Link = gRuntimeTemplate.ImageHead.ForwardLink; Link != &gRuntimeTemplate.ImageHead; Link = TempLinkNode.ForwardLink) {
- CopyMem (&TempLinkNode, Link, sizeof (LIST_ENTRY));
- InsertTailList (&gRuntime->ImageHead, Link);
- }
-
- //
- // Copy all the registered Event to new gRuntime protocol
- //
- for (Link = gRuntimeTemplate.EventHead.ForwardLink; Link != &gRuntimeTemplate.EventHead; Link = TempLinkNode.ForwardLink) {
- CopyMem (&TempLinkNode, Link, sizeof (LIST_ENTRY));
- InsertTailList (&gRuntime->EventHead, Link);
- }
-
- //
- // Clean up gRuntimeTemplate
- //
- gRuntimeTemplate.ImageHead.ForwardLink = &gRuntimeTemplate.ImageHead;
- gRuntimeTemplate.ImageHead.BackLink = &gRuntimeTemplate.ImageHead;
- gRuntimeTemplate.EventHead.ForwardLink = &gRuntimeTemplate.EventHead;
- gRuntimeTemplate.EventHead.BackLink = &gRuntimeTemplate.EventHead;
- }
-
- //
- // It's over kill to do them all every time, but it saves a lot of code.
- //
- CalculateEfiHdrCrc (&gDxeCoreRT->Hdr);
- CalculateEfiHdrCrc (&gBS->Hdr);
- CalculateEfiHdrCrc (&gDxeCoreST->Hdr);
- CalculateEfiHdrCrc (&gDxeCoreDS->Hdr);
-}
-
-/**
- Creates an event for each entry in a table that is fired everytime a Protocol
- of a specific type is installed.
-
- @param Entry Pointer to EFI_CORE_PROTOCOL_NOTIFY_ENTRY.
-
-**/
-VOID
-CoreNotifyOnProtocolEntryTable (
- EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry
- )
-{
- EFI_STATUS Status;
-
- for ( ; Entry->ProtocolGuid != NULL; Entry++) {
- //
- // Create the event
- //
- Status = CoreCreateEvent (
- EVT_NOTIFY_SIGNAL,
- TPL_CALLBACK,
- GenericProtocolNotify,
- Entry,
- &Entry->Event
- );
- ASSERT_EFI_ERROR (Status);
-
- //
- // Register for protocol notifactions on this event
- //
- Status = CoreRegisterProtocolNotify (
- Entry->ProtocolGuid,
- Entry->Event,
- &Entry->Registration
- );
- ASSERT_EFI_ERROR (Status);
- }
-}
-
-/**
- Creates an events for the Architectural Protocols and the optional protocols
- that are fired everytime a Protocol of a specific type is installed.
-
-**/
-VOID
-CoreNotifyOnProtocolInstallation (
- VOID
- )
-{
- CoreNotifyOnProtocolEntryTable (mArchProtocols);
- CoreNotifyOnProtocolEntryTable (mOptionalProtocols);
-}
-
-/**
- Displays Architectural protocols that were not loaded and are required for DXE
- core to function. Only used in Debug Builds.
-
-**/
-VOID
-CoreDisplayMissingArchProtocols (
- VOID
- )
-{
- EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry;
- CONST GUID_TO_STRING_PROTOCOL_ENTRY *MissingEntry;
-
- for (Entry = mArchProtocols; Entry->ProtocolGuid != NULL; Entry++) {
- if (!Entry->Present) {
- for (MissingEntry = mMissingProtocols; MissingEntry->ProtocolGuid != NULL; MissingEntry++) {
- if (CompareGuid (Entry->ProtocolGuid, MissingEntry->ProtocolGuid)) {
- DEBUG ((DEBUG_ERROR, "\n%a Arch Protocol not present!!\n", MissingEntry->GuidString));
- break;
- }
- }
- }
- }
-}
+/** @file + This file deals with Architecture Protocol (AP) registration in + the Dxe Core. The mArchProtocols[] array represents a list of + events that represent the Architectural Protocols. + +Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR> +SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +#include "DxeMain.h" + +// +// DXE Core Global Variables for all of the Architectural Protocols. +// If a protocol is installed mArchProtocols[].Present will be TRUE. +// +// CoreNotifyOnArchProtocolInstallation () fills in mArchProtocols[].Event +// and mArchProtocols[].Registration as it creates events for every array +// entry. +// +EFI_CORE_PROTOCOL_NOTIFY_ENTRY mArchProtocols[] = { + { &gEfiSecurityArchProtocolGuid, (VOID **)&gSecurity, NULL, NULL, FALSE }, + { &gEfiCpuArchProtocolGuid, (VOID **)&gCpu, NULL, NULL, FALSE }, + { &gEfiMetronomeArchProtocolGuid, (VOID **)&gMetronome, NULL, NULL, FALSE }, + { &gEfiTimerArchProtocolGuid, (VOID **)&gTimer, NULL, NULL, FALSE }, + { &gEfiBdsArchProtocolGuid, (VOID **)&gBds, NULL, NULL, FALSE }, + { &gEfiWatchdogTimerArchProtocolGuid, (VOID **)&gWatchdogTimer, NULL, NULL, FALSE }, + { &gEfiRuntimeArchProtocolGuid, (VOID **)&gRuntime, NULL, NULL, FALSE }, + { &gEfiVariableArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE }, + { &gEfiVariableWriteArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE }, + { &gEfiCapsuleArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE }, + { &gEfiMonotonicCounterArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE }, + { &gEfiResetArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE }, + { &gEfiRealTimeClockArchProtocolGuid, (VOID **)NULL, NULL, NULL, FALSE }, + { NULL, (VOID **)NULL, NULL, NULL, FALSE } +}; + +// +// Optional protocols that the DXE Core will use if they are present +// +EFI_CORE_PROTOCOL_NOTIFY_ENTRY mOptionalProtocols[] = { + { &gEfiSecurity2ArchProtocolGuid, (VOID **)&gSecurity2, NULL, NULL, FALSE }, + { &gEfiSmmBase2ProtocolGuid, (VOID **)&gSmmBase2, NULL, NULL, FALSE }, + { NULL, (VOID **)NULL, NULL, NULL, FALSE } +}; + +// +// Following is needed to display missing architectural protocols in debug builds +// +typedef struct { + EFI_GUID *ProtocolGuid; + CHAR8 *GuidString; +} GUID_TO_STRING_PROTOCOL_ENTRY; + +GLOBAL_REMOVE_IF_UNREFERENCED CONST GUID_TO_STRING_PROTOCOL_ENTRY mMissingProtocols[] = { + { &gEfiSecurityArchProtocolGuid, "Security" }, + { &gEfiCpuArchProtocolGuid, "CPU" }, + { &gEfiMetronomeArchProtocolGuid, "Metronome" }, + { &gEfiTimerArchProtocolGuid, "Timer" }, + { &gEfiBdsArchProtocolGuid, "Bds" }, + { &gEfiWatchdogTimerArchProtocolGuid, "Watchdog Timer" }, + { &gEfiRuntimeArchProtocolGuid, "Runtime" }, + { &gEfiVariableArchProtocolGuid, "Variable" }, + { &gEfiVariableWriteArchProtocolGuid, "Variable Write" }, + { &gEfiCapsuleArchProtocolGuid, "Capsule" }, + { &gEfiMonotonicCounterArchProtocolGuid, "Monotonic Counter" }, + { &gEfiResetArchProtocolGuid, "Reset" }, + { &gEfiRealTimeClockArchProtocolGuid, "Real Time Clock" }, + { NULL, "" } +}; + +/** + Return TRUE if all AP services are available. + + @retval EFI_SUCCESS All AP services are available + @retval EFI_NOT_FOUND At least one AP service is not available + +**/ +EFI_STATUS +CoreAllEfiServicesAvailable ( + VOID + ) +{ + EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry; + + for (Entry = mArchProtocols; Entry->ProtocolGuid != NULL; Entry++) { + if (!Entry->Present) { + return EFI_NOT_FOUND; + } + } + + return EFI_SUCCESS; +} + +/** + Notification event handler registered by CoreNotifyOnArchProtocolInstallation (). + This notify function is registered for every architectural protocol. This handler + updates mArchProtocol[] array entry with protocol instance data and sets it's + present flag to TRUE. If any constructor is required it is executed. The EFI + System Table headers are updated. + + @param Event The Event that is being processed, not used. + @param Context Event Context, not used. + +**/ +VOID +EFIAPI +GenericProtocolNotify ( + IN EFI_EVENT Event, + IN VOID *Context + ) +{ + EFI_STATUS Status; + EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry; + VOID *Protocol; + LIST_ENTRY *Link; + LIST_ENTRY TempLinkNode; + + Protocol = NULL; + + // + // Get Entry from Context + // + Entry = (EFI_CORE_PROTOCOL_NOTIFY_ENTRY *)Context; + + // + // See if the expected protocol is present in the handle database + // + Status = CoreLocateProtocol (Entry->ProtocolGuid, Entry->Registration, &Protocol); + if (EFI_ERROR (Status)) { + return; + } + + // + // Mark the protocol as present + // + Entry->Present = TRUE; + + // + // Update protocol global variable if one exists. Entry->Protocol points to a global variable + // if one exists in the DXE core for this Architectural Protocol + // + if (Entry->Protocol != NULL) { + *(Entry->Protocol) = Protocol; + } + + // + // Do special operations for Architectural Protocols + // + + if (CompareGuid (Entry->ProtocolGuid, &gEfiTimerArchProtocolGuid)) { + // + // Register the Core timer tick handler with the Timer AP + // + gTimer->RegisterHandler (gTimer, CoreTimerTick); + } + + if (CompareGuid (Entry->ProtocolGuid, &gEfiRuntimeArchProtocolGuid)) { + // + // When runtime architectural protocol is available, updates CRC32 in the Debug Table + // + CoreUpdateDebugTableCrc32 (); + + // + // Update the Runtime Architectural protocol with the template that the core was + // using so there would not need to be a dependency on the Runtime AP + // + + // + // Copy all the registered Image to new gRuntime protocol + // + for (Link = gRuntimeTemplate.ImageHead.ForwardLink; Link != &gRuntimeTemplate.ImageHead; Link = TempLinkNode.ForwardLink) { + CopyMem (&TempLinkNode, Link, sizeof (LIST_ENTRY)); + InsertTailList (&gRuntime->ImageHead, Link); + } + + // + // Copy all the registered Event to new gRuntime protocol + // + for (Link = gRuntimeTemplate.EventHead.ForwardLink; Link != &gRuntimeTemplate.EventHead; Link = TempLinkNode.ForwardLink) { + CopyMem (&TempLinkNode, Link, sizeof (LIST_ENTRY)); + InsertTailList (&gRuntime->EventHead, Link); + } + + // + // Clean up gRuntimeTemplate + // + gRuntimeTemplate.ImageHead.ForwardLink = &gRuntimeTemplate.ImageHead; + gRuntimeTemplate.ImageHead.BackLink = &gRuntimeTemplate.ImageHead; + gRuntimeTemplate.EventHead.ForwardLink = &gRuntimeTemplate.EventHead; + gRuntimeTemplate.EventHead.BackLink = &gRuntimeTemplate.EventHead; + } + + // + // It's over kill to do them all every time, but it saves a lot of code. + // + CalculateEfiHdrCrc (&gDxeCoreRT->Hdr); + CalculateEfiHdrCrc (&gBS->Hdr); + CalculateEfiHdrCrc (&gDxeCoreST->Hdr); + CalculateEfiHdrCrc (&gDxeCoreDS->Hdr); +} + +/** + Creates an event for each entry in a table that is fired everytime a Protocol + of a specific type is installed. + + @param Entry Pointer to EFI_CORE_PROTOCOL_NOTIFY_ENTRY. + +**/ +VOID +CoreNotifyOnProtocolEntryTable ( + EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry + ) +{ + EFI_STATUS Status; + + for ( ; Entry->ProtocolGuid != NULL; Entry++) { + // + // Create the event + // + Status = CoreCreateEvent ( + EVT_NOTIFY_SIGNAL, + TPL_CALLBACK, + GenericProtocolNotify, + Entry, + &Entry->Event + ); + ASSERT_EFI_ERROR (Status); + + // + // Register for protocol notifactions on this event + // + Status = CoreRegisterProtocolNotify ( + Entry->ProtocolGuid, + Entry->Event, + &Entry->Registration + ); + ASSERT_EFI_ERROR (Status); + } +} + +/** + Creates an events for the Architectural Protocols and the optional protocols + that are fired everytime a Protocol of a specific type is installed. + +**/ +VOID +CoreNotifyOnProtocolInstallation ( + VOID + ) +{ + CoreNotifyOnProtocolEntryTable (mArchProtocols); + CoreNotifyOnProtocolEntryTable (mOptionalProtocols); +} + +/** + Displays Architectural protocols that were not loaded and are required for DXE + core to function. Only used in Debug Builds. + +**/ +VOID +CoreDisplayMissingArchProtocols ( + VOID + ) +{ + EFI_CORE_PROTOCOL_NOTIFY_ENTRY *Entry; + CONST GUID_TO_STRING_PROTOCOL_ENTRY *MissingEntry; + + for (Entry = mArchProtocols; Entry->ProtocolGuid != NULL; Entry++) { + if (!Entry->Present) { + for (MissingEntry = mMissingProtocols; MissingEntry->ProtocolGuid != NULL; MissingEntry++) { + if (CompareGuid (Entry->ProtocolGuid, MissingEntry->ProtocolGuid)) { + DEBUG ((DEBUG_ERROR, "\n%a Arch Protocol not present!!\n", MissingEntry->GuidString)); + break; + } + } + } + } +} |
