Curle
4300dc655c
The lib/inc folders are from the GNU-EFI project. The documentation is from the uefi.org site. Yes, I know there are duplicate includes. I have a plan for them.
155 lines
3.2 KiB
C
155 lines
3.2 KiB
C
/*++
|
|
|
|
Copyright (c) 1998 Intel Corporation
|
|
|
|
Module Name:
|
|
|
|
event.c
|
|
|
|
Abstract:
|
|
|
|
|
|
|
|
|
|
Revision History
|
|
|
|
--*/
|
|
|
|
#include "lib.h"
|
|
|
|
|
|
EFI_EVENT
|
|
LibCreateProtocolNotifyEvent (
|
|
IN EFI_GUID *ProtocolGuid,
|
|
IN EFI_TPL NotifyTpl,
|
|
IN EFI_EVENT_NOTIFY NotifyFunction,
|
|
IN VOID *NotifyContext,
|
|
OUT VOID *Registration
|
|
)
|
|
{
|
|
EFI_STATUS Status;
|
|
EFI_EVENT Event;
|
|
|
|
//
|
|
// Create the event
|
|
//
|
|
|
|
Status = uefi_call_wrapper(
|
|
BS->CreateEvent,
|
|
5,
|
|
EVT_NOTIFY_SIGNAL,
|
|
NotifyTpl,
|
|
NotifyFunction,
|
|
NotifyContext,
|
|
&Event
|
|
);
|
|
if ( EFI_ERROR( Status ) ) return NULL ;
|
|
ASSERT (!EFI_ERROR(Status));
|
|
|
|
//
|
|
// Register for protocol notifactions on this event
|
|
//
|
|
|
|
Status = uefi_call_wrapper(
|
|
BS->RegisterProtocolNotify,
|
|
3,
|
|
ProtocolGuid,
|
|
Event,
|
|
Registration
|
|
);
|
|
if ( EFI_ERROR( Status ) ) return NULL ;
|
|
ASSERT (!EFI_ERROR(Status));
|
|
|
|
//
|
|
// Kick the event so we will perform an initial pass of
|
|
// current installed drivers
|
|
//
|
|
|
|
uefi_call_wrapper(BS->SignalEvent, 1, Event);
|
|
return Event;
|
|
}
|
|
|
|
|
|
EFI_STATUS
|
|
WaitForSingleEvent (
|
|
IN EFI_EVENT Event,
|
|
IN UINT64 Timeout OPTIONAL
|
|
)
|
|
{
|
|
EFI_STATUS Status;
|
|
UINTN Index;
|
|
EFI_EVENT TimerEvent;
|
|
EFI_EVENT WaitList[2];
|
|
|
|
if (Timeout) {
|
|
//
|
|
// Create a timer event
|
|
//
|
|
|
|
Status = uefi_call_wrapper(BS->CreateEvent, 5, EVT_TIMER, 0, NULL, NULL, &TimerEvent);
|
|
if (!EFI_ERROR(Status)) {
|
|
|
|
//
|
|
// Set the timer event
|
|
//
|
|
|
|
uefi_call_wrapper(BS->SetTimer, 3, TimerEvent, TimerRelative, Timeout);
|
|
|
|
//
|
|
// Wait for the original event or the timer
|
|
//
|
|
|
|
WaitList[0] = Event;
|
|
WaitList[1] = TimerEvent;
|
|
Status = uefi_call_wrapper(BS->WaitForEvent, 3, 2, WaitList, &Index);
|
|
uefi_call_wrapper(BS->CloseEvent, 1, TimerEvent);
|
|
|
|
//
|
|
// If the timer expired, change the return to timed out
|
|
//
|
|
|
|
if (!EFI_ERROR(Status) && Index == 1) {
|
|
Status = EFI_TIMEOUT;
|
|
}
|
|
}
|
|
|
|
} else {
|
|
|
|
//
|
|
// No timeout... just wait on the event
|
|
//
|
|
|
|
Status = uefi_call_wrapper(BS->WaitForEvent, 3, 1, &Event, &Index);
|
|
ASSERT (!EFI_ERROR(Status));
|
|
ASSERT (Index == 0);
|
|
}
|
|
|
|
return Status;
|
|
}
|
|
|
|
VOID
|
|
WaitForEventWithTimeout (
|
|
IN EFI_EVENT Event,
|
|
IN UINTN Timeout,
|
|
IN UINTN Row,
|
|
IN UINTN Column,
|
|
IN CHAR16 *String,
|
|
IN EFI_INPUT_KEY TimeoutKey,
|
|
OUT EFI_INPUT_KEY *Key
|
|
)
|
|
{
|
|
EFI_STATUS Status;
|
|
|
|
do {
|
|
PrintAt (Column, Row, String, Timeout);
|
|
Status = WaitForSingleEvent (Event, 10000000);
|
|
if (Status == EFI_SUCCESS) {
|
|
if (!EFI_ERROR(uefi_call_wrapper(ST->ConIn->ReadKeyStroke, 2, ST->ConIn, Key))) {
|
|
return;
|
|
}
|
|
}
|
|
} while (Timeout > 0);
|
|
CopyMem(Key, &TimeoutKey, sizeof(EFI_INPUT_KEY));
|
|
}
|
|
|