Standarized code styles (clang-format)
This commit is contained in:
parent
ebe85dc0f2
commit
aee5d4edfa
17
.clang-format
Normal file
17
.clang-format
Normal file
@ -0,0 +1,17 @@
|
||||
Language: Cpp
|
||||
BreakBeforeBraces: Stroustrup
|
||||
PointerAlignment: Right
|
||||
IndentWidth: 2
|
||||
AccessModifierOffset: 0
|
||||
ColumnLimit: 80
|
||||
NamespaceIndentation: All
|
||||
AlignTrailingComments: true
|
||||
AllowAllParametersOfDeclarationOnNextLine: true
|
||||
AlwaysBreakTemplateDeclarations: true
|
||||
AlignAfterOpenBracket: AlwaysBreak
|
||||
UseTab: Never
|
||||
IncludeBlocks: Preserve
|
||||
AlignConsecutiveDeclarations: true
|
||||
AlignConsecutiveAssignments: true
|
||||
SpacesInParentheses: false
|
||||
SpaceBeforeParens: ControlStatements
|
@ -16,27 +16,26 @@
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/
|
||||
*/
|
||||
|
||||
#include <Library/UefiApplicationEntryPoint.h>
|
||||
#include <Library/BootSlotLib.h>
|
||||
#include <Library/UefiApplicationEntryPoint.h>
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
SwitchSlotsAppEntryPoint (
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
)
|
||||
SwitchSlotsAppEntryPoint(
|
||||
IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
{
|
||||
|
||||
MemCardType Type = CheckRootDeviceType();
|
||||
if (Type == UNKNOWN) {
|
||||
PrintAndWaitAnyKey(SystemTable, L"Unknown device storage. Press any key to exit.\n");
|
||||
PrintAndWaitAnyKey(
|
||||
SystemTable, L"Unknown device storage. Press any key to exit.\n");
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
|
||||
EFI_STATUS Status = EnumeratePartitions();
|
||||
|
||||
if (EFI_ERROR (Status)) {
|
||||
Print (L"Could not enumerate partitions. Code %d\n", Status);
|
||||
if (EFI_ERROR(Status)) {
|
||||
Print(L"Could not enumerate partitions. Code %d\n", Status);
|
||||
WaitAnyKey(SystemTable);
|
||||
return Status;
|
||||
}
|
||||
@ -44,39 +43,46 @@ SwitchSlotsAppEntryPoint (
|
||||
UpdatePartitionEntries();
|
||||
|
||||
/*Check for multislot boot support*/
|
||||
BOOLEAN MultiSlotSupported = PartitionHasMultiSlot ((CONST CHAR16 *)L"boot");
|
||||
BOOLEAN MultiSlotSupported = PartitionHasMultiSlot((CONST CHAR16 *)L"boot");
|
||||
if (!MultiSlotSupported) {
|
||||
PrintAndWaitAnyKey(SystemTable, L"A/B slots aren't supported on this device. Press any key to exit.\n");
|
||||
PrintAndWaitAnyKey(
|
||||
SystemTable,
|
||||
L"A/B slots aren't supported on this device. Press any key to exit.\n");
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
|
||||
Slot CurrentSlot = GetCurrentSlotSuffix();
|
||||
if (IsSuffixEmpty(&CurrentSlot)) {
|
||||
PrintAndWaitAnyKey(SystemTable, L"Current active slot not found, try to boot Android first. Press any key to exit.\n");
|
||||
PrintAndWaitAnyKey(
|
||||
SystemTable, L"Current active slot not found, try to boot Android "
|
||||
L"first. Press any key to exit.\n");
|
||||
return EFI_NOT_READY;
|
||||
}
|
||||
|
||||
Slot *NewSlot = NULL;
|
||||
Slot Slots[] = {{L"_a"}, {L"_b"}};
|
||||
if (StrnCmp (CurrentSlot.Suffix, Slots[0].Suffix, StrLen (Slots[0].Suffix)) == 0) {
|
||||
if (StrnCmp(CurrentSlot.Suffix, Slots[0].Suffix, StrLen(Slots[0].Suffix)) ==
|
||||
0) {
|
||||
NewSlot = &Slots[1];
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
NewSlot = &Slots[0];
|
||||
}
|
||||
|
||||
//Print (L"Current active slot suffix is: %s, next slot suffix is: %s\n", &CurrentSlot.Suffix, &NewSlot->Suffix);
|
||||
// Print (L"Current active slot suffix is: %s, next slot suffix is: %s\n",
|
||||
// &CurrentSlot.Suffix, &NewSlot->Suffix);
|
||||
|
||||
Status = SetActiveSlot(NewSlot, TRUE, FALSE);
|
||||
|
||||
if (EFI_ERROR(Status)) {
|
||||
Print (L"Could not update active slot. Code %d\n", Status);
|
||||
Print(L"Could not update active slot. Code %d\n", Status);
|
||||
WaitAnyKey(SystemTable);
|
||||
return Status;
|
||||
}
|
||||
|
||||
//Print (L"Current active slot has been updated successfully! Press any key to reboot.\n");
|
||||
//WaitAnyKey(SystemTable);
|
||||
gRT->ResetSystem (EfiResetWarm, EFI_SUCCESS, 0, NULL);
|
||||
CpuDeadLoop ();
|
||||
// Print (L"Current active slot has been updated successfully! Press any key
|
||||
// to reboot.\n"); WaitAnyKey(SystemTable);
|
||||
gRT->ResetSystem(EfiResetWarm, EFI_SUCCESS, 0, NULL);
|
||||
CpuDeadLoop();
|
||||
return EFI_SUCCESS;
|
||||
}
|
@ -16,35 +16,35 @@
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/
|
||||
*/
|
||||
|
||||
#include <Uefi.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Library/BootSlotLib.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Uefi.h>
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
BootSlotMain(
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
) {
|
||||
BootSlotMain(IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
{
|
||||
MemCardType Type = CheckRootDeviceType();
|
||||
if (Type == UNKNOWN) {
|
||||
DEBUG ((EFI_D_ERROR, "Device storage is not supported \n"));
|
||||
DEBUG((EFI_D_ERROR, "Device storage is not supported \n"));
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
EFI_STATUS Status = EnumeratePartitions();
|
||||
|
||||
if (EFI_ERROR (Status)) {
|
||||
DEBUG ((EFI_D_ERROR, "Could not enumerate partitions. Code %d\n", Status));
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG((EFI_D_ERROR, "Could not enumerate partitions. Code %d\n", Status));
|
||||
return Status;
|
||||
}
|
||||
|
||||
UpdatePartitionEntries();
|
||||
|
||||
/*Check for multislot boot support*/
|
||||
BOOLEAN MultiSlotSupported = PartitionHasMultiSlot ((CONST CHAR16 *)L"boot");
|
||||
BOOLEAN MultiSlotSupported = PartitionHasMultiSlot((CONST CHAR16 *)L"boot");
|
||||
if (!MultiSlotSupported) {
|
||||
DEBUG ((EFI_D_ERROR, "A/B slots aren't supported on this device. Press any key to exit.\n"));
|
||||
DEBUG((
|
||||
EFI_D_ERROR,
|
||||
"A/B slots aren't supported on this device. Press any key to exit.\n"));
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
@ -52,22 +52,24 @@ BootSlotMain(
|
||||
|
||||
Slot CurrentSlot = GetCurrentSlotSuffix();
|
||||
if (IsSuffixEmpty(&CurrentSlot)) {
|
||||
CurrentSlot = Slots[0]; // Set A as active if there is no slot available (shouldn't happen though)
|
||||
CurrentSlot = Slots[0]; // Set A as active if there is no slot available
|
||||
// (shouldn't happen though)
|
||||
}
|
||||
|
||||
// Clear all unbootable bits if exists
|
||||
for (UINTN SlotIndex = 0; SlotIndex < ARRAY_SIZE (Slots); SlotIndex++) {
|
||||
for (UINTN SlotIndex = 0; SlotIndex < ARRAY_SIZE(Slots); SlotIndex++) {
|
||||
Slot *SlotEntry = &Slots[SlotIndex];
|
||||
if (!IsSlotBootable(SlotEntry)) {
|
||||
ClearUnbootable(SlotEntry);
|
||||
}
|
||||
}
|
||||
|
||||
// Set current slot as active again just refresh its attributes + mark it successful
|
||||
// Set current slot as active again just refresh its attributes + mark it
|
||||
// successful
|
||||
Status = SetActiveSlot(&CurrentSlot, FALSE, TRUE);
|
||||
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG ((EFI_D_ERROR, "Could not update active slot. Code %d\n", Status));
|
||||
DEBUG((EFI_D_ERROR, "Could not update active slot. Code %d\n", Status));
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
@ -1,8 +1,8 @@
|
||||
#include <PiDxe.h>
|
||||
#include <Protocol/KeypadDevice.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/KeypadDeviceImplLib.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <PiDxe.h>
|
||||
#include <Protocol/KeypadDevice.h>
|
||||
|
||||
typedef struct {
|
||||
VENDOR_DEVICE_PATH Keypad;
|
||||
@ -21,12 +21,9 @@ KEYPAD_DEVICE_PATH mInternalDevicePath = {
|
||||
},
|
||||
EFI_CALLER_ID_GUID,
|
||||
},
|
||||
{
|
||||
END_DEVICE_PATH_TYPE,
|
||||
{END_DEVICE_PATH_TYPE,
|
||||
END_ENTIRE_DEVICE_PATH_SUBTYPE,
|
||||
{ sizeof (EFI_DEVICE_PATH_PROTOCOL), 0 }
|
||||
}
|
||||
};
|
||||
{sizeof(EFI_DEVICE_PATH_PROTOCOL), 0}}};
|
||||
|
||||
STATIC KEYPAD_DEVICE_PROTOCOL mInternalKeypadDevice = {
|
||||
KeypadDeviceImplReset,
|
||||
@ -35,21 +32,14 @@ STATIC KEYPAD_DEVICE_PROTOCOL mInternalKeypadDevice = {
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadDeviceDxeInitialize (
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
)
|
||||
KeypadDeviceDxeInitialize(
|
||||
IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
Status = gBS->InstallMultipleProtocolInterfaces(
|
||||
&ImageHandle,
|
||||
&gEFIDroidKeypadDeviceProtocolGuid,
|
||||
&mInternalKeypadDevice,
|
||||
&gEfiDevicePathProtocolGuid,
|
||||
&mInternalDevicePath,
|
||||
NULL
|
||||
);
|
||||
&ImageHandle, &gEFIDroidKeypadDeviceProtocolGuid, &mInternalKeypadDevice,
|
||||
&gEfiDevicePathProtocolGuid, &mInternalDevicePath, NULL);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
return Status;
|
||||
|
@ -3,9 +3,9 @@
|
||||
|
||||
Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
|
||||
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
|
||||
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.
|
||||
@ -58,12 +58,9 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadComponentNameGetDriverName (
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This,
|
||||
IN CHAR8 *Language,
|
||||
OUT CHAR16 **DriverName
|
||||
);
|
||||
|
||||
KeypadComponentNameGetDriverName(
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This, IN CHAR8 *Language,
|
||||
OUT CHAR16 **DriverName);
|
||||
|
||||
/**
|
||||
Retrieves a Unicode string that is the user readable name of the controller
|
||||
@ -135,44 +132,30 @@ KeypadComponentNameGetDriverName (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadComponentNameGetControllerName (
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This,
|
||||
IN EFI_HANDLE ControllerHandle,
|
||||
IN EFI_HANDLE ChildHandle OPTIONAL,
|
||||
IN CHAR8 *Language,
|
||||
OUT CHAR16 **ControllerName
|
||||
);
|
||||
|
||||
KeypadComponentNameGetControllerName(
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This, IN EFI_HANDLE ControllerHandle,
|
||||
IN EFI_HANDLE ChildHandle OPTIONAL, IN CHAR8 *Language,
|
||||
OUT CHAR16 **ControllerName);
|
||||
|
||||
//
|
||||
// EFI Component Name Protocol
|
||||
//
|
||||
GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME_PROTOCOL gKeypadComponentName = {
|
||||
KeypadComponentNameGetDriverName,
|
||||
KeypadComponentNameGetControllerName,
|
||||
"eng"
|
||||
};
|
||||
GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME_PROTOCOL gKeypadComponentName =
|
||||
{KeypadComponentNameGetDriverName, KeypadComponentNameGetControllerName,
|
||||
"eng"};
|
||||
|
||||
//
|
||||
// EFI Component Name 2 Protocol
|
||||
//
|
||||
GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME2_PROTOCOL gKeypadComponentName2 = {
|
||||
(EFI_COMPONENT_NAME2_GET_DRIVER_NAME) KeypadComponentNameGetDriverName,
|
||||
(EFI_COMPONENT_NAME2_GET_CONTROLLER_NAME) KeypadComponentNameGetControllerName,
|
||||
"en"
|
||||
};
|
||||
GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME2_PROTOCOL
|
||||
gKeypadComponentName2 = {
|
||||
(EFI_COMPONENT_NAME2_GET_DRIVER_NAME)KeypadComponentNameGetDriverName,
|
||||
(EFI_COMPONENT_NAME2_GET_CONTROLLER_NAME)
|
||||
KeypadComponentNameGetControllerName,
|
||||
"en"};
|
||||
|
||||
|
||||
GLOBAL_REMOVE_IF_UNREFERENCED EFI_UNICODE_STRING_TABLE mKeypadDriverNameTable[] = {
|
||||
{
|
||||
"eng;en",
|
||||
L"Keypad Driver"
|
||||
},
|
||||
{
|
||||
NULL,
|
||||
NULL
|
||||
}
|
||||
};
|
||||
GLOBAL_REMOVE_IF_UNREFERENCED EFI_UNICODE_STRING_TABLE
|
||||
mKeypadDriverNameTable[] = {{"eng;en", L"Keypad Driver"}, {NULL, NULL}};
|
||||
|
||||
/**
|
||||
Retrieves a Unicode string that is the user readable name of the driver.
|
||||
@ -215,19 +198,13 @@ GLOBAL_REMOVE_IF_UNREFERENCED EFI_UNICODE_STRING_TABLE mKeypadDriverNameTable[]
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadComponentNameGetDriverName (
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This,
|
||||
IN CHAR8 *Language,
|
||||
OUT CHAR16 **DriverName
|
||||
)
|
||||
KeypadComponentNameGetDriverName(
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This, IN CHAR8 *Language,
|
||||
OUT CHAR16 **DriverName)
|
||||
{
|
||||
return LookupUnicodeString2 (
|
||||
Language,
|
||||
This->SupportedLanguages,
|
||||
mKeypadDriverNameTable,
|
||||
DriverName,
|
||||
(BOOLEAN)(This == &gKeypadComponentName)
|
||||
);
|
||||
return LookupUnicodeString2(
|
||||
Language, This->SupportedLanguages, mKeypadDriverNameTable, DriverName,
|
||||
(BOOLEAN)(This == &gKeypadComponentName));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -300,17 +277,14 @@ KeypadComponentNameGetDriverName (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadComponentNameGetControllerName (
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This,
|
||||
IN EFI_HANDLE ControllerHandle,
|
||||
IN EFI_HANDLE ChildHandle OPTIONAL,
|
||||
IN CHAR8 *Language,
|
||||
OUT CHAR16 **ControllerName
|
||||
)
|
||||
KeypadComponentNameGetControllerName(
|
||||
IN EFI_COMPONENT_NAME_PROTOCOL *This, IN EFI_HANDLE ControllerHandle,
|
||||
IN EFI_HANDLE ChildHandle OPTIONAL, IN CHAR8 *Language,
|
||||
OUT CHAR16 **ControllerName)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_SIMPLE_TEXT_INPUT_PROTOCOL *ConIn;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
KEYPAD_CONSOLE_IN_DEV * ConsoleIn;
|
||||
//
|
||||
// This is a device driver, so ChildHandle must be NULL.
|
||||
//
|
||||
@ -321,32 +295,26 @@ KeypadComponentNameGetControllerName (
|
||||
//
|
||||
// Check Controller's handle
|
||||
//
|
||||
Status = EfiTestManagedDevice (ControllerHandle, gKeypadControllerDriver.DriverBindingHandle, &gEFIDroidKeypadDeviceProtocolGuid);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = EfiTestManagedDevice(
|
||||
ControllerHandle, gKeypadControllerDriver.DriverBindingHandle,
|
||||
&gEFIDroidKeypadDeviceProtocolGuid);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
//
|
||||
// Get the device context
|
||||
//
|
||||
Status = gBS->OpenProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiSimpleTextInProtocolGuid,
|
||||
(VOID **) &ConIn,
|
||||
gKeypadControllerDriver.DriverBindingHandle,
|
||||
ControllerHandle,
|
||||
EFI_OPEN_PROTOCOL_GET_PROTOCOL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->OpenProtocol(
|
||||
ControllerHandle, &gEfiSimpleTextInProtocolGuid, (VOID **)&ConIn,
|
||||
gKeypadControllerDriver.DriverBindingHandle, ControllerHandle,
|
||||
EFI_OPEN_PROTOCOL_GET_PROTOCOL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS (ConIn);
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS(ConIn);
|
||||
|
||||
return LookupUnicodeString2 (
|
||||
Language,
|
||||
This->SupportedLanguages,
|
||||
ConsoleIn->ControllerNameTable,
|
||||
ControllerName,
|
||||
(BOOLEAN)(This == &gKeypadComponentName)
|
||||
);
|
||||
return LookupUnicodeString2(
|
||||
Language, This->SupportedLanguages, ConsoleIn->ControllerNameTable,
|
||||
ControllerName, (BOOLEAN)(This == &gKeypadComponentName));
|
||||
}
|
||||
|
@ -5,9 +5,9 @@
|
||||
|
||||
Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
|
||||
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
|
||||
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.
|
||||
@ -32,11 +32,9 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadControllerDriverSupported (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath
|
||||
);
|
||||
KeypadControllerDriverSupported(
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This, IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath);
|
||||
|
||||
/**
|
||||
Create KEYPAD_CONSOLE_IN_DEV instance on controller.
|
||||
@ -49,11 +47,9 @@ KeypadControllerDriverSupported (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadControllerDriverStart (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath
|
||||
);
|
||||
KeypadControllerDriverStart(
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This, IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath);
|
||||
|
||||
/**
|
||||
Stop this driver on ControllerHandle. Support stopping any child handles
|
||||
@ -71,12 +67,9 @@ KeypadControllerDriverStart (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadControllerDriverStop (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE Controller,
|
||||
IN UINTN NumberOfChildren,
|
||||
IN EFI_HANDLE *ChildHandleBuffer
|
||||
);
|
||||
KeypadControllerDriverStop(
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This, IN EFI_HANDLE Controller,
|
||||
IN UINTN NumberOfChildren, IN EFI_HANDLE *ChildHandleBuffer);
|
||||
|
||||
/**
|
||||
Free the waiting key notify list.
|
||||
@ -87,9 +80,7 @@ KeypadControllerDriverStop (
|
||||
@retval EFI_SUCCESS Sucess to free NotifyList
|
||||
**/
|
||||
EFI_STATUS
|
||||
KbdFreeNotifyList (
|
||||
IN OUT LIST_ENTRY *ListHead
|
||||
);
|
||||
KbdFreeNotifyList(IN OUT LIST_ENTRY *ListHead);
|
||||
|
||||
//
|
||||
// DriverBinding Protocol Instance
|
||||
@ -100,8 +91,7 @@ EFI_DRIVER_BINDING_PROTOCOL gKeypadControllerDriver = {
|
||||
KeypadControllerDriverStop,
|
||||
0xa,
|
||||
NULL,
|
||||
NULL
|
||||
};
|
||||
NULL};
|
||||
|
||||
/**
|
||||
Test controller is a keypad Controller.
|
||||
@ -115,11 +105,9 @@ EFI_DRIVER_BINDING_PROTOCOL gKeypadControllerDriver = {
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadControllerDriverSupported (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath
|
||||
)
|
||||
KeypadControllerDriverSupported(
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This, IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
KEYPAD_DEVICE_PROTOCOL *KeypadDevice;
|
||||
@ -127,77 +115,65 @@ KeypadControllerDriverSupported (
|
||||
//
|
||||
// Open the IO Abstraction(s) needed to perform the supported test
|
||||
//
|
||||
Status = gBS->OpenProtocol (
|
||||
Controller,
|
||||
&gEFIDroidKeypadDeviceProtocolGuid,
|
||||
(VOID **) &KeypadDevice,
|
||||
This->DriverBindingHandle,
|
||||
Controller,
|
||||
EFI_OPEN_PROTOCOL_BY_DRIVER
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->OpenProtocol(
|
||||
Controller, &gEFIDroidKeypadDeviceProtocolGuid, (VOID **)&KeypadDevice,
|
||||
This->DriverBindingHandle, Controller, EFI_OPEN_PROTOCOL_BY_DRIVER);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
//
|
||||
// Close the I/O Abstraction(s) used to perform the supported test
|
||||
//
|
||||
gBS->CloseProtocol (
|
||||
Controller,
|
||||
&gEFIDroidKeypadDeviceProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
Controller
|
||||
);
|
||||
gBS->CloseProtocol(
|
||||
Controller, &gEFIDroidKeypadDeviceProtocolGuid, This->DriverBindingHandle,
|
||||
Controller);
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
EFIAPI
|
||||
KeypadReturnApiPushEfikeyBufTail (
|
||||
KEYPAD_RETURN_API *This,
|
||||
EFI_KEY_DATA *KeyData
|
||||
)
|
||||
VOID EFIAPI
|
||||
KeypadReturnApiPushEfikeyBufTail(KEYPAD_RETURN_API *This, EFI_KEY_DATA *KeyData)
|
||||
{
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
LIST_ENTRY *Link;
|
||||
KEYPAD_CONSOLE_IN_DEV * ConsoleIn;
|
||||
LIST_ENTRY * Link;
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY *CurrentNotify;
|
||||
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_KEYPAD_RETURN_API (This);
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_KEYPAD_RETURN_API(This);
|
||||
|
||||
//
|
||||
// If the key can not be converted then just return.
|
||||
//
|
||||
if (KeyData->Key.ScanCode == SCAN_NULL && KeyData->Key.UnicodeChar == CHAR_NULL) {
|
||||
if (KeyData->Key.ScanCode == SCAN_NULL &&
|
||||
KeyData->Key.UnicodeChar == CHAR_NULL) {
|
||||
if (!ConsoleIn->IsSupportPartialKey) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Signal KeyNotify process event if this key pressed matches any key registered.
|
||||
// Signal KeyNotify process event if this key pressed matches any key
|
||||
// registered.
|
||||
//
|
||||
for (Link = GetFirstNode (&ConsoleIn->NotifyList); !IsNull (&ConsoleIn->NotifyList, Link); Link = GetNextNode (&ConsoleIn->NotifyList, Link)) {
|
||||
CurrentNotify = CR (
|
||||
Link,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY,
|
||||
NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE
|
||||
);
|
||||
if (IsKeyRegistered (&CurrentNotify->KeyData, KeyData)) {
|
||||
for (Link = GetFirstNode(&ConsoleIn->NotifyList);
|
||||
!IsNull(&ConsoleIn->NotifyList, Link);
|
||||
Link = GetNextNode(&ConsoleIn->NotifyList, Link)) {
|
||||
CurrentNotify =
|
||||
CR(Link, KEYPAD_CONSOLE_IN_EX_NOTIFY, NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE);
|
||||
if (IsKeyRegistered(&CurrentNotify->KeyData, KeyData)) {
|
||||
//
|
||||
// The key notification function needs to run at TPL_CALLBACK
|
||||
// while current TPL is TPL_NOTIFY. It will be invoked in
|
||||
// KeyNotifyProcessHandler() which runs at TPL_CALLBACK.
|
||||
//
|
||||
PushEfikeyBufTail (&ConsoleIn->EfiKeyQueueForNotify, KeyData);
|
||||
gBS->SignalEvent (ConsoleIn->KeyNotifyProcessEvent);
|
||||
PushEfikeyBufTail(&ConsoleIn->EfiKeyQueueForNotify, KeyData);
|
||||
gBS->SignalEvent(ConsoleIn->KeyNotifyProcessEvent);
|
||||
}
|
||||
}
|
||||
|
||||
PushEfikeyBufTail (&ConsoleIn->EfiKeyQueue, KeyData);
|
||||
PushEfikeyBufTail(&ConsoleIn->EfiKeyQueue, KeyData);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -211,34 +187,27 @@ KeypadReturnApiPushEfikeyBufTail (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadControllerDriverStart (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath
|
||||
)
|
||||
KeypadControllerDriverStart(
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This, IN EFI_HANDLE Controller,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
KEYPAD_DEVICE_PROTOCOL *KeypadDevice;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
KEYPAD_CONSOLE_IN_DEV * ConsoleIn;
|
||||
|
||||
//
|
||||
// Get the ISA I/O Protocol on Controller's handle
|
||||
//
|
||||
Status = gBS->OpenProtocol (
|
||||
Controller,
|
||||
&gEFIDroidKeypadDeviceProtocolGuid,
|
||||
(VOID **) &KeypadDevice,
|
||||
This->DriverBindingHandle,
|
||||
Controller,
|
||||
EFI_OPEN_PROTOCOL_BY_DRIVER
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->OpenProtocol(
|
||||
Controller, &gEFIDroidKeypadDeviceProtocolGuid, (VOID **)&KeypadDevice,
|
||||
This->DriverBindingHandle, Controller, EFI_OPEN_PROTOCOL_BY_DRIVER);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
//
|
||||
// Allocate private data
|
||||
//
|
||||
ConsoleIn = AllocateZeroPool (sizeof (KEYPAD_CONSOLE_IN_DEV));
|
||||
ConsoleIn = AllocateZeroPool(sizeof(KEYPAD_CONSOLE_IN_DEV));
|
||||
if (ConsoleIn == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto ErrorExit;
|
||||
@ -251,7 +220,8 @@ KeypadControllerDriverStart (
|
||||
(ConsoleIn->ConIn).Reset = KeypadEfiReset;
|
||||
(ConsoleIn->ConIn).ReadKeyStroke = KeypadReadKeyStroke;
|
||||
ConsoleIn->KeypadDevice = KeypadDevice;
|
||||
ConsoleIn->KeypadReturnApi.PushEfikeyBufTail = KeypadReturnApiPushEfikeyBufTail;
|
||||
ConsoleIn->KeypadReturnApi.PushEfikeyBufTail =
|
||||
KeypadReturnApiPushEfikeyBufTail;
|
||||
ConsoleIn->Last = (UINT64)-1;
|
||||
|
||||
ConsoleIn->ConInEx.Reset = KeypadEfiResetEx;
|
||||
@ -260,75 +230,56 @@ KeypadControllerDriverStart (
|
||||
ConsoleIn->ConInEx.RegisterKeyNotify = KeypadRegisterKeyNotify;
|
||||
ConsoleIn->ConInEx.UnregisterKeyNotify = KeypadUnregisterKeyNotify;
|
||||
|
||||
InitializeListHead (&ConsoleIn->NotifyList);
|
||||
InitializeListHead(&ConsoleIn->NotifyList);
|
||||
|
||||
//
|
||||
// Fix for random hangs in System waiting for the Key if no KBC is present in BIOS.
|
||||
// When KBC decode (IO port 0x60/0x64 decode) is not enabled,
|
||||
// KeypadRead will read back as 0xFF and return status is EFI_SUCCESS.
|
||||
// So instead we read status register to detect after read if KBC decode is enabled.
|
||||
// Fix for random hangs in System waiting for the Key if no KBC is present in
|
||||
// BIOS. When KBC decode (IO port 0x60/0x64 decode) is not enabled, KeypadRead
|
||||
// will read back as 0xFF and return status is EFI_SUCCESS. So instead we read
|
||||
// status register to detect after read if KBC decode is enabled.
|
||||
//
|
||||
|
||||
//
|
||||
// Setup the WaitForKey event
|
||||
//
|
||||
Status = gBS->CreateEvent (
|
||||
EVT_NOTIFY_WAIT,
|
||||
TPL_NOTIFY,
|
||||
KeypadWaitForKey,
|
||||
ConsoleIn,
|
||||
&((ConsoleIn->ConIn).WaitForKey)
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->CreateEvent(
|
||||
EVT_NOTIFY_WAIT, TPL_NOTIFY, KeypadWaitForKey, ConsoleIn,
|
||||
&((ConsoleIn->ConIn).WaitForKey));
|
||||
if (EFI_ERROR(Status)) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto ErrorExit;
|
||||
}
|
||||
//
|
||||
// Setup the WaitForKeyEx event
|
||||
//
|
||||
Status = gBS->CreateEvent (
|
||||
EVT_NOTIFY_WAIT,
|
||||
TPL_NOTIFY,
|
||||
KeypadWaitForKeyEx,
|
||||
ConsoleIn,
|
||||
&(ConsoleIn->ConInEx.WaitForKeyEx)
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->CreateEvent(
|
||||
EVT_NOTIFY_WAIT, TPL_NOTIFY, KeypadWaitForKeyEx, ConsoleIn,
|
||||
&(ConsoleIn->ConInEx.WaitForKeyEx));
|
||||
if (EFI_ERROR(Status)) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto ErrorExit;
|
||||
}
|
||||
// Setup a periodic timer, used for reading keystrokes at a fixed interval
|
||||
//
|
||||
Status = gBS->CreateEvent (
|
||||
EVT_TIMER | EVT_NOTIFY_SIGNAL,
|
||||
TPL_NOTIFY,
|
||||
KeypadTimerHandler,
|
||||
ConsoleIn,
|
||||
&ConsoleIn->TimerEvent
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->CreateEvent(
|
||||
EVT_TIMER | EVT_NOTIFY_SIGNAL, TPL_NOTIFY, KeypadTimerHandler, ConsoleIn,
|
||||
&ConsoleIn->TimerEvent);
|
||||
if (EFI_ERROR(Status)) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto ErrorExit;
|
||||
}
|
||||
|
||||
Status = gBS->SetTimer (
|
||||
ConsoleIn->TimerEvent,
|
||||
TimerPeriodic,
|
||||
KEYPAD_TIMER_INTERVAL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->SetTimer(
|
||||
ConsoleIn->TimerEvent, TimerPeriodic, KEYPAD_TIMER_INTERVAL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto ErrorExit;
|
||||
}
|
||||
|
||||
Status = gBS->CreateEvent (
|
||||
EVT_NOTIFY_SIGNAL,
|
||||
TPL_CALLBACK,
|
||||
KeyNotifyProcessHandler,
|
||||
ConsoleIn,
|
||||
&ConsoleIn->KeyNotifyProcessEvent
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->CreateEvent(
|
||||
EVT_NOTIFY_SIGNAL, TPL_CALLBACK, KeyNotifyProcessHandler, ConsoleIn,
|
||||
&ConsoleIn->KeyNotifyProcessEvent);
|
||||
if (EFI_ERROR(Status)) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto ErrorExit;
|
||||
}
|
||||
@ -336,41 +287,27 @@ KeypadControllerDriverStart (
|
||||
//
|
||||
// Reset the keypad device
|
||||
//
|
||||
Status = ConsoleIn->ConInEx.Reset (&ConsoleIn->ConInEx, FALSE);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = ConsoleIn->ConInEx.Reset(&ConsoleIn->ConInEx, FALSE);
|
||||
if (EFI_ERROR(Status)) {
|
||||
Status = EFI_DEVICE_ERROR;
|
||||
goto ErrorExit;
|
||||
}
|
||||
|
||||
ConsoleIn->ControllerNameTable = NULL;
|
||||
AddUnicodeString2 (
|
||||
"eng",
|
||||
gKeypadComponentName.SupportedLanguages,
|
||||
&ConsoleIn->ControllerNameTable,
|
||||
L"Keypad Device",
|
||||
TRUE
|
||||
);
|
||||
AddUnicodeString2 (
|
||||
"en",
|
||||
gKeypadComponentName2.SupportedLanguages,
|
||||
&ConsoleIn->ControllerNameTable,
|
||||
L"Keypad Device",
|
||||
FALSE
|
||||
);
|
||||
|
||||
AddUnicodeString2(
|
||||
"eng", gKeypadComponentName.SupportedLanguages,
|
||||
&ConsoleIn->ControllerNameTable, L"Keypad Device", TRUE);
|
||||
AddUnicodeString2(
|
||||
"en", gKeypadComponentName2.SupportedLanguages,
|
||||
&ConsoleIn->ControllerNameTable, L"Keypad Device", FALSE);
|
||||
|
||||
//
|
||||
// Install protocol interfaces for the keypad device.
|
||||
//
|
||||
Status = gBS->InstallMultipleProtocolInterfaces (
|
||||
&Controller,
|
||||
&gEfiSimpleTextInProtocolGuid,
|
||||
&ConsoleIn->ConIn,
|
||||
&gEfiSimpleTextInputExProtocolGuid,
|
||||
&ConsoleIn->ConInEx,
|
||||
NULL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->InstallMultipleProtocolInterfaces(
|
||||
&Controller, &gEfiSimpleTextInProtocolGuid, &ConsoleIn->ConIn,
|
||||
&gEfiSimpleTextInputExProtocolGuid, &ConsoleIn->ConInEx, NULL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
goto ErrorExit;
|
||||
}
|
||||
|
||||
@ -378,33 +315,30 @@ KeypadControllerDriverStart (
|
||||
|
||||
ErrorExit:
|
||||
if ((ConsoleIn != NULL) && (ConsoleIn->ConIn.WaitForKey != NULL)) {
|
||||
gBS->CloseEvent (ConsoleIn->ConIn.WaitForKey);
|
||||
gBS->CloseEvent(ConsoleIn->ConIn.WaitForKey);
|
||||
}
|
||||
|
||||
if ((ConsoleIn != NULL) && (ConsoleIn->TimerEvent != NULL)) {
|
||||
gBS->CloseEvent (ConsoleIn->TimerEvent);
|
||||
gBS->CloseEvent(ConsoleIn->TimerEvent);
|
||||
}
|
||||
if ((ConsoleIn != NULL) && (ConsoleIn->ConInEx.WaitForKeyEx != NULL)) {
|
||||
gBS->CloseEvent (ConsoleIn->ConInEx.WaitForKeyEx);
|
||||
gBS->CloseEvent(ConsoleIn->ConInEx.WaitForKeyEx);
|
||||
}
|
||||
if ((ConsoleIn != NULL) && (ConsoleIn->KeyNotifyProcessEvent != NULL)) {
|
||||
gBS->CloseEvent (ConsoleIn->KeyNotifyProcessEvent);
|
||||
gBS->CloseEvent(ConsoleIn->KeyNotifyProcessEvent);
|
||||
}
|
||||
KbdFreeNotifyList (&ConsoleIn->NotifyList);
|
||||
KbdFreeNotifyList(&ConsoleIn->NotifyList);
|
||||
if ((ConsoleIn != NULL) && (ConsoleIn->ControllerNameTable != NULL)) {
|
||||
FreeUnicodeStringTable (ConsoleIn->ControllerNameTable);
|
||||
FreeUnicodeStringTable(ConsoleIn->ControllerNameTable);
|
||||
}
|
||||
|
||||
if (ConsoleIn != NULL) {
|
||||
gBS->FreePool (ConsoleIn);
|
||||
gBS->FreePool(ConsoleIn);
|
||||
}
|
||||
|
||||
gBS->CloseProtocol (
|
||||
Controller,
|
||||
&gEFIDroidKeypadDeviceProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
Controller
|
||||
);
|
||||
gBS->CloseProtocol(
|
||||
Controller, &gEFIDroidKeypadDeviceProtocolGuid, This->DriverBindingHandle,
|
||||
Controller);
|
||||
|
||||
return Status;
|
||||
}
|
||||
@ -425,90 +359,69 @@ ErrorExit:
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadControllerDriverStop (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE Controller,
|
||||
IN UINTN NumberOfChildren,
|
||||
IN EFI_HANDLE *ChildHandleBuffer
|
||||
)
|
||||
KeypadControllerDriverStop(
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This, IN EFI_HANDLE Controller,
|
||||
IN UINTN NumberOfChildren, IN EFI_HANDLE *ChildHandleBuffer)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_SIMPLE_TEXT_INPUT_PROTOCOL *ConIn;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
KEYPAD_CONSOLE_IN_DEV * ConsoleIn;
|
||||
|
||||
//
|
||||
// Disable Keypad
|
||||
//
|
||||
Status = gBS->OpenProtocol (
|
||||
Controller,
|
||||
&gEfiSimpleTextInProtocolGuid,
|
||||
(VOID **) &ConIn,
|
||||
This->DriverBindingHandle,
|
||||
Controller,
|
||||
EFI_OPEN_PROTOCOL_GET_PROTOCOL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->OpenProtocol(
|
||||
Controller, &gEfiSimpleTextInProtocolGuid, (VOID **)&ConIn,
|
||||
This->DriverBindingHandle, Controller, EFI_OPEN_PROTOCOL_GET_PROTOCOL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
Status = gBS->OpenProtocol (
|
||||
Controller,
|
||||
&gEfiSimpleTextInputExProtocolGuid,
|
||||
NULL,
|
||||
This->DriverBindingHandle,
|
||||
Controller,
|
||||
EFI_OPEN_PROTOCOL_TEST_PROTOCOL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->OpenProtocol(
|
||||
Controller, &gEfiSimpleTextInputExProtocolGuid, NULL,
|
||||
This->DriverBindingHandle, Controller, EFI_OPEN_PROTOCOL_TEST_PROTOCOL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS (ConIn);
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS(ConIn);
|
||||
|
||||
if (ConsoleIn->TimerEvent != NULL) {
|
||||
gBS->CloseEvent (ConsoleIn->TimerEvent);
|
||||
gBS->CloseEvent(ConsoleIn->TimerEvent);
|
||||
ConsoleIn->TimerEvent = NULL;
|
||||
}
|
||||
|
||||
//
|
||||
// Uninstall the SimpleTextIn and SimpleTextInEx protocols
|
||||
//
|
||||
Status = gBS->UninstallMultipleProtocolInterfaces (
|
||||
Controller,
|
||||
&gEfiSimpleTextInProtocolGuid,
|
||||
&ConsoleIn->ConIn,
|
||||
&gEfiSimpleTextInputExProtocolGuid,
|
||||
&ConsoleIn->ConInEx,
|
||||
NULL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->UninstallMultipleProtocolInterfaces(
|
||||
Controller, &gEfiSimpleTextInProtocolGuid, &ConsoleIn->ConIn,
|
||||
&gEfiSimpleTextInputExProtocolGuid, &ConsoleIn->ConInEx, NULL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
gBS->CloseProtocol (
|
||||
Controller,
|
||||
&gEFIDroidKeypadDeviceProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
Controller
|
||||
);
|
||||
gBS->CloseProtocol(
|
||||
Controller, &gEFIDroidKeypadDeviceProtocolGuid, This->DriverBindingHandle,
|
||||
Controller);
|
||||
|
||||
//
|
||||
// Free other resources
|
||||
//
|
||||
if ((ConsoleIn->ConIn).WaitForKey != NULL) {
|
||||
gBS->CloseEvent ((ConsoleIn->ConIn).WaitForKey);
|
||||
gBS->CloseEvent((ConsoleIn->ConIn).WaitForKey);
|
||||
(ConsoleIn->ConIn).WaitForKey = NULL;
|
||||
}
|
||||
if (ConsoleIn->ConInEx.WaitForKeyEx != NULL) {
|
||||
gBS->CloseEvent (ConsoleIn->ConInEx.WaitForKeyEx);
|
||||
gBS->CloseEvent(ConsoleIn->ConInEx.WaitForKeyEx);
|
||||
ConsoleIn->ConInEx.WaitForKeyEx = NULL;
|
||||
}
|
||||
if (ConsoleIn->KeyNotifyProcessEvent != NULL) {
|
||||
gBS->CloseEvent (ConsoleIn->KeyNotifyProcessEvent);
|
||||
gBS->CloseEvent(ConsoleIn->KeyNotifyProcessEvent);
|
||||
ConsoleIn->KeyNotifyProcessEvent = NULL;
|
||||
}
|
||||
KbdFreeNotifyList (&ConsoleIn->NotifyList);
|
||||
FreeUnicodeStringTable (ConsoleIn->ControllerNameTable);
|
||||
gBS->FreePool (ConsoleIn);
|
||||
KbdFreeNotifyList(&ConsoleIn->NotifyList);
|
||||
FreeUnicodeStringTable(ConsoleIn->ControllerNameTable);
|
||||
gBS->FreePool(ConsoleIn);
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
@ -522,24 +435,19 @@ KeypadControllerDriverStop (
|
||||
@retval EFI_SUCCESS Sucess to free NotifyList
|
||||
**/
|
||||
EFI_STATUS
|
||||
KbdFreeNotifyList (
|
||||
IN OUT LIST_ENTRY *ListHead
|
||||
)
|
||||
KbdFreeNotifyList(IN OUT LIST_ENTRY *ListHead)
|
||||
{
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY *NotifyNode;
|
||||
|
||||
if (ListHead == NULL) {
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
while (!IsListEmpty (ListHead)) {
|
||||
NotifyNode = CR (
|
||||
ListHead->ForwardLink,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY,
|
||||
NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE
|
||||
);
|
||||
RemoveEntryList (ListHead->ForwardLink);
|
||||
gBS->FreePool (NotifyNode);
|
||||
while (!IsListEmpty(ListHead)) {
|
||||
NotifyNode =
|
||||
CR(ListHead->ForwardLink, KEYPAD_CONSOLE_IN_EX_NOTIFY, NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE);
|
||||
RemoveEntryList(ListHead->ForwardLink);
|
||||
gBS->FreePool(NotifyNode);
|
||||
}
|
||||
|
||||
return EFI_SUCCESS;
|
||||
@ -557,27 +465,17 @@ KbdFreeNotifyList (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
InitializeKeypad(
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
)
|
||||
InitializeKeypad(IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
//
|
||||
// Install driver model protocol(s).
|
||||
//
|
||||
Status = EfiLibInstallDriverBindingComponentName2 (
|
||||
ImageHandle,
|
||||
SystemTable,
|
||||
&gKeypadControllerDriver,
|
||||
ImageHandle,
|
||||
&gKeypadComponentName,
|
||||
&gKeypadComponentName2
|
||||
);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
Status = EfiLibInstallDriverBindingComponentName2(
|
||||
ImageHandle, SystemTable, &gKeypadControllerDriver, ImageHandle,
|
||||
&gKeypadComponentName, &gKeypadComponentName2);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
@ -3,9 +3,9 @@
|
||||
|
||||
Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
|
||||
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
|
||||
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.
|
||||
@ -17,21 +17,21 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
|
||||
|
||||
#include <Uefi.h>
|
||||
|
||||
#include <Protocol/KeypadDevice.h>
|
||||
#include <Protocol/SimpleTextIn.h>
|
||||
#include <Protocol/SimpleTextInEx.h>
|
||||
#include <Protocol/KeypadDevice.h>
|
||||
|
||||
#include <Library/IoLib.h>
|
||||
#include <Library/UefiDriverEntryPoint.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/UefiRuntimeServicesTableLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/BaseLib.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/TimerLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/IoLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/PcdLib.h>
|
||||
#include <Library/TimerLib.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <Library/UefiDriverEntryPoint.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Library/UefiRuntimeServicesTableLib.h>
|
||||
|
||||
//
|
||||
// Global Variables
|
||||
@ -43,8 +43,8 @@ extern EFI_COMPONENT_NAME2_PROTOCOL gKeypadComponentName2;
|
||||
//
|
||||
// Driver Private Data
|
||||
//
|
||||
#define KEYPAD_CONSOLE_IN_DEV_SIGNATURE SIGNATURE_32 ('k', 'k', 'e', 'y')
|
||||
#define KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE SIGNATURE_32 ('k', 'c', 'e', 'n')
|
||||
#define KEYPAD_CONSOLE_IN_DEV_SIGNATURE SIGNATURE_32('k', 'k', 'e', 'y')
|
||||
#define KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE SIGNATURE_32('k', 'c', 'e', 'n')
|
||||
|
||||
typedef struct _KEYPAD_CONSOLE_IN_EX_NOTIFY {
|
||||
UINTN Signature;
|
||||
@ -111,14 +111,12 @@ typedef struct {
|
||||
EFI_EVENT KeyNotifyProcessEvent;
|
||||
} KEYPAD_CONSOLE_IN_DEV;
|
||||
|
||||
#define KEYPAD_CONSOLE_IN_DEV_FROM_KEYPAD_RETURN_API(a) CR (a, KEYPAD_CONSOLE_IN_DEV, KeypadReturnApi, KEYPAD_CONSOLE_IN_DEV_SIGNATURE)
|
||||
#define KEYPAD_CONSOLE_IN_DEV_FROM_THIS(a) CR (a, KEYPAD_CONSOLE_IN_DEV, ConIn, KEYPAD_CONSOLE_IN_DEV_SIGNATURE)
|
||||
#define KEYPAD_CONSOLE_IN_DEV_FROM_KEYPAD_RETURN_API(a) \
|
||||
CR(a, KEYPAD_CONSOLE_IN_DEV, KeypadReturnApi, KEYPAD_CONSOLE_IN_DEV_SIGNATURE)
|
||||
#define KEYPAD_CONSOLE_IN_DEV_FROM_THIS(a) \
|
||||
CR(a, KEYPAD_CONSOLE_IN_DEV, ConIn, KEYPAD_CONSOLE_IN_DEV_SIGNATURE)
|
||||
#define TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS(a) \
|
||||
CR (a, \
|
||||
KEYPAD_CONSOLE_IN_DEV, \
|
||||
ConInEx, \
|
||||
KEYPAD_CONSOLE_IN_DEV_SIGNATURE \
|
||||
)
|
||||
CR(a, KEYPAD_CONSOLE_IN_DEV, ConInEx, KEYPAD_CONSOLE_IN_DEV_SIGNATURE)
|
||||
|
||||
#define TABLE_END 0x0
|
||||
|
||||
@ -128,7 +126,8 @@ typedef struct {
|
||||
// Driver entry point
|
||||
//
|
||||
/**
|
||||
The user Entry Point for module KeypadDxe. The user code starts with this function.
|
||||
The user Entry Point for module KeypadDxe. The user code starts with this
|
||||
function.
|
||||
|
||||
@param[in] ImageHandle The firmware allocated handle for the EFI image.
|
||||
@param[in] SystemTable A pointer to the EFI System Table.
|
||||
@ -139,10 +138,8 @@ typedef struct {
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
InstallKeypadDriver (
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
);
|
||||
InstallKeypadDriver(
|
||||
IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable);
|
||||
|
||||
//
|
||||
// Other functions that are used among .c files
|
||||
@ -154,12 +151,7 @@ InstallKeypadDriver (
|
||||
@param Event Indicates the event that invoke this function.
|
||||
@param Context Indicates the calling context.
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeyNotifyProcessHandler (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
);
|
||||
VOID EFIAPI KeyNotifyProcessHandler(IN EFI_EVENT Event, IN VOID *Context);
|
||||
|
||||
/**
|
||||
Perform 8042 controller and keypad Initialization.
|
||||
@ -173,10 +165,8 @@ KeyNotifyProcessHandler (
|
||||
@retval EFI_SUCCESS Success to init keypad
|
||||
**/
|
||||
EFI_STATUS
|
||||
InitKeypad (
|
||||
IN OUT KEYPAD_CONSOLE_IN_DEV *ConsoleIn,
|
||||
IN BOOLEAN ExtendedVerification
|
||||
);
|
||||
InitKeypad(
|
||||
IN OUT KEYPAD_CONSOLE_IN_DEV *ConsoleIn, IN BOOLEAN ExtendedVerification);
|
||||
|
||||
/**
|
||||
Timer event handler: read a series of scancodes from 8042
|
||||
@ -189,12 +179,7 @@ InitKeypad (
|
||||
@param Context - A KEYPAD_CONSOLE_IN_DEV pointer
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeypadTimerHandler (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
);
|
||||
VOID EFIAPI KeypadTimerHandler(IN EFI_EVENT Event, IN VOID *Context);
|
||||
|
||||
/**
|
||||
logic reset keypad
|
||||
@ -203,16 +188,14 @@ KeypadTimerHandler (
|
||||
|
||||
@param This Pointer to instance of EFI_SIMPLE_TEXT_INPUT_PROTOCOL
|
||||
@param ExtendedVerification Indicate that the driver may perform a more
|
||||
exhaustive verification operation of the device during
|
||||
reset, now this par is ignored in this driver
|
||||
exhaustive verification operation of the device
|
||||
during reset, now this par is ignored in this driver
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadEfiReset (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This,
|
||||
IN BOOLEAN ExtendedVerification
|
||||
);
|
||||
KeypadEfiReset(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This, IN BOOLEAN ExtendedVerification);
|
||||
|
||||
/**
|
||||
Implement SIMPLE_TEXT_IN.ReadKeyStroke().
|
||||
@ -225,10 +208,8 @@ KeypadEfiReset (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadReadKeyStroke (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This,
|
||||
OUT EFI_INPUT_KEY *Key
|
||||
);
|
||||
KeypadReadKeyStroke(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This, OUT EFI_INPUT_KEY *Key);
|
||||
|
||||
/**
|
||||
Event notification function for SIMPLE_TEXT_IN.WaitForKey event
|
||||
@ -238,27 +219,17 @@ KeypadReadKeyStroke (
|
||||
@param Context waitting context
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeypadWaitForKey (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
);
|
||||
VOID EFIAPI KeypadWaitForKey(IN EFI_EVENT Event, IN VOID *Context);
|
||||
|
||||
/**
|
||||
Event notification function for SIMPLE_TEXT_INPUT_EX_PROTOCOL.WaitForKeyEx event
|
||||
Signal the event if there is key available
|
||||
Event notification function for SIMPLE_TEXT_INPUT_EX_PROTOCOL.WaitForKeyEx
|
||||
event Signal the event if there is key available
|
||||
|
||||
@param Event event object
|
||||
@param Context waiting context
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeypadWaitForKeyEx (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
);
|
||||
VOID EFIAPI KeypadWaitForKeyEx(IN EFI_EVENT Event, IN VOID *Context);
|
||||
|
||||
//
|
||||
// Simple Text Input Ex protocol function prototypes
|
||||
@ -271,16 +242,15 @@ KeypadWaitForKeyEx (
|
||||
@param ExtendedVerification - Driver may perform diagnostics on reset.
|
||||
|
||||
@retval EFI_SUCCESS - The device was reset.
|
||||
@retval EFI_DEVICE_ERROR - The device is not functioning properly and could
|
||||
not be reset.
|
||||
@retval EFI_DEVICE_ERROR - The device is not functioning properly and
|
||||
could not be reset.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadEfiResetEx (
|
||||
KeypadEfiResetEx(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN BOOLEAN ExtendedVerification
|
||||
);
|
||||
IN BOOLEAN ExtendedVerification);
|
||||
|
||||
/**
|
||||
Reads the next keystroke from the input device. The WaitForKey Event can
|
||||
@ -288,22 +258,20 @@ KeypadEfiResetEx (
|
||||
|
||||
|
||||
@param This - Protocol instance pointer.
|
||||
@param KeyData - A pointer to a buffer that is filled in with the keystroke
|
||||
state data for the key that was pressed.
|
||||
@param KeyData - A pointer to a buffer that is filled in with the
|
||||
keystroke state data for the key that was pressed.
|
||||
|
||||
@retval EFI_SUCCESS - The keystroke information was returned.
|
||||
@retval EFI_NOT_READY - There was no keystroke data availiable.
|
||||
@retval EFI_DEVICE_ERROR - The keystroke information was not returned due to
|
||||
hardware errors.
|
||||
@retval EFI_DEVICE_ERROR - The keystroke information was not returned
|
||||
due to hardware errors.
|
||||
@retval EFI_INVALID_PARAMETER - KeyData is NULL.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadReadKeyStrokeEx (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
OUT EFI_KEY_DATA *KeyData
|
||||
);
|
||||
KeypadReadKeyStrokeEx(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This, OUT EFI_KEY_DATA *KeyData);
|
||||
|
||||
/**
|
||||
Set certain state for the input device.
|
||||
@ -313,61 +281,64 @@ KeypadReadKeyStrokeEx (
|
||||
state for the input device.
|
||||
|
||||
@retval EFI_SUCCESS - The device state was set successfully.
|
||||
@retval EFI_DEVICE_ERROR - The device is not functioning correctly and could
|
||||
not have the setting adjusted.
|
||||
@retval EFI_UNSUPPORTED - The device does not have the ability to set its state.
|
||||
@retval EFI_DEVICE_ERROR - The device is not functioning correctly and
|
||||
could not have the setting adjusted.
|
||||
@retval EFI_UNSUPPORTED - The device does not have the ability to set
|
||||
its state.
|
||||
@retval EFI_INVALID_PARAMETER - KeyToggleState is NULL.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadSetState (
|
||||
KeypadSetState(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN EFI_KEY_TOGGLE_STATE *KeyToggleState
|
||||
);
|
||||
IN EFI_KEY_TOGGLE_STATE *KeyToggleState);
|
||||
|
||||
/**
|
||||
Register a notification function for a particular keystroke for the input device.
|
||||
Register a notification function for a particular keystroke for the input
|
||||
device.
|
||||
|
||||
@param This - Protocol instance pointer.
|
||||
@param KeyData - A pointer to a buffer that is filled in with the keystroke
|
||||
information data for the key that was pressed.
|
||||
@param KeyNotificationFunction - Points to the function to be called when the key
|
||||
sequence is typed specified by KeyData.
|
||||
@param NotifyHandle - Points to the unique handle assigned to the registered notification.
|
||||
@param KeyData - A pointer to a buffer that is filled in
|
||||
with the keystroke information data for the key that was pressed.
|
||||
@param KeyNotificationFunction - Points to the function to be called when
|
||||
the key sequence is typed specified by KeyData.
|
||||
@param NotifyHandle - Points to the unique handle assigned to the
|
||||
registered notification.
|
||||
|
||||
@retval EFI_SUCCESS - The notification function was registered successfully.
|
||||
@retval EFI_OUT_OF_RESOURCES - Unable to allocate resources for necesssary data structures.
|
||||
@retval EFI_SUCCESS - The notification function was registered
|
||||
successfully.
|
||||
@retval EFI_OUT_OF_RESOURCES - Unable to allocate resources for
|
||||
necesssary data structures.
|
||||
@retval EFI_INVALID_PARAMETER - KeyData or NotifyHandle is NULL.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadRegisterKeyNotify (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN EFI_KEY_DATA *KeyData,
|
||||
KeypadRegisterKeyNotify(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This, IN EFI_KEY_DATA *KeyData,
|
||||
IN EFI_KEY_NOTIFY_FUNCTION KeyNotificationFunction,
|
||||
OUT VOID **NotifyHandle
|
||||
);
|
||||
OUT VOID **NotifyHandle);
|
||||
|
||||
/**
|
||||
Remove a registered notification function from a particular keystroke.
|
||||
|
||||
@param This - Protocol instance pointer.
|
||||
@param NotificationHandle - The handle of the notification function being unregistered.
|
||||
@param NotificationHandle - The handle of the notification function
|
||||
being unregistered.
|
||||
|
||||
|
||||
@retval EFI_SUCCESS - The notification function was unregistered successfully.
|
||||
@retval EFI_SUCCESS - The notification function was unregistered
|
||||
successfully.
|
||||
@retval EFI_INVALID_PARAMETER - The NotificationHandle is invalid.
|
||||
@retval EFI_NOT_FOUND - Can not find the matching entry in database.
|
||||
@retval EFI_NOT_FOUND - Can not find the matching entry in
|
||||
database.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadUnregisterKeyNotify (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN VOID *NotificationHandle
|
||||
);
|
||||
KeypadUnregisterKeyNotify(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This, IN VOID *NotificationHandle);
|
||||
|
||||
/**
|
||||
Push one key data to the EFI key buffer.
|
||||
@ -375,28 +346,21 @@ KeypadUnregisterKeyNotify (
|
||||
@param Queue Pointer to instance of EFI_KEY_QUEUE.
|
||||
@param KeyData The key data to push.
|
||||
**/
|
||||
VOID
|
||||
PushEfikeyBufTail (
|
||||
IN EFI_KEY_QUEUE *Queue,
|
||||
IN EFI_KEY_DATA *KeyData
|
||||
);
|
||||
VOID PushEfikeyBufTail(IN EFI_KEY_QUEUE *Queue, IN EFI_KEY_DATA *KeyData);
|
||||
|
||||
/**
|
||||
Judge whether is a registed key
|
||||
|
||||
@param RegsiteredData A pointer to a buffer that is filled in with the keystroke
|
||||
state data for the key that was registered.
|
||||
@param InputData A pointer to a buffer that is filled in with the keystroke
|
||||
state data for the key that was pressed.
|
||||
@param RegsiteredData A pointer to a buffer that is filled in with the
|
||||
keystroke state data for the key that was registered.
|
||||
@param InputData A pointer to a buffer that is filled in with the
|
||||
keystroke state data for the key that was pressed.
|
||||
|
||||
@retval TRUE Key be pressed matches a registered key.
|
||||
@retval FLASE Match failed.
|
||||
|
||||
**/
|
||||
BOOLEAN
|
||||
IsKeyRegistered (
|
||||
IN EFI_KEY_DATA *RegsiteredData,
|
||||
IN EFI_KEY_DATA *InputData
|
||||
);
|
||||
IsKeyRegistered(IN EFI_KEY_DATA *RegsiteredData, IN EFI_KEY_DATA *InputData);
|
||||
|
||||
#endif
|
||||
|
@ -3,9 +3,9 @@
|
||||
|
||||
Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
|
||||
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
|
||||
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.
|
||||
@ -21,11 +21,7 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
|
||||
@param ErrMsg Unicode string of error message
|
||||
|
||||
**/
|
||||
VOID
|
||||
KeypadError (
|
||||
IN KEYPAD_CONSOLE_IN_DEV *ConsoleIn,
|
||||
IN CHAR16 *ErrMsg
|
||||
)
|
||||
VOID KeypadError(IN KEYPAD_CONSOLE_IN_DEV *ConsoleIn, IN CHAR16 *ErrMsg)
|
||||
{
|
||||
ConsoleIn->KeypadErr = TRUE;
|
||||
}
|
||||
@ -41,42 +37,39 @@ KeypadError (
|
||||
@param Context A KEYPAD_CONSOLE_IN_DEV pointer
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeypadTimerHandler (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
VOID EFIAPI KeypadTimerHandler(IN EFI_EVENT Event, IN VOID *Context)
|
||||
|
||||
{
|
||||
EFI_TPL OldTpl;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
|
||||
ConsoleIn = (KEYPAD_CONSOLE_IN_DEV *) Context;
|
||||
ConsoleIn = (KEYPAD_CONSOLE_IN_DEV *)Context;
|
||||
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
|
||||
if (((KEYPAD_CONSOLE_IN_DEV *) Context)->KeypadErr) {
|
||||
if (((KEYPAD_CONSOLE_IN_DEV *)Context)->KeypadErr) {
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
return ;
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
return;
|
||||
}
|
||||
|
||||
UINT64 CurrentCounterValue = GetPerformanceCounter();
|
||||
UINT64 DeltaCounter = CurrentCounterValue - ConsoleIn->Last;
|
||||
ConsoleIn->Last = CurrentCounterValue;
|
||||
|
||||
ConsoleIn->KeypadDevice->GetKeys(ConsoleIn->KeypadDevice, &ConsoleIn->KeypadReturnApi, GetTimeInNanoSecond(DeltaCounter));
|
||||
ConsoleIn->KeypadDevice->GetKeys(
|
||||
ConsoleIn->KeypadDevice, &ConsoleIn->KeypadReturnApi,
|
||||
GetTimeInNanoSecond(DeltaCounter));
|
||||
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -91,10 +84,8 @@ KeypadTimerHandler (
|
||||
@retval EFI_SUCCESS Success to init keypad
|
||||
**/
|
||||
EFI_STATUS
|
||||
InitKeypad (
|
||||
IN OUT KEYPAD_CONSOLE_IN_DEV *ConsoleIn,
|
||||
IN BOOLEAN ExtendedVerification
|
||||
)
|
||||
InitKeypad(
|
||||
IN OUT KEYPAD_CONSOLE_IN_DEV *ConsoleIn, IN BOOLEAN ExtendedVerification)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
@ -129,10 +120,10 @@ InitKeypad (
|
||||
|
||||
ConsoleIn->IsSupportPartialKey = FALSE;
|
||||
|
||||
if (!EFI_ERROR (Status)) {
|
||||
if (!EFI_ERROR(Status)) {
|
||||
return EFI_SUCCESS;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
return EFI_DEVICE_ERROR;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -4,16 +4,15 @@
|
||||
|
||||
Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
|
||||
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
|
||||
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.
|
||||
|
||||
**/
|
||||
|
||||
|
||||
#include "Keypad.h"
|
||||
|
||||
/**
|
||||
@ -25,11 +24,9 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
|
||||
@retval FALSE The EFI key buffer isn't empty.
|
||||
**/
|
||||
BOOLEAN
|
||||
IsEfikeyBufEmpty (
|
||||
IN EFI_KEY_QUEUE *Queue
|
||||
)
|
||||
IsEfikeyBufEmpty(IN EFI_KEY_QUEUE *Queue)
|
||||
{
|
||||
return (BOOLEAN) (Queue->Head == Queue->Tail);
|
||||
return (BOOLEAN)(Queue->Head == Queue->Tail);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -42,19 +39,16 @@ IsEfikeyBufEmpty (
|
||||
@retval EFI_NOT_READY There is no key data available.
|
||||
**/
|
||||
EFI_STATUS
|
||||
PopEfikeyBufHead (
|
||||
IN EFI_KEY_QUEUE *Queue,
|
||||
OUT EFI_KEY_DATA *KeyData OPTIONAL
|
||||
)
|
||||
PopEfikeyBufHead(IN EFI_KEY_QUEUE *Queue, OUT EFI_KEY_DATA *KeyData OPTIONAL)
|
||||
{
|
||||
if (IsEfikeyBufEmpty (Queue)) {
|
||||
if (IsEfikeyBufEmpty(Queue)) {
|
||||
return EFI_NOT_READY;
|
||||
}
|
||||
//
|
||||
// Retrieve and remove the values
|
||||
//
|
||||
if (KeyData != NULL) {
|
||||
CopyMem (KeyData, &Queue->Buffer[Queue->Head], sizeof (EFI_KEY_DATA));
|
||||
CopyMem(KeyData, &Queue->Buffer[Queue->Head], sizeof(EFI_KEY_DATA));
|
||||
}
|
||||
Queue->Head = (Queue->Head + 1) % KEYPAD_EFI_KEY_MAX_COUNT;
|
||||
return EFI_SUCCESS;
|
||||
@ -66,42 +60,35 @@ PopEfikeyBufHead (
|
||||
@param Queue Pointer to instance of EFI_KEY_QUEUE.
|
||||
@param KeyData The key data to push.
|
||||
**/
|
||||
VOID
|
||||
PushEfikeyBufTail (
|
||||
IN EFI_KEY_QUEUE *Queue,
|
||||
IN EFI_KEY_DATA *KeyData
|
||||
)
|
||||
VOID PushEfikeyBufTail(IN EFI_KEY_QUEUE *Queue, IN EFI_KEY_DATA *KeyData)
|
||||
{
|
||||
if ((Queue->Tail + 1) % KEYPAD_EFI_KEY_MAX_COUNT == Queue->Head) {
|
||||
//
|
||||
// If Queue is full, pop the one from head.
|
||||
//
|
||||
PopEfikeyBufHead (Queue, NULL);
|
||||
PopEfikeyBufHead(Queue, NULL);
|
||||
}
|
||||
CopyMem (&Queue->Buffer[Queue->Tail], KeyData, sizeof (EFI_KEY_DATA));
|
||||
CopyMem(&Queue->Buffer[Queue->Tail], KeyData, sizeof(EFI_KEY_DATA));
|
||||
Queue->Tail = (Queue->Tail + 1) % KEYPAD_EFI_KEY_MAX_COUNT;
|
||||
}
|
||||
|
||||
/**
|
||||
Judge whether is a registed key
|
||||
|
||||
@param RegsiteredData A pointer to a buffer that is filled in with the keystroke
|
||||
state data for the key that was registered.
|
||||
@param InputData A pointer to a buffer that is filled in with the keystroke
|
||||
state data for the key that was pressed.
|
||||
@param RegsiteredData A pointer to a buffer that is filled in with the
|
||||
keystroke state data for the key that was registered.
|
||||
@param InputData A pointer to a buffer that is filled in with the
|
||||
keystroke state data for the key that was pressed.
|
||||
|
||||
@retval TRUE Key be pressed matches a registered key.
|
||||
@retval FLASE Match failed.
|
||||
|
||||
**/
|
||||
BOOLEAN
|
||||
IsKeyRegistered (
|
||||
IN EFI_KEY_DATA *RegsiteredData,
|
||||
IN EFI_KEY_DATA *InputData
|
||||
)
|
||||
IsKeyRegistered(IN EFI_KEY_DATA *RegsiteredData, IN EFI_KEY_DATA *InputData)
|
||||
|
||||
{
|
||||
ASSERT (RegsiteredData != NULL && InputData != NULL);
|
||||
ASSERT(RegsiteredData != NULL && InputData != NULL);
|
||||
|
||||
if ((RegsiteredData->Key.ScanCode != InputData->Key.ScanCode) ||
|
||||
(RegsiteredData->Key.UnicodeChar != InputData->Key.UnicodeChar)) {
|
||||
@ -109,19 +96,21 @@ IsKeyRegistered (
|
||||
}
|
||||
|
||||
//
|
||||
// Assume KeyShiftState/KeyToggleState = 0 in Registered key data means these state could be ignored.
|
||||
// Assume KeyShiftState/KeyToggleState = 0 in Registered key data means these
|
||||
// state could be ignored.
|
||||
//
|
||||
if (RegsiteredData->KeyState.KeyShiftState != 0 &&
|
||||
RegsiteredData->KeyState.KeyShiftState != InputData->KeyState.KeyShiftState) {
|
||||
RegsiteredData->KeyState.KeyShiftState !=
|
||||
InputData->KeyState.KeyShiftState) {
|
||||
return FALSE;
|
||||
}
|
||||
if (RegsiteredData->KeyState.KeyToggleState != 0 &&
|
||||
RegsiteredData->KeyState.KeyToggleState != InputData->KeyState.KeyToggleState) {
|
||||
RegsiteredData->KeyState.KeyToggleState !=
|
||||
InputData->KeyState.KeyToggleState) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@ -129,22 +118,20 @@ IsKeyRegistered (
|
||||
be used to test for existance of a keystroke via WaitForEvent () call.
|
||||
|
||||
@param ConsoleInDev Keypad private structure
|
||||
@param KeyData A pointer to a buffer that is filled in with the keystroke
|
||||
state data for the key that was pressed.
|
||||
@param KeyData A pointer to a buffer that is filled in with
|
||||
the keystroke state data for the key that was pressed.
|
||||
|
||||
|
||||
@retval EFI_SUCCESS The keystroke information was returned.
|
||||
@retval EFI_NOT_READY There was no keystroke data availiable.
|
||||
@retval EFI_DEVICE_ERROR The keystroke information was not returned due to
|
||||
hardware errors.
|
||||
@retval EFI_DEVICE_ERROR The keystroke information was not returned
|
||||
due to hardware errors.
|
||||
@retval EFI_INVALID_PARAMETER KeyData is NULL.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
KeypadReadKeyStrokeWorker (
|
||||
IN KEYPAD_CONSOLE_IN_DEV *ConsoleInDev,
|
||||
OUT EFI_KEY_DATA *KeyData
|
||||
)
|
||||
KeypadReadKeyStrokeWorker(
|
||||
IN KEYPAD_CONSOLE_IN_DEV *ConsoleInDev, OUT EFI_KEY_DATA *KeyData)
|
||||
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
@ -157,41 +144,42 @@ KeypadReadKeyStrokeWorker (
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
|
||||
KeypadTimerHandler (NULL, ConsoleInDev);
|
||||
KeypadTimerHandler(NULL, ConsoleInDev);
|
||||
|
||||
if (ConsoleInDev->KeypadErr) {
|
||||
Status = EFI_DEVICE_ERROR;
|
||||
} else {
|
||||
Status = PopEfikeyBufHead (&ConsoleInDev->EfiKeyQueue, KeyData);
|
||||
}
|
||||
else {
|
||||
Status = PopEfikeyBufHead(&ConsoleInDev->EfiKeyQueue, KeyData);
|
||||
}
|
||||
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
Perform 8042 controller and keypad initialization which implement SIMPLE_TEXT_IN.Reset()
|
||||
Perform 8042 controller and keypad initialization which implement
|
||||
SIMPLE_TEXT_IN.Reset()
|
||||
|
||||
@param This Pointer to instance of EFI_SIMPLE_TEXT_INPUT_PROTOCOL
|
||||
@param This Pointer to instance of
|
||||
EFI_SIMPLE_TEXT_INPUT_PROTOCOL
|
||||
@param ExtendedVerification Indicate that the driver may perform a more
|
||||
exhaustive verification operation of the device during
|
||||
reset, now this par is ignored in this driver
|
||||
exhaustive verification operation of the device
|
||||
during reset, now this par is ignored in this driver
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadEfiReset (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This,
|
||||
IN BOOLEAN ExtendedVerification
|
||||
)
|
||||
KeypadEfiReset(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This, IN BOOLEAN ExtendedVerification)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
EFI_TPL OldTpl;
|
||||
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS (This);
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS(This);
|
||||
if (ConsoleIn->KeypadErr) {
|
||||
return EFI_DEVICE_ERROR;
|
||||
}
|
||||
@ -199,30 +187,31 @@ KeypadEfiReset (
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
|
||||
//
|
||||
// Call InitKeypad to initialize the keypad
|
||||
//
|
||||
Status = InitKeypad (ConsoleIn, ExtendedVerification);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = InitKeypad(ConsoleIn, ExtendedVerification);
|
||||
if (EFI_ERROR(Status)) {
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
return EFI_DEVICE_ERROR;
|
||||
}
|
||||
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
/**
|
||||
Retrieve key values for driver user which implement SIMPLE_TEXT_IN.ReadKeyStroke().
|
||||
Retrieve key values for driver user which implement
|
||||
SIMPLE_TEXT_IN.ReadKeyStroke().
|
||||
|
||||
@param This Pointer to instance of EFI_SIMPLE_TEXT_INPUT_PROTOCOL
|
||||
@param Key The output buffer for key value
|
||||
@ -231,16 +220,14 @@ KeypadEfiReset (
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadReadKeyStroke (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This,
|
||||
OUT EFI_INPUT_KEY *Key
|
||||
)
|
||||
KeypadReadKeyStroke(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_PROTOCOL *This, OUT EFI_INPUT_KEY *Key)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
EFI_KEY_DATA KeyData;
|
||||
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS (This);
|
||||
ConsoleIn = KEYPAD_CONSOLE_IN_DEV_FROM_THIS(This);
|
||||
|
||||
//
|
||||
// Considering if the partial keystroke is enabled, there maybe a partial
|
||||
@ -251,29 +238,33 @@ KeypadReadKeyStroke (
|
||||
//
|
||||
// If there is no pending key, then return.
|
||||
//
|
||||
Status = KeypadReadKeyStrokeWorker (ConsoleIn, &KeyData);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = KeypadReadKeyStrokeWorker(ConsoleIn, &KeyData);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
//
|
||||
// If it is partial keystroke, skip it.
|
||||
//
|
||||
if (KeyData.Key.ScanCode == SCAN_NULL && KeyData.Key.UnicodeChar == CHAR_NULL) {
|
||||
if (KeyData.Key.ScanCode == SCAN_NULL &&
|
||||
KeyData.Key.UnicodeChar == CHAR_NULL) {
|
||||
continue;
|
||||
}
|
||||
//
|
||||
// Translate the CTRL-Alpha characters to their corresponding control value
|
||||
// (ctrl-a = 0x0001 through ctrl-Z = 0x001A)
|
||||
//
|
||||
if ((KeyData.KeyState.KeyShiftState & (EFI_LEFT_CONTROL_PRESSED | EFI_RIGHT_CONTROL_PRESSED)) != 0) {
|
||||
if ((KeyData.KeyState.KeyShiftState &
|
||||
(EFI_LEFT_CONTROL_PRESSED | EFI_RIGHT_CONTROL_PRESSED)) != 0) {
|
||||
if (KeyData.Key.UnicodeChar >= L'a' && KeyData.Key.UnicodeChar <= L'z') {
|
||||
KeyData.Key.UnicodeChar = (CHAR16) (KeyData.Key.UnicodeChar - L'a' + 1);
|
||||
} else if (KeyData.Key.UnicodeChar >= L'A' && KeyData.Key.UnicodeChar <= L'Z') {
|
||||
KeyData.Key.UnicodeChar = (CHAR16) (KeyData.Key.UnicodeChar - L'A' + 1);
|
||||
KeyData.Key.UnicodeChar = (CHAR16)(KeyData.Key.UnicodeChar - L'a' + 1);
|
||||
}
|
||||
else if (
|
||||
KeyData.Key.UnicodeChar >= L'A' && KeyData.Key.UnicodeChar <= L'Z') {
|
||||
KeyData.Key.UnicodeChar = (CHAR16)(KeyData.Key.UnicodeChar - L'A' + 1);
|
||||
}
|
||||
}
|
||||
|
||||
CopyMem (Key, &KeyData.Key, sizeof (EFI_INPUT_KEY));
|
||||
CopyMem(Key, &KeyData.Key, sizeof(EFI_INPUT_KEY));
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
}
|
||||
@ -286,25 +277,20 @@ KeypadReadKeyStroke (
|
||||
@param Context waitting context
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeypadWaitForKey (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
VOID EFIAPI KeypadWaitForKey(IN EFI_EVENT Event, IN VOID *Context)
|
||||
{
|
||||
EFI_TPL OldTpl;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
EFI_KEY_DATA KeyData;
|
||||
|
||||
ConsoleIn = (KEYPAD_CONSOLE_IN_DEV *) Context;
|
||||
ConsoleIn = (KEYPAD_CONSOLE_IN_DEV *)Context;
|
||||
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
|
||||
KeypadTimerHandler (NULL, ConsoleIn);
|
||||
KeypadTimerHandler(NULL, ConsoleIn);
|
||||
|
||||
if (!ConsoleIn->KeypadErr) {
|
||||
//
|
||||
@ -313,46 +299,41 @@ KeypadWaitForKey (
|
||||
// keystroke in the queue, so here skip the partial keystroke and get the
|
||||
// next key from the queue
|
||||
//
|
||||
while (!IsEfikeyBufEmpty (&ConsoleIn->EfiKeyQueue)) {
|
||||
CopyMem (
|
||||
while (!IsEfikeyBufEmpty(&ConsoleIn->EfiKeyQueue)) {
|
||||
CopyMem(
|
||||
&KeyData,
|
||||
&(ConsoleIn->EfiKeyQueue.Buffer[ConsoleIn->EfiKeyQueue.Head]),
|
||||
sizeof (EFI_KEY_DATA)
|
||||
);
|
||||
if (KeyData.Key.ScanCode == SCAN_NULL && KeyData.Key.UnicodeChar == CHAR_NULL) {
|
||||
PopEfikeyBufHead (&ConsoleIn->EfiKeyQueue, &KeyData);
|
||||
sizeof(EFI_KEY_DATA));
|
||||
if (KeyData.Key.ScanCode == SCAN_NULL &&
|
||||
KeyData.Key.UnicodeChar == CHAR_NULL) {
|
||||
PopEfikeyBufHead(&ConsoleIn->EfiKeyQueue, &KeyData);
|
||||
continue;
|
||||
}
|
||||
//
|
||||
// if there is pending value key, signal the event.
|
||||
//
|
||||
gBS->SignalEvent (Event);
|
||||
gBS->SignalEvent(Event);
|
||||
break;
|
||||
}
|
||||
}
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
}
|
||||
|
||||
/**
|
||||
Event notification function for SIMPLE_TEXT_INPUT_EX_PROTOCOL.WaitForKeyEx event
|
||||
Signal the event if there is key available
|
||||
Event notification function for SIMPLE_TEXT_INPUT_EX_PROTOCOL.WaitForKeyEx
|
||||
event Signal the event if there is key available
|
||||
|
||||
@param Event event object
|
||||
@param Context waiting context
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeypadWaitForKeyEx (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
VOID EFIAPI KeypadWaitForKeyEx(IN EFI_EVENT Event, IN VOID *Context)
|
||||
|
||||
{
|
||||
KeypadWaitForKey (Event, Context);
|
||||
KeypadWaitForKey(Event, Context);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -362,26 +343,21 @@ KeypadWaitForKeyEx (
|
||||
@param ExtendedVerification Driver may perform diagnostics on reset.
|
||||
|
||||
@retval EFI_SUCCESS The device was reset.
|
||||
@retval EFI_DEVICE_ERROR The device is not functioning properly and could
|
||||
not be reset.
|
||||
@retval EFI_DEVICE_ERROR The device is not functioning properly and
|
||||
could not be reset.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadEfiResetEx (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN BOOLEAN ExtendedVerification
|
||||
)
|
||||
KeypadEfiResetEx(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This, IN BOOLEAN ExtendedVerification)
|
||||
|
||||
{
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleInDev;
|
||||
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS (This);
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS(This);
|
||||
|
||||
return ConsoleInDev->ConIn.Reset (
|
||||
&ConsoleInDev->ConIn,
|
||||
ExtendedVerification
|
||||
);
|
||||
return ConsoleInDev->ConIn.Reset(&ConsoleInDev->ConIn, ExtendedVerification);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -390,22 +366,20 @@ KeypadEfiResetEx (
|
||||
|
||||
|
||||
@param This Protocol instance pointer.
|
||||
@param KeyData A pointer to a buffer that is filled in with the keystroke
|
||||
state data for the key that was pressed.
|
||||
@param KeyData A pointer to a buffer that is filled in with the
|
||||
keystroke state data for the key that was pressed.
|
||||
|
||||
@retval EFI_SUCCESS The keystroke information was returned.
|
||||
@retval EFI_NOT_READY There was no keystroke data availiable.
|
||||
@retval EFI_DEVICE_ERROR The keystroke information was not returned due to
|
||||
hardware errors.
|
||||
@retval EFI_DEVICE_ERROR The keystroke information was not returned due
|
||||
to hardware errors.
|
||||
@retval EFI_INVALID_PARAMETER KeyData is NULL.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadReadKeyStrokeEx (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
OUT EFI_KEY_DATA *KeyData
|
||||
)
|
||||
KeypadReadKeyStrokeEx(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This, OUT EFI_KEY_DATA *KeyData)
|
||||
|
||||
{
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleInDev;
|
||||
@ -414,8 +388,8 @@ KeypadReadKeyStrokeEx (
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS (This);
|
||||
return KeypadReadKeyStrokeWorker (ConsoleInDev, KeyData);
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS(This);
|
||||
return KeypadReadKeyStrokeWorker(ConsoleInDev, KeyData);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -426,18 +400,18 @@ KeypadReadKeyStrokeEx (
|
||||
state for the input device.
|
||||
|
||||
@retval EFI_SUCCESS The device state was set successfully.
|
||||
@retval EFI_DEVICE_ERROR The device is not functioning correctly and could
|
||||
not have the setting adjusted.
|
||||
@retval EFI_UNSUPPORTED The device does not have the ability to set its state.
|
||||
@retval EFI_DEVICE_ERROR The device is not functioning correctly and
|
||||
could not have the setting adjusted.
|
||||
@retval EFI_UNSUPPORTED The device does not have the ability to set its
|
||||
state.
|
||||
@retval EFI_INVALID_PARAMETER KeyToggleState is NULL.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadSetState (
|
||||
KeypadSetState(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN EFI_KEY_TOGGLE_STATE *KeyToggleState
|
||||
)
|
||||
IN EFI_KEY_TOGGLE_STATE *KeyToggleState)
|
||||
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
@ -448,12 +422,12 @@ KeypadSetState (
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS (This);
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS(This);
|
||||
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
|
||||
if (ConsoleInDev->KeypadErr) {
|
||||
Status = EFI_DEVICE_ERROR;
|
||||
@ -490,65 +464,66 @@ Exit:
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
|
||||
return Status;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
Register a notification function for a particular keystroke for the input device.
|
||||
Register a notification function for a particular keystroke for the input
|
||||
device.
|
||||
|
||||
@param This Protocol instance pointer.
|
||||
@param KeyData A pointer to a buffer that is filled in with the keystroke
|
||||
information data for the key that was pressed.
|
||||
@param KeyNotificationFunction Points to the function to be called when the key
|
||||
sequence is typed specified by KeyData.
|
||||
@param NotifyHandle Points to the unique handle assigned to the registered notification.
|
||||
@param KeyData A pointer to a buffer that is filled in
|
||||
with the keystroke information data for the key that was pressed.
|
||||
@param KeyNotificationFunction Points to the function to be called when
|
||||
the key sequence is typed specified by KeyData.
|
||||
@param NotifyHandle Points to the unique handle assigned to
|
||||
the registered notification.
|
||||
|
||||
@retval EFI_SUCCESS The notification function was registered successfully.
|
||||
@retval EFI_OUT_OF_RESOURCES Unable to allocate resources for necesssary data structures.
|
||||
@retval EFI_INVALID_PARAMETER KeyData or NotifyHandle or KeyNotificationFunction is NULL.
|
||||
@retval EFI_SUCCESS The notification function was registered
|
||||
successfully.
|
||||
@retval EFI_OUT_OF_RESOURCES Unable to allocate resources for
|
||||
necesssary data structures.
|
||||
@retval EFI_INVALID_PARAMETER KeyData or NotifyHandle or
|
||||
KeyNotificationFunction is NULL.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadRegisterKeyNotify (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN EFI_KEY_DATA *KeyData,
|
||||
IN EFI_KEY_NOTIFY_FUNCTION KeyNotificationFunction,
|
||||
OUT VOID **NotifyHandle
|
||||
)
|
||||
KeypadRegisterKeyNotify(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This, IN EFI_KEY_DATA *KeyData,
|
||||
IN EFI_KEY_NOTIFY_FUNCTION KeyNotificationFunction, OUT VOID **NotifyHandle)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleInDev;
|
||||
KEYPAD_CONSOLE_IN_DEV * ConsoleInDev;
|
||||
EFI_TPL OldTpl;
|
||||
LIST_ENTRY *Link;
|
||||
LIST_ENTRY * Link;
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY *CurrentNotify;
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY *NewNotify;
|
||||
|
||||
if (KeyData == NULL || NotifyHandle == NULL || KeyNotificationFunction == NULL) {
|
||||
if (KeyData == NULL || NotifyHandle == NULL ||
|
||||
KeyNotificationFunction == NULL) {
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS (This);
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS(This);
|
||||
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
|
||||
//
|
||||
// Return EFI_SUCCESS if the (KeyData, NotificationFunction) is already registered.
|
||||
// Return EFI_SUCCESS if the (KeyData, NotificationFunction) is already
|
||||
// registered.
|
||||
//
|
||||
for (Link = ConsoleInDev->NotifyList.ForwardLink; Link != &ConsoleInDev->NotifyList; Link = Link->ForwardLink) {
|
||||
CurrentNotify = CR (
|
||||
Link,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY,
|
||||
NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE
|
||||
);
|
||||
if (IsKeyRegistered (&CurrentNotify->KeyData, KeyData)) {
|
||||
for (Link = ConsoleInDev->NotifyList.ForwardLink;
|
||||
Link != &ConsoleInDev->NotifyList; Link = Link->ForwardLink) {
|
||||
CurrentNotify =
|
||||
CR(Link, KEYPAD_CONSOLE_IN_EX_NOTIFY, NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE);
|
||||
if (IsKeyRegistered(&CurrentNotify->KeyData, KeyData)) {
|
||||
if (CurrentNotify->KeyNotificationFn == KeyNotificationFunction) {
|
||||
*NotifyHandle = CurrentNotify;
|
||||
Status = EFI_SUCCESS;
|
||||
@ -560,7 +535,8 @@ KeypadRegisterKeyNotify (
|
||||
//
|
||||
// Allocate resource to save the notification function
|
||||
//
|
||||
NewNotify = (KEYPAD_CONSOLE_IN_EX_NOTIFY *) AllocateZeroPool (sizeof (KEYPAD_CONSOLE_IN_EX_NOTIFY));
|
||||
NewNotify = (KEYPAD_CONSOLE_IN_EX_NOTIFY *)AllocateZeroPool(
|
||||
sizeof(KEYPAD_CONSOLE_IN_EX_NOTIFY));
|
||||
if (NewNotify == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Exit;
|
||||
@ -568,8 +544,8 @@ KeypadRegisterKeyNotify (
|
||||
|
||||
NewNotify->Signature = KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE;
|
||||
NewNotify->KeyNotificationFn = KeyNotificationFunction;
|
||||
CopyMem (&NewNotify->KeyData, KeyData, sizeof (EFI_KEY_DATA));
|
||||
InsertTailList (&ConsoleInDev->NotifyList, &NewNotify->NotifyEntry);
|
||||
CopyMem(&NewNotify->KeyData, KeyData, sizeof(EFI_KEY_DATA));
|
||||
InsertTailList(&ConsoleInDev->NotifyList, &NewNotify->NotifyEntry);
|
||||
|
||||
*NotifyHandle = NewNotify;
|
||||
Status = EFI_SUCCESS;
|
||||
@ -578,60 +554,57 @@ Exit:
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
return Status;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
Remove a registered notification function from a particular keystroke.
|
||||
|
||||
@param This Protocol instance pointer.
|
||||
@param NotificationHandle The handle of the notification function being unregistered.
|
||||
@param NotificationHandle The handle of the notification function
|
||||
being unregistered.
|
||||
|
||||
|
||||
@retval EFI_SUCCESS The notification function was unregistered successfully.
|
||||
@retval EFI_SUCCESS The notification function was unregistered
|
||||
successfully.
|
||||
@retval EFI_INVALID_PARAMETER The NotificationHandle is invalid.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
KeypadUnregisterKeyNotify (
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
|
||||
IN VOID *NotificationHandle
|
||||
)
|
||||
KeypadUnregisterKeyNotify(
|
||||
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This, IN VOID *NotificationHandle)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleInDev;
|
||||
KEYPAD_CONSOLE_IN_DEV * ConsoleInDev;
|
||||
EFI_TPL OldTpl;
|
||||
LIST_ENTRY *Link;
|
||||
LIST_ENTRY * Link;
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY *CurrentNotify;
|
||||
|
||||
if (NotificationHandle == NULL) {
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS (This);
|
||||
ConsoleInDev = TEXT_INPUT_EX_KEYPAD_CONSOLE_IN_DEV_FROM_THIS(This);
|
||||
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
|
||||
for (Link = ConsoleInDev->NotifyList.ForwardLink; Link != &ConsoleInDev->NotifyList; Link = Link->ForwardLink) {
|
||||
CurrentNotify = CR (
|
||||
Link,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY,
|
||||
NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE
|
||||
);
|
||||
for (Link = ConsoleInDev->NotifyList.ForwardLink;
|
||||
Link != &ConsoleInDev->NotifyList; Link = Link->ForwardLink) {
|
||||
CurrentNotify =
|
||||
CR(Link, KEYPAD_CONSOLE_IN_EX_NOTIFY, NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE);
|
||||
if (CurrentNotify == NotificationHandle) {
|
||||
//
|
||||
// Remove the notification function from NotifyList and free resources
|
||||
//
|
||||
RemoveEntryList (&CurrentNotify->NotifyEntry);
|
||||
RemoveEntryList(&CurrentNotify->NotifyEntry);
|
||||
|
||||
gBS->FreePool (CurrentNotify);
|
||||
gBS->FreePool(CurrentNotify);
|
||||
Status = EFI_SUCCESS;
|
||||
goto Exit;
|
||||
}
|
||||
@ -645,7 +618,7 @@ Exit:
|
||||
//
|
||||
// Leave critical section and return
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
return Status;
|
||||
}
|
||||
|
||||
@ -655,22 +628,17 @@ Exit:
|
||||
@param Event Indicates the event that invoke this function.
|
||||
@param Context Indicates the calling context.
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
KeyNotifyProcessHandler (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
VOID EFIAPI KeyNotifyProcessHandler(IN EFI_EVENT Event, IN VOID *Context)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
KEYPAD_CONSOLE_IN_DEV *ConsoleIn;
|
||||
KEYPAD_CONSOLE_IN_DEV * ConsoleIn;
|
||||
EFI_KEY_DATA KeyData;
|
||||
LIST_ENTRY *Link;
|
||||
LIST_ENTRY *NotifyList;
|
||||
LIST_ENTRY * Link;
|
||||
LIST_ENTRY * NotifyList;
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY *CurrentNotify;
|
||||
EFI_TPL OldTpl;
|
||||
|
||||
ConsoleIn = (KEYPAD_CONSOLE_IN_DEV *) Context;
|
||||
ConsoleIn = (KEYPAD_CONSOLE_IN_DEV *)Context;
|
||||
|
||||
//
|
||||
// Invoke notification functions.
|
||||
@ -680,21 +648,23 @@ KeyNotifyProcessHandler (
|
||||
//
|
||||
// Enter critical section
|
||||
//
|
||||
OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
Status = PopEfikeyBufHead (&ConsoleIn->EfiKeyQueueForNotify, &KeyData);
|
||||
OldTpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
Status = PopEfikeyBufHead(&ConsoleIn->EfiKeyQueueForNotify, &KeyData);
|
||||
//
|
||||
// Leave critical section
|
||||
//
|
||||
gBS->RestoreTPL (OldTpl);
|
||||
if (EFI_ERROR (Status)) {
|
||||
gBS->RestoreTPL(OldTpl);
|
||||
if (EFI_ERROR(Status)) {
|
||||
break;
|
||||
}
|
||||
for (Link = GetFirstNode (NotifyList); !IsNull (NotifyList, Link); Link = GetNextNode (NotifyList, Link)) {
|
||||
CurrentNotify = CR (Link, KEYPAD_CONSOLE_IN_EX_NOTIFY, NotifyEntry, KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE);
|
||||
if (IsKeyRegistered (&CurrentNotify->KeyData, &KeyData)) {
|
||||
CurrentNotify->KeyNotificationFn (&KeyData);
|
||||
for (Link = GetFirstNode(NotifyList); !IsNull(NotifyList, Link);
|
||||
Link = GetNextNode(NotifyList, Link)) {
|
||||
CurrentNotify =
|
||||
CR(Link, KEYPAD_CONSOLE_IN_EX_NOTIFY, NotifyEntry,
|
||||
KEYPAD_CONSOLE_IN_EX_NOTIFY_SIGNATURE);
|
||||
if (IsKeyRegistered(&CurrentNotify->KeyData, &KeyData)) {
|
||||
CurrentNotify->KeyNotificationFn(&KeyData);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -20,9 +20,10 @@
|
||||
#include "crc32.h"
|
||||
#include <Library/UefiLib.h>
|
||||
|
||||
EFI_STATUS FixGptCRC32(EFI_BLOCK_IO_PROTOCOL *mBlockIoProtocol,
|
||||
EFI_DISK_IO_PROTOCOL *mDiskIoProtocol,
|
||||
EFI_SYSTEM_TABLE *mSystemTable){
|
||||
EFI_STATUS FixGptCRC32(
|
||||
EFI_BLOCK_IO_PROTOCOL *mBlockIoProtocol,
|
||||
EFI_DISK_IO_PROTOCOL *mDiskIoProtocol, EFI_SYSTEM_TABLE *mSystemTable)
|
||||
{
|
||||
EFI_STATUS status;
|
||||
UINT32 mMediaId;
|
||||
UINT32 mBlockSize;
|
||||
@ -33,28 +34,26 @@ EFI_STATUS FixGptCRC32(EFI_BLOCK_IO_PROTOCOL *mBlockIoProtocol,
|
||||
unsigned char *bufGptHeader;
|
||||
unsigned char *bufGptEntry;
|
||||
// try to allocate pool for bufGptEntry
|
||||
status = mSystemTable->BootServices->AllocatePool(EfiBootServicesCode, GPT_ENTRY_COUNT * mBlockSize, (VOID**)&bufGptEntry);
|
||||
status = mSystemTable->BootServices->AllocatePool(
|
||||
EfiBootServicesCode, GPT_ENTRY_COUNT * mBlockSize, (VOID **)&bufGptEntry);
|
||||
if (EFI_ERROR(status)) {
|
||||
return status;
|
||||
}
|
||||
// read gpt entry list
|
||||
status = mDiskIoProtocol->ReadDisk(mDiskIoProtocol,
|
||||
mMediaId,
|
||||
2 * mBlockSize,
|
||||
GPT_ENTRY_COUNT * mBlockSize,
|
||||
status = mDiskIoProtocol->ReadDisk(
|
||||
mDiskIoProtocol, mMediaId, 2 * mBlockSize, GPT_ENTRY_COUNT * mBlockSize,
|
||||
bufGptEntry);
|
||||
|
||||
if (EFI_ERROR(status))
|
||||
return status;
|
||||
// get gpt entry crc32 value
|
||||
get_result_array(calculate_crc32(bufGptEntry, GPT_ENTRY_COUNT * mBlockSize), crc32_entry);
|
||||
get_result_array(
|
||||
calculate_crc32(bufGptEntry, GPT_ENTRY_COUNT * mBlockSize), crc32_entry);
|
||||
|
||||
// write gpt entry crc32 value to disk
|
||||
status = mDiskIoProtocol->WriteDisk(mDiskIoProtocol,
|
||||
mMediaId,
|
||||
mBlockSize + GPT_ENTRY_CRC32_LBA1_OFFSET,
|
||||
GPT_CRC32_LEN,
|
||||
crc32_entry);
|
||||
status = mDiskIoProtocol->WriteDisk(
|
||||
mDiskIoProtocol, mMediaId, mBlockSize + GPT_ENTRY_CRC32_LBA1_OFFSET,
|
||||
GPT_CRC32_LEN, crc32_entry);
|
||||
if (EFI_ERROR(status))
|
||||
return status;
|
||||
// try to release bufGptEntry
|
||||
@ -63,27 +62,25 @@ EFI_STATUS FixGptCRC32(EFI_BLOCK_IO_PROTOCOL *mBlockIoProtocol,
|
||||
return status;
|
||||
}
|
||||
// try to allocate pool for bufGptHeader
|
||||
status = mSystemTable->BootServices->AllocatePool(EfiBootServicesCode, GPT_HEADER_SIZE, (VOID**)&bufGptHeader);
|
||||
status = mSystemTable->BootServices->AllocatePool(
|
||||
EfiBootServicesCode, GPT_HEADER_SIZE, (VOID **)&bufGptHeader);
|
||||
// get gpt header
|
||||
status = mDiskIoProtocol->ReadDisk(mDiskIoProtocol,
|
||||
mMediaId,
|
||||
mBlockSize,
|
||||
GPT_HEADER_SIZE,
|
||||
bufGptHeader);
|
||||
status = mDiskIoProtocol->ReadDisk(
|
||||
mDiskIoProtocol, mMediaId, mBlockSize, GPT_HEADER_SIZE, bufGptHeader);
|
||||
if (EFI_ERROR(status))
|
||||
return status;
|
||||
// set previous crc32 value to 0x00
|
||||
for (int i = GPT_HEADER_CRC32_LBA1_OFFSET; i < GPT_HEADER_CRC32_LBA1_OFFSET + GPT_CRC32_LEN; i++) {
|
||||
for (int i = GPT_HEADER_CRC32_LBA1_OFFSET;
|
||||
i < GPT_HEADER_CRC32_LBA1_OFFSET + GPT_CRC32_LEN; i++) {
|
||||
bufGptHeader[i] = 0x00;
|
||||
}
|
||||
// get gpt header crc32 value
|
||||
get_result_array(calculate_crc32(bufGptHeader, GPT_HEADER_SIZE), crc32_header);
|
||||
get_result_array(
|
||||
calculate_crc32(bufGptHeader, GPT_HEADER_SIZE), crc32_header);
|
||||
// write gpt header crc32 value to disk
|
||||
status = mDiskIoProtocol->WriteDisk(mDiskIoProtocol,
|
||||
mMediaId,
|
||||
mBlockSize + GPT_HEADER_CRC32_LBA1_OFFSET,
|
||||
GPT_CRC32_LEN,
|
||||
crc32_header);
|
||||
status = mDiskIoProtocol->WriteDisk(
|
||||
mDiskIoProtocol, mMediaId, mBlockSize + GPT_HEADER_CRC32_LBA1_OFFSET,
|
||||
GPT_CRC32_LEN, crc32_header);
|
||||
if (EFI_ERROR(status))
|
||||
return status;
|
||||
// try to release bufGptHeader
|
||||
@ -95,8 +92,8 @@ EFI_STATUS FixGptCRC32(EFI_BLOCK_IO_PROTOCOL *mBlockIoProtocol,
|
||||
}
|
||||
|
||||
/*
|
||||
* A8h reflected is 15h, i.e. 10101000 <--> 00010101
|
||||
*/
|
||||
* A8h reflected is 15h, i.e. 10101000 <--> 00010101
|
||||
*/
|
||||
int reflect(int data, int len)
|
||||
{
|
||||
int ref = 0;
|
||||
@ -112,8 +109,8 @@ int reflect(int data, int len)
|
||||
}
|
||||
|
||||
/*
|
||||
* Function to calculate the CRC32
|
||||
*/
|
||||
* Function to calculate the CRC32
|
||||
*/
|
||||
unsigned int calculate_crc32(unsigned char *buffer, int len)
|
||||
{
|
||||
int byte_length = 8; /*length of unit (i.e. byte) */
|
||||
@ -146,13 +143,12 @@ unsigned int calculate_crc32(unsigned char *buffer, int len)
|
||||
}
|
||||
|
||||
// Convert Function
|
||||
//unsigned char** convert(unsigned int reflected_regs, int *size)
|
||||
void get_result_array(unsigned int reflected_regs, unsigned char * res)
|
||||
// unsigned char** convert(unsigned int reflected_regs, int *size)
|
||||
void get_result_array(unsigned int reflected_regs, unsigned char *res)
|
||||
{
|
||||
|
||||
for (int i = 0; i < 4; i++) {
|
||||
res[i] = reflected_regs & 0xff;
|
||||
reflected_regs >>= 8;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -32,8 +32,9 @@
|
||||
|
||||
int reflect(int, int);
|
||||
|
||||
unsigned int calculate_crc32(unsigned char*, int);
|
||||
unsigned int calculate_crc32(unsigned char *, int);
|
||||
|
||||
void get_result_array(unsigned int, unsigned char*);
|
||||
void get_result_array(unsigned int, unsigned char *);
|
||||
|
||||
EFI_STATUS FixGptCRC32(EFI_BLOCK_IO_PROTOCOL*, EFI_DISK_IO_PROTOCOL*, EFI_SYSTEM_TABLE*);
|
||||
EFI_STATUS FixGptCRC32(
|
||||
EFI_BLOCK_IO_PROTOCOL *, EFI_DISK_IO_PROTOCOL *, EFI_SYSTEM_TABLE *);
|
||||
|
@ -16,22 +16,22 @@
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/
|
||||
*/
|
||||
|
||||
#include <Uefi.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Protocol/DiskIo.h>
|
||||
#include <Protocol/BlockIo.h>
|
||||
#include "slot.h"
|
||||
#include "crc32.h"
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Protocol/BlockIo.h>
|
||||
#include <Protocol/DiskIo.h>
|
||||
#include <Uefi.h>
|
||||
|
||||
void WaitAnyKey(EFI_SYSTEM_TABLE *mSystemTable);
|
||||
|
||||
EFI_STATUS EFIAPI SlotMain(IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
EFI_STATUS EFIAPI
|
||||
SlotMain(IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
{
|
||||
EFI_STATUS status;
|
||||
EFI_HANDLE *controllerHandles = NULL;
|
||||
EFI_HANDLE * controllerHandles = NULL;
|
||||
UINTN handleIndex, numHandles;
|
||||
EFI_DISK_IO_PROTOCOL *mDiskIoProtocol = NULL;
|
||||
EFI_DISK_IO_PROTOCOL * mDiskIoProtocol = NULL;
|
||||
EFI_BLOCK_IO_PROTOCOL *mBlockIoProtocol = NULL;
|
||||
UINT32 mMediaId;
|
||||
UINT32 mBlockSize;
|
||||
@ -39,46 +39,42 @@ EFI_STATUS EFIAPI SlotMain(IN EFI_HANDLE ImageHandle,
|
||||
unsigned char currentSlotA[OP6T_SLOT_FLAG_SIZE];
|
||||
unsigned char currentSlotB[OP6T_SLOT_FLAG_SIZE];
|
||||
// list all Handles that installed DiskIoProtocol
|
||||
status = SystemTable->BootServices->LocateHandleBuffer(ByProtocol,
|
||||
&gEfiDiskIoProtocolGuid,
|
||||
NULL,
|
||||
&numHandles,
|
||||
status = SystemTable->BootServices->LocateHandleBuffer(
|
||||
ByProtocol, &gEfiDiskIoProtocolGuid, NULL, &numHandles,
|
||||
&controllerHandles);
|
||||
if (EFI_ERROR(status)) {
|
||||
//WaitAnyKey(SystemTable);
|
||||
// WaitAnyKey(SystemTable);
|
||||
return status;
|
||||
}
|
||||
// ergodic the handles
|
||||
for (handleIndex = 0; handleIndex < numHandles; handleIndex++) {
|
||||
// open DiskIoProtocol on target handle
|
||||
status = SystemTable->BootServices->HandleProtocol(
|
||||
controllerHandles[handleIndex],
|
||||
&gEfiDiskIoProtocolGuid,
|
||||
(VOID**)&mDiskIoProtocol);
|
||||
controllerHandles[handleIndex], &gEfiDiskIoProtocolGuid,
|
||||
(VOID **)&mDiskIoProtocol);
|
||||
unsigned char slotNameBuffer[OP6T_SLOT_BOOT_BUFFER_LEN];
|
||||
if (EFI_ERROR(status))
|
||||
continue;
|
||||
// open BlockIoProtocol on target handle
|
||||
status = SystemTable->BootServices->HandleProtocol(
|
||||
controllerHandles[handleIndex],
|
||||
&gEfiBlockIoProtocolGuid,
|
||||
(VOID**)&mBlockIoProtocol);
|
||||
controllerHandles[handleIndex], &gEfiBlockIoProtocolGuid,
|
||||
(VOID **)&mBlockIoProtocol);
|
||||
if (EFI_ERROR(status)) {
|
||||
continue;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
// filter disk device by LogicalPartition
|
||||
if (mBlockIoProtocol->Media->LogicalPartition)
|
||||
continue;
|
||||
SystemTable->ConOut->OutputString(SystemTable->ConOut, L"The media is disk.\n");
|
||||
SystemTable->ConOut->OutputString(
|
||||
SystemTable->ConOut, L"The media is disk.\n");
|
||||
mMediaId = mBlockIoProtocol->Media->MediaId;
|
||||
mBlockSize = mBlockIoProtocol->Media->BlockSize;
|
||||
// read buffers from disk
|
||||
status = mDiskIoProtocol->ReadDisk(
|
||||
mDiskIoProtocol,
|
||||
mMediaId,
|
||||
mDiskIoProtocol, mMediaId,
|
||||
2 * mBlockSize + OP6T_SLOT_A_BOOT_BUFFER_LBA2_OFFSET,
|
||||
OP6T_SLOT_BOOT_BUFFER_LEN,
|
||||
slotNameBuffer);
|
||||
OP6T_SLOT_BOOT_BUFFER_LEN, slotNameBuffer);
|
||||
if (EFI_ERROR(status))
|
||||
continue;
|
||||
// filter disk device by the name of boot partition
|
||||
@ -91,23 +87,20 @@ EFI_STATUS EFIAPI SlotMain(IN EFI_HANDLE ImageHandle,
|
||||
}
|
||||
if (i == 1)
|
||||
continue;
|
||||
SystemTable->ConOut->OutputString(SystemTable->ConOut, L"The name of target partition is matched.\n");
|
||||
SystemTable->ConOut->OutputString(
|
||||
SystemTable->ConOut, L"The name of target partition is matched.\n");
|
||||
// read flag of slot A
|
||||
status = mDiskIoProtocol->ReadDisk(
|
||||
mDiskIoProtocol,
|
||||
mMediaId,
|
||||
mDiskIoProtocol, mMediaId,
|
||||
2 * mBlockSize + OP6T_SLOT_A_BOOT_FLAG_LBA2_OFFSET,
|
||||
OP6T_SLOT_FLAG_SIZE,
|
||||
currentSlotA);
|
||||
OP6T_SLOT_FLAG_SIZE, currentSlotA);
|
||||
if (EFI_ERROR(status))
|
||||
return status;
|
||||
// read flag of slot B
|
||||
status = mDiskIoProtocol->ReadDisk(
|
||||
mDiskIoProtocol,
|
||||
mMediaId,
|
||||
mDiskIoProtocol, mMediaId,
|
||||
3 * mBlockSize + OP6T_SLOT_B_BOOT_FLAG_LBA3_OFFSET,
|
||||
OP6T_SLOT_FLAG_SIZE,
|
||||
currentSlotB);
|
||||
OP6T_SLOT_FLAG_SIZE, currentSlotB);
|
||||
if (EFI_ERROR(status))
|
||||
return status;
|
||||
|
||||
@ -125,44 +118,45 @@ EFI_STATUS EFIAPI SlotMain(IN EFI_HANDLE ImageHandle,
|
||||
else
|
||||
flag_offset = 2 * mBlockSize + OP6T_SLOT_A_BOOT_FLAG_LBA2_OFFSET;
|
||||
|
||||
|
||||
// write flag into disk
|
||||
unsigned char f[1] = {OP6T_SLOT_FLAG_ACTIVE};
|
||||
status = mDiskIoProtocol->WriteDisk(
|
||||
mDiskIoProtocol,
|
||||
mMediaId,
|
||||
flag_offset,
|
||||
OP6T_SLOT_FLAG_SIZE,
|
||||
f);
|
||||
mDiskIoProtocol, mMediaId, flag_offset, OP6T_SLOT_FLAG_SIZE, f);
|
||||
if (EFI_ERROR(status)) {
|
||||
SystemTable->ConOut->OutputString(SystemTable->ConOut, L"Failed to write flag into disk.\n");
|
||||
SystemTable->ConOut->OutputString(
|
||||
SystemTable->ConOut, L"Failed to write flag into disk.\n");
|
||||
continue;
|
||||
} else {
|
||||
SystemTable->ConOut->OutputString(SystemTable->ConOut, L"Succeed to write flag into disk.\n");
|
||||
}
|
||||
else {
|
||||
SystemTable->ConOut->OutputString(
|
||||
SystemTable->ConOut, L"Succeed to write flag into disk.\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
//try to fix gpt crc32
|
||||
// try to fix gpt crc32
|
||||
if (mBlockIoProtocol != NULL) {
|
||||
status = (FixGptCRC32(mBlockIoProtocol, mDiskIoProtocol, SystemTable));
|
||||
if (EFI_ERROR(status))
|
||||
SystemTable->ConOut->OutputString(SystemTable->ConOut, L"Failed to fix CRC32 value.\n");
|
||||
SystemTable->ConOut->OutputString(
|
||||
SystemTable->ConOut, L"Failed to fix CRC32 value.\n");
|
||||
else
|
||||
SystemTable->ConOut->OutputString(SystemTable->ConOut, L"Succeed to fix CRC32 value.\n");
|
||||
SystemTable->ConOut->OutputString(
|
||||
SystemTable->ConOut, L"Succeed to fix CRC32 value.\n");
|
||||
}
|
||||
|
||||
// release memory
|
||||
if (controllerHandles != NULL)
|
||||
SystemTable->BootServices->FreePool(controllerHandles);
|
||||
//WaitAnyKey(SystemTable);
|
||||
// WaitAnyKey(SystemTable);
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
void WaitAnyKey(EFI_SYSTEM_TABLE *mSystemTable) {
|
||||
void WaitAnyKey(EFI_SYSTEM_TABLE *mSystemTable)
|
||||
{
|
||||
UINTN index = 0;
|
||||
EFI_INPUT_KEY Key;
|
||||
mSystemTable->BootServices->WaitForEvent(1, &mSystemTable->ConIn->WaitForKey, &index);
|
||||
mSystemTable->BootServices->WaitForEvent(
|
||||
1, &mSystemTable->ConIn->WaitForKey, &index);
|
||||
mSystemTable->ConIn->ReadKeyStroke(mSystemTable->ConIn, &Key);
|
||||
}
|
||||
|
||||
|
@ -17,8 +17,8 @@
|
||||
*/
|
||||
|
||||
/*
|
||||
* Flags of OP6T slots
|
||||
*/
|
||||
* Flags of OP6T slots
|
||||
*/
|
||||
|
||||
const unsigned char OP6T_SLOT_FLAG_ACTIVE = 0x6F;
|
||||
|
||||
@ -36,38 +36,41 @@ const unsigned char OP6T_SLOT_FLAG_BOOTABLE_6 = 0x2F;
|
||||
|
||||
const unsigned OP6T_SLOT_FLAG_BOOTABLE_7 = 0x37;
|
||||
|
||||
const unsigned OP6T_SLOT_FLAG_BOOTABLE = 0x37; /* defaultly set bootable the same as bootable_7 */
|
||||
const unsigned OP6T_SLOT_FLAG_BOOTABLE =
|
||||
0x37; /* defaultly set bootable the same as bootable_7 */
|
||||
|
||||
const unsigned OP6T_SLOT_FLAG_UNBOOTABLE = 0xBA;
|
||||
|
||||
// const unsigned OP6T_SLOT_FLAG_SUCCESSFUL = 0xFF; /* OP6T_SLOT_FLAG_SUCCESSFUL maybe uncorrect in this file */
|
||||
// const unsigned OP6T_SLOT_FLAG_SUCCESSFUL = 0xFF; /* OP6T_SLOT_FLAG_SUCCESSFUL
|
||||
// maybe uncorrect in this file */
|
||||
|
||||
#define OP6T_SLOT_FLAG_SIZE 1
|
||||
|
||||
/*
|
||||
* Flag's offset on disk
|
||||
* The offset may very from device to device
|
||||
* Make sure the offset is correct before using it
|
||||
*/
|
||||
* Flag's offset on disk
|
||||
* The offset may very from device to device
|
||||
* Make sure the offset is correct before using it
|
||||
*/
|
||||
|
||||
#define OP6T_SLOT_A_BOOT_FLAG_LBA2_OFFSET 0x536
|
||||
|
||||
#define OP6T_SLOT_B_BOOT_FLAG_LBA3_OFFSET 0x336
|
||||
|
||||
/*
|
||||
* Boot partitions name and their offsets
|
||||
* Find the right device by comparaing the partition name on the offset
|
||||
*/
|
||||
* Boot partitions name and their offsets
|
||||
* Find the right device by comparaing the partition name on the offset
|
||||
*/
|
||||
|
||||
const unsigned char OP6T_SLOT_A_BOOT_BUFFER[] = {0x62, 0x00, 0x6F, 0x00, 0x6F,
|
||||
0x00, 0x74, 0x00, 0x5F, 0x00, 0x61}; /* ACSII: b.o.o.t._.a */
|
||||
const unsigned char OP6T_SLOT_A_BOOT_BUFFER[] = {
|
||||
0x62, 0x00, 0x6F, 0x00, 0x6F, 0x00,
|
||||
0x74, 0x00, 0x5F, 0x00, 0x61}; /* ACSII: b.o.o.t._.a */
|
||||
|
||||
const unsigned char OP6T_SLOT_B_BOOT_BUFFER[] = {0x62, 0x00, 0x6F, 0x00, 0x6F,
|
||||
0x00, 0x74, 0x00, 0x5F, 0x00, 0x62}; /* ACSII: b.o.o.t._.b */
|
||||
const unsigned char OP6T_SLOT_B_BOOT_BUFFER[] = {
|
||||
0x62, 0x00, 0x6F, 0x00, 0x6F, 0x00,
|
||||
0x74, 0x00, 0x5F, 0x00, 0x62}; /* ACSII: b.o.o.t._.b */
|
||||
|
||||
#define OP6T_SLOT_BOOT_BUFFER_LEN 11
|
||||
|
||||
#define OP6T_SLOT_A_BOOT_BUFFER_LBA2_OFFSET 0x538
|
||||
|
||||
#define OP6T_SLOT_B_BOOT_BUFFER_LBA3_OFFSET 0x338
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,17 +1,17 @@
|
||||
/* SimpleFbDxe: Simple FrameBuffer */
|
||||
#include <PiDxe.h>
|
||||
#include <Uefi.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/PcdLib.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/DxeServicesTableLib.h>
|
||||
#include <Protocol/GraphicsOutput.h>
|
||||
#include <Library/BaseLib.h>
|
||||
#include <Library/FrameBufferBltLib.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/CacheMaintenanceLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/DxeServicesTableLib.h>
|
||||
#include <Library/FrameBufferBltLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/PcdLib.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <PiDxe.h>
|
||||
#include <Protocol/GraphicsOutput.h>
|
||||
#include <Uefi.h>
|
||||
|
||||
/// Defines
|
||||
/*
|
||||
@ -42,28 +42,17 @@ typedef struct {
|
||||
EFI_DEVICE_PATH EndDevicePath;
|
||||
} DISPLAY_DEVICE_PATH;
|
||||
|
||||
DISPLAY_DEVICE_PATH mDisplayDevicePath =
|
||||
{
|
||||
{
|
||||
{
|
||||
HARDWARE_DEVICE_PATH,
|
||||
DISPLAY_DEVICE_PATH mDisplayDevicePath = {
|
||||
{{HARDWARE_DEVICE_PATH,
|
||||
HW_VENDOR_DP,
|
||||
{
|
||||
(UINT8)(sizeof(VENDOR_DEVICE_PATH)),
|
||||
(UINT8)((sizeof(VENDOR_DEVICE_PATH)) >> 8),
|
||||
}
|
||||
},
|
||||
EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID
|
||||
},
|
||||
{
|
||||
END_DEVICE_PATH_TYPE,
|
||||
}},
|
||||
EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID},
|
||||
{END_DEVICE_PATH_TYPE,
|
||||
END_ENTIRE_DEVICE_PATH_SUBTYPE,
|
||||
{
|
||||
sizeof(EFI_DEVICE_PATH_PROTOCOL),
|
||||
0
|
||||
}
|
||||
}
|
||||
};
|
||||
{sizeof(EFI_DEVICE_PATH_PROTOCOL), 0}}};
|
||||
|
||||
/// Declares
|
||||
|
||||
@ -73,63 +62,40 @@ STATIC UINTN mFrameBufferBltLibConfigureSize;
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
DisplayQueryMode
|
||||
(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
|
||||
IN UINT32 ModeNumber,
|
||||
OUT UINTN *SizeOfInfo,
|
||||
OUT EFI_GRAPHICS_OUTPUT_MODE_INFORMATION **Info
|
||||
);
|
||||
DisplayQueryMode(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This, IN UINT32 ModeNumber,
|
||||
OUT UINTN *SizeOfInfo, OUT EFI_GRAPHICS_OUTPUT_MODE_INFORMATION **Info);
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
DisplaySetMode
|
||||
(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
|
||||
IN UINT32 ModeNumber
|
||||
);
|
||||
DisplaySetMode(IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This, IN UINT32 ModeNumber);
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
DisplayBlt
|
||||
(
|
||||
DisplayBlt(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
|
||||
IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BltBuffer, OPTIONAL
|
||||
IN EFI_GRAPHICS_OUTPUT_BLT_OPERATION BltOperation,
|
||||
IN UINTN SourceX,
|
||||
IN UINTN SourceY,
|
||||
IN UINTN DestinationX,
|
||||
IN UINTN DestinationY,
|
||||
IN UINTN Width,
|
||||
IN UINTN Height,
|
||||
IN UINTN Delta OPTIONAL
|
||||
);
|
||||
IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL * BltBuffer,
|
||||
OPTIONAL IN EFI_GRAPHICS_OUTPUT_BLT_OPERATION BltOperation,
|
||||
IN UINTN SourceX, IN UINTN SourceY, IN UINTN DestinationX,
|
||||
IN UINTN DestinationY, IN UINTN Width, IN UINTN Height,
|
||||
IN UINTN Delta OPTIONAL);
|
||||
|
||||
STATIC EFI_GRAPHICS_OUTPUT_PROTOCOL mDisplay = {
|
||||
DisplayQueryMode,
|
||||
DisplaySetMode,
|
||||
DisplayBlt,
|
||||
NULL
|
||||
};
|
||||
DisplayQueryMode, DisplaySetMode, DisplayBlt, NULL};
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
DisplayQueryMode
|
||||
(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
|
||||
IN UINT32 ModeNumber,
|
||||
OUT UINTN *SizeOfInfo,
|
||||
OUT EFI_GRAPHICS_OUTPUT_MODE_INFORMATION **Info
|
||||
)
|
||||
DisplayQueryMode(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This, IN UINT32 ModeNumber,
|
||||
OUT UINTN *SizeOfInfo, OUT EFI_GRAPHICS_OUTPUT_MODE_INFORMATION **Info)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
Status = gBS->AllocatePool(
|
||||
EfiBootServicesData,
|
||||
sizeof(EFI_GRAPHICS_OUTPUT_MODE_INFORMATION),
|
||||
(VOID **) Info);
|
||||
EfiBootServicesData, sizeof(EFI_GRAPHICS_OUTPUT_MODE_INFORMATION),
|
||||
(VOID **)Info);
|
||||
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
@ -146,11 +112,7 @@ DisplayQueryMode
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
DisplaySetMode
|
||||
(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
|
||||
IN UINT32 ModeNumber
|
||||
)
|
||||
DisplaySetMode(IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This, IN UINT32 ModeNumber)
|
||||
{
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
@ -158,97 +120,82 @@ DisplaySetMode
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
DisplayBlt
|
||||
(
|
||||
DisplayBlt(
|
||||
IN EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
|
||||
IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BltBuffer, OPTIONAL
|
||||
IN EFI_GRAPHICS_OUTPUT_BLT_OPERATION BltOperation,
|
||||
IN UINTN SourceX,
|
||||
IN UINTN SourceY,
|
||||
IN UINTN DestinationX,
|
||||
IN UINTN DestinationY,
|
||||
IN UINTN Width,
|
||||
IN UINTN Height,
|
||||
IN UINTN Delta OPTIONAL
|
||||
)
|
||||
IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL * BltBuffer,
|
||||
OPTIONAL IN EFI_GRAPHICS_OUTPUT_BLT_OPERATION BltOperation,
|
||||
IN UINTN SourceX, IN UINTN SourceY, IN UINTN DestinationX,
|
||||
IN UINTN DestinationY, IN UINTN Width, IN UINTN Height,
|
||||
IN UINTN Delta OPTIONAL)
|
||||
{
|
||||
|
||||
RETURN_STATUS Status;
|
||||
EFI_TPL Tpl;
|
||||
//
|
||||
// We have to raise to TPL_NOTIFY, so we make an atomic write to the frame buffer.
|
||||
// We would not want a timer based event (Cursor, ...) to come in while we are
|
||||
// doing this operation.
|
||||
// We have to raise to TPL_NOTIFY, so we make an atomic write to the frame
|
||||
// buffer. We would not want a timer based event (Cursor, ...) to come in
|
||||
// while we are doing this operation.
|
||||
//
|
||||
Tpl = gBS->RaiseTPL (TPL_NOTIFY);
|
||||
Status = FrameBufferBlt (
|
||||
mFrameBufferBltLibConfigure,
|
||||
BltBuffer,
|
||||
BltOperation,
|
||||
SourceX, SourceY,
|
||||
DestinationX, DestinationY, Width, Height,
|
||||
Delta
|
||||
);
|
||||
gBS->RestoreTPL (Tpl);
|
||||
Tpl = gBS->RaiseTPL(TPL_NOTIFY);
|
||||
Status = FrameBufferBlt(
|
||||
mFrameBufferBltLibConfigure, BltBuffer, BltOperation, SourceX, SourceY,
|
||||
DestinationX, DestinationY, Width, Height, Delta);
|
||||
gBS->RestoreTPL(Tpl);
|
||||
|
||||
// zhuowei: hack: flush the cache manually since my memory maps are still broken
|
||||
WriteBackInvalidateDataCacheRange((void*)mDisplay.Mode->FrameBufferBase,
|
||||
mDisplay.Mode->FrameBufferSize);
|
||||
// zhuowei: hack: flush the cache manually since my memory maps are still
|
||||
// broken
|
||||
WriteBackInvalidateDataCacheRange(
|
||||
(void *)mDisplay.Mode->FrameBufferBase, mDisplay.Mode->FrameBufferSize);
|
||||
// zhuowei: end hack
|
||||
|
||||
return RETURN_ERROR (Status) ? EFI_INVALID_PARAMETER : EFI_SUCCESS;
|
||||
return RETURN_ERROR(Status) ? EFI_INVALID_PARAMETER : EFI_SUCCESS;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
SimpleFbDxeInitialize
|
||||
(
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
)
|
||||
SimpleFbDxeInitialize(
|
||||
IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
{
|
||||
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
EFI_HANDLE hUEFIDisplayHandle = NULL;
|
||||
|
||||
/* Retrieve simple frame buffer from pre-SEC bootloader */
|
||||
DEBUG((EFI_D_ERROR, "SimpleFbDxe: Retrieve MIPI FrameBuffer parameters from PCD\n"));
|
||||
DEBUG(
|
||||
(EFI_D_ERROR,
|
||||
"SimpleFbDxe: Retrieve MIPI FrameBuffer parameters from PCD\n"));
|
||||
UINT32 MipiFrameBufferAddr = FixedPcdGet32(PcdMipiFrameBufferAddress);
|
||||
UINT32 MipiFrameBufferWidth = FixedPcdGet32(PcdMipiFrameBufferWidth);
|
||||
UINT32 MipiFrameBufferHeight = FixedPcdGet32(PcdMipiFrameBufferHeight);
|
||||
|
||||
/* Sanity check */
|
||||
if (MipiFrameBufferAddr == 0 || MipiFrameBufferWidth == 0 || MipiFrameBufferHeight == 0)
|
||||
{
|
||||
if (MipiFrameBufferAddr == 0 || MipiFrameBufferWidth == 0 ||
|
||||
MipiFrameBufferHeight == 0) {
|
||||
DEBUG((EFI_D_ERROR, "SimpleFbDxe: Invalid FrameBuffer parameters\n"));
|
||||
return EFI_DEVICE_ERROR;
|
||||
}
|
||||
|
||||
/* Prepare struct */
|
||||
if (mDisplay.Mode == NULL)
|
||||
{
|
||||
if (mDisplay.Mode == NULL) {
|
||||
Status = gBS->AllocatePool(
|
||||
EfiBootServicesData,
|
||||
sizeof(EFI_GRAPHICS_OUTPUT_PROTOCOL_MODE),
|
||||
(VOID **) &mDisplay.Mode
|
||||
);
|
||||
EfiBootServicesData, sizeof(EFI_GRAPHICS_OUTPUT_PROTOCOL_MODE),
|
||||
(VOID **)&mDisplay.Mode);
|
||||
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
if (EFI_ERROR(Status)) return Status;
|
||||
if (EFI_ERROR(Status))
|
||||
return Status;
|
||||
|
||||
ZeroMem(mDisplay.Mode, sizeof(EFI_GRAPHICS_OUTPUT_PROTOCOL_MODE));
|
||||
}
|
||||
|
||||
if (mDisplay.Mode->Info == NULL)
|
||||
{
|
||||
if (mDisplay.Mode->Info == NULL) {
|
||||
Status = gBS->AllocatePool(
|
||||
EfiBootServicesData,
|
||||
sizeof(EFI_GRAPHICS_OUTPUT_MODE_INFORMATION),
|
||||
(VOID **) &mDisplay.Mode->Info
|
||||
);
|
||||
EfiBootServicesData, sizeof(EFI_GRAPHICS_OUTPUT_MODE_INFORMATION),
|
||||
(VOID **)&mDisplay.Mode->Info);
|
||||
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
if (EFI_ERROR(Status)) return Status;
|
||||
if (EFI_ERROR(Status))
|
||||
return Status;
|
||||
|
||||
ZeroMem(mDisplay.Mode->Info, sizeof(EFI_GRAPHICS_OUTPUT_MODE_INFORMATION));
|
||||
}
|
||||
@ -275,43 +222,34 @@ SimpleFbDxeInitialize
|
||||
//
|
||||
// Create the FrameBufferBltLib configuration.
|
||||
//
|
||||
Status = FrameBufferBltConfigure (
|
||||
(VOID *) (UINTN) mDisplay.Mode->FrameBufferBase,
|
||||
mDisplay.Mode->Info,
|
||||
mFrameBufferBltLibConfigure,
|
||||
&mFrameBufferBltLibConfigureSize
|
||||
);
|
||||
Status = FrameBufferBltConfigure(
|
||||
(VOID *)(UINTN)mDisplay.Mode->FrameBufferBase, mDisplay.Mode->Info,
|
||||
mFrameBufferBltLibConfigure, &mFrameBufferBltLibConfigureSize);
|
||||
if (Status == RETURN_BUFFER_TOO_SMALL) {
|
||||
mFrameBufferBltLibConfigure = AllocatePool (mFrameBufferBltLibConfigureSize);
|
||||
mFrameBufferBltLibConfigure = AllocatePool(mFrameBufferBltLibConfigureSize);
|
||||
if (mFrameBufferBltLibConfigure != NULL) {
|
||||
Status = FrameBufferBltConfigure (
|
||||
(VOID *) (UINTN) mDisplay.Mode->FrameBufferBase,
|
||||
mDisplay.Mode->Info,
|
||||
mFrameBufferBltLibConfigure,
|
||||
&mFrameBufferBltLibConfigureSize
|
||||
);
|
||||
Status = FrameBufferBltConfigure(
|
||||
(VOID *)(UINTN)mDisplay.Mode->FrameBufferBase, mDisplay.Mode->Info,
|
||||
mFrameBufferBltLibConfigure, &mFrameBufferBltLibConfigureSize);
|
||||
}
|
||||
}
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
// zhuowei: clear the screen to black
|
||||
// UEFI standard requires this, since text is white - see OvmfPkg/QemuVideoDxe/Gop.c
|
||||
ZeroMem((void*)FrameBufferAddress, FrameBufferSize);
|
||||
// UEFI standard requires this, since text is white - see
|
||||
// OvmfPkg/QemuVideoDxe/Gop.c
|
||||
ZeroMem((void *)FrameBufferAddress, FrameBufferSize);
|
||||
// hack: clear cache
|
||||
WriteBackInvalidateDataCacheRange((void*)FrameBufferAddress, FrameBufferSize);
|
||||
WriteBackInvalidateDataCacheRange(
|
||||
(void *)FrameBufferAddress, FrameBufferSize);
|
||||
// zhuowei: end
|
||||
|
||||
/* Register handle */
|
||||
Status = gBS->InstallMultipleProtocolInterfaces(
|
||||
&hUEFIDisplayHandle,
|
||||
&gEfiDevicePathProtocolGuid,
|
||||
&mDisplayDevicePath,
|
||||
&gEfiGraphicsOutputProtocolGuid,
|
||||
&mDisplay,
|
||||
NULL);
|
||||
&hUEFIDisplayHandle, &gEfiDevicePathProtocolGuid, &mDisplayDevicePath,
|
||||
&gEfiGraphicsOutputProtocolGuid, &mDisplay, NULL);
|
||||
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
return Status;
|
||||
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,16 +1,17 @@
|
||||
/** @file
|
||||
*
|
||||
* Copyright (c) 2018, Linaro Ltd. 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.
|
||||
*
|
||||
**/
|
||||
*
|
||||
* Copyright (c) 2018, Linaro Ltd. 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.
|
||||
*
|
||||
**/
|
||||
|
||||
#include <Guid/EventGroup.h>
|
||||
|
||||
@ -38,15 +39,11 @@
|
||||
|
||||
EFI_CPU_ARCH_PROTOCOL *gCpu;
|
||||
|
||||
VOID
|
||||
InitPeripherals (
|
||||
IN VOID
|
||||
)
|
||||
VOID InitPeripherals(IN VOID)
|
||||
{
|
||||
//Lock the QcomWdogTimer in a cage on certain devices
|
||||
MmioWrite32(0x17980008,0x000000);
|
||||
DEBUG ((EFI_D_WARN, "\n \v The Dog has been locked in a cage :)\v"));
|
||||
|
||||
// Lock the QcomWdogTimer in a cage on certain devices
|
||||
MmioWrite32(0x17980008, 0x000000);
|
||||
DEBUG((EFI_D_WARN, "\n \v The Dog has been locked in a cage :)\v"));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -64,28 +61,19 @@ InitPeripherals (
|
||||
@param[in] Context NULL
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
OnEndOfDxe (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
{
|
||||
}
|
||||
VOID OnEndOfDxe(IN EFI_EVENT Event, IN VOID *Context) {}
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
sdm845EntryPoint (
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
)
|
||||
sdm845EntryPoint(IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_EVENT EndOfDxeEvent;
|
||||
|
||||
Status = gBS->LocateProtocol (&gEfiCpuArchProtocolGuid, NULL, (VOID **)&gCpu);
|
||||
Status = gBS->LocateProtocol(&gEfiCpuArchProtocolGuid, NULL, (VOID **)&gCpu);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
InitPeripherals ();
|
||||
InitPeripherals();
|
||||
|
||||
//
|
||||
// Create an event belonging to the "gEfiEndOfDxeEventGroupGuid" group.
|
||||
@ -94,13 +82,8 @@ sdm845EntryPoint (
|
||||
// same group is signalled to inform about the end of the DXE phase.
|
||||
// Install the INSTALL_FDT_PROTOCOL protocol.
|
||||
//
|
||||
Status = gBS->CreateEventEx (
|
||||
EVT_NOTIFY_SIGNAL,
|
||||
TPL_CALLBACK,
|
||||
OnEndOfDxe,
|
||||
NULL,
|
||||
&gEfiEndOfDxeEventGroupGuid,
|
||||
&EndOfDxeEvent
|
||||
);
|
||||
Status = gBS->CreateEventEx(
|
||||
EVT_NOTIFY_SIGNAL, TPL_CALLBACK, OnEndOfDxe, NULL,
|
||||
&gEfiEndOfDxeEventGroupGuid, &EndOfDxeEvent);
|
||||
return Status;
|
||||
}
|
||||
|
@ -1,16 +1,17 @@
|
||||
/** @file
|
||||
*
|
||||
* Copyright (c) 2013-2017, ARM Limited. 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.
|
||||
*
|
||||
**/
|
||||
*
|
||||
* Copyright (c) 2013-2017, ARM Limited. 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.
|
||||
*
|
||||
**/
|
||||
|
||||
#ifndef __ARM_JUNO_H__
|
||||
#define __ARM_JUNO_H__
|
||||
@ -26,20 +27,23 @@
|
||||
//
|
||||
// ACPI table information used to initialize tables.
|
||||
//
|
||||
#define EFI_ACPI_ARM_OEM_ID 'A','R','M','L','T','D' // OEMID 6 bytes long
|
||||
#define EFI_ACPI_ARM_OEM_TABLE_ID SIGNATURE_64('A','R','M','-','J','U','N','O') // OEM table id 8 bytes long
|
||||
#define EFI_ACPI_ARM_OEM_ID 'A', 'R', 'M', 'L', 'T', 'D' // OEMID 6 bytes long
|
||||
#define EFI_ACPI_ARM_OEM_TABLE_ID \
|
||||
SIGNATURE_64( \
|
||||
'A', 'R', 'M', '-', 'J', 'U', 'N', 'O') // OEM table id 8 bytes long
|
||||
#define EFI_ACPI_ARM_OEM_REVISION 0x20140727
|
||||
#define EFI_ACPI_ARM_CREATOR_ID SIGNATURE_32('A','R','M',' ')
|
||||
#define EFI_ACPI_ARM_CREATOR_ID SIGNATURE_32('A', 'R', 'M', ' ')
|
||||
#define EFI_ACPI_ARM_CREATOR_REVISION 0x00000099
|
||||
|
||||
// A macro to initialise the common header part of EFI ACPI tables as defined by
|
||||
// EFI_ACPI_DESCRIPTION_HEADER structure.
|
||||
#define ARM_ACPI_HEADER(Signature, Type, Revision) { \
|
||||
#define ARM_ACPI_HEADER(Signature, Type, Revision) \
|
||||
{ \
|
||||
Signature, /* UINT32 Signature */ \
|
||||
sizeof (Type), /* UINT32 Length */ \
|
||||
sizeof(Type), /* UINT32 Length */ \
|
||||
Revision, /* UINT8 Revision */ \
|
||||
0, /* UINT8 Checksum */ \
|
||||
{ EFI_ACPI_ARM_OEM_ID }, /* UINT8 OemId[6] */ \
|
||||
{EFI_ACPI_ARM_OEM_ID}, /* UINT8 OemId[6] */ \
|
||||
EFI_ACPI_ARM_OEM_TABLE_ID, /* UINT64 OemTableId */ \
|
||||
EFI_ACPI_ARM_OEM_REVISION, /* UINT32 OemRevision */ \
|
||||
EFI_ACPI_ARM_CREATOR_ID, /* UINT32 CreatorId */ \
|
||||
|
@ -39,8 +39,7 @@ static ARM_MEMORY_REGION_DESCRIPTOR_EX gDeviceMemoryDescriptorEx[] = {
|
||||
/* HLOS1 */
|
||||
{0x81AC0000, 0x03C40000, EFI_RESOURCE_SYSTEM_MEMORY,
|
||||
SYSTEM_MEMORY_RESOURCE_ATTR_CAPABILITIES,
|
||||
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK, AddMem,
|
||||
EfiBootServicesData},
|
||||
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK, AddMem, EfiBootServicesData},
|
||||
/* MPSS_EFS */
|
||||
{0x85D00000, 0x00200000, EFI_RESOURCE_SYSTEM_MEMORY,
|
||||
SYSTEM_MEMORY_RESOURCE_ATTR_CAPABILITIES,
|
||||
@ -168,7 +167,7 @@ static ARM_MEMORY_REGION_DESCRIPTOR_EX gDeviceMemoryDescriptorEx[] = {
|
||||
{0xA0000000, 0xE0000000, EFI_RESOURCE_SYSTEM_MEMORY,
|
||||
SYSTEM_MEMORY_RESOURCE_ATTR_CAPABILITIES,
|
||||
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK, AddMem, EfiConventionalMemory},
|
||||
{0x180000000,0xFC8A0000, EFI_RESOURCE_SYSTEM_MEMORY,
|
||||
{0x180000000, 0xFC8A0000, EFI_RESOURCE_SYSTEM_MEMORY,
|
||||
SYSTEM_MEMORY_RESOURCE_ATTR_CAPABILITIES,
|
||||
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK, AddMem, EfiConventionalMemory},
|
||||
#else
|
||||
|
@ -24,7 +24,7 @@
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
|
||||
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
*/
|
||||
|
||||
#ifndef __BSL_BLOCK_UTILS_H__
|
||||
#define __BSL_BLOCK_UTILS_H__
|
||||
@ -97,14 +97,13 @@ typedef struct {
|
||||
typedef struct {
|
||||
EFI_GUID *RootDeviceType; /* GUID Selecting the root device type */
|
||||
EFI_GUID *PartitionType; /* Partition Type to match */
|
||||
CHAR8 *VolumeName; /* Mounted filesystem volume name to match */
|
||||
CHAR16 *PartitionLabel; /* Partition label to match */
|
||||
CHAR8 * VolumeName; /* Mounted filesystem volume name to match */
|
||||
CHAR16 * PartitionLabel; /* Partition label to match */
|
||||
} PartiSelectFilter;
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
GetPartitionEntry (IN EFI_HANDLE Handle,
|
||||
OUT EFI_PARTITION_ENTRY **PartEntry);
|
||||
GetPartitionEntry(IN EFI_HANDLE Handle, OUT EFI_PARTITION_ENTRY **PartEntry);
|
||||
|
||||
/**
|
||||
Returns a list of BlkIo handles based on required criteria
|
||||
@ -122,9 +121,8 @@ GetPartitionEntry (IN EFI_HANDLE Handle,
|
||||
*/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
IN PartiSelectFilter *FilterData,
|
||||
OUT HandleInfo *HandleInfoPtr,
|
||||
IN OUT UINT32 *MaxBlkIopCnt);
|
||||
GetBlkIOHandles(
|
||||
IN UINT32 SelectionAttrib, IN PartiSelectFilter *FilterData,
|
||||
OUT HandleInfo *HandleInfoPtr, IN OUT UINT32 *MaxBlkIopCnt);
|
||||
|
||||
#endif
|
@ -163,7 +163,8 @@ table in the respective position mentioned below.
|
||||
do { \
|
||||
Status = (code); \
|
||||
if (Status != EFI_SUCCESS) { \
|
||||
DEBUG ((EFI_D_ERROR, "Err: line:%d %a() status: %r\n", __LINE__, \
|
||||
DEBUG( \
|
||||
(EFI_D_ERROR, "Err: line:%d %a() status: %r\n", __LINE__, \
|
||||
__FUNCTION__, Status)); \
|
||||
return Status; \
|
||||
} \
|
||||
@ -179,10 +180,10 @@ typedef struct {
|
||||
CHAR16 Suffix[MAX_SLOT_SUFFIX_SZ];
|
||||
} Slot;
|
||||
|
||||
Slot GetCurrentSlotSuffix ();
|
||||
UINT32 GetMaxLuns ();
|
||||
VOID GetPartitionCount (UINT32 *Val);
|
||||
VOID SetMultiSlotBootVal (BOOLEAN Val);
|
||||
Slot GetCurrentSlotSuffix();
|
||||
UINT32 GetMaxLuns();
|
||||
VOID GetPartitionCount(UINT32 *Val);
|
||||
VOID SetMultiSlotBootVal(BOOLEAN Val);
|
||||
|
||||
struct PartitionEntry {
|
||||
EFI_PARTITION_ENTRY PartEntry;
|
||||
@ -195,15 +196,16 @@ struct BootPartsLinkedList {
|
||||
struct BootPartsLinkedList *Next;
|
||||
};
|
||||
|
||||
INT32 GetPartitionIndex (CHAR16 *PartitionName);
|
||||
BOOLEAN PartitionHasMultiSlot (CONST CHAR16 *Pname);
|
||||
EFI_STATUS EnumeratePartitions (VOID);
|
||||
VOID UpdatePartitionEntries (VOID);
|
||||
VOID UpdatePartitionAttributes (UINT32 UpdateType);
|
||||
BOOLEAN IsSuffixEmpty (Slot *CheckSlot);
|
||||
EFI_STATUS SetActiveSlot (Slot *NewSlot, BOOLEAN ResetSuccessBit, BOOLEAN SetSuccessBit);
|
||||
BOOLEAN IsSlotBootable (Slot *CheckSlot);
|
||||
EFI_STATUS ClearUnbootable (Slot *CheckSlot);
|
||||
UINT64 GetPartitionSize (EFI_BLOCK_IO_PROTOCOL *BlockIo);
|
||||
INT32 GetPartitionIndex(CHAR16 *PartitionName);
|
||||
BOOLEAN PartitionHasMultiSlot(CONST CHAR16 *Pname);
|
||||
EFI_STATUS EnumeratePartitions(VOID);
|
||||
VOID UpdatePartitionEntries(VOID);
|
||||
VOID UpdatePartitionAttributes(UINT32 UpdateType);
|
||||
BOOLEAN IsSuffixEmpty(Slot *CheckSlot);
|
||||
EFI_STATUS
|
||||
SetActiveSlot(Slot *NewSlot, BOOLEAN ResetSuccessBit, BOOLEAN SetSuccessBit);
|
||||
BOOLEAN IsSlotBootable(Slot *CheckSlot);
|
||||
EFI_STATUS ClearUnbootable(Slot *CheckSlot);
|
||||
UINT64 GetPartitionSize(EFI_BLOCK_IO_PROTOCOL *BlockIo);
|
||||
|
||||
#endif
|
||||
|
@ -1,4 +1,5 @@
|
||||
/* Copyright (c) 2015-2018, 2020-2021, The Linux Foundation. All rights reserved.
|
||||
/* Copyright (c) 2015-2018, 2020-2021, The Linux Foundation. All rights
|
||||
* reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are
|
||||
@ -24,18 +25,18 @@
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
|
||||
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
*/
|
||||
|
||||
#ifndef __BSL_BOARD_H__
|
||||
#define __BSL_BOARD_H__
|
||||
|
||||
#include <Uefi.h>
|
||||
#include <Library/PrintLib.h>
|
||||
#include <Library/BootSlotLib/EFICardInfo.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/PrintLib.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Library/BootSlotLib/EFICardInfo.h>
|
||||
#include <Uefi.h>
|
||||
|
||||
#define HANDLE_MAX_INFO_LIST 128
|
||||
|
||||
@ -45,11 +46,9 @@ typedef enum {
|
||||
UNKNOWN,
|
||||
} MemCardType;
|
||||
|
||||
VOID
|
||||
GetRootDeviceType (CHAR8 *StrDeviceType, UINT32 Len);
|
||||
MemCardType
|
||||
CheckRootDeviceType (VOID);
|
||||
VOID GetRootDeviceType(CHAR8 *StrDeviceType, UINT32 Len);
|
||||
MemCardType CheckRootDeviceType(VOID);
|
||||
EFI_STATUS
|
||||
UfsGetSetBootLun (UINT32 *UfsBootlun, BOOLEAN IsGet);
|
||||
UfsGetSetBootLun(UINT32 *UfsBootlun, BOOLEAN IsGet);
|
||||
|
||||
#endif
|
@ -32,10 +32,6 @@ void ResetFb(void);
|
||||
|
||||
UINTN
|
||||
EFIAPI
|
||||
SerialPortWriteCritical
|
||||
(
|
||||
IN UINT8 *Buffer,
|
||||
IN UINTN NumberOfBytes
|
||||
);
|
||||
SerialPortWriteCritical(IN UINT8 *Buffer, IN UINTN NumberOfBytes);
|
||||
|
||||
#endif
|
||||
|
@ -35,102 +35,38 @@
|
||||
#define SCALE_FACTOR 2
|
||||
|
||||
unsigned font5x12[] = {
|
||||
0x00000000, 0x00000000,
|
||||
0x08421080, 0x00020084,
|
||||
0x00052940, 0x00000000,
|
||||
0x15f52800, 0x0000295f,
|
||||
0x1c52f880, 0x00023e94,
|
||||
0x08855640, 0x0004d542,
|
||||
0x04528800, 0x000b2725,
|
||||
0x00021080, 0x00000000,
|
||||
0x04211088, 0x00821042,
|
||||
0x10841082, 0x00221108,
|
||||
0x09575480, 0x00000000,
|
||||
0x3e420000, 0x00000084,
|
||||
0x00000000, 0x00223000,
|
||||
0x3e000000, 0x00000000,
|
||||
0x00000000, 0x00471000,
|
||||
0x08844200, 0x00008442,
|
||||
0x2318a880, 0x00022a31,
|
||||
0x08429880, 0x000f9084,
|
||||
0x1108c5c0, 0x000f8444,
|
||||
0x1c4443e0, 0x00074610,
|
||||
0x14a62100, 0x000423e9,
|
||||
0x26d087e0, 0x00074610,
|
||||
0x1e10c5c0, 0x00074631,
|
||||
0x088443e0, 0x00010844,
|
||||
0x1d18c5c0, 0x00074631,
|
||||
0x3d18c5c0, 0x00074610,
|
||||
0x08e20000, 0x00471000,
|
||||
0x08e20000, 0x00223000,
|
||||
0x02222200, 0x00082082,
|
||||
0x01f00000, 0x000003e0,
|
||||
0x20820820, 0x00008888,
|
||||
0x1108c5c0, 0x00020084,
|
||||
0x2b98c5c0, 0x000f05b5,
|
||||
0x2318a880, 0x0008c63f,
|
||||
0x1d2949e0, 0x0007ca52,
|
||||
0x0210c5c0, 0x00074421,
|
||||
0x252949e0, 0x0007ca52,
|
||||
0x1e1087e0, 0x000f8421,
|
||||
0x1e1087e0, 0x00008421,
|
||||
0x0210c5c0, 0x00074639,
|
||||
0x3f18c620, 0x0008c631,
|
||||
0x084211c0, 0x00071084,
|
||||
0x10842380, 0x00032508,
|
||||
0x0654c620, 0x0008c525,
|
||||
0x02108420, 0x000f8421,
|
||||
0x2b5dc620, 0x0008c631,
|
||||
0x2b59ce20, 0x0008c739,
|
||||
0x2318c5c0, 0x00074631,
|
||||
0x1f18c5e0, 0x00008421,
|
||||
0x2318c5c0, 0x01075631,
|
||||
0x1f18c5e0, 0x0008c525,
|
||||
0x1c10c5c0, 0x00074610,
|
||||
0x084213e0, 0x00021084,
|
||||
0x2318c620, 0x00074631,
|
||||
0x1518c620, 0x0002114a,
|
||||
0x2b18c620, 0x000556b5,
|
||||
0x08a54620, 0x0008c54a,
|
||||
0x08a54620, 0x00021084,
|
||||
0x088443e0, 0x000f8442,
|
||||
0x0421084e, 0x00e10842,
|
||||
0x08210420, 0x00084108,
|
||||
0x1084210e, 0x00e42108,
|
||||
0x0008a880, 0x00000000,
|
||||
0x00000000, 0x01f00000,
|
||||
0x00000104, 0x00000000,
|
||||
0x20e00000, 0x000b663e,
|
||||
0x22f08420, 0x0007c631,
|
||||
0x22e00000, 0x00074421,
|
||||
0x23e84200, 0x000f4631,
|
||||
0x22e00000, 0x0007443f,
|
||||
0x1e214980, 0x00010842,
|
||||
0x22e00000, 0x1d187a31,
|
||||
0x26d08420, 0x0008c631,
|
||||
0x08601000, 0x00071084,
|
||||
0x10c02000, 0x0c94a108,
|
||||
0x0a908420, 0x0008a4a3,
|
||||
0x084210c0, 0x00071084,
|
||||
0x2ab00000, 0x0008d6b5,
|
||||
0x26d00000, 0x0008c631,
|
||||
0x22e00000, 0x00074631,
|
||||
0x22f00000, 0x0210be31,
|
||||
0x23e00000, 0x21087a31,
|
||||
0x26d00000, 0x00008421,
|
||||
0x22e00000, 0x00074506,
|
||||
0x04f10800, 0x00064842,
|
||||
0x23100000, 0x000b6631,
|
||||
0x23100000, 0x00022951,
|
||||
0x23100000, 0x000556b5,
|
||||
0x15100000, 0x0008a884,
|
||||
0x23100000, 0x1d185b31,
|
||||
0x11f00000, 0x000f8444,
|
||||
0x06421098, 0x01821084,
|
||||
0x08421080, 0x00021084,
|
||||
0x30421083, 0x00321084,
|
||||
0x0004d640, 0x00000000,
|
||||
0x00000000, 0x00000000,
|
||||
0x00000000, 0x00000000, 0x08421080, 0x00020084, 0x00052940, 0x00000000,
|
||||
0x15f52800, 0x0000295f, 0x1c52f880, 0x00023e94, 0x08855640, 0x0004d542,
|
||||
0x04528800, 0x000b2725, 0x00021080, 0x00000000, 0x04211088, 0x00821042,
|
||||
0x10841082, 0x00221108, 0x09575480, 0x00000000, 0x3e420000, 0x00000084,
|
||||
0x00000000, 0x00223000, 0x3e000000, 0x00000000, 0x00000000, 0x00471000,
|
||||
0x08844200, 0x00008442, 0x2318a880, 0x00022a31, 0x08429880, 0x000f9084,
|
||||
0x1108c5c0, 0x000f8444, 0x1c4443e0, 0x00074610, 0x14a62100, 0x000423e9,
|
||||
0x26d087e0, 0x00074610, 0x1e10c5c0, 0x00074631, 0x088443e0, 0x00010844,
|
||||
0x1d18c5c0, 0x00074631, 0x3d18c5c0, 0x00074610, 0x08e20000, 0x00471000,
|
||||
0x08e20000, 0x00223000, 0x02222200, 0x00082082, 0x01f00000, 0x000003e0,
|
||||
0x20820820, 0x00008888, 0x1108c5c0, 0x00020084, 0x2b98c5c0, 0x000f05b5,
|
||||
0x2318a880, 0x0008c63f, 0x1d2949e0, 0x0007ca52, 0x0210c5c0, 0x00074421,
|
||||
0x252949e0, 0x0007ca52, 0x1e1087e0, 0x000f8421, 0x1e1087e0, 0x00008421,
|
||||
0x0210c5c0, 0x00074639, 0x3f18c620, 0x0008c631, 0x084211c0, 0x00071084,
|
||||
0x10842380, 0x00032508, 0x0654c620, 0x0008c525, 0x02108420, 0x000f8421,
|
||||
0x2b5dc620, 0x0008c631, 0x2b59ce20, 0x0008c739, 0x2318c5c0, 0x00074631,
|
||||
0x1f18c5e0, 0x00008421, 0x2318c5c0, 0x01075631, 0x1f18c5e0, 0x0008c525,
|
||||
0x1c10c5c0, 0x00074610, 0x084213e0, 0x00021084, 0x2318c620, 0x00074631,
|
||||
0x1518c620, 0x0002114a, 0x2b18c620, 0x000556b5, 0x08a54620, 0x0008c54a,
|
||||
0x08a54620, 0x00021084, 0x088443e0, 0x000f8442, 0x0421084e, 0x00e10842,
|
||||
0x08210420, 0x00084108, 0x1084210e, 0x00e42108, 0x0008a880, 0x00000000,
|
||||
0x00000000, 0x01f00000, 0x00000104, 0x00000000, 0x20e00000, 0x000b663e,
|
||||
0x22f08420, 0x0007c631, 0x22e00000, 0x00074421, 0x23e84200, 0x000f4631,
|
||||
0x22e00000, 0x0007443f, 0x1e214980, 0x00010842, 0x22e00000, 0x1d187a31,
|
||||
0x26d08420, 0x0008c631, 0x08601000, 0x00071084, 0x10c02000, 0x0c94a108,
|
||||
0x0a908420, 0x0008a4a3, 0x084210c0, 0x00071084, 0x2ab00000, 0x0008d6b5,
|
||||
0x26d00000, 0x0008c631, 0x22e00000, 0x00074631, 0x22f00000, 0x0210be31,
|
||||
0x23e00000, 0x21087a31, 0x26d00000, 0x00008421, 0x22e00000, 0x00074506,
|
||||
0x04f10800, 0x00064842, 0x23100000, 0x000b6631, 0x23100000, 0x00022951,
|
||||
0x23100000, 0x000556b5, 0x15100000, 0x0008a884, 0x23100000, 0x1d185b31,
|
||||
0x11f00000, 0x000f8444, 0x06421098, 0x01821084, 0x08421080, 0x00021084,
|
||||
0x30421083, 0x00321084, 0x0004d640, 0x00000000, 0x00000000, 0x00000000,
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1,32 +1,30 @@
|
||||
/** @file
|
||||
* File managing the MMU for ARMv8 architecture
|
||||
*
|
||||
* Copyright (c) 2011-2014, ARM Limited. All rights reserved.
|
||||
* Copyright (c) 2016, Linaro Limited. All rights reserved.
|
||||
* Copyright (c) 2017, Intel Corporation. All rights reserved.<BR>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause-Patent
|
||||
*
|
||||
**/
|
||||
* File managing the MMU for ARMv8 architecture
|
||||
*
|
||||
* Copyright (c) 2011-2014, ARM Limited. All rights reserved.
|
||||
* Copyright (c) 2016, Linaro Limited. All rights reserved.
|
||||
* Copyright (c) 2017, Intel Corporation. All rights reserved.<BR>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause-Patent
|
||||
*
|
||||
**/
|
||||
|
||||
#include <Uefi.h>
|
||||
#include <Chipset/AArch64.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/CacheMaintenanceLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/ArmLib.h>
|
||||
#include <Library/ArmMmuLib.h>
|
||||
#include <Library/BaseLib.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/CacheMaintenanceLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Uefi.h>
|
||||
|
||||
// We use this index definition to define an invalid block entry
|
||||
#define TT_ATTR_INDX_INVALID ((UINT32)~0)
|
||||
|
||||
STATIC
|
||||
UINT64
|
||||
ArmMemoryAttributeToPageAttribute (
|
||||
IN ARM_MEMORY_REGION_ATTRIBUTES Attributes
|
||||
)
|
||||
ArmMemoryAttributeToPageAttribute(IN ARM_MEMORY_REGION_ATTRIBUTES Attributes)
|
||||
{
|
||||
switch (Attributes) {
|
||||
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE:
|
||||
@ -50,7 +48,7 @@ ArmMemoryAttributeToPageAttribute (
|
||||
ASSERT(0);
|
||||
case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE:
|
||||
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_DEVICE:
|
||||
if (ArmReadCurrentEL () == AARCH64_EL2)
|
||||
if (ArmReadCurrentEL() == AARCH64_EL2)
|
||||
return TT_ATTR_INDX_DEVICE_MEMORY | TT_XN_MASK;
|
||||
else
|
||||
return TT_ATTR_INDX_DEVICE_MEMORY | TT_UXN_MASK | TT_PXN_MASK;
|
||||
@ -58,9 +56,7 @@ ArmMemoryAttributeToPageAttribute (
|
||||
}
|
||||
|
||||
UINT64
|
||||
PageAttributeToGcdAttribute (
|
||||
IN UINT64 PageAttributes
|
||||
)
|
||||
PageAttributeToGcdAttribute(IN UINT64 PageAttributes)
|
||||
{
|
||||
UINT64 GcdAttributes;
|
||||
|
||||
@ -78,21 +74,25 @@ PageAttributeToGcdAttribute (
|
||||
GcdAttributes = EFI_MEMORY_WB;
|
||||
break;
|
||||
default:
|
||||
DEBUG ((EFI_D_ERROR, "PageAttributeToGcdAttribute: PageAttributes:0x%lX not supported.\n", PageAttributes));
|
||||
ASSERT (0);
|
||||
DEBUG(
|
||||
(EFI_D_ERROR,
|
||||
"PageAttributeToGcdAttribute: PageAttributes:0x%lX not supported.\n",
|
||||
PageAttributes));
|
||||
ASSERT(0);
|
||||
// The Global Coherency Domain (GCD) value is defined as a bit set.
|
||||
// Returning 0 means no attribute has been set.
|
||||
GcdAttributes = 0;
|
||||
}
|
||||
|
||||
// Determine protection attributes
|
||||
if (((PageAttributes & TT_AP_MASK) == TT_AP_NO_RO) || ((PageAttributes & TT_AP_MASK) == TT_AP_RO_RO)) {
|
||||
if (((PageAttributes & TT_AP_MASK) == TT_AP_NO_RO) ||
|
||||
((PageAttributes & TT_AP_MASK) == TT_AP_RO_RO)) {
|
||||
// Read only cases map to write-protect
|
||||
GcdAttributes |= EFI_MEMORY_RO;
|
||||
}
|
||||
|
||||
// Process eXecute Never attribute
|
||||
if ((PageAttributes & (TT_PXN_MASK | TT_UXN_MASK)) != 0 ) {
|
||||
if ((PageAttributes & (TT_PXN_MASK | TT_UXN_MASK)) != 0) {
|
||||
GcdAttributes |= EFI_MEMORY_XP;
|
||||
}
|
||||
|
||||
@ -102,12 +102,8 @@ PageAttributeToGcdAttribute (
|
||||
#define MIN_T0SZ 16
|
||||
#define BITS_PER_LEVEL 9
|
||||
|
||||
VOID
|
||||
GetRootTranslationTableInfo (
|
||||
IN UINTN T0SZ,
|
||||
OUT UINTN *TableLevel,
|
||||
OUT UINTN *TableEntryCount
|
||||
)
|
||||
VOID GetRootTranslationTableInfo(
|
||||
IN UINTN T0SZ, OUT UINTN *TableLevel, OUT UINTN *TableEntryCount)
|
||||
{
|
||||
// Get the level of the root table
|
||||
if (TableLevel) {
|
||||
@ -115,7 +111,8 @@ GetRootTranslationTableInfo (
|
||||
}
|
||||
|
||||
if (TableEntryCount) {
|
||||
*TableEntryCount = 1UL << (BITS_PER_LEVEL - (T0SZ - MIN_T0SZ) % BITS_PER_LEVEL);
|
||||
*TableEntryCount =
|
||||
1UL << (BITS_PER_LEVEL - (T0SZ - MIN_T0SZ) % BITS_PER_LEVEL);
|
||||
}
|
||||
}
|
||||
|
||||
@ -137,17 +134,13 @@ ReplaceLiveEntry (
|
||||
*/
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
LookupAddresstoRootTable (
|
||||
IN UINT64 MaxAddress,
|
||||
OUT UINTN *T0SZ,
|
||||
OUT UINTN *TableEntryCount
|
||||
)
|
||||
VOID LookupAddresstoRootTable(
|
||||
IN UINT64 MaxAddress, OUT UINTN *T0SZ, OUT UINTN *TableEntryCount)
|
||||
{
|
||||
UINTN TopBit;
|
||||
|
||||
// Check the parameters are not NULL
|
||||
ASSERT ((T0SZ != NULL) && (TableEntryCount != NULL));
|
||||
ASSERT((T0SZ != NULL) && (TableEntryCount != NULL));
|
||||
|
||||
// Look for the highest bit set in MaxAddress
|
||||
for (TopBit = 63; TopBit != 0; TopBit--) {
|
||||
@ -157,24 +150,19 @@ LookupAddresstoRootTable (
|
||||
break;
|
||||
}
|
||||
}
|
||||
ASSERT (TopBit != 0);
|
||||
ASSERT(TopBit != 0);
|
||||
|
||||
// Calculate T0SZ from the top bit of the MaxAddress
|
||||
*T0SZ = 64 - TopBit;
|
||||
|
||||
// Get the Table info from T0SZ
|
||||
GetRootTranslationTableInfo (*T0SZ, NULL, TableEntryCount);
|
||||
GetRootTranslationTableInfo(*T0SZ, NULL, TableEntryCount);
|
||||
}
|
||||
|
||||
STATIC
|
||||
UINT64*
|
||||
GetBlockEntryListFromAddress (
|
||||
IN UINT64 *RootTable,
|
||||
IN UINT64 RegionStart,
|
||||
OUT UINTN *TableLevel,
|
||||
IN OUT UINT64 *BlockEntrySize,
|
||||
OUT UINT64 **LastBlockEntry
|
||||
)
|
||||
UINT64 *GetBlockEntryListFromAddress(
|
||||
IN UINT64 *RootTable, IN UINT64 RegionStart, OUT UINTN *TableLevel,
|
||||
IN OUT UINT64 *BlockEntrySize, OUT UINT64 **LastBlockEntry)
|
||||
{
|
||||
UINTN RootTableLevel;
|
||||
UINTN RootTableEntryCount;
|
||||
@ -195,65 +183,72 @@ GetBlockEntryListFromAddress (
|
||||
|
||||
// Ensure the parameters are valid
|
||||
if (!(TableLevel && BlockEntrySize && LastBlockEntry)) {
|
||||
ASSERT_EFI_ERROR (EFI_INVALID_PARAMETER);
|
||||
ASSERT_EFI_ERROR(EFI_INVALID_PARAMETER);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Ensure the Region is aligned on 4KB boundary
|
||||
if ((RegionStart & (SIZE_4KB - 1)) != 0) {
|
||||
ASSERT_EFI_ERROR (EFI_INVALID_PARAMETER);
|
||||
ASSERT_EFI_ERROR(EFI_INVALID_PARAMETER);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Ensure the required size is aligned on 4KB boundary and not 0
|
||||
if ((*BlockEntrySize & (SIZE_4KB - 1)) != 0 || *BlockEntrySize == 0) {
|
||||
ASSERT_EFI_ERROR (EFI_INVALID_PARAMETER);
|
||||
ASSERT_EFI_ERROR(EFI_INVALID_PARAMETER);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
T0SZ = ArmGetTCR () & TCR_T0SZ_MASK;
|
||||
T0SZ = ArmGetTCR() & TCR_T0SZ_MASK;
|
||||
// Get the Table info from T0SZ
|
||||
GetRootTranslationTableInfo (T0SZ, &RootTableLevel, &RootTableEntryCount);
|
||||
GetRootTranslationTableInfo(T0SZ, &RootTableLevel, &RootTableEntryCount);
|
||||
|
||||
// If the start address is 0x0 then we use the size of the region to identify the alignment
|
||||
// If the start address is 0x0 then we use the size of the region to identify
|
||||
// the alignment
|
||||
if (RegionStart == 0) {
|
||||
// Identify the highest possible alignment for the Region Size
|
||||
BaseAddressAlignment = LowBitSet64 (*BlockEntrySize);
|
||||
} else {
|
||||
BaseAddressAlignment = LowBitSet64(*BlockEntrySize);
|
||||
}
|
||||
else {
|
||||
// Identify the highest possible alignment for the Base Address
|
||||
BaseAddressAlignment = LowBitSet64 (RegionStart);
|
||||
BaseAddressAlignment = LowBitSet64(RegionStart);
|
||||
}
|
||||
|
||||
// Identify the Page Level the RegionStart must belong to. Note that PageLevel
|
||||
// should be at least 1 since block translations are not supported at level 0
|
||||
PageLevel = MAX (3 - ((BaseAddressAlignment - 12) / 9), 1);
|
||||
PageLevel = MAX(3 - ((BaseAddressAlignment - 12) / 9), 1);
|
||||
|
||||
// If the required size is smaller than the current block size then we need to go to the page below.
|
||||
// The PageLevel was calculated on the Base Address alignment but did not take in account the alignment
|
||||
// of the allocation size
|
||||
while (*BlockEntrySize < TT_BLOCK_ENTRY_SIZE_AT_LEVEL (PageLevel)) {
|
||||
// If the required size is smaller than the current block size then we need to
|
||||
// go to the page below. The PageLevel was calculated on the Base Address
|
||||
// alignment but did not take in account the alignment of the allocation size
|
||||
while (*BlockEntrySize < TT_BLOCK_ENTRY_SIZE_AT_LEVEL(PageLevel)) {
|
||||
// It does not fit so we need to go a page level above
|
||||
PageLevel++;
|
||||
}
|
||||
|
||||
//
|
||||
// Get the Table Descriptor for the corresponding PageLevel. We need to decompose RegionStart to get appropriate entries
|
||||
// Get the Table Descriptor for the corresponding PageLevel. We need to
|
||||
// decompose RegionStart to get appropriate entries
|
||||
//
|
||||
|
||||
TranslationTable = RootTable;
|
||||
for (IndexLevel = RootTableLevel; IndexLevel <= PageLevel; IndexLevel++) {
|
||||
BlockEntry = (UINT64*)TT_GET_ENTRY_FOR_ADDRESS (TranslationTable, IndexLevel, RegionStart);
|
||||
BlockEntry = (UINT64 *)TT_GET_ENTRY_FOR_ADDRESS(
|
||||
TranslationTable, IndexLevel, RegionStart);
|
||||
|
||||
if ((IndexLevel != 3) && ((*BlockEntry & TT_TYPE_MASK) == TT_TYPE_TABLE_ENTRY)) {
|
||||
if ((IndexLevel != 3) &&
|
||||
((*BlockEntry & TT_TYPE_MASK) == TT_TYPE_TABLE_ENTRY)) {
|
||||
// Go to the next table
|
||||
TranslationTable = (UINT64*)(*BlockEntry & TT_ADDRESS_MASK_DESCRIPTION_TABLE);
|
||||
TranslationTable =
|
||||
(UINT64 *)(*BlockEntry & TT_ADDRESS_MASK_DESCRIPTION_TABLE);
|
||||
|
||||
// If we are at the last level then update the last level to next level
|
||||
if (IndexLevel == PageLevel) {
|
||||
// Enter the next level
|
||||
PageLevel++;
|
||||
}
|
||||
} else if ((*BlockEntry & TT_TYPE_MASK) == TT_TYPE_BLOCK_ENTRY) {
|
||||
}
|
||||
else if ((*BlockEntry & TT_TYPE_MASK) == TT_TYPE_BLOCK_ENTRY) {
|
||||
// If we are not at the last level then we need to split this BlockEntry
|
||||
if (IndexLevel != PageLevel) {
|
||||
// Retrieve the attributes from the block entry
|
||||
@ -267,19 +262,22 @@ GetBlockEntryListFromAddress (
|
||||
|
||||
// Get the address corresponding at this entry
|
||||
BlockEntryAddress = RegionStart;
|
||||
BlockEntryAddress = BlockEntryAddress >> TT_ADDRESS_OFFSET_AT_LEVEL(IndexLevel);
|
||||
BlockEntryAddress =
|
||||
BlockEntryAddress >> TT_ADDRESS_OFFSET_AT_LEVEL(IndexLevel);
|
||||
// Shift back to right to set zero before the effective address
|
||||
BlockEntryAddress = BlockEntryAddress << TT_ADDRESS_OFFSET_AT_LEVEL(IndexLevel);
|
||||
BlockEntryAddress = BlockEntryAddress
|
||||
<< TT_ADDRESS_OFFSET_AT_LEVEL(IndexLevel);
|
||||
|
||||
// Set the correct entry type for the next page level
|
||||
if ((IndexLevel + 1) == 3) {
|
||||
Attributes |= TT_TYPE_BLOCK_ENTRY_LEVEL3;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
Attributes |= TT_TYPE_BLOCK_ENTRY;
|
||||
}
|
||||
|
||||
// Create a new translation table
|
||||
TranslationTable = AllocatePages (1);
|
||||
TranslationTable = AllocatePages(1);
|
||||
if (TranslationTable == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
@ -287,29 +285,38 @@ GetBlockEntryListFromAddress (
|
||||
// Populate the newly created lower level table
|
||||
SubTableBlockEntry = TranslationTable;
|
||||
for (Index = 0; Index < TT_ENTRY_COUNT; Index++) {
|
||||
*SubTableBlockEntry = Attributes | (BlockEntryAddress + (Index << TT_ADDRESS_OFFSET_AT_LEVEL(IndexLevel + 1)));
|
||||
*SubTableBlockEntry =
|
||||
Attributes |
|
||||
(BlockEntryAddress +
|
||||
(Index << TT_ADDRESS_OFFSET_AT_LEVEL(IndexLevel + 1)));
|
||||
SubTableBlockEntry++;
|
||||
}
|
||||
|
||||
// Fill the BlockEntry with the new TranslationTable
|
||||
*BlockEntry = ((UINTN)TranslationTable & TT_ADDRESS_MASK_DESCRIPTION_TABLE) | TableAttributes | TT_TYPE_TABLE_ENTRY;
|
||||
*BlockEntry =
|
||||
((UINTN)TranslationTable & TT_ADDRESS_MASK_DESCRIPTION_TABLE) |
|
||||
TableAttributes | TT_TYPE_TABLE_ENTRY;
|
||||
}
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
if (IndexLevel != PageLevel) {
|
||||
//
|
||||
// Case when we have an Invalid Entry and we are at a page level above of the one targetted.
|
||||
// Case when we have an Invalid Entry and we are at a page level above
|
||||
// of the one targetted.
|
||||
//
|
||||
|
||||
// Create a new translation table
|
||||
TranslationTable = AllocatePages (1);
|
||||
TranslationTable = AllocatePages(1);
|
||||
if (TranslationTable == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ZeroMem (TranslationTable, TT_ENTRY_COUNT * sizeof(UINT64));
|
||||
ZeroMem(TranslationTable, TT_ENTRY_COUNT * sizeof(UINT64));
|
||||
|
||||
// Fill the new BlockEntry with the TranslationTable
|
||||
*BlockEntry = ((UINTN)TranslationTable & TT_ADDRESS_MASK_DESCRIPTION_TABLE) | TT_TYPE_TABLE_ENTRY;
|
||||
*BlockEntry =
|
||||
((UINTN)TranslationTable & TT_ADDRESS_MASK_DESCRIPTION_TABLE) |
|
||||
TT_TYPE_TABLE_ENTRY;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -317,12 +324,15 @@ GetBlockEntryListFromAddress (
|
||||
// Expose the found PageLevel to the caller
|
||||
*TableLevel = PageLevel;
|
||||
|
||||
// Now, we have the Table Level we can get the Block Size associated to this table
|
||||
*BlockEntrySize = TT_BLOCK_ENTRY_SIZE_AT_LEVEL (PageLevel);
|
||||
// Now, we have the Table Level we can get the Block Size associated to this
|
||||
// table
|
||||
*BlockEntrySize = TT_BLOCK_ENTRY_SIZE_AT_LEVEL(PageLevel);
|
||||
|
||||
// The last block of the root table depends on the number of entry in this table,
|
||||
// otherwise it is always the (TT_ENTRY_COUNT - 1)th entry in the table.
|
||||
*LastBlockEntry = TT_LAST_BLOCK_ADDRESS(TranslationTable,
|
||||
// The last block of the root table depends on the number of entry in this
|
||||
// table, otherwise it is always the (TT_ENTRY_COUNT - 1)th entry in the
|
||||
// table.
|
||||
*LastBlockEntry = TT_LAST_BLOCK_ADDRESS(
|
||||
TranslationTable,
|
||||
(PageLevel == RootTableLevel) ? RootTableEntryCount : TT_ENTRY_COUNT);
|
||||
|
||||
return BlockEntry;
|
||||
@ -330,13 +340,9 @@ GetBlockEntryListFromAddress (
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
UpdateRegionMapping (
|
||||
IN UINT64 *RootTable,
|
||||
IN UINT64 RegionStart,
|
||||
IN UINT64 RegionLength,
|
||||
IN UINT64 Attributes,
|
||||
IN UINT64 BlockEntryMask
|
||||
)
|
||||
UpdateRegionMapping(
|
||||
IN UINT64 *RootTable, IN UINT64 RegionStart, IN UINT64 RegionLength,
|
||||
IN UINT64 Attributes, IN UINT64 BlockEntryMask)
|
||||
{
|
||||
UINT32 Type;
|
||||
UINT64 *BlockEntry;
|
||||
@ -346,32 +352,37 @@ UpdateRegionMapping (
|
||||
|
||||
// Ensure the Length is aligned on 4KB boundary
|
||||
if ((RegionLength == 0) || ((RegionLength & (SIZE_4KB - 1)) != 0)) {
|
||||
ASSERT_EFI_ERROR (EFI_INVALID_PARAMETER);
|
||||
ASSERT_EFI_ERROR(EFI_INVALID_PARAMETER);
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
do {
|
||||
// Get the first Block Entry that matches the Virtual Address and also the information on the Table Descriptor
|
||||
// such as the size of the Block Entry and the address of the last BlockEntry of the Table Descriptor
|
||||
// Get the first Block Entry that matches the Virtual Address and also the
|
||||
// information on the Table Descriptor such as the size of the Block Entry
|
||||
// and the address of the last BlockEntry of the Table Descriptor
|
||||
BlockEntrySize = RegionLength;
|
||||
BlockEntry = GetBlockEntryListFromAddress (RootTable, RegionStart, &TableLevel, &BlockEntrySize, &LastBlockEntry);
|
||||
BlockEntry = GetBlockEntryListFromAddress(
|
||||
RootTable, RegionStart, &TableLevel, &BlockEntrySize, &LastBlockEntry);
|
||||
if (BlockEntry == NULL) {
|
||||
// GetBlockEntryListFromAddress() return NULL when it fails to allocate new pages from the Translation Tables
|
||||
// GetBlockEntryListFromAddress() return NULL when it fails to allocate
|
||||
// new pages from the Translation Tables
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
if (TableLevel != 3) {
|
||||
Type = TT_TYPE_BLOCK_ENTRY;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
Type = TT_TYPE_BLOCK_ENTRY_LEVEL3;
|
||||
}
|
||||
|
||||
do {
|
||||
// Fill the Block Entry with attribute and output block address
|
||||
*BlockEntry &= BlockEntryMask;
|
||||
*BlockEntry |= (RegionStart & TT_ADDRESS_MASK_BLOCK_ENTRY) | Attributes | Type;
|
||||
*BlockEntry |=
|
||||
(RegionStart & TT_ADDRESS_MASK_BLOCK_ENTRY) | Attributes | Type;
|
||||
|
||||
ArmUpdateTranslationTableEntry (BlockEntry, (VOID *)RegionStart);
|
||||
ArmUpdateTranslationTableEntry(BlockEntry, (VOID *)RegionStart);
|
||||
|
||||
// Go to the next BlockEntry
|
||||
RegionStart += BlockEntrySize;
|
||||
@ -384,7 +395,8 @@ UpdateRegionMapping (
|
||||
(*BlockEntry & TT_TYPE_MASK) == TT_TYPE_TABLE_ENTRY) {
|
||||
break;
|
||||
}
|
||||
} while ((RegionLength >= BlockEntrySize) && (BlockEntry <= LastBlockEntry));
|
||||
} while ((RegionLength >= BlockEntrySize) &&
|
||||
(BlockEntry <= LastBlockEntry));
|
||||
} while (RegionLength != 0);
|
||||
|
||||
return EFI_SUCCESS;
|
||||
@ -392,25 +404,17 @@ UpdateRegionMapping (
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
FillTranslationTable (
|
||||
IN UINT64 *RootTable,
|
||||
IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryRegion
|
||||
)
|
||||
FillTranslationTable(
|
||||
IN UINT64 *RootTable, IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryRegion)
|
||||
{
|
||||
return UpdateRegionMapping (
|
||||
RootTable,
|
||||
MemoryRegion->VirtualBase,
|
||||
MemoryRegion->Length,
|
||||
ArmMemoryAttributeToPageAttribute (MemoryRegion->Attributes) | TT_AF,
|
||||
0
|
||||
);
|
||||
return UpdateRegionMapping(
|
||||
RootTable, MemoryRegion->VirtualBase, MemoryRegion->Length,
|
||||
ArmMemoryAttributeToPageAttribute(MemoryRegion->Attributes) | TT_AF, 0);
|
||||
}
|
||||
|
||||
STATIC
|
||||
UINT64
|
||||
GcdAttributeToPageAttribute (
|
||||
IN UINT64 GcdAttributes
|
||||
)
|
||||
GcdAttributeToPageAttribute(IN UINT64 GcdAttributes)
|
||||
{
|
||||
UINT64 PageAttributes;
|
||||
|
||||
@ -434,9 +438,10 @@ GcdAttributeToPageAttribute (
|
||||
|
||||
if ((GcdAttributes & EFI_MEMORY_XP) != 0 ||
|
||||
(GcdAttributes & EFI_MEMORY_CACHETYPE_MASK) == EFI_MEMORY_UC) {
|
||||
if (ArmReadCurrentEL () == AARCH64_EL2) {
|
||||
if (ArmReadCurrentEL() == AARCH64_EL2) {
|
||||
PageAttributes |= TT_XN_MASK;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
PageAttributes |= TT_UXN_MASK | TT_PXN_MASK;
|
||||
}
|
||||
}
|
||||
@ -449,18 +454,15 @@ GcdAttributeToPageAttribute (
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmSetMemoryAttributes (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length,
|
||||
IN UINT64 Attributes
|
||||
)
|
||||
ArmSetMemoryAttributes(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, IN UINT64 Attributes)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINT64 *TranslationTable;
|
||||
UINT64 * TranslationTable;
|
||||
UINT64 PageAttributes;
|
||||
UINT64 PageAttributeMask;
|
||||
|
||||
PageAttributes = GcdAttributeToPageAttribute (Attributes);
|
||||
PageAttributes = GcdAttributeToPageAttribute(Attributes);
|
||||
PageAttributeMask = 0;
|
||||
|
||||
if ((Attributes & EFI_MEMORY_CACHETYPE_MASK) == 0) {
|
||||
@ -469,19 +471,15 @@ ArmSetMemoryAttributes (
|
||||
// permissions only.
|
||||
//
|
||||
PageAttributes &= TT_AP_MASK | TT_UXN_MASK | TT_PXN_MASK;
|
||||
PageAttributeMask = ~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AP_MASK |
|
||||
TT_PXN_MASK | TT_XN_MASK);
|
||||
PageAttributeMask =
|
||||
~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AP_MASK | TT_PXN_MASK | TT_XN_MASK);
|
||||
}
|
||||
|
||||
TranslationTable = ArmGetTTBR0BaseAddress ();
|
||||
TranslationTable = ArmGetTTBR0BaseAddress();
|
||||
|
||||
Status = UpdateRegionMapping (
|
||||
TranslationTable,
|
||||
BaseAddress,
|
||||
Length,
|
||||
PageAttributes,
|
||||
PageAttributeMask);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = UpdateRegionMapping(
|
||||
TranslationTable, BaseAddress, Length, PageAttributes, PageAttributeMask);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
@ -490,20 +488,18 @@ ArmSetMemoryAttributes (
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
SetMemoryRegionAttribute (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length,
|
||||
IN UINT64 Attributes,
|
||||
IN UINT64 BlockEntryMask
|
||||
)
|
||||
SetMemoryRegionAttribute(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, IN UINT64 Attributes,
|
||||
IN UINT64 BlockEntryMask)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINT64 *RootTable;
|
||||
UINT64 * RootTable;
|
||||
|
||||
RootTable = ArmGetTTBR0BaseAddress ();
|
||||
RootTable = ArmGetTTBR0BaseAddress();
|
||||
|
||||
Status = UpdateRegionMapping (RootTable, BaseAddress, Length, Attributes, BlockEntryMask);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = UpdateRegionMapping(
|
||||
RootTable, BaseAddress, Length, Attributes, BlockEntryMask);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
@ -511,79 +507,58 @@ SetMemoryRegionAttribute (
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmSetMemoryRegionNoExec (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmSetMemoryRegionNoExec(IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
UINT64 Val;
|
||||
|
||||
if (ArmReadCurrentEL () == AARCH64_EL1) {
|
||||
if (ArmReadCurrentEL() == AARCH64_EL1) {
|
||||
Val = TT_PXN_MASK | TT_UXN_MASK;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
Val = TT_XN_MASK;
|
||||
}
|
||||
|
||||
return SetMemoryRegionAttribute (
|
||||
BaseAddress,
|
||||
Length,
|
||||
Val,
|
||||
~TT_ADDRESS_MASK_BLOCK_ENTRY);
|
||||
return SetMemoryRegionAttribute(
|
||||
BaseAddress, Length, Val, ~TT_ADDRESS_MASK_BLOCK_ENTRY);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmClearMemoryRegionNoExec (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmClearMemoryRegionNoExec(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
UINT64 Mask;
|
||||
|
||||
// XN maps to UXN in the EL1&0 translation regime
|
||||
Mask = ~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_PXN_MASK | TT_XN_MASK);
|
||||
|
||||
return SetMemoryRegionAttribute (
|
||||
BaseAddress,
|
||||
Length,
|
||||
0,
|
||||
Mask);
|
||||
return SetMemoryRegionAttribute(BaseAddress, Length, 0, Mask);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmSetMemoryRegionReadOnly (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmSetMemoryRegionReadOnly(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
return SetMemoryRegionAttribute (
|
||||
BaseAddress,
|
||||
Length,
|
||||
TT_AP_RO_RO,
|
||||
~TT_ADDRESS_MASK_BLOCK_ENTRY);
|
||||
return SetMemoryRegionAttribute(
|
||||
BaseAddress, Length, TT_AP_RO_RO, ~TT_ADDRESS_MASK_BLOCK_ENTRY);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmClearMemoryRegionReadOnly (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmClearMemoryRegionReadOnly(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
return SetMemoryRegionAttribute (
|
||||
BaseAddress,
|
||||
Length,
|
||||
TT_AP_RW_RW,
|
||||
return SetMemoryRegionAttribute(
|
||||
BaseAddress, Length, TT_AP_RW_RW,
|
||||
~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AP_MASK));
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
ArmConfigureMmu (
|
||||
ArmConfigureMmu(
|
||||
IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryTable,
|
||||
OUT VOID **TranslationTableBase OPTIONAL,
|
||||
OUT UINTN *TranslationTableSize OPTIONAL
|
||||
)
|
||||
OUT UINTN *TranslationTableSize OPTIONAL)
|
||||
{
|
||||
VOID* TranslationTable;
|
||||
VOID * TranslationTable;
|
||||
UINT32 TranslationTableAttribute;
|
||||
UINT64 MaxAddress;
|
||||
UINTN T0SZ;
|
||||
@ -591,8 +566,8 @@ ArmConfigureMmu (
|
||||
UINT64 TCR;
|
||||
EFI_STATUS Status;
|
||||
|
||||
if(MemoryTable == NULL) {
|
||||
ASSERT (MemoryTable != NULL);
|
||||
if (MemoryTable == NULL) {
|
||||
ASSERT(MemoryTable != NULL);
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
@ -603,63 +578,86 @@ ArmConfigureMmu (
|
||||
// into account the architectural limitations that result from UEFI's
|
||||
// use of 4 KB pages.
|
||||
//
|
||||
MaxAddress = MIN (LShiftU64 (1ULL, ArmGetPhysicalAddressBits ()) - 1,
|
||||
MAX_ALLOC_ADDRESS);
|
||||
MaxAddress =
|
||||
MIN(LShiftU64(1ULL, ArmGetPhysicalAddressBits()) - 1, MAX_ALLOC_ADDRESS);
|
||||
|
||||
// Lookup the Table Level to get the information
|
||||
LookupAddresstoRootTable (MaxAddress, &T0SZ, &RootTableEntryCount);
|
||||
LookupAddresstoRootTable(MaxAddress, &T0SZ, &RootTableEntryCount);
|
||||
|
||||
//
|
||||
// Set TCR that allows us to retrieve T0SZ in the subsequent functions
|
||||
//
|
||||
// Ideally we will be running at EL2, but should support EL1 as well.
|
||||
// UEFI should not run at EL3.
|
||||
if (ArmReadCurrentEL () == AARCH64_EL2) {
|
||||
//Note: Bits 23 and 31 are reserved(RES1) bits in TCR_EL2
|
||||
if (ArmReadCurrentEL() == AARCH64_EL2) {
|
||||
// Note: Bits 23 and 31 are reserved(RES1) bits in TCR_EL2
|
||||
TCR = T0SZ | (1UL << 31) | (1UL << 23) | TCR_TG0_4KB;
|
||||
|
||||
// Set the Physical Address Size using MaxAddress
|
||||
if (MaxAddress < SIZE_4GB) {
|
||||
TCR |= TCR_PS_4GB;
|
||||
} else if (MaxAddress < SIZE_64GB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_64GB) {
|
||||
TCR |= TCR_PS_64GB;
|
||||
} else if (MaxAddress < SIZE_1TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_1TB) {
|
||||
TCR |= TCR_PS_1TB;
|
||||
} else if (MaxAddress < SIZE_4TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_4TB) {
|
||||
TCR |= TCR_PS_4TB;
|
||||
} else if (MaxAddress < SIZE_16TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_16TB) {
|
||||
TCR |= TCR_PS_16TB;
|
||||
} else if (MaxAddress < SIZE_256TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_256TB) {
|
||||
TCR |= TCR_PS_256TB;
|
||||
} else {
|
||||
DEBUG ((EFI_D_ERROR, "ArmConfigureMmu: The MaxAddress 0x%lX is not supported by this MMU configuration.\n", MaxAddress));
|
||||
ASSERT (0); // Bigger than 48-bit memory space are not supported
|
||||
}
|
||||
else {
|
||||
DEBUG(
|
||||
(EFI_D_ERROR,
|
||||
"ArmConfigureMmu: The MaxAddress 0x%lX is not supported by this MMU "
|
||||
"configuration.\n",
|
||||
MaxAddress));
|
||||
ASSERT(0); // Bigger than 48-bit memory space are not supported
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
} else if (ArmReadCurrentEL () == AARCH64_EL1) {
|
||||
// Due to Cortex-A57 erratum #822227 we must set TG1[1] == 1, regardless of EPD1.
|
||||
}
|
||||
else if (ArmReadCurrentEL() == AARCH64_EL1) {
|
||||
// Due to Cortex-A57 erratum #822227 we must set TG1[1] == 1, regardless of
|
||||
// EPD1.
|
||||
TCR = T0SZ | TCR_TG0_4KB | TCR_TG1_4KB | TCR_EPD1;
|
||||
|
||||
// Set the Physical Address Size using MaxAddress
|
||||
if (MaxAddress < SIZE_4GB) {
|
||||
TCR |= TCR_IPS_4GB;
|
||||
} else if (MaxAddress < SIZE_64GB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_64GB) {
|
||||
TCR |= TCR_IPS_64GB;
|
||||
} else if (MaxAddress < SIZE_1TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_1TB) {
|
||||
TCR |= TCR_IPS_1TB;
|
||||
} else if (MaxAddress < SIZE_4TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_4TB) {
|
||||
TCR |= TCR_IPS_4TB;
|
||||
} else if (MaxAddress < SIZE_16TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_16TB) {
|
||||
TCR |= TCR_IPS_16TB;
|
||||
} else if (MaxAddress < SIZE_256TB) {
|
||||
}
|
||||
else if (MaxAddress < SIZE_256TB) {
|
||||
TCR |= TCR_IPS_256TB;
|
||||
} else {
|
||||
DEBUG ((EFI_D_ERROR, "ArmConfigureMmu: The MaxAddress 0x%lX is not supported by this MMU configuration.\n", MaxAddress));
|
||||
ASSERT (0); // Bigger than 48-bit memory space are not supported
|
||||
}
|
||||
else {
|
||||
DEBUG(
|
||||
(EFI_D_ERROR,
|
||||
"ArmConfigureMmu: The MaxAddress 0x%lX is not supported by this MMU "
|
||||
"configuration.\n",
|
||||
MaxAddress));
|
||||
ASSERT(0); // Bigger than 48-bit memory space are not supported
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
} else {
|
||||
ASSERT (0); // UEFI is only expected to run at EL2 and EL1, not EL3.
|
||||
}
|
||||
else {
|
||||
ASSERT(0); // UEFI is only expected to run at EL2 and EL1, not EL3.
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
|
||||
@ -672,22 +670,22 @@ ArmConfigureMmu (
|
||||
// assert below that that matches the attributes we use for CPU accesses to
|
||||
// the region.
|
||||
//
|
||||
TCR |= TCR_SH_INNER_SHAREABLE |
|
||||
TCR_RGN_OUTER_WRITE_BACK_ALLOC |
|
||||
TCR |= TCR_SH_INNER_SHAREABLE | TCR_RGN_OUTER_WRITE_BACK_ALLOC |
|
||||
TCR_RGN_INNER_WRITE_BACK_ALLOC;
|
||||
|
||||
// Set TCR
|
||||
ArmSetTCR (TCR);
|
||||
ArmSetTCR(TCR);
|
||||
|
||||
// Allocate pages for translation table
|
||||
TranslationTable = AllocatePages (1);
|
||||
TranslationTable = AllocatePages(1);
|
||||
if (TranslationTable == NULL) {
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
}
|
||||
// We set TTBR0 just after allocating the table to retrieve its location from the subsequent
|
||||
// functions without needing to pass this value across the functions. The MMU is only enabled
|
||||
// after the translation tables are populated.
|
||||
ArmSetTTBR0 (TranslationTable);
|
||||
// We set TTBR0 just after allocating the table to retrieve its location from
|
||||
// the subsequent functions without needing to pass this value across the
|
||||
// functions. The MMU is only enabled after the translation tables are
|
||||
// populated.
|
||||
ArmSetTTBR0(TranslationTable);
|
||||
|
||||
if (TranslationTableBase != NULL) {
|
||||
*TranslationTableBase = TranslationTable;
|
||||
@ -697,67 +695,76 @@ ArmConfigureMmu (
|
||||
*TranslationTableSize = RootTableEntryCount * sizeof(UINT64);
|
||||
}
|
||||
|
||||
ZeroMem (TranslationTable, RootTableEntryCount * sizeof(UINT64));
|
||||
ZeroMem(TranslationTable, RootTableEntryCount * sizeof(UINT64));
|
||||
|
||||
// Disable MMU and caches. ArmDisableMmu() also invalidates the TLBs
|
||||
ArmDisableMmu ();
|
||||
ArmDisableDataCache ();
|
||||
ArmDisableInstructionCache ();
|
||||
ArmDisableMmu();
|
||||
ArmDisableDataCache();
|
||||
ArmDisableInstructionCache();
|
||||
|
||||
// Make sure nothing sneaked into the cache
|
||||
ArmCleanInvalidateDataCache ();
|
||||
ArmInvalidateInstructionCache ();
|
||||
ArmCleanInvalidateDataCache();
|
||||
ArmInvalidateInstructionCache();
|
||||
|
||||
TranslationTableAttribute = TT_ATTR_INDX_INVALID;
|
||||
UINTN idx = 0;
|
||||
while (MemoryTable->Length != 0) {
|
||||
if ((MemoryTable->Length & (SIZE_4KB - 1)) != 0) {
|
||||
DEBUG ((DEBUG_ERROR, "bruh: %d\n", idx));
|
||||
DEBUG((DEBUG_ERROR, "bruh: %d\n", idx));
|
||||
}
|
||||
|
||||
DEBUG_CODE_BEGIN ();
|
||||
DEBUG_CODE_BEGIN();
|
||||
// Find the memory attribute for the Translation Table
|
||||
if ((UINTN)TranslationTable >= MemoryTable->PhysicalBase &&
|
||||
(UINTN)TranslationTable + EFI_PAGE_SIZE <= MemoryTable->PhysicalBase +
|
||||
MemoryTable->Length) {
|
||||
(UINTN)TranslationTable + EFI_PAGE_SIZE <=
|
||||
MemoryTable->PhysicalBase + MemoryTable->Length) {
|
||||
TranslationTableAttribute = MemoryTable->Attributes;
|
||||
}
|
||||
DEBUG_CODE_END ();
|
||||
DEBUG_CODE_END();
|
||||
|
||||
Status = FillTranslationTable (TranslationTable, MemoryTable);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = FillTranslationTable(TranslationTable, MemoryTable);
|
||||
if (EFI_ERROR(Status)) {
|
||||
goto FREE_TRANSLATION_TABLE;
|
||||
}
|
||||
MemoryTable++;
|
||||
idx++;
|
||||
}
|
||||
|
||||
ASSERT (TranslationTableAttribute == ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK ||
|
||||
TranslationTableAttribute == ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK);
|
||||
ASSERT(
|
||||
TranslationTableAttribute == ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK ||
|
||||
TranslationTableAttribute ==
|
||||
ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK);
|
||||
|
||||
ArmSetMAIR (MAIR_ATTR(TT_ATTR_INDX_DEVICE_MEMORY, MAIR_ATTR_DEVICE_MEMORY) | // mapped to EFI_MEMORY_UC
|
||||
MAIR_ATTR(TT_ATTR_INDX_MEMORY_NON_CACHEABLE, MAIR_ATTR_NORMAL_MEMORY_NON_CACHEABLE) | // mapped to EFI_MEMORY_WC
|
||||
MAIR_ATTR(TT_ATTR_INDX_MEMORY_WRITE_THROUGH, MAIR_ATTR_NORMAL_MEMORY_WRITE_THROUGH) | // mapped to EFI_MEMORY_WT
|
||||
MAIR_ATTR(TT_ATTR_INDX_MEMORY_WRITE_BACK, MAIR_ATTR_NORMAL_MEMORY_WRITE_BACK)); // mapped to EFI_MEMORY_WB
|
||||
ArmSetMAIR(
|
||||
MAIR_ATTR(
|
||||
TT_ATTR_INDX_DEVICE_MEMORY,
|
||||
MAIR_ATTR_DEVICE_MEMORY) | // mapped to EFI_MEMORY_UC
|
||||
MAIR_ATTR(
|
||||
TT_ATTR_INDX_MEMORY_NON_CACHEABLE,
|
||||
MAIR_ATTR_NORMAL_MEMORY_NON_CACHEABLE) | // mapped to EFI_MEMORY_WC
|
||||
MAIR_ATTR(
|
||||
TT_ATTR_INDX_MEMORY_WRITE_THROUGH,
|
||||
MAIR_ATTR_NORMAL_MEMORY_WRITE_THROUGH) | // mapped to EFI_MEMORY_WT
|
||||
MAIR_ATTR(
|
||||
TT_ATTR_INDX_MEMORY_WRITE_BACK,
|
||||
MAIR_ATTR_NORMAL_MEMORY_WRITE_BACK)); // mapped to EFI_MEMORY_WB
|
||||
|
||||
ArmDisableAlignmentCheck ();
|
||||
ArmEnableStackAlignmentCheck ();
|
||||
ArmEnableInstructionCache ();
|
||||
ArmEnableDataCache ();
|
||||
ArmDisableAlignmentCheck();
|
||||
ArmEnableStackAlignmentCheck();
|
||||
ArmEnableInstructionCache();
|
||||
ArmEnableDataCache();
|
||||
|
||||
ArmEnableMmu ();
|
||||
ArmEnableMmu();
|
||||
return EFI_SUCCESS;
|
||||
|
||||
FREE_TRANSLATION_TABLE:
|
||||
FreePages (TranslationTable, 1);
|
||||
FreePages(TranslationTable, 1);
|
||||
return Status;
|
||||
}
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
ArmMmuBaseLibConstructor (
|
||||
VOID
|
||||
)
|
||||
ArmMmuBaseLibConstructor(VOID)
|
||||
{
|
||||
extern UINT32 ArmReplaceLiveTranslationEntrySize;
|
||||
|
||||
@ -765,8 +772,8 @@ ArmMmuBaseLibConstructor (
|
||||
// The ArmReplaceLiveTranslationEntry () helper function may be invoked
|
||||
// with the MMU off so we have to ensure that it gets cleaned to the PoC
|
||||
//
|
||||
WriteBackDataCacheRange (ArmReplaceLiveTranslationEntry,
|
||||
ArmReplaceLiveTranslationEntrySize);
|
||||
WriteBackDataCacheRange(
|
||||
ArmReplaceLiveTranslationEntry, ArmReplaceLiveTranslationEntrySize);
|
||||
|
||||
return RETURN_SUCCESS;
|
||||
}
|
||||
|
@ -15,20 +15,18 @@
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
ArmMmuPeiLibConstructor (
|
||||
IN EFI_PEI_FILE_HANDLE FileHandle,
|
||||
IN CONST EFI_PEI_SERVICES **PeiServices
|
||||
)
|
||||
ArmMmuPeiLibConstructor(
|
||||
IN EFI_PEI_FILE_HANDLE FileHandle, IN CONST EFI_PEI_SERVICES **PeiServices)
|
||||
{
|
||||
extern UINT32 ArmReplaceLiveTranslationEntrySize;
|
||||
|
||||
EFI_FV_FILE_INFO FileInfo;
|
||||
EFI_STATUS Status;
|
||||
|
||||
ASSERT (FileHandle != NULL);
|
||||
ASSERT(FileHandle != NULL);
|
||||
|
||||
Status = (*PeiServices)->FfsGetFileInfo (FileHandle, &FileInfo);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
Status = (*PeiServices)->FfsGetFileInfo(FileHandle, &FileInfo);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
//
|
||||
// Some platforms do not cope very well with cache maintenance being
|
||||
@ -39,16 +37,20 @@ ArmMmuPeiLibConstructor (
|
||||
//
|
||||
if ((UINTN)FileInfo.Buffer <= (UINTN)ArmReplaceLiveTranslationEntry &&
|
||||
((UINTN)FileInfo.Buffer + FileInfo.BufferSize >=
|
||||
(UINTN)ArmReplaceLiveTranslationEntry + ArmReplaceLiveTranslationEntrySize)) {
|
||||
DEBUG ((EFI_D_INFO, "ArmMmuLib: skipping cache maintenance on XIP PEIM\n"));
|
||||
} else {
|
||||
DEBUG ((EFI_D_INFO, "ArmMmuLib: performing cache maintenance on shadowed PEIM\n"));
|
||||
(UINTN)ArmReplaceLiveTranslationEntry +
|
||||
ArmReplaceLiveTranslationEntrySize)) {
|
||||
DEBUG((EFI_D_INFO, "ArmMmuLib: skipping cache maintenance on XIP PEIM\n"));
|
||||
}
|
||||
else {
|
||||
DEBUG(
|
||||
(EFI_D_INFO,
|
||||
"ArmMmuLib: performing cache maintenance on shadowed PEIM\n"));
|
||||
//
|
||||
// The ArmReplaceLiveTranslationEntry () helper function may be invoked
|
||||
// with the MMU off so we have to ensure that it gets cleaned to the PoC
|
||||
//
|
||||
WriteBackDataCacheRange (ArmReplaceLiveTranslationEntry,
|
||||
ArmReplaceLiveTranslationEntrySize);
|
||||
WriteBackDataCacheRange(
|
||||
ArmReplaceLiveTranslationEntry, ArmReplaceLiveTranslationEntrySize);
|
||||
}
|
||||
|
||||
return RETURN_SUCCESS;
|
||||
|
@ -1,21 +1,21 @@
|
||||
/** @file
|
||||
* File managing the MMU for ARMv7 architecture
|
||||
*
|
||||
* Copyright (c) 2011-2016, ARM Limited. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause-Patent
|
||||
*
|
||||
**/
|
||||
* File managing the MMU for ARMv7 architecture
|
||||
*
|
||||
* Copyright (c) 2011-2016, ARM Limited. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause-Patent
|
||||
*
|
||||
**/
|
||||
|
||||
#include <Uefi.h>
|
||||
#include <Chipset/ArmV7.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/CacheMaintenanceLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/ArmLib.h>
|
||||
#include <Library/BaseLib.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/CacheMaintenanceLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/PcdLib.h>
|
||||
#include <Uefi.h>
|
||||
|
||||
#define ID_MMFR0_SHARELVL_SHIFT 12
|
||||
#define ID_MMFR0_SHARELVL_MASK 0xf
|
||||
@ -33,53 +33,44 @@
|
||||
|
||||
#define __EFI_MEMORY_RWX 0 // no restrictions
|
||||
|
||||
#define CACHE_ATTRIBUTE_MASK (EFI_MEMORY_UC | \
|
||||
EFI_MEMORY_WC | \
|
||||
EFI_MEMORY_WT | \
|
||||
EFI_MEMORY_WB | \
|
||||
EFI_MEMORY_UCE | \
|
||||
EFI_MEMORY_WP)
|
||||
#define CACHE_ATTRIBUTE_MASK \
|
||||
(EFI_MEMORY_UC | EFI_MEMORY_WC | EFI_MEMORY_WT | EFI_MEMORY_WB | \
|
||||
EFI_MEMORY_UCE | EFI_MEMORY_WP)
|
||||
|
||||
UINTN
|
||||
EFIAPI
|
||||
ArmReadIdMmfr0 (
|
||||
VOID
|
||||
);
|
||||
ArmReadIdMmfr0(VOID);
|
||||
|
||||
BOOLEAN
|
||||
EFIAPI
|
||||
ArmHasMpExtensions (
|
||||
VOID
|
||||
);
|
||||
ArmHasMpExtensions(VOID);
|
||||
|
||||
UINT32
|
||||
ConvertSectionAttributesToPageAttributes (
|
||||
IN UINT32 SectionAttributes,
|
||||
IN BOOLEAN IsLargePage
|
||||
)
|
||||
ConvertSectionAttributesToPageAttributes(
|
||||
IN UINT32 SectionAttributes, IN BOOLEAN IsLargePage)
|
||||
{
|
||||
UINT32 PageAttributes;
|
||||
|
||||
PageAttributes = 0;
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY (SectionAttributes, IsLargePage);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_AP (SectionAttributes);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_XN (SectionAttributes, IsLargePage);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_NG (SectionAttributes);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_S (SectionAttributes);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY(
|
||||
SectionAttributes, IsLargePage);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_AP(SectionAttributes);
|
||||
PageAttributes |=
|
||||
TT_DESCRIPTOR_CONVERT_TO_PAGE_XN(SectionAttributes, IsLargePage);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_NG(SectionAttributes);
|
||||
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_S(SectionAttributes);
|
||||
|
||||
return PageAttributes;
|
||||
}
|
||||
|
||||
STATIC
|
||||
BOOLEAN
|
||||
PreferNonshareableMemory (
|
||||
VOID
|
||||
)
|
||||
PreferNonshareableMemory(VOID)
|
||||
{
|
||||
UINTN Mmfr;
|
||||
UINTN Val;
|
||||
|
||||
if (FeaturePcdGet (PcdNormalMemoryNonshareableOverride)) {
|
||||
if (FeaturePcdGet(PcdNormalMemoryNonshareableOverride)) {
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
@ -88,7 +79,7 @@ PreferNonshareableMemory (
|
||||
// by default to map normal memory) is implemented with hardware coherency
|
||||
// support. Otherwise, revert to mapping as non-shareable.
|
||||
//
|
||||
Mmfr = ArmReadIdMmfr0 ();
|
||||
Mmfr = ArmReadIdMmfr0();
|
||||
switch ((Mmfr >> ID_MMFR0_SHARELVL_SHIFT) & ID_MMFR0_SHARELVL_MASK) {
|
||||
case ID_MMFR0_SHARELVL_ONE:
|
||||
// one level of shareability
|
||||
@ -100,22 +91,18 @@ PreferNonshareableMemory (
|
||||
break;
|
||||
default:
|
||||
// unexpected value -> shareable is the safe option
|
||||
ASSERT (FALSE);
|
||||
ASSERT(FALSE);
|
||||
return FALSE;
|
||||
}
|
||||
return Val != ID_MMFR0_SHR_IMP_HW_COHERENT;
|
||||
}
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
PopulateLevel2PageTable (
|
||||
IN UINT32 *SectionEntry,
|
||||
IN UINT32 PhysicalBase,
|
||||
IN UINT32 RemainLength,
|
||||
IN ARM_MEMORY_REGION_ATTRIBUTES Attributes
|
||||
)
|
||||
VOID PopulateLevel2PageTable(
|
||||
IN UINT32 *SectionEntry, IN UINT32 PhysicalBase, IN UINT32 RemainLength,
|
||||
IN ARM_MEMORY_REGION_ATTRIBUTES Attributes)
|
||||
{
|
||||
UINT32* PageEntry;
|
||||
UINT32 *PageEntry;
|
||||
UINT32 Pages;
|
||||
UINT32 Index;
|
||||
UINT32 PageAttributes;
|
||||
@ -151,73 +138,91 @@ PopulateLevel2PageTable (
|
||||
break;
|
||||
}
|
||||
|
||||
if (PreferNonshareableMemory ()) {
|
||||
if (PreferNonshareableMemory()) {
|
||||
PageAttributes &= ~TT_DESCRIPTOR_PAGE_S_SHARED;
|
||||
}
|
||||
|
||||
// Check if the Section Entry has already been populated. Otherwise attach a
|
||||
// Level 2 Translation Table to it
|
||||
if (*SectionEntry != 0) {
|
||||
// The entry must be a page table. Otherwise it exists an overlapping in the memory map
|
||||
// The entry must be a page table. Otherwise it exists an overlapping in the
|
||||
// memory map
|
||||
if (TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(*SectionEntry)) {
|
||||
TranslationTable = *SectionEntry & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK;
|
||||
} else if ((*SectionEntry & TT_DESCRIPTOR_SECTION_TYPE_MASK) == TT_DESCRIPTOR_SECTION_TYPE_SECTION) {
|
||||
TranslationTable =
|
||||
*SectionEntry & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK;
|
||||
}
|
||||
else if (
|
||||
(*SectionEntry & TT_DESCRIPTOR_SECTION_TYPE_MASK) ==
|
||||
TT_DESCRIPTOR_SECTION_TYPE_SECTION) {
|
||||
// Case where a virtual memory map descriptor overlapped a section entry
|
||||
|
||||
// Allocate a Level2 Page Table for this Section
|
||||
TranslationTable = (UINTN)AllocatePages(EFI_SIZE_TO_PAGES(TRANSLATION_TABLE_PAGE_SIZE + TRANSLATION_TABLE_PAGE_ALIGNMENT));
|
||||
TranslationTable = ((UINTN)TranslationTable + TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK) & ~TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK;
|
||||
TranslationTable = (UINTN)AllocatePages(EFI_SIZE_TO_PAGES(
|
||||
TRANSLATION_TABLE_PAGE_SIZE + TRANSLATION_TABLE_PAGE_ALIGNMENT));
|
||||
TranslationTable =
|
||||
((UINTN)TranslationTable + TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK) &
|
||||
~TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK;
|
||||
|
||||
// Translate the Section Descriptor into Page Descriptor
|
||||
SectionDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (*SectionEntry, FALSE);
|
||||
SectionDescriptor =
|
||||
TT_DESCRIPTOR_PAGE_TYPE_PAGE |
|
||||
ConvertSectionAttributesToPageAttributes(*SectionEntry, FALSE);
|
||||
|
||||
BaseSectionAddress = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(*SectionEntry);
|
||||
|
||||
// Populate the new Level2 Page Table for the section
|
||||
PageEntry = (UINT32*)TranslationTable;
|
||||
PageEntry = (UINT32 *)TranslationTable;
|
||||
for (Index = 0; Index < TRANSLATION_TABLE_PAGE_COUNT; Index++) {
|
||||
PageEntry[Index] = TT_DESCRIPTOR_PAGE_BASE_ADDRESS(BaseSectionAddress + (Index << 12)) | SectionDescriptor;
|
||||
PageEntry[Index] = TT_DESCRIPTOR_PAGE_BASE_ADDRESS(
|
||||
BaseSectionAddress + (Index << 12)) |
|
||||
SectionDescriptor;
|
||||
}
|
||||
|
||||
// Overwrite the section entry to point to the new Level2 Translation Table
|
||||
*SectionEntry = (TranslationTable & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) |
|
||||
// Overwrite the section entry to point to the new Level2 Translation
|
||||
// Table
|
||||
*SectionEntry =
|
||||
(TranslationTable & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) |
|
||||
(IS_ARM_MEMORY_REGION_ATTRIBUTES_SECURE(Attributes) ? (1 << 3) : 0) |
|
||||
TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
// We do not support the other section type (16MB Section)
|
||||
ASSERT(0);
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
TranslationTable = (UINTN)AllocatePages(EFI_SIZE_TO_PAGES(TRANSLATION_TABLE_PAGE_SIZE + TRANSLATION_TABLE_PAGE_ALIGNMENT));
|
||||
TranslationTable = ((UINTN)TranslationTable + TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK) & ~TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK;
|
||||
}
|
||||
else {
|
||||
TranslationTable = (UINTN)AllocatePages(EFI_SIZE_TO_PAGES(
|
||||
TRANSLATION_TABLE_PAGE_SIZE + TRANSLATION_TABLE_PAGE_ALIGNMENT));
|
||||
TranslationTable =
|
||||
((UINTN)TranslationTable + TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK) &
|
||||
~TRANSLATION_TABLE_PAGE_ALIGNMENT_MASK;
|
||||
|
||||
ZeroMem ((VOID *)TranslationTable, TRANSLATION_TABLE_PAGE_SIZE);
|
||||
ZeroMem((VOID *)TranslationTable, TRANSLATION_TABLE_PAGE_SIZE);
|
||||
|
||||
*SectionEntry = (TranslationTable & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) |
|
||||
*SectionEntry =
|
||||
(TranslationTable & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) |
|
||||
(IS_ARM_MEMORY_REGION_ATTRIBUTES_SECURE(Attributes) ? (1 << 3) : 0) |
|
||||
TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE;
|
||||
}
|
||||
|
||||
FirstPageOffset = (PhysicalBase & TT_DESCRIPTOR_PAGE_INDEX_MASK) >> TT_DESCRIPTOR_PAGE_BASE_SHIFT;
|
||||
FirstPageOffset = (PhysicalBase & TT_DESCRIPTOR_PAGE_INDEX_MASK) >>
|
||||
TT_DESCRIPTOR_PAGE_BASE_SHIFT;
|
||||
PageEntry = (UINT32 *)TranslationTable + FirstPageOffset;
|
||||
Pages = RemainLength / TT_DESCRIPTOR_PAGE_SIZE;
|
||||
|
||||
ASSERT (FirstPageOffset + Pages <= TRANSLATION_TABLE_PAGE_COUNT);
|
||||
ASSERT(FirstPageOffset + Pages <= TRANSLATION_TABLE_PAGE_COUNT);
|
||||
|
||||
for (Index = 0; Index < Pages; Index++) {
|
||||
*PageEntry++ = TT_DESCRIPTOR_PAGE_BASE_ADDRESS(PhysicalBase) | PageAttributes;
|
||||
*PageEntry++ =
|
||||
TT_DESCRIPTOR_PAGE_BASE_ADDRESS(PhysicalBase) | PageAttributes;
|
||||
PhysicalBase += TT_DESCRIPTOR_PAGE_SIZE;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
FillTranslationTable (
|
||||
IN UINT32 *TranslationTable,
|
||||
IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryRegion
|
||||
)
|
||||
VOID FillTranslationTable(
|
||||
IN UINT32 *TranslationTable, IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryRegion)
|
||||
{
|
||||
UINT32 *SectionEntry;
|
||||
UINT32 Attributes;
|
||||
@ -272,29 +277,34 @@ FillTranslationTable (
|
||||
break;
|
||||
}
|
||||
|
||||
if (PreferNonshareableMemory ()) {
|
||||
if (PreferNonshareableMemory()) {
|
||||
Attributes &= ~TT_DESCRIPTOR_SECTION_S_SHARED;
|
||||
}
|
||||
|
||||
// Get the first section entry for this mapping
|
||||
SectionEntry = TRANSLATION_TABLE_ENTRY_FOR_VIRTUAL_ADDRESS(TranslationTable, MemoryRegion->VirtualBase);
|
||||
SectionEntry = TRANSLATION_TABLE_ENTRY_FOR_VIRTUAL_ADDRESS(
|
||||
TranslationTable, MemoryRegion->VirtualBase);
|
||||
|
||||
while (RemainLength != 0) {
|
||||
if (PhysicalBase % TT_DESCRIPTOR_SECTION_SIZE == 0 &&
|
||||
RemainLength >= TT_DESCRIPTOR_SECTION_SIZE) {
|
||||
// Case: Physical address aligned on the Section Size (1MB) && the length
|
||||
// is greater than the Section Size
|
||||
*SectionEntry++ = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(PhysicalBase) | Attributes;
|
||||
*SectionEntry++ =
|
||||
TT_DESCRIPTOR_SECTION_BASE_ADDRESS(PhysicalBase) | Attributes;
|
||||
PhysicalBase += TT_DESCRIPTOR_SECTION_SIZE;
|
||||
RemainLength -= TT_DESCRIPTOR_SECTION_SIZE;
|
||||
} else {
|
||||
PageMapLength = MIN (RemainLength, TT_DESCRIPTOR_SECTION_SIZE -
|
||||
}
|
||||
else {
|
||||
PageMapLength =
|
||||
MIN(RemainLength, TT_DESCRIPTOR_SECTION_SIZE -
|
||||
(PhysicalBase % TT_DESCRIPTOR_SECTION_SIZE));
|
||||
|
||||
// Case: Physical address aligned on the Section Size (1MB) && the length
|
||||
// does not fill a section
|
||||
// Case: Physical address NOT aligned on the Section Size (1MB)
|
||||
PopulateLevel2PageTable (SectionEntry++, PhysicalBase, PageMapLength,
|
||||
PopulateLevel2PageTable(
|
||||
SectionEntry++, PhysicalBase, PageMapLength,
|
||||
MemoryRegion->Attributes);
|
||||
|
||||
// If it is the last entry
|
||||
@ -310,22 +320,24 @@ FillTranslationTable (
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
ArmConfigureMmu (
|
||||
ArmConfigureMmu(
|
||||
IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryTable,
|
||||
OUT VOID **TranslationTableBase OPTIONAL,
|
||||
OUT UINTN *TranslationTableSize OPTIONAL
|
||||
)
|
||||
OUT UINTN *TranslationTableSize OPTIONAL)
|
||||
{
|
||||
VOID* TranslationTable;
|
||||
VOID * TranslationTable;
|
||||
ARM_MEMORY_REGION_ATTRIBUTES TranslationTableAttribute;
|
||||
UINT32 TTBRAttributes;
|
||||
|
||||
// Allocate pages for translation table.
|
||||
TranslationTable = AllocatePages (EFI_SIZE_TO_PAGES (TRANSLATION_TABLE_SECTION_SIZE + TRANSLATION_TABLE_SECTION_ALIGNMENT));
|
||||
TranslationTable = AllocatePages(EFI_SIZE_TO_PAGES(
|
||||
TRANSLATION_TABLE_SECTION_SIZE + TRANSLATION_TABLE_SECTION_ALIGNMENT));
|
||||
if (TranslationTable == NULL) {
|
||||
return RETURN_OUT_OF_RESOURCES;
|
||||
}
|
||||
TranslationTable = (VOID*)(((UINTN)TranslationTable + TRANSLATION_TABLE_SECTION_ALIGNMENT_MASK) & ~TRANSLATION_TABLE_SECTION_ALIGNMENT_MASK);
|
||||
TranslationTable =
|
||||
(VOID
|
||||
*)(((UINTN)TranslationTable + TRANSLATION_TABLE_SECTION_ALIGNMENT_MASK) & ~TRANSLATION_TABLE_SECTION_ALIGNMENT_MASK);
|
||||
|
||||
if (TranslationTableBase != NULL) {
|
||||
*TranslationTableBase = TranslationTable;
|
||||
@ -335,60 +347,69 @@ ArmConfigureMmu (
|
||||
*TranslationTableSize = TRANSLATION_TABLE_SECTION_SIZE;
|
||||
}
|
||||
|
||||
ZeroMem (TranslationTable, TRANSLATION_TABLE_SECTION_SIZE);
|
||||
ZeroMem(TranslationTable, TRANSLATION_TABLE_SECTION_SIZE);
|
||||
|
||||
// By default, mark the translation table as belonging to a uncached region
|
||||
TranslationTableAttribute = ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED;
|
||||
while (MemoryTable->Length != 0) {
|
||||
// Find the memory attribute for the Translation Table
|
||||
if (((UINTN)TranslationTable >= MemoryTable->PhysicalBase) && ((UINTN)TranslationTable <= MemoryTable->PhysicalBase - 1 + MemoryTable->Length)) {
|
||||
if (((UINTN)TranslationTable >= MemoryTable->PhysicalBase) &&
|
||||
((UINTN)TranslationTable <=
|
||||
MemoryTable->PhysicalBase - 1 + MemoryTable->Length)) {
|
||||
TranslationTableAttribute = MemoryTable->Attributes;
|
||||
}
|
||||
|
||||
FillTranslationTable (TranslationTable, MemoryTable);
|
||||
FillTranslationTable(TranslationTable, MemoryTable);
|
||||
MemoryTable++;
|
||||
}
|
||||
|
||||
// Translate the Memory Attributes into Translation Table Register Attributes
|
||||
if ((TranslationTableAttribute == ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK) ||
|
||||
(TranslationTableAttribute == ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK)) {
|
||||
TTBRAttributes = ArmHasMpExtensions () ? TTBR_MP_WRITE_BACK_ALLOC : TTBR_WRITE_BACK_ALLOC;
|
||||
} else {
|
||||
(TranslationTableAttribute ==
|
||||
ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK)) {
|
||||
TTBRAttributes =
|
||||
ArmHasMpExtensions() ? TTBR_MP_WRITE_BACK_ALLOC : TTBR_WRITE_BACK_ALLOC;
|
||||
}
|
||||
else {
|
||||
// Page tables must reside in memory mapped as write-back cacheable
|
||||
ASSERT (0);
|
||||
ASSERT(0);
|
||||
return RETURN_UNSUPPORTED;
|
||||
}
|
||||
|
||||
if (TTBRAttributes & TTBR_SHAREABLE) {
|
||||
if (PreferNonshareableMemory ()) {
|
||||
if (PreferNonshareableMemory()) {
|
||||
TTBRAttributes ^= TTBR_SHAREABLE;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
//
|
||||
// Unlike the S bit in the short descriptors, which implies inner shareable
|
||||
// on an implementation that supports two levels, the meaning of the S bit
|
||||
// in the TTBR depends on the NOS bit, which defaults to Outer Shareable.
|
||||
// However, we should only set this bit after we have confirmed that the
|
||||
// implementation supports multiple levels, or else the NOS bit is UNK/SBZP
|
||||
// Unlike the S bit in the short descriptors, which implies inner
|
||||
// shareable on an implementation that supports two levels, the meaning of
|
||||
// the S bit in the TTBR depends on the NOS bit, which defaults to Outer
|
||||
// Shareable. However, we should only set this bit after we have confirmed
|
||||
// that the implementation supports multiple levels, or else the NOS bit
|
||||
// is UNK/SBZP
|
||||
//
|
||||
if (((ArmReadIdMmfr0 () >> 12) & 0xf) != 0) {
|
||||
if (((ArmReadIdMmfr0() >> 12) & 0xf) != 0) {
|
||||
TTBRAttributes |= TTBR_NOT_OUTER_SHAREABLE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ArmCleanInvalidateDataCache ();
|
||||
ArmInvalidateInstructionCache ();
|
||||
ArmCleanInvalidateDataCache();
|
||||
ArmInvalidateInstructionCache();
|
||||
|
||||
ArmDisableDataCache ();
|
||||
ArmDisableDataCache();
|
||||
ArmDisableInstructionCache();
|
||||
// TLBs are also invalidated when calling ArmDisableMmu()
|
||||
ArmDisableMmu ();
|
||||
ArmDisableMmu();
|
||||
|
||||
// Make sure nothing sneaked into the cache
|
||||
ArmCleanInvalidateDataCache ();
|
||||
ArmInvalidateInstructionCache ();
|
||||
ArmCleanInvalidateDataCache();
|
||||
ArmInvalidateInstructionCache();
|
||||
|
||||
ArmSetTTBR0 ((VOID *)(UINTN)(((UINTN)TranslationTable & ~TRANSLATION_TABLE_SECTION_ALIGNMENT_MASK) | (TTBRAttributes & 0x7F)));
|
||||
ArmSetTTBR0((
|
||||
VOID
|
||||
*)(UINTN)(((UINTN)TranslationTable & ~TRANSLATION_TABLE_SECTION_ALIGNMENT_MASK) | (TTBRAttributes & 0x7F)));
|
||||
|
||||
//
|
||||
// The TTBCR register value is undefined at reset in the Non-Secure world.
|
||||
@ -399,24 +420,17 @@ ArmConfigureMmu (
|
||||
// (0 is the default reset value in systems not implementing
|
||||
// the Security Extensions.)
|
||||
//
|
||||
ArmSetTTBCR (0);
|
||||
ArmSetTTBCR(0);
|
||||
|
||||
ArmSetDomainAccessControl (DOMAIN_ACCESS_CONTROL_NONE(15) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(14) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(13) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(12) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(11) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(10) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 9) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 8) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 7) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 6) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 5) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 4) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 3) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 2) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE( 1) |
|
||||
DOMAIN_ACCESS_CONTROL_CLIENT(0));
|
||||
ArmSetDomainAccessControl(
|
||||
DOMAIN_ACCESS_CONTROL_NONE(15) | DOMAIN_ACCESS_CONTROL_NONE(14) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(13) | DOMAIN_ACCESS_CONTROL_NONE(12) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(11) | DOMAIN_ACCESS_CONTROL_NONE(10) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(9) | DOMAIN_ACCESS_CONTROL_NONE(8) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(7) | DOMAIN_ACCESS_CONTROL_NONE(6) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(5) | DOMAIN_ACCESS_CONTROL_NONE(4) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(3) | DOMAIN_ACCESS_CONTROL_NONE(2) |
|
||||
DOMAIN_ACCESS_CONTROL_NONE(1) | DOMAIN_ACCESS_CONTROL_CLIENT(0));
|
||||
|
||||
ArmEnableInstructionCache();
|
||||
ArmEnableDataCache();
|
||||
@ -426,9 +440,7 @@ ArmConfigureMmu (
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
ConvertSectionToPages (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress
|
||||
)
|
||||
ConvertSectionToPages(IN EFI_PHYSICAL_ADDRESS BaseAddress)
|
||||
{
|
||||
UINT32 FirstLevelIdx;
|
||||
UINT32 SectionDescriptor;
|
||||
@ -437,34 +449,44 @@ ConvertSectionToPages (
|
||||
UINT32 Index;
|
||||
|
||||
volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable;
|
||||
volatile ARM_PAGE_TABLE_ENTRY *PageTable;
|
||||
volatile ARM_PAGE_TABLE_ENTRY * PageTable;
|
||||
|
||||
DEBUG ((EFI_D_PAGE, "Converting section at 0x%x to pages\n", (UINTN)BaseAddress));
|
||||
DEBUG((
|
||||
EFI_D_PAGE, "Converting section at 0x%x to pages\n", (UINTN)BaseAddress));
|
||||
|
||||
// Obtain page table base
|
||||
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress ();
|
||||
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress();
|
||||
|
||||
// Calculate index into first level translation table for start of modification
|
||||
FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT);
|
||||
// Calculate index into first level translation table for start of
|
||||
// modification
|
||||
FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress) >>
|
||||
TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
ASSERT(FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT);
|
||||
|
||||
// Get section attributes and convert to page attributes
|
||||
SectionDescriptor = FirstLevelTable[FirstLevelIdx];
|
||||
PageDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (SectionDescriptor, FALSE);
|
||||
PageDescriptor =
|
||||
TT_DESCRIPTOR_PAGE_TYPE_PAGE |
|
||||
ConvertSectionAttributesToPageAttributes(SectionDescriptor, FALSE);
|
||||
|
||||
// Allocate a page table for the 4KB entries (we use up a full page even though we only need 1KB)
|
||||
PageTable = (volatile ARM_PAGE_TABLE_ENTRY *)AllocatePages (1);
|
||||
// Allocate a page table for the 4KB entries (we use up a full page even
|
||||
// though we only need 1KB)
|
||||
PageTable = (volatile ARM_PAGE_TABLE_ENTRY *)AllocatePages(1);
|
||||
if (PageTable == NULL) {
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
// Write the page table entries out
|
||||
for (Index = 0; Index < TRANSLATION_TABLE_PAGE_COUNT; Index++) {
|
||||
PageTable[Index] = TT_DESCRIPTOR_PAGE_BASE_ADDRESS(BaseAddress + (Index << 12)) | PageDescriptor;
|
||||
PageTable[Index] =
|
||||
TT_DESCRIPTOR_PAGE_BASE_ADDRESS(BaseAddress + (Index << 12)) |
|
||||
PageDescriptor;
|
||||
}
|
||||
|
||||
// Formulate page table entry, Domain=0, NS=0
|
||||
PageTableDescriptor = (((UINTN)PageTable) & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) | TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE;
|
||||
PageTableDescriptor =
|
||||
(((UINTN)PageTable) & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) |
|
||||
TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE;
|
||||
|
||||
// Write the page table entry out, replacing section entry
|
||||
FirstLevelTable[FirstLevelIdx] = PageTableDescriptor;
|
||||
@ -474,12 +496,9 @@ ConvertSectionToPages (
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
UpdatePageEntries (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length,
|
||||
IN UINT64 Attributes,
|
||||
OUT BOOLEAN *FlushTlbs OPTIONAL
|
||||
)
|
||||
UpdatePageEntries(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, IN UINT64 Attributes,
|
||||
OUT BOOLEAN *FlushTlbs OPTIONAL)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINT32 EntryValue;
|
||||
@ -492,19 +511,20 @@ UpdatePageEntries (
|
||||
UINT32 PageTableIndex;
|
||||
UINT32 PageTableEntry;
|
||||
UINT32 CurrentPageTableEntry;
|
||||
VOID *Mva;
|
||||
VOID * Mva;
|
||||
|
||||
volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable;
|
||||
volatile ARM_PAGE_TABLE_ENTRY *PageTable;
|
||||
volatile ARM_PAGE_TABLE_ENTRY * PageTable;
|
||||
|
||||
Status = EFI_SUCCESS;
|
||||
|
||||
// EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone)
|
||||
// EntryValue: values at bit positions specified by EntryMask
|
||||
// EntryMask: bitmask of values to change (1 = change this value, 0 = leave
|
||||
// alone) EntryValue: values at bit positions specified by EntryMask
|
||||
EntryMask = TT_DESCRIPTOR_PAGE_TYPE_MASK | TT_DESCRIPTOR_PAGE_AP_MASK;
|
||||
if (Attributes & EFI_MEMORY_XP) {
|
||||
EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE_XN;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE;
|
||||
}
|
||||
|
||||
@ -517,54 +537,69 @@ UpdatePageEntries (
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK;
|
||||
// map to strongly ordered
|
||||
EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0, C=0, B=0
|
||||
} else if (Attributes & EFI_MEMORY_WC) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_PAGE_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0, C=0,
|
||||
// B=0
|
||||
}
|
||||
else if (Attributes & EFI_MEMORY_WC) {
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK;
|
||||
// map to normal non-cachable
|
||||
EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 = 0x2, B=0, C=0
|
||||
} else if (Attributes & EFI_MEMORY_WT) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 = 0x2,
|
||||
// B=0, C=0
|
||||
}
|
||||
else if (Attributes & EFI_MEMORY_WT) {
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK;
|
||||
// write through with no-allocate
|
||||
EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0] = 0, C=1, B=0
|
||||
} else if (Attributes & EFI_MEMORY_WB) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0] =
|
||||
// 0, C=1, B=0
|
||||
}
|
||||
else if (Attributes & EFI_MEMORY_WB) {
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK;
|
||||
// write back (with allocate)
|
||||
EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001, C=1, B=1
|
||||
} else if (Attributes & CACHE_ATTRIBUTE_MASK) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001,
|
||||
// C=1, B=1
|
||||
}
|
||||
else if (Attributes & CACHE_ATTRIBUTE_MASK) {
|
||||
// catch unsupported memory type attributes
|
||||
ASSERT (FALSE);
|
||||
ASSERT(FALSE);
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
|
||||
if (Attributes & EFI_MEMORY_RO) {
|
||||
EntryValue |= TT_DESCRIPTOR_PAGE_AP_RO_RO;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
EntryValue |= TT_DESCRIPTOR_PAGE_AP_RW_RW;
|
||||
}
|
||||
|
||||
// Obtain page table base
|
||||
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress ();
|
||||
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress();
|
||||
|
||||
// Calculate number of 4KB page table entries to change
|
||||
NumPageEntries = Length / TT_DESCRIPTOR_PAGE_SIZE;
|
||||
|
||||
// Iterate for the number of 4KB pages to change
|
||||
Offset = 0;
|
||||
for(p = 0; p < NumPageEntries; p++) {
|
||||
for (p = 0; p < NumPageEntries; p++) {
|
||||
// Calculate index into first level translation table for page table value
|
||||
|
||||
FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress + Offset) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT);
|
||||
FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress + Offset) >>
|
||||
TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
ASSERT(FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT);
|
||||
|
||||
// Read the descriptor from the first level page table
|
||||
Descriptor = FirstLevelTable[FirstLevelIdx];
|
||||
|
||||
// Does this descriptor need to be converted from section entry to 4K pages?
|
||||
if (!TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(Descriptor)) {
|
||||
Status = ConvertSectionToPages (FirstLevelIdx << TT_DESCRIPTOR_SECTION_BASE_SHIFT);
|
||||
Status = ConvertSectionToPages(
|
||||
FirstLevelIdx << TT_DESCRIPTOR_SECTION_BASE_SHIFT);
|
||||
if (EFI_ERROR(Status)) {
|
||||
// Exit for loop
|
||||
break;
|
||||
@ -578,11 +613,13 @@ UpdatePageEntries (
|
||||
}
|
||||
|
||||
// Obtain page table base address
|
||||
PageTable = (ARM_PAGE_TABLE_ENTRY *)TT_DESCRIPTOR_PAGE_BASE_ADDRESS(Descriptor);
|
||||
PageTable =
|
||||
(ARM_PAGE_TABLE_ENTRY *)TT_DESCRIPTOR_PAGE_BASE_ADDRESS(Descriptor);
|
||||
|
||||
// Calculate index into the page table
|
||||
PageTableIndex = ((BaseAddress + Offset) & TT_DESCRIPTOR_PAGE_INDEX_MASK) >> TT_DESCRIPTOR_PAGE_BASE_SHIFT;
|
||||
ASSERT (PageTableIndex < TRANSLATION_TABLE_PAGE_COUNT);
|
||||
PageTableIndex = ((BaseAddress + Offset) & TT_DESCRIPTOR_PAGE_INDEX_MASK) >>
|
||||
TT_DESCRIPTOR_PAGE_BASE_SHIFT;
|
||||
ASSERT(PageTableIndex < TRANSLATION_TABLE_PAGE_COUNT);
|
||||
|
||||
// Get the entry
|
||||
CurrentPageTableEntry = PageTable[PageTableIndex];
|
||||
@ -594,11 +631,13 @@ UpdatePageEntries (
|
||||
PageTableEntry |= EntryValue;
|
||||
|
||||
if (CurrentPageTableEntry != PageTableEntry) {
|
||||
Mva = (VOID *)(UINTN)((((UINTN)FirstLevelIdx) << TT_DESCRIPTOR_SECTION_BASE_SHIFT) + (PageTableIndex << TT_DESCRIPTOR_PAGE_BASE_SHIFT));
|
||||
Mva =
|
||||
(VOID
|
||||
*)(UINTN)((((UINTN)FirstLevelIdx) << TT_DESCRIPTOR_SECTION_BASE_SHIFT) + (PageTableIndex << TT_DESCRIPTOR_PAGE_BASE_SHIFT));
|
||||
|
||||
// Only need to update if we are changing the entry
|
||||
PageTable[PageTableIndex] = PageTableEntry;
|
||||
ArmUpdateTranslationTableEntry ((VOID *)&PageTable[PageTableIndex], Mva);
|
||||
ArmUpdateTranslationTableEntry((VOID *)&PageTable[PageTableIndex], Mva);
|
||||
}
|
||||
|
||||
Status = EFI_SUCCESS;
|
||||
@ -611,11 +650,8 @@ UpdatePageEntries (
|
||||
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
UpdateSectionEntries (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length,
|
||||
IN UINT64 Attributes
|
||||
)
|
||||
UpdateSectionEntries(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, IN UINT64 Attributes)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT32 EntryMask;
|
||||
@ -625,11 +661,11 @@ UpdateSectionEntries (
|
||||
UINT32 i;
|
||||
UINT32 CurrentDescriptor;
|
||||
UINT32 Descriptor;
|
||||
VOID *Mva;
|
||||
VOID * Mva;
|
||||
volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable;
|
||||
|
||||
// EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone)
|
||||
// EntryValue: values at bit positions specified by EntryMask
|
||||
// EntryMask: bitmask of values to change (1 = change this value, 0 = leave
|
||||
// alone) EntryValue: values at bit positions specified by EntryMask
|
||||
|
||||
// Make sure we handle a section range that is unmapped
|
||||
EntryMask = TT_DESCRIPTOR_SECTION_TYPE_MASK | TT_DESCRIPTOR_SECTION_XN_MASK |
|
||||
@ -645,31 +681,45 @@ UpdateSectionEntries (
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK;
|
||||
// map to strongly ordered
|
||||
EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0, C=0, B=0
|
||||
} else if (Attributes & EFI_MEMORY_WC) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_SECTION_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0,
|
||||
// C=0, B=0
|
||||
}
|
||||
else if (Attributes & EFI_MEMORY_WC) {
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK;
|
||||
// map to normal non-cachable
|
||||
EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 = 0x2, B=0, C=0
|
||||
} else if (Attributes & EFI_MEMORY_WT) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_SECTION_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 =
|
||||
// 0x2, B=0, C=0
|
||||
}
|
||||
else if (Attributes & EFI_MEMORY_WT) {
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK;
|
||||
// write through with no-allocate
|
||||
EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0] = 0, C=1, B=0
|
||||
} else if (Attributes & EFI_MEMORY_WB) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0]
|
||||
// = 0, C=1,
|
||||
// B=0
|
||||
}
|
||||
else if (Attributes & EFI_MEMORY_WB) {
|
||||
// modify cacheability attributes
|
||||
EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK;
|
||||
// write back (with allocate)
|
||||
EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001, C=1, B=1
|
||||
} else if (Attributes & CACHE_ATTRIBUTE_MASK) {
|
||||
EntryValue |=
|
||||
TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001,
|
||||
// C=1, B=1
|
||||
}
|
||||
else if (Attributes & CACHE_ATTRIBUTE_MASK) {
|
||||
// catch unsupported memory type attributes
|
||||
ASSERT (FALSE);
|
||||
ASSERT(FALSE);
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
|
||||
if (Attributes & EFI_MEMORY_RO) {
|
||||
EntryValue |= TT_DESCRIPTOR_SECTION_AP_RO_RO;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
EntryValue |= TT_DESCRIPTOR_SECTION_AP_RW_RW;
|
||||
}
|
||||
|
||||
@ -678,46 +728,52 @@ UpdateSectionEntries (
|
||||
}
|
||||
|
||||
// obtain page table base
|
||||
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress ();
|
||||
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress();
|
||||
|
||||
// calculate index into first level translation table for start of modification
|
||||
FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT);
|
||||
// calculate index into first level translation table for start of
|
||||
// modification
|
||||
FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress) >>
|
||||
TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
ASSERT(FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT);
|
||||
|
||||
// calculate number of 1MB first level entries this applies to
|
||||
NumSections = Length / TT_DESCRIPTOR_SECTION_SIZE;
|
||||
|
||||
// iterate through each descriptor
|
||||
for(i=0; i<NumSections; i++) {
|
||||
for (i = 0; i < NumSections; i++) {
|
||||
CurrentDescriptor = FirstLevelTable[FirstLevelIdx + i];
|
||||
|
||||
// has this descriptor already been converted to pages?
|
||||
if (TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(CurrentDescriptor)) {
|
||||
// forward this 1MB range to page table function instead
|
||||
Status = UpdatePageEntries (
|
||||
Status = UpdatePageEntries(
|
||||
(FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT,
|
||||
TT_DESCRIPTOR_SECTION_SIZE,
|
||||
Attributes,
|
||||
NULL);
|
||||
} else {
|
||||
TT_DESCRIPTOR_SECTION_SIZE, Attributes, NULL);
|
||||
}
|
||||
else {
|
||||
// still a section entry
|
||||
|
||||
if (CurrentDescriptor != 0) {
|
||||
// mask off appropriate fields
|
||||
Descriptor = CurrentDescriptor & ~EntryMask;
|
||||
} else {
|
||||
Descriptor = ((UINTN)FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
}
|
||||
else {
|
||||
Descriptor = ((UINTN)FirstLevelIdx + i)
|
||||
<< TT_DESCRIPTOR_SECTION_BASE_SHIFT;
|
||||
}
|
||||
|
||||
// mask in new attributes and/or permissions
|
||||
Descriptor |= EntryValue;
|
||||
|
||||
if (CurrentDescriptor != Descriptor) {
|
||||
Mva = (VOID *)(UINTN)(((UINTN)FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT);
|
||||
Mva =
|
||||
(VOID
|
||||
*)(UINTN)(((UINTN)FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT);
|
||||
|
||||
// Only need to update if we are changing the descriptor
|
||||
FirstLevelTable[FirstLevelIdx + i] = Descriptor;
|
||||
ArmUpdateTranslationTableEntry ((VOID *)&FirstLevelTable[FirstLevelIdx + i], Mva);
|
||||
ArmUpdateTranslationTableEntry(
|
||||
(VOID *)&FirstLevelTable[FirstLevelIdx + i], Mva);
|
||||
}
|
||||
|
||||
Status = EFI_SUCCESS;
|
||||
@ -728,11 +784,8 @@ UpdateSectionEntries (
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmSetMemoryAttributes (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length,
|
||||
IN UINT64 Attributes
|
||||
)
|
||||
ArmSetMemoryAttributes(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, IN UINT64 Attributes)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINT64 ChunkLength;
|
||||
@ -742,7 +795,7 @@ ArmSetMemoryAttributes (
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
|
||||
Length = MIN (Length, (UINT64)MAX_ADDRESS - BaseAddress + 1);
|
||||
Length = MIN(Length, (UINT64)MAX_ADDRESS - BaseAddress + 1);
|
||||
if (Length == 0) {
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
@ -754,14 +807,16 @@ ArmSetMemoryAttributes (
|
||||
|
||||
ChunkLength = Length - Length % TT_DESCRIPTOR_SECTION_SIZE;
|
||||
|
||||
DEBUG ((DEBUG_PAGE,
|
||||
DEBUG(
|
||||
(DEBUG_PAGE,
|
||||
"SetMemoryAttributes(): MMU section 0x%lx length 0x%lx to %lx\n",
|
||||
BaseAddress, ChunkLength, Attributes));
|
||||
|
||||
Status = UpdateSectionEntries (BaseAddress, ChunkLength, Attributes);
|
||||
Status = UpdateSectionEntries(BaseAddress, ChunkLength, Attributes);
|
||||
|
||||
FlushTlbs = TRUE;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
|
||||
//
|
||||
// Process page by page until the next section boundary, but only if
|
||||
@ -773,15 +828,16 @@ ArmSetMemoryAttributes (
|
||||
ChunkLength = Length;
|
||||
}
|
||||
|
||||
DEBUG ((DEBUG_PAGE,
|
||||
DEBUG(
|
||||
(DEBUG_PAGE,
|
||||
"SetMemoryAttributes(): MMU page 0x%lx length 0x%lx to %lx\n",
|
||||
BaseAddress, ChunkLength, Attributes));
|
||||
|
||||
Status = UpdatePageEntries (BaseAddress, ChunkLength, Attributes,
|
||||
&FlushTlbs);
|
||||
Status =
|
||||
UpdatePageEntries(BaseAddress, ChunkLength, Attributes, &FlushTlbs);
|
||||
}
|
||||
|
||||
if (EFI_ERROR (Status)) {
|
||||
if (EFI_ERROR(Status)) {
|
||||
break;
|
||||
}
|
||||
|
||||
@ -790,52 +846,38 @@ ArmSetMemoryAttributes (
|
||||
}
|
||||
|
||||
if (FlushTlbs) {
|
||||
ArmInvalidateTlb ();
|
||||
ArmInvalidateTlb();
|
||||
}
|
||||
return Status;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmSetMemoryRegionNoExec (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmSetMemoryRegionNoExec(IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
return ArmSetMemoryAttributes (BaseAddress, Length, EFI_MEMORY_XP);
|
||||
return ArmSetMemoryAttributes(BaseAddress, Length, EFI_MEMORY_XP);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmClearMemoryRegionNoExec (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmClearMemoryRegionNoExec(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
return ArmSetMemoryAttributes (BaseAddress, Length, __EFI_MEMORY_RWX);
|
||||
return ArmSetMemoryAttributes(BaseAddress, Length, __EFI_MEMORY_RWX);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmSetMemoryRegionReadOnly (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmSetMemoryRegionReadOnly(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
return ArmSetMemoryAttributes (BaseAddress, Length, EFI_MEMORY_RO);
|
||||
return ArmSetMemoryAttributes(BaseAddress, Length, EFI_MEMORY_RO);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
ArmClearMemoryRegionReadOnly (
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||
IN UINT64 Length
|
||||
)
|
||||
ArmClearMemoryRegionReadOnly(
|
||||
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length)
|
||||
{
|
||||
return ArmSetMemoryAttributes (BaseAddress, Length, __EFI_MEMORY_RWX);
|
||||
return ArmSetMemoryAttributes(BaseAddress, Length, __EFI_MEMORY_RWX);
|
||||
}
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
ArmMmuBaseLibConstructor (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
return RETURN_SUCCESS;
|
||||
}
|
||||
ArmMmuBaseLibConstructor(VOID) { return RETURN_SUCCESS; }
|
||||
|
@ -24,7 +24,7 @@
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
|
||||
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
*/
|
||||
|
||||
#include "AutoGen.h"
|
||||
#include <Library/BootSlotLib/BlockIoUtils.h>
|
||||
@ -42,20 +42,19 @@
|
||||
BLK_IO_SEL_MATCH_ROOT_DEVICE)
|
||||
|
||||
/* Returns 0 if the volume label matches otherwise non zero */
|
||||
STATIC UINTN
|
||||
CompareVolumeLabel (IN EFI_SIMPLE_FILE_SYSTEM_PROTOCOL* Fs,
|
||||
IN CHAR8* ReqVolumeName)
|
||||
STATIC UINTN CompareVolumeLabel(
|
||||
IN EFI_SIMPLE_FILE_SYSTEM_PROTOCOL *Fs, IN CHAR8 *ReqVolumeName)
|
||||
{
|
||||
INT32 CmpResult;
|
||||
UINT32 j;
|
||||
UINT16 VolumeLabel[VOLUME_LABEL_SIZE];
|
||||
EFI_FILE_PROTOCOL *FsVolume = NULL;
|
||||
EFI_FILE_PROTOCOL * FsVolume = NULL;
|
||||
EFI_STATUS Status;
|
||||
UINTN Size;
|
||||
EFI_FILE_SYSTEM_INFO *FsInfo;
|
||||
|
||||
// Get information about the volume
|
||||
Status = Fs->OpenVolume (Fs, &FsVolume);
|
||||
Status = Fs->OpenVolume(Fs, &FsVolume);
|
||||
|
||||
if (Status != EFI_SUCCESS) {
|
||||
return 1;
|
||||
@ -64,13 +63,13 @@ CompareVolumeLabel (IN EFI_SIMPLE_FILE_SYSTEM_PROTOCOL* Fs,
|
||||
/* Get the Volume name */
|
||||
Size = 0;
|
||||
FsInfo = NULL;
|
||||
Status = FsVolume->GetInfo (FsVolume, &gEfiFileSystemInfoGuid, &Size, FsInfo);
|
||||
Status = FsVolume->GetInfo(FsVolume, &gEfiFileSystemInfoGuid, &Size, FsInfo);
|
||||
if (Status == EFI_BUFFER_TOO_SMALL) {
|
||||
FsInfo = AllocateZeroPool (Size);
|
||||
Status = FsVolume->GetInfo (FsVolume,
|
||||
&gEfiFileSystemInfoGuid, &Size, FsInfo);
|
||||
FsInfo = AllocateZeroPool(Size);
|
||||
Status =
|
||||
FsVolume->GetInfo(FsVolume, &gEfiFileSystemInfoGuid, &Size, FsInfo);
|
||||
if (Status != EFI_SUCCESS) {
|
||||
FreePool (FsInfo);
|
||||
FreePool(FsInfo);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@ -83,8 +82,7 @@ CompareVolumeLabel (IN EFI_SIMPLE_FILE_SYSTEM_PROTOCOL* Fs,
|
||||
for (j = 0; (j < VOLUME_LABEL_SIZE - 1) && ReqVolumeName[j]; ++j) {
|
||||
VolumeLabel[j] = ReqVolumeName[j];
|
||||
|
||||
if ((VolumeLabel[j] >= 'a') &&
|
||||
(VolumeLabel[j] <= 'z')) {
|
||||
if ((VolumeLabel[j] >= 'a') && (VolumeLabel[j] <= 'z')) {
|
||||
VolumeLabel[j] -= ('a' - 'A');
|
||||
}
|
||||
}
|
||||
@ -95,27 +93,26 @@ CompareVolumeLabel (IN EFI_SIMPLE_FILE_SYSTEM_PROTOCOL* Fs,
|
||||
/* Change any lower chars in volume name to upper
|
||||
* (ideally this is not needed) */
|
||||
for (j = 0; (j < VOLUME_LABEL_SIZE - 1) && FsInfo->VolumeLabel[j]; ++j) {
|
||||
if ((FsInfo->VolumeLabel[j] >= 'a') &&
|
||||
(FsInfo->VolumeLabel[j] <= 'z')) {
|
||||
if ((FsInfo->VolumeLabel[j] >= 'a') && (FsInfo->VolumeLabel[j] <= 'z')) {
|
||||
FsInfo->VolumeLabel[j] -= ('a' - 'A');
|
||||
}
|
||||
}
|
||||
|
||||
CmpResult = StrnCmp (FsInfo->VolumeLabel, VolumeLabel, VOLUME_LABEL_SIZE);
|
||||
CmpResult = StrnCmp(FsInfo->VolumeLabel, VolumeLabel, VOLUME_LABEL_SIZE);
|
||||
|
||||
FreePool (FsInfo);
|
||||
FsVolume->Close (FsVolume);
|
||||
FreePool(FsInfo);
|
||||
FsVolume->Close(FsVolume);
|
||||
|
||||
return CmpResult;
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
GetPartitionEntry (IN EFI_HANDLE Handle,
|
||||
OUT EFI_PARTITION_ENTRY **PartEntry)
|
||||
GetPartitionEntry(IN EFI_HANDLE Handle, OUT EFI_PARTITION_ENTRY **PartEntry)
|
||||
{
|
||||
EFI_PARTITION_INFO_PROTOCOL *PartInfo;
|
||||
EFI_STATUS Status = gBS->HandleProtocol (Handle, &gEfiPartitionInfoProtocolGuid, (VOID **)&PartInfo);
|
||||
EFI_STATUS Status = gBS->HandleProtocol(
|
||||
Handle, &gEfiPartitionInfoProtocolGuid, (VOID **)&PartInfo);
|
||||
if (!EFI_ERROR(Status)) {
|
||||
*PartEntry = &PartInfo->Info.Gpt;
|
||||
}
|
||||
@ -139,24 +136,23 @@ On output, the number of handle structures returned.
|
||||
*/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
IN PartiSelectFilter *FilterData,
|
||||
OUT HandleInfo *HandleInfoPtr,
|
||||
IN OUT UINT32* MaxBlkIopCnt)
|
||||
GetBlkIOHandles(
|
||||
IN UINT32 SelectionAttrib, IN PartiSelectFilter *FilterData,
|
||||
OUT HandleInfo *HandleInfoPtr, IN OUT UINT32 *MaxBlkIopCnt)
|
||||
{
|
||||
EFI_BLOCK_IO_PROTOCOL *BlkIo;
|
||||
EFI_HANDLE *BlkIoHandles;
|
||||
EFI_BLOCK_IO_PROTOCOL * BlkIo;
|
||||
EFI_HANDLE * BlkIoHandles;
|
||||
UINTN BlkIoHandleCount;
|
||||
UINTN i;
|
||||
UINTN DevicePathDepth;
|
||||
HARDDRIVE_DEVICE_PATH *Partition, *PartitionOut;
|
||||
HARDDRIVE_DEVICE_PATH * Partition, *PartitionOut;
|
||||
EFI_STATUS Status;
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevPathInst;
|
||||
EFI_DEVICE_PATH_PROTOCOL *TempDevicePath;
|
||||
VENDOR_DEVICE_PATH *RootDevicePath;
|
||||
EFI_DEVICE_PATH_PROTOCOL * DevPathInst;
|
||||
EFI_DEVICE_PATH_PROTOCOL * TempDevicePath;
|
||||
VENDOR_DEVICE_PATH * RootDevicePath;
|
||||
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL *Fs;
|
||||
UINT32 BlkIoCnt = 0;
|
||||
EFI_PARTITION_ENTRY *PartEntry;
|
||||
EFI_PARTITION_ENTRY * PartEntry;
|
||||
|
||||
if ((MaxBlkIopCnt == NULL) || (HandleInfoPtr == NULL))
|
||||
return EFI_INVALID_PARAMETER;
|
||||
@ -176,32 +172,33 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
* than BlkIo */
|
||||
if (SelectionAttrib & (BLK_IO_SEL_SELECT_MOUNTED_FILESYSTEM |
|
||||
BLK_IO_SEL_SELECT_BY_VOLUME_NAME)) {
|
||||
Status =
|
||||
gBS->LocateHandleBuffer (ByProtocol, &gEfiSimpleFileSystemProtocolGuid,
|
||||
NULL, &BlkIoHandleCount, &BlkIoHandles);
|
||||
} else {
|
||||
Status = gBS->LocateHandleBuffer (ByProtocol, &gEfiBlockIoProtocolGuid,
|
||||
NULL, &BlkIoHandleCount, &BlkIoHandles);
|
||||
Status = gBS->LocateHandleBuffer(
|
||||
ByProtocol, &gEfiSimpleFileSystemProtocolGuid, NULL, &BlkIoHandleCount,
|
||||
&BlkIoHandles);
|
||||
}
|
||||
else {
|
||||
Status = gBS->LocateHandleBuffer(
|
||||
ByProtocol, &gEfiBlockIoProtocolGuid, NULL, &BlkIoHandleCount,
|
||||
&BlkIoHandles);
|
||||
}
|
||||
|
||||
if (Status != EFI_SUCCESS) {
|
||||
DEBUG (
|
||||
(EFI_D_ERROR, "Unable to get Filesystem Handle buffer %r\n", Status));
|
||||
DEBUG((EFI_D_ERROR, "Unable to get Filesystem Handle buffer %r\n", Status));
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* Loop through to search for the ones we are interested in. */
|
||||
for (i = 0; i < BlkIoHandleCount; i++) {
|
||||
|
||||
Status = gBS->HandleProtocol (BlkIoHandles[i], &gEfiBlockIoProtocolGuid,
|
||||
(VOID **)&BlkIo);
|
||||
Status = gBS->HandleProtocol(
|
||||
BlkIoHandles[i], &gEfiBlockIoProtocolGuid, (VOID **)&BlkIo);
|
||||
/* Fv volumes will not support Blk I/O protocol */
|
||||
if (Status == EFI_UNSUPPORTED) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (Status != EFI_SUCCESS) {
|
||||
DEBUG ((EFI_D_ERROR, "Unable to get Filesystem Handle %r\n", Status));
|
||||
DEBUG((EFI_D_ERROR, "Unable to get Filesystem Handle %r\n", Status));
|
||||
return Status;
|
||||
}
|
||||
|
||||
@ -209,7 +206,8 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
if (BlkIo->Media->RemovableMedia) {
|
||||
if ((SelectionAttrib & BLK_IO_SEL_MEDIA_TYPE_REMOVABLE) == 0)
|
||||
continue;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
if ((SelectionAttrib & BLK_IO_SEL_MEDIA_TYPE_NON_REMOVABLE) == 0)
|
||||
continue;
|
||||
}
|
||||
@ -219,12 +217,12 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
|
||||
/* Check if partition related criteria satisfies */
|
||||
if ((SelectionAttrib & FILTERS_NEEDING_DEVICEPATH) != 0) {
|
||||
Status = gBS->HandleProtocol (
|
||||
Status = gBS->HandleProtocol(
|
||||
BlkIoHandles[i], &gEfiDevicePathProtocolGuid, (VOID **)&DevPathInst);
|
||||
|
||||
/* If we didn't get the DevicePath Protocol then this handle
|
||||
* cannot be used */
|
||||
if (EFI_ERROR (Status))
|
||||
if (EFI_ERROR(Status))
|
||||
continue;
|
||||
|
||||
DevicePathDepth = 0;
|
||||
@ -245,18 +243,18 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
RootDevicePath->Header.SubType != HW_VENDOR_DP ||
|
||||
(RootDevicePath->Header.Length[0] |
|
||||
(RootDevicePath->Header.Length[1] << 8)) !=
|
||||
sizeof (VENDOR_DEVICE_PATH) ||
|
||||
sizeof(VENDOR_DEVICE_PATH) ||
|
||||
((FilterData->RootDeviceType != NULL) &&
|
||||
(CompareGuid (FilterData->RootDeviceType,
|
||||
&RootDevicePath->Guid) == FALSE)))
|
||||
(CompareGuid(FilterData->RootDeviceType, &RootDevicePath->Guid) ==
|
||||
FALSE)))
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Locate the last Device Path Node */
|
||||
while (!IsDevicePathEnd (TempDevicePath)) {
|
||||
while (!IsDevicePathEnd(TempDevicePath)) {
|
||||
DevicePathDepth++;
|
||||
Partition = (HARDDRIVE_DEVICE_PATH *)TempDevicePath;
|
||||
TempDevicePath = NextDevicePathNode (TempDevicePath);
|
||||
TempDevicePath = NextDevicePathNode(TempDevicePath);
|
||||
}
|
||||
|
||||
/* If we need the handle for root device only and if this is representing
|
||||
@ -270,7 +268,7 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
if (Partition->Header.Type == MEDIA_DEVICE_PATH &&
|
||||
Partition->Header.SubType == MEDIA_HARDDRIVE_DP &&
|
||||
(Partition->Header.Length[0] | (Partition->Header.Length[1] << 8)) ==
|
||||
sizeof (*Partition)) {
|
||||
sizeof(*Partition)) {
|
||||
PartitionOut = Partition;
|
||||
|
||||
if ((SelectionAttrib & BLK_IO_SEL_PARTITIONED_GPT) == 0)
|
||||
@ -285,20 +283,20 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
if ((SelectionAttrib & BLK_IO_SEL_MATCH_PARTITION_TYPE_GUID) != 0) {
|
||||
VOID *Interface;
|
||||
|
||||
if (!FilterData ||
|
||||
FilterData->PartitionType == NULL) {
|
||||
if (!FilterData || FilterData->PartitionType == NULL) {
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
Status = gBS->HandleProtocol (BlkIoHandles[i],
|
||||
FilterData->PartitionType,
|
||||
(VOID**)&Interface);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->HandleProtocol(
|
||||
BlkIoHandles[i], FilterData->PartitionType, (VOID **)&Interface);
|
||||
if (EFI_ERROR(Status)) {
|
||||
Status = GetPartitionEntry(BlkIoHandles[i], &PartEntry);
|
||||
if (EFI_ERROR (Status)) {
|
||||
if (EFI_ERROR(Status)) {
|
||||
continue;
|
||||
}
|
||||
if (CompareGuid (&PartEntry->PartitionTypeGUID, FilterData->PartitionType) == FALSE) {
|
||||
if (CompareGuid(
|
||||
&PartEntry->PartitionTypeGUID, FilterData->PartitionType) ==
|
||||
FALSE) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
@ -312,18 +310,17 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
|
||||
/* Check if the Filesystem related criteria satisfies */
|
||||
if ((SelectionAttrib & BLK_IO_SEL_SELECT_MOUNTED_FILESYSTEM) != 0) {
|
||||
Status = gBS->HandleProtocol (BlkIoHandles[i],
|
||||
&gEfiSimpleFileSystemProtocolGuid, (VOID **)&Fs);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->HandleProtocol(
|
||||
BlkIoHandles[i], &gEfiSimpleFileSystemProtocolGuid, (VOID **)&Fs);
|
||||
if (EFI_ERROR(Status)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((SelectionAttrib & BLK_IO_SEL_SELECT_BY_VOLUME_NAME) != 0) {
|
||||
if (!FilterData ||
|
||||
FilterData->VolumeName == NULL) {
|
||||
if (!FilterData || FilterData->VolumeName == NULL) {
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
if (CompareVolumeLabel (Fs, FilterData->VolumeName) != 0) {
|
||||
if (CompareVolumeLabel(Fs, FilterData->VolumeName) != 0) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
@ -334,9 +331,10 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
Status = GetPartitionEntry(BlkIoHandles[i], &PartEntry);
|
||||
if (Status != EFI_SUCCESS)
|
||||
continue;
|
||||
if (StrnCmp (PartEntry->PartitionName, FilterData->PartitionLabel,
|
||||
MAX (StrLen (PartEntry->PartitionName),
|
||||
StrLen (FilterData->PartitionLabel))))
|
||||
if (StrnCmp(
|
||||
PartEntry->PartitionName, FilterData->PartitionLabel,
|
||||
MAX(StrLen(PartEntry->PartitionName),
|
||||
StrLen(FilterData->PartitionLabel))))
|
||||
continue;
|
||||
}
|
||||
/* We came here means, this handle satisfies all the conditions needed,
|
||||
@ -353,7 +351,7 @@ GetBlkIOHandles (IN UINT32 SelectionAttrib,
|
||||
|
||||
/* Free the handle buffer */
|
||||
if (BlkIoHandles != NULL) {
|
||||
FreePool (BlkIoHandles);
|
||||
FreePool(BlkIoHandles);
|
||||
BlkIoHandles = NULL;
|
||||
}
|
||||
|
||||
|
@ -19,14 +19,17 @@
|
||||
#include <Library/BootSlotLib/EFIUtils.h>
|
||||
#include <Library/UefiLib.h>
|
||||
|
||||
void WaitAnyKey(EFI_SYSTEM_TABLE *mSystemTable) {
|
||||
void WaitAnyKey(EFI_SYSTEM_TABLE *mSystemTable)
|
||||
{
|
||||
UINTN index = 0;
|
||||
EFI_INPUT_KEY Key;
|
||||
mSystemTable->BootServices->WaitForEvent(1, &mSystemTable->ConIn->WaitForKey, &index);
|
||||
mSystemTable->BootServices->WaitForEvent(
|
||||
1, &mSystemTable->ConIn->WaitForKey, &index);
|
||||
mSystemTable->ConIn->ReadKeyStroke(mSystemTable->ConIn, &Key);
|
||||
}
|
||||
|
||||
void PrintAndWaitAnyKey(EFI_SYSTEM_TABLE *mSystemTable, CHAR16 *Message) {
|
||||
void PrintAndWaitAnyKey(EFI_SYSTEM_TABLE *mSystemTable, CHAR16 *Message)
|
||||
{
|
||||
Print(Message);
|
||||
WaitAnyKey(mSystemTable);
|
||||
}
|
File diff suppressed because it is too large
Load Diff
@ -1,4 +1,5 @@
|
||||
/* Copyright (c) 2015-2018, 2020-2021, The Linux Foundation. All rights reserved.
|
||||
/* Copyright (c) 2015-2018, 2020-2021, The Linux Foundation. All rights
|
||||
* reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are
|
||||
@ -24,15 +25,17 @@
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
|
||||
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
*/
|
||||
|
||||
#include "AutoGen.h"
|
||||
|
||||
#include <Library/BootSlotLib/StorageUtils.h>
|
||||
#include <Library/BootSlotLib/BlockIoUtils.h>
|
||||
#include <Library/BootSlotLib/StorageUtils.h>
|
||||
|
||||
STATIC CONST CHAR8 *DeviceType[] = {
|
||||
[EMMC] = "EMMC", [UFS] = "UFS", [UNKNOWN] = "Unknown",
|
||||
[EMMC] = "EMMC",
|
||||
[UFS] = "UFS",
|
||||
[UNKNOWN] = "Unknown",
|
||||
};
|
||||
|
||||
/**
|
||||
@ -48,12 +51,12 @@ STATIC CONST CHAR8 *DeviceType[] = {
|
||||
**/
|
||||
|
||||
STATIC EFI_STATUS
|
||||
GetDeviceHandleInfo (VOID *HndlInfo, UINT32 MaxHandles, MemCardType Type)
|
||||
GetDeviceHandleInfo(VOID *HndlInfo, UINT32 MaxHandles, MemCardType Type)
|
||||
{
|
||||
EFI_STATUS Status = EFI_INVALID_PARAMETER;
|
||||
UINT32 Attribs = 0;
|
||||
PartiSelectFilter HandleFilter;
|
||||
HandleInfo *HandleInfoList = HndlInfo;
|
||||
HandleInfo * HandleInfoList = HndlInfo;
|
||||
|
||||
Attribs |= BLK_IO_SEL_MATCH_ROOT_DEVICE;
|
||||
HandleFilter.PartitionType = NULL;
|
||||
@ -67,15 +70,13 @@ GetDeviceHandleInfo (VOID *HndlInfo, UINT32 MaxHandles, MemCardType Type)
|
||||
HandleFilter.RootDeviceType = &gEfiEmmcUserPartitionGuid;
|
||||
break;
|
||||
case UNKNOWN:
|
||||
DEBUG ((EFI_D_ERROR, "Device type unknown\n"));
|
||||
DEBUG((EFI_D_ERROR, "Device type unknown\n"));
|
||||
return Status;
|
||||
}
|
||||
|
||||
Status =
|
||||
GetBlkIOHandles (Attribs, &HandleFilter, HandleInfoList, &MaxHandles);
|
||||
if (EFI_ERROR (Status) ||
|
||||
MaxHandles == 0) {
|
||||
DEBUG ((EFI_D_ERROR, "Get BlkIohandles failed\n"));
|
||||
Status = GetBlkIOHandles(Attribs, &HandleFilter, HandleInfoList, &MaxHandles);
|
||||
if (EFI_ERROR(Status) || MaxHandles == 0) {
|
||||
DEBUG((EFI_D_ERROR, "Get BlkIohandles failed\n"));
|
||||
return Status;
|
||||
}
|
||||
return Status;
|
||||
@ -85,16 +86,15 @@ GetDeviceHandleInfo (VOID *HndlInfo, UINT32 MaxHandles, MemCardType Type)
|
||||
Return a device type
|
||||
@retval Device type : UNKNOWN | UFS | EMMC | NAND
|
||||
**/
|
||||
STATIC UINT32
|
||||
GetCompatibleRootDeviceType (VOID)
|
||||
STATIC UINT32 GetCompatibleRootDeviceType(VOID)
|
||||
{
|
||||
EFI_STATUS Status = EFI_INVALID_PARAMETER;
|
||||
HandleInfo HandleInfoList[HANDLE_MAX_INFO_LIST];
|
||||
UINT32 MaxHandles = ARRAY_SIZE (HandleInfoList);
|
||||
UINT32 MaxHandles = ARRAY_SIZE(HandleInfoList);
|
||||
UINT32 Index;
|
||||
|
||||
for (Index = 0; Index < UNKNOWN; Index++) {
|
||||
Status = GetDeviceHandleInfo (HandleInfoList, MaxHandles, Index);
|
||||
Status = GetDeviceHandleInfo(HandleInfoList, MaxHandles, Index);
|
||||
if (Status == EFI_SUCCESS) {
|
||||
return Index;
|
||||
}
|
||||
@ -108,8 +108,7 @@ GetCompatibleRootDeviceType (VOID)
|
||||
@retval Device type : UNKNOWN | UFS | EMMC, default is UNKNOWN
|
||||
**/
|
||||
|
||||
MemCardType
|
||||
CheckRootDeviceType (VOID)
|
||||
MemCardType CheckRootDeviceType(VOID)
|
||||
{
|
||||
EFI_STATUS Status = EFI_INVALID_PARAMETER;
|
||||
STATIC MemCardType Type = UNKNOWN;
|
||||
@ -117,22 +116,25 @@ CheckRootDeviceType (VOID)
|
||||
EFI_MEM_CARDINFO_PROTOCOL *CardInfo;
|
||||
|
||||
if (Type == UNKNOWN) {
|
||||
Status = gBS->LocateProtocol (&gEfiMemCardInfoProtocolGuid, NULL,
|
||||
(VOID **)&CardInfo);
|
||||
if (!EFI_ERROR (Status)) {
|
||||
Status = gBS->LocateProtocol(
|
||||
&gEfiMemCardInfoProtocolGuid, NULL, (VOID **)&CardInfo);
|
||||
if (!EFI_ERROR(Status)) {
|
||||
|
||||
Status = CardInfo->GetCardInfo (CardInfo, &CardInfoData);
|
||||
Status = CardInfo->GetCardInfo(CardInfo, &CardInfoData);
|
||||
|
||||
if (!EFI_ERROR (Status)) {
|
||||
if (!EFI_ERROR(Status)) {
|
||||
|
||||
if (!AsciiStrnCmp ((CHAR8 *)CardInfoData.card_type, "UFS",
|
||||
AsciiStrLen ("UFS"))) {
|
||||
if (!AsciiStrnCmp(
|
||||
(CHAR8 *)CardInfoData.card_type, "UFS", AsciiStrLen("UFS"))) {
|
||||
Type = UFS;
|
||||
} else if (!AsciiStrnCmp ((CHAR8 *)CardInfoData.card_type, "EMMC",
|
||||
AsciiStrLen ("EMMC"))) {
|
||||
}
|
||||
else if (!AsciiStrnCmp(
|
||||
(CHAR8 *)CardInfoData.card_type, "EMMC",
|
||||
AsciiStrLen("EMMC"))) {
|
||||
Type = EMMC;
|
||||
} else {
|
||||
Type = GetCompatibleRootDeviceType ();
|
||||
}
|
||||
else {
|
||||
Type = GetCompatibleRootDeviceType();
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -145,17 +147,16 @@ CheckRootDeviceType (VOID)
|
||||
@param[out] StrDeviceType : Pointer to array of device type string.
|
||||
@param[in] Len : The size of the device type string
|
||||
**/
|
||||
VOID
|
||||
GetRootDeviceType (CHAR8 *StrDeviceType, UINT32 Len)
|
||||
VOID GetRootDeviceType(CHAR8 *StrDeviceType, UINT32 Len)
|
||||
{
|
||||
UINT32 Type;
|
||||
|
||||
Type = CheckRootDeviceType ();
|
||||
AsciiSPrint (StrDeviceType, Len, "%a", DeviceType[Type]);
|
||||
Type = CheckRootDeviceType();
|
||||
AsciiSPrint(StrDeviceType, Len, "%a", DeviceType[Type]);
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
UfsGetSetBootLun (UINT32 *UfsBootlun, BOOLEAN IsGet)
|
||||
UfsGetSetBootLun(UINT32 *UfsBootlun, BOOLEAN IsGet)
|
||||
{
|
||||
EFI_STATUS Status = EFI_INVALID_PARAMETER;
|
||||
EFI_MEM_CARDINFO_PROTOCOL *CardInfo;
|
||||
@ -165,37 +166,38 @@ UfsGetSetBootLun (UINT32 *UfsBootlun, BOOLEAN IsGet)
|
||||
PartiSelectFilter HandleFilter;
|
||||
|
||||
Attribs |= BLK_IO_SEL_MATCH_ROOT_DEVICE;
|
||||
MaxHandles = ARRAY_SIZE (HandleInfoList);
|
||||
MaxHandles = ARRAY_SIZE(HandleInfoList);
|
||||
HandleFilter.PartitionType = NULL;
|
||||
HandleFilter.VolumeName = NULL;
|
||||
HandleFilter.RootDeviceType = &gEfiUfsLU0Guid;
|
||||
|
||||
Status =
|
||||
GetBlkIOHandles (Attribs, &HandleFilter, HandleInfoList, &MaxHandles);
|
||||
if (EFI_ERROR (Status))
|
||||
Status = GetBlkIOHandles(Attribs, &HandleFilter, HandleInfoList, &MaxHandles);
|
||||
if (EFI_ERROR(Status))
|
||||
return EFI_NOT_FOUND;
|
||||
|
||||
Status =
|
||||
gBS->HandleProtocol (HandleInfoList[0].Handle,
|
||||
&gEfiMemCardInfoProtocolGuid, (VOID **)&CardInfo);
|
||||
Status = gBS->HandleProtocol(
|
||||
HandleInfoList[0].Handle, &gEfiMemCardInfoProtocolGuid,
|
||||
(VOID **)&CardInfo);
|
||||
|
||||
if (Status != EFI_SUCCESS) {
|
||||
DEBUG ((EFI_D_ERROR, "Error locating MemCardInfoProtocol:%x\n", Status));
|
||||
DEBUG((EFI_D_ERROR, "Error locating MemCardInfoProtocol:%x\n", Status));
|
||||
return Status;
|
||||
}
|
||||
|
||||
if (CardInfo->Revision < EFI_MEM_CARD_INFO_PROTOCOL_REVISION) {
|
||||
DEBUG ((EFI_D_ERROR, "This API not supported in Revision =%u\n",
|
||||
DEBUG(
|
||||
(EFI_D_ERROR, "This API not supported in Revision =%u\n",
|
||||
CardInfo->Revision));
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
|
||||
if (IsGet == TRUE) {
|
||||
if (CardInfo->GetBootLU (CardInfo, UfsBootlun) == EFI_SUCCESS)
|
||||
DEBUG ((EFI_D_VERBOSE, "Get BootLun =%u\n", *UfsBootlun));
|
||||
} else {
|
||||
if (CardInfo->SetBootLU (CardInfo, *UfsBootlun) == EFI_SUCCESS)
|
||||
DEBUG ((EFI_D_VERBOSE, "SetBootLun =%u\n", *UfsBootlun));
|
||||
if (CardInfo->GetBootLU(CardInfo, UfsBootlun) == EFI_SUCCESS)
|
||||
DEBUG((EFI_D_VERBOSE, "Get BootLun =%u\n", *UfsBootlun));
|
||||
}
|
||||
else {
|
||||
if (CardInfo->SetBootLU(CardInfo, *UfsBootlun) == EFI_SUCCESS)
|
||||
DEBUG((EFI_D_VERBOSE, "SetBootLun =%u\n", *UfsBootlun));
|
||||
}
|
||||
return Status;
|
||||
}
|
@ -5,8 +5,8 @@
|
||||
#include <Library/HobLib.h>
|
||||
#include <Library/SerialPortLib.h>
|
||||
|
||||
#include <Resources/font5x12.h>
|
||||
#include <Resources/FbColor.h>
|
||||
#include <Resources/font5x12.h>
|
||||
|
||||
#include "FrameBufferSerialPortLib.h"
|
||||
|
||||
@ -21,21 +21,11 @@ UINTN gHeight = FixedPcdGet32(PcdMipiFrameBufferHeight);
|
||||
UINTN gBpp = FixedPcdGet32(PcdMipiFrameBufferPixelBpp);
|
||||
|
||||
// Module-used internal routine
|
||||
void FbConPutCharWithFactor
|
||||
(
|
||||
char c,
|
||||
int type,
|
||||
unsigned scale_factor
|
||||
);
|
||||
void FbConPutCharWithFactor(char c, int type, unsigned scale_factor);
|
||||
|
||||
void FbConDrawglyph
|
||||
(
|
||||
char *pixels,
|
||||
unsigned stride,
|
||||
unsigned bpp,
|
||||
unsigned *glyph,
|
||||
unsigned scale_factor
|
||||
);
|
||||
void FbConDrawglyph(
|
||||
char *pixels, unsigned stride, unsigned bpp, unsigned *glyph,
|
||||
unsigned scale_factor);
|
||||
|
||||
void FbConReset(void);
|
||||
void FbConScrollUp(void);
|
||||
@ -43,15 +33,13 @@ void FbConFlush(void);
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortInitialize
|
||||
(
|
||||
VOID
|
||||
)
|
||||
SerialPortInitialize(VOID)
|
||||
{
|
||||
UINTN InterruptState = 0;
|
||||
|
||||
// Prevent dup initialization
|
||||
if (m_Initialized) return RETURN_SUCCESS;
|
||||
if (m_Initialized)
|
||||
return RETURN_SUCCESS;
|
||||
|
||||
// Interrupt Disable
|
||||
InterruptState = ArmGetInterruptState();
|
||||
@ -63,25 +51,23 @@ SerialPortInitialize
|
||||
// Set flag
|
||||
m_Initialized = TRUE;
|
||||
|
||||
if (InterruptState) ArmEnableInterrupts();
|
||||
if (InterruptState)
|
||||
ArmEnableInterrupts();
|
||||
return RETURN_SUCCESS;
|
||||
}
|
||||
|
||||
void ResetFb(void)
|
||||
{
|
||||
// Clear current screen.
|
||||
char* Pixels = (void*)FixedPcdGet32(PcdMipiFrameBufferAddress);
|
||||
char *Pixels = (void *)FixedPcdGet32(PcdMipiFrameBufferAddress);
|
||||
UINTN BgColor = FB_BGRA8888_BLACK;
|
||||
|
||||
// Set to black color.
|
||||
for (UINTN i = 0; i < gWidth; i++)
|
||||
{
|
||||
for (UINTN j = 0; j < gHeight; j++)
|
||||
{
|
||||
for (UINTN i = 0; i < gWidth; i++) {
|
||||
for (UINTN j = 0; j < gHeight; j++) {
|
||||
BgColor = FB_BGRA8888_BLACK;
|
||||
// Set pixel bit
|
||||
for (UINTN p = 0; p < (gBpp / 8); p++)
|
||||
{
|
||||
for (UINTN p = 0; p < (gBpp / 8); p++) {
|
||||
*Pixels = (unsigned char)BgColor;
|
||||
BgColor = BgColor >> 8;
|
||||
Pixels++;
|
||||
@ -105,112 +91,91 @@ void FbConReset(void)
|
||||
m_Color.Background = FB_BGRA8888_BLACK;
|
||||
}
|
||||
|
||||
void FbConPutCharWithFactor
|
||||
(
|
||||
char c,
|
||||
int type,
|
||||
unsigned scale_factor
|
||||
)
|
||||
void FbConPutCharWithFactor(char c, int type, unsigned scale_factor)
|
||||
{
|
||||
char* Pixels;
|
||||
char *Pixels;
|
||||
|
||||
if (!m_Initialized) return;
|
||||
if (!m_Initialized)
|
||||
return;
|
||||
|
||||
paint:
|
||||
|
||||
if ((unsigned char)c > 127) return;
|
||||
if ((unsigned char)c > 127)
|
||||
return;
|
||||
|
||||
if ((unsigned char)c < 32)
|
||||
{
|
||||
if (c == '\n')
|
||||
{
|
||||
if ((unsigned char)c < 32) {
|
||||
if (c == '\n') {
|
||||
goto newline;
|
||||
}
|
||||
else if (c == '\r')
|
||||
{
|
||||
else if (c == '\r') {
|
||||
m_Position.x = 0;
|
||||
return;
|
||||
}
|
||||
else
|
||||
{
|
||||
else {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Save some space
|
||||
if (m_Position.x == 0 && (unsigned char)c == ' ' &&
|
||||
type != FBCON_SUBTITLE_MSG &&
|
||||
type != FBCON_TITLE_MSG)
|
||||
type != FBCON_SUBTITLE_MSG && type != FBCON_TITLE_MSG)
|
||||
return;
|
||||
|
||||
BOOLEAN intstate = ArmGetInterruptState();
|
||||
ArmDisableInterrupts();
|
||||
|
||||
Pixels = (void*)FixedPcdGet32(PcdMipiFrameBufferAddress);
|
||||
Pixels = (void *)FixedPcdGet32(PcdMipiFrameBufferAddress);
|
||||
Pixels += m_Position.y * ((gBpp / 8) * FONT_HEIGHT * gWidth);
|
||||
Pixels += m_Position.x * scale_factor * ((gBpp / 8) * (FONT_WIDTH + 1));
|
||||
|
||||
FbConDrawglyph(
|
||||
Pixels,
|
||||
gWidth,
|
||||
(gBpp / 8),
|
||||
font5x12 + (c - 32) * 2,
|
||||
scale_factor);
|
||||
Pixels, gWidth, (gBpp / 8), font5x12 + (c - 32) * 2, scale_factor);
|
||||
|
||||
m_Position.x++;
|
||||
|
||||
if (m_Position.x >= (int)(m_MaxPosition.x / scale_factor)) goto newline;
|
||||
if (m_Position.x >= (int)(m_MaxPosition.x / scale_factor))
|
||||
goto newline;
|
||||
|
||||
if (intstate) ArmEnableInterrupts();
|
||||
if (intstate)
|
||||
ArmEnableInterrupts();
|
||||
return;
|
||||
|
||||
newline:
|
||||
m_Position.y += scale_factor;
|
||||
m_Position.x = 0;
|
||||
if (m_Position.y >= m_MaxPosition.y - scale_factor)
|
||||
{
|
||||
if (m_Position.y >= m_MaxPosition.y - scale_factor) {
|
||||
ResetFb();
|
||||
FbConFlush();
|
||||
m_Position.y = 0;
|
||||
|
||||
if (intstate) ArmEnableInterrupts();
|
||||
if (intstate)
|
||||
ArmEnableInterrupts();
|
||||
goto paint;
|
||||
}
|
||||
else
|
||||
{
|
||||
else {
|
||||
FbConFlush();
|
||||
if (intstate) ArmEnableInterrupts();
|
||||
if (intstate)
|
||||
ArmEnableInterrupts();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void FbConDrawglyph
|
||||
(
|
||||
char *pixels,
|
||||
unsigned stride,
|
||||
unsigned bpp,
|
||||
unsigned *glyph,
|
||||
unsigned scale_factor
|
||||
)
|
||||
void FbConDrawglyph(
|
||||
char *pixels, unsigned stride, unsigned bpp, unsigned *glyph,
|
||||
unsigned scale_factor)
|
||||
{
|
||||
char *bg_pixels = pixels;
|
||||
char * bg_pixels = pixels;
|
||||
unsigned x, y, i, j, k;
|
||||
unsigned data, temp;
|
||||
unsigned int fg_color = m_Color.Foreground;
|
||||
unsigned int bg_color = m_Color.Background;
|
||||
stride -= FONT_WIDTH * scale_factor;
|
||||
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y)
|
||||
{
|
||||
for (i = 0; i < scale_factor; i++)
|
||||
{
|
||||
for (x = 0; x < FONT_WIDTH; ++x)
|
||||
{
|
||||
for (j = 0; j < scale_factor; j++)
|
||||
{
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y) {
|
||||
for (i = 0; i < scale_factor; i++) {
|
||||
for (x = 0; x < FONT_WIDTH; ++x) {
|
||||
for (j = 0; j < scale_factor; j++) {
|
||||
bg_color = m_Color.Background;
|
||||
for (k = 0; k < bpp; k++)
|
||||
{
|
||||
for (k = 0; k < bpp; k++) {
|
||||
*bg_pixels = (unsigned char)bg_color;
|
||||
bg_color = bg_color >> 8;
|
||||
bg_pixels++;
|
||||
@ -221,17 +186,12 @@ void FbConDrawglyph
|
||||
}
|
||||
}
|
||||
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y)
|
||||
{
|
||||
for (i = 0; i < scale_factor; i++)
|
||||
{
|
||||
for (x = 0; x < FONT_WIDTH; ++x)
|
||||
{
|
||||
for (j = 0; j < scale_factor; j++)
|
||||
{
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y) {
|
||||
for (i = 0; i < scale_factor; i++) {
|
||||
for (x = 0; x < FONT_WIDTH; ++x) {
|
||||
for (j = 0; j < scale_factor; j++) {
|
||||
bg_color = m_Color.Background;
|
||||
for (k = 0; k < bpp; k++)
|
||||
{
|
||||
for (k = 0; k < bpp; k++) {
|
||||
*bg_pixels = (unsigned char)bg_color;
|
||||
bg_color = bg_color >> 8;
|
||||
bg_pixels++;
|
||||
@ -243,31 +203,23 @@ void FbConDrawglyph
|
||||
}
|
||||
|
||||
data = glyph[0];
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y)
|
||||
{
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y) {
|
||||
temp = data;
|
||||
for (i = 0; i < scale_factor; i++)
|
||||
{
|
||||
for (i = 0; i < scale_factor; i++) {
|
||||
data = temp;
|
||||
for (x = 0; x < FONT_WIDTH; ++x)
|
||||
{
|
||||
if (data & 1)
|
||||
{
|
||||
for (j = 0; j < scale_factor; j++)
|
||||
{
|
||||
for (x = 0; x < FONT_WIDTH; ++x) {
|
||||
if (data & 1) {
|
||||
for (j = 0; j < scale_factor; j++) {
|
||||
fg_color = m_Color.Foreground;
|
||||
for (k = 0; k < bpp; k++)
|
||||
{
|
||||
for (k = 0; k < bpp; k++) {
|
||||
*pixels = (unsigned char)fg_color;
|
||||
fg_color = fg_color >> 8;
|
||||
pixels++;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (j = 0; j < scale_factor; j++)
|
||||
{
|
||||
else {
|
||||
for (j = 0; j < scale_factor; j++) {
|
||||
pixels = pixels + bpp;
|
||||
}
|
||||
}
|
||||
@ -278,31 +230,23 @@ void FbConDrawglyph
|
||||
}
|
||||
|
||||
data = glyph[1];
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y)
|
||||
{
|
||||
for (y = 0; y < FONT_HEIGHT / 2; ++y) {
|
||||
temp = data;
|
||||
for (i = 0; i < scale_factor; i++)
|
||||
{
|
||||
for (i = 0; i < scale_factor; i++) {
|
||||
data = temp;
|
||||
for (x = 0; x < FONT_WIDTH; ++x)
|
||||
{
|
||||
if (data & 1)
|
||||
{
|
||||
for (j = 0; j < scale_factor; j++)
|
||||
{
|
||||
for (x = 0; x < FONT_WIDTH; ++x) {
|
||||
if (data & 1) {
|
||||
for (j = 0; j < scale_factor; j++) {
|
||||
fg_color = m_Color.Foreground;
|
||||
for (k = 0; k < bpp; k++)
|
||||
{
|
||||
for (k = 0; k < bpp; k++) {
|
||||
*pixels = (unsigned char)fg_color;
|
||||
fg_color = fg_color >> 8;
|
||||
pixels++;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (j = 0; j < scale_factor; j++)
|
||||
{
|
||||
else {
|
||||
for (j = 0; j < scale_factor; j++) {
|
||||
pixels = pixels + bpp;
|
||||
}
|
||||
}
|
||||
@ -316,18 +260,16 @@ void FbConDrawglyph
|
||||
/* TODO: Take stride into account */
|
||||
void FbConScrollUp(void)
|
||||
{
|
||||
unsigned short *dst = (void*)FixedPcdGet32(PcdMipiFrameBufferAddress);
|
||||
unsigned short *dst = (void *)FixedPcdGet32(PcdMipiFrameBufferAddress);
|
||||
unsigned short *src = dst + (gWidth * FONT_HEIGHT);
|
||||
unsigned count = gWidth * (gHeight - FONT_HEIGHT);
|
||||
|
||||
while (count--)
|
||||
{
|
||||
while (count--) {
|
||||
*dst++ = *src++;
|
||||
}
|
||||
|
||||
count = gWidth * FONT_HEIGHT;
|
||||
while (count--)
|
||||
{
|
||||
while (count--) {
|
||||
*dst++ = m_Color.Background;
|
||||
}
|
||||
|
||||
@ -344,121 +286,78 @@ void FbConFlush(void)
|
||||
bytes_per_bpp = (gBpp / 8);
|
||||
|
||||
WriteBackInvalidateDataCacheRange(
|
||||
(void*)FixedPcdGet32(PcdMipiFrameBufferAddress),
|
||||
(total_x * total_y * bytes_per_bpp)
|
||||
);
|
||||
(void *)FixedPcdGet32(PcdMipiFrameBufferAddress),
|
||||
(total_x * total_y * bytes_per_bpp));
|
||||
}
|
||||
|
||||
UINTN
|
||||
EFIAPI
|
||||
SerialPortWrite
|
||||
(
|
||||
IN UINT8 *Buffer,
|
||||
IN UINTN NumberOfBytes
|
||||
)
|
||||
SerialPortWrite(IN UINT8 *Buffer, IN UINTN NumberOfBytes)
|
||||
{
|
||||
UINT8* CONST Final = &Buffer[NumberOfBytes];
|
||||
UINT8 *CONST Final = &Buffer[NumberOfBytes];
|
||||
UINTN InterruptState = ArmGetInterruptState();
|
||||
ArmDisableInterrupts();
|
||||
|
||||
while (Buffer < Final)
|
||||
{
|
||||
while (Buffer < Final) {
|
||||
FbConPutCharWithFactor(*Buffer++, FBCON_COMMON_MSG, SCALE_FACTOR);
|
||||
}
|
||||
|
||||
if (InterruptState) ArmEnableInterrupts();
|
||||
if (InterruptState)
|
||||
ArmEnableInterrupts();
|
||||
return NumberOfBytes;
|
||||
}
|
||||
|
||||
UINTN
|
||||
EFIAPI
|
||||
SerialPortWriteCritical
|
||||
(
|
||||
IN UINT8 *Buffer,
|
||||
IN UINTN NumberOfBytes
|
||||
)
|
||||
SerialPortWriteCritical(IN UINT8 *Buffer, IN UINTN NumberOfBytes)
|
||||
{
|
||||
UINT8* CONST Final = &Buffer[NumberOfBytes];
|
||||
UINT8 *CONST Final = &Buffer[NumberOfBytes];
|
||||
UINTN CurrentForeground = m_Color.Foreground;
|
||||
UINTN InterruptState = ArmGetInterruptState();
|
||||
|
||||
ArmDisableInterrupts();
|
||||
m_Color.Foreground = FB_BGRA8888_YELLOW;
|
||||
|
||||
while (Buffer < Final)
|
||||
{
|
||||
while (Buffer < Final) {
|
||||
FbConPutCharWithFactor(*Buffer++, FBCON_COMMON_MSG, SCALE_FACTOR);
|
||||
}
|
||||
|
||||
m_Color.Foreground = CurrentForeground;
|
||||
|
||||
if (InterruptState) ArmEnableInterrupts();
|
||||
if (InterruptState)
|
||||
ArmEnableInterrupts();
|
||||
return NumberOfBytes;
|
||||
}
|
||||
|
||||
UINTN
|
||||
EFIAPI
|
||||
SerialPortRead
|
||||
(
|
||||
OUT UINT8 *Buffer,
|
||||
IN UINTN NumberOfBytes
|
||||
)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
SerialPortRead(OUT UINT8 *Buffer, IN UINTN NumberOfBytes) { return 0; }
|
||||
|
||||
BOOLEAN
|
||||
EFIAPI
|
||||
SerialPortPoll
|
||||
(
|
||||
VOID
|
||||
)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
SerialPortPoll(VOID) { return FALSE; }
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortSetControl
|
||||
(
|
||||
IN UINT32 Control
|
||||
)
|
||||
SerialPortSetControl(IN UINT32 Control) { return RETURN_UNSUPPORTED; }
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortGetControl(OUT UINT32 *Control) { return RETURN_UNSUPPORTED; }
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortSetAttributes(
|
||||
IN OUT UINT64 *BaudRate, IN OUT UINT32 *ReceiveFifoDepth,
|
||||
IN OUT UINT32 *Timeout, IN OUT EFI_PARITY_TYPE *Parity,
|
||||
IN OUT UINT8 *DataBits, IN OUT EFI_STOP_BITS_TYPE *StopBits)
|
||||
{
|
||||
return RETURN_UNSUPPORTED;
|
||||
}
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortGetControl
|
||||
(
|
||||
OUT UINT32 *Control
|
||||
)
|
||||
{
|
||||
return RETURN_UNSUPPORTED;
|
||||
}
|
||||
UINTN SerialPortFlush(VOID) { return 0; }
|
||||
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortSetAttributes
|
||||
(
|
||||
IN OUT UINT64 *BaudRate,
|
||||
IN OUT UINT32 *ReceiveFifoDepth,
|
||||
IN OUT UINT32 *Timeout,
|
||||
IN OUT EFI_PARITY_TYPE *Parity,
|
||||
IN OUT UINT8 *DataBits,
|
||||
IN OUT EFI_STOP_BITS_TYPE *StopBits
|
||||
)
|
||||
{
|
||||
return RETURN_UNSUPPORTED;
|
||||
}
|
||||
|
||||
UINTN SerialPortFlush(VOID)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
VOID
|
||||
EnableSynchronousSerialPortIO(VOID)
|
||||
VOID EnableSynchronousSerialPortIO(VOID)
|
||||
{
|
||||
// Already synchronous
|
||||
}
|
@ -32,10 +32,6 @@ void ResetFb(void);
|
||||
|
||||
UINTN
|
||||
EFIAPI
|
||||
SerialPortWriteCritical
|
||||
(
|
||||
IN UINT8 *Buffer,
|
||||
IN UINTN NumberOfBytes
|
||||
);
|
||||
SerialPortWriteCritical(IN UINT8 *Buffer, IN UINTN NumberOfBytes);
|
||||
|
||||
#endif
|
||||
|
@ -3,26 +3,26 @@
|
||||
|
||||
Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
|
||||
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.
|
||||
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.
|
||||
|
||||
**/
|
||||
|
||||
|
||||
#include <Base.h>
|
||||
#include <Library/SerialPortLib.h>
|
||||
#include <Library/CacheMaintenanceLib.h>
|
||||
#include <Library/SerialPortLib.h>
|
||||
|
||||
/**
|
||||
Initialize the serial device hardware.
|
||||
|
||||
If no initialization is required, then return RETURN_SUCCESS.
|
||||
If the serial device was successfully initialized, then return RETURN_SUCCESS.
|
||||
If the serial device could not be initialized, then return RETURN_DEVICE_ERROR.
|
||||
If the serial device could not be initialized, then return
|
||||
RETURN_DEVICE_ERROR.
|
||||
|
||||
@retval RETURN_SUCCESS The serial device was initialized.
|
||||
@retval RETURN_DEVICE_ERROR The serial device could not be initialized.
|
||||
@ -30,9 +30,7 @@
|
||||
**/
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortInitialize (
|
||||
VOID
|
||||
)
|
||||
SerialPortInitialize(VOID)
|
||||
{
|
||||
#if 0
|
||||
UINT8* base = (UINT8*)0xa1a10000ull;
|
||||
@ -43,10 +41,11 @@ SerialPortInitialize (
|
||||
return RETURN_SUCCESS;
|
||||
}
|
||||
|
||||
static void mem_putchar(UINT8 c) {
|
||||
static void mem_putchar(UINT8 c)
|
||||
{
|
||||
static const UINTN size = 0x200000;
|
||||
static UINTN offset = 0;
|
||||
UINT8* base = (UINT8*)0xa1a10000ull;
|
||||
UINT8 * base = (UINT8 *)0xa1a10000ull;
|
||||
base[offset++] = c;
|
||||
if (offset >= size) {
|
||||
offset = 0;
|
||||
@ -59,24 +58,22 @@ static void mem_putchar(UINT8 c) {
|
||||
|
||||
Writes NumberOfBytes data bytes from Buffer to the serial device.
|
||||
The number of bytes actually written to the serial device is returned.
|
||||
If the return value is less than NumberOfBytes, then the write operation failed.
|
||||
If Buffer is NULL, then ASSERT().
|
||||
If NumberOfBytes is zero, then return 0.
|
||||
If the return value is less than NumberOfBytes, then the write operation
|
||||
failed. If Buffer is NULL, then ASSERT(). If NumberOfBytes is zero, then return
|
||||
0.
|
||||
|
||||
@param Buffer The pointer to the data buffer to be written.
|
||||
@param NumberOfBytes The number of bytes to written to the serial device.
|
||||
|
||||
@retval 0 NumberOfBytes is 0.
|
||||
@retval >0 The number of bytes written to the serial device.
|
||||
If this value is less than NumberOfBytes, then the write operation failed.
|
||||
If this value is less than NumberOfBytes, then the
|
||||
write operation failed.
|
||||
|
||||
**/
|
||||
UINTN
|
||||
EFIAPI
|
||||
SerialPortWrite (
|
||||
IN UINT8 *Buffer,
|
||||
IN UINTN NumberOfBytes
|
||||
)
|
||||
SerialPortWrite(IN UINT8 *Buffer, IN UINTN NumberOfBytes)
|
||||
{
|
||||
for (UINTN i = 0; i < NumberOfBytes; i++) {
|
||||
mem_putchar(Buffer[i]);
|
||||
@ -84,17 +81,17 @@ SerialPortWrite (
|
||||
return NumberOfBytes;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
Read data from serial device and save the datas in buffer.
|
||||
|
||||
Reads NumberOfBytes data bytes from a serial device into the buffer
|
||||
specified by Buffer. The number of bytes actually read is returned.
|
||||
If the return value is less than NumberOfBytes, then the rest operation failed.
|
||||
If Buffer is NULL, then ASSERT().
|
||||
If NumberOfBytes is zero, then return 0.
|
||||
If the return value is less than NumberOfBytes, then the rest operation
|
||||
failed. If Buffer is NULL, then ASSERT(). If NumberOfBytes is zero, then return
|
||||
0.
|
||||
|
||||
@param Buffer The pointer to the data buffer to store the data read from the serial device.
|
||||
@param Buffer The pointer to the data buffer to store the data read
|
||||
from the serial device.
|
||||
@param NumberOfBytes The number of bytes which will be read.
|
||||
|
||||
@retval 0 Read data failed; No data is to be read.
|
||||
@ -103,116 +100,97 @@ SerialPortWrite (
|
||||
**/
|
||||
UINTN
|
||||
EFIAPI
|
||||
SerialPortRead (
|
||||
OUT UINT8 *Buffer,
|
||||
IN UINTN NumberOfBytes
|
||||
)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
SerialPortRead(OUT UINT8 *Buffer, IN UINTN NumberOfBytes) { return 0; }
|
||||
|
||||
/**
|
||||
Polls a serial device to see if there is any data waiting to be read.
|
||||
|
||||
Polls a serial device to see if there is any data waiting to be read.
|
||||
If there is data waiting to be read from the serial device, then TRUE is returned.
|
||||
If there is no data waiting to be read from the serial device, then FALSE is returned.
|
||||
If there is data waiting to be read from the serial device, then TRUE is
|
||||
returned. If there is no data waiting to be read from the serial device, then
|
||||
FALSE is returned.
|
||||
|
||||
@retval TRUE Data is waiting to be read from the serial device.
|
||||
@retval FALSE There is no data waiting to be read from the serial device.
|
||||
@retval FALSE There is no data waiting to be read from the serial
|
||||
device.
|
||||
|
||||
**/
|
||||
BOOLEAN
|
||||
EFIAPI
|
||||
SerialPortPoll (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
SerialPortPoll(VOID) { return FALSE; }
|
||||
|
||||
/**
|
||||
Sets the control bits on a serial device.
|
||||
|
||||
@param Control Sets the bits of Control that are settable.
|
||||
|
||||
@retval RETURN_SUCCESS The new control bits were set on the serial device.
|
||||
@retval RETURN_UNSUPPORTED The serial device does not support this operation.
|
||||
@retval RETURN_SUCCESS The new control bits were set on the serial
|
||||
device.
|
||||
@retval RETURN_UNSUPPORTED The serial device does not support this
|
||||
operation.
|
||||
@retval RETURN_DEVICE_ERROR The serial device is not functioning correctly.
|
||||
|
||||
**/
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortSetControl (
|
||||
IN UINT32 Control
|
||||
)
|
||||
{
|
||||
return RETURN_UNSUPPORTED;
|
||||
}
|
||||
SerialPortSetControl(IN UINT32 Control) { return RETURN_UNSUPPORTED; }
|
||||
|
||||
/**
|
||||
Retrieve the status of the control bits on a serial device.
|
||||
|
||||
@param Control A pointer to return the current control signals from the serial device.
|
||||
@param Control A pointer to return the current control signals
|
||||
from the serial device.
|
||||
|
||||
@retval RETURN_SUCCESS The control bits were read from the serial device.
|
||||
@retval RETURN_UNSUPPORTED The serial device does not support this operation.
|
||||
@retval RETURN_SUCCESS The control bits were read from the serial
|
||||
device.
|
||||
@retval RETURN_UNSUPPORTED The serial device does not support this
|
||||
operation.
|
||||
@retval RETURN_DEVICE_ERROR The serial device is not functioning correctly.
|
||||
|
||||
**/
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortGetControl (
|
||||
OUT UINT32 *Control
|
||||
)
|
||||
{
|
||||
return RETURN_UNSUPPORTED;
|
||||
}
|
||||
SerialPortGetControl(OUT UINT32 *Control) { return RETURN_UNSUPPORTED; }
|
||||
|
||||
/**
|
||||
Sets the baud rate, receive FIFO depth, transmit/receice time out, parity,
|
||||
data bits, and stop bits on a serial device.
|
||||
|
||||
@param BaudRate The requested baud rate. A BaudRate value of 0 will use the
|
||||
device's default interface speed.
|
||||
On output, the value actually set.
|
||||
@param ReveiveFifoDepth The requested depth of the FIFO on the receive side of the
|
||||
serial interface. A ReceiveFifoDepth value of 0 will use
|
||||
the device's default FIFO depth.
|
||||
On output, the value actually set.
|
||||
@param Timeout The requested time out for a single character in microseconds.
|
||||
This timeout applies to both the transmit and receive side of the
|
||||
interface. A Timeout value of 0 will use the device's default time
|
||||
out value.
|
||||
On output, the value actually set.
|
||||
@param Parity The type of parity to use on this serial device. A Parity value of
|
||||
DefaultParity will use the device's default parity value.
|
||||
On output, the value actually set.
|
||||
@param DataBits The number of data bits to use on the serial device. A DataBits
|
||||
vaule of 0 will use the device's default data bit setting.
|
||||
On output, the value actually set.
|
||||
@param StopBits The number of stop bits to use on this serial device. A StopBits
|
||||
value of DefaultStopBits will use the device's default number of
|
||||
stop bits.
|
||||
On output, the value actually set.
|
||||
@param BaudRate The requested baud rate. A BaudRate value of 0 will
|
||||
use the device's default interface speed. On output, the value actually set.
|
||||
@param ReveiveFifoDepth The requested depth of the FIFO on the receive side
|
||||
of the serial interface. A ReceiveFifoDepth value of 0 will use the device's
|
||||
default FIFO depth. On output, the value actually set.
|
||||
@param Timeout The requested time out for a single character in
|
||||
microseconds. This timeout applies to both the transmit and receive side of the
|
||||
interface. A Timeout value of 0 will use the
|
||||
device's default time out value. On output, the value actually set.
|
||||
@param Parity The type of parity to use on this serial device. A
|
||||
Parity value of DefaultParity will use the device's default parity value. On
|
||||
output, the value actually set.
|
||||
@param DataBits The number of data bits to use on the serial device.
|
||||
A DataBits vaule of 0 will use the device's default data bit setting. On output,
|
||||
the value actually set.
|
||||
@param StopBits The number of stop bits to use on this serial
|
||||
device. A StopBits value of DefaultStopBits will use the device's default number
|
||||
of stop bits. On output, the value actually set.
|
||||
|
||||
@retval RETURN_SUCCESS The new attributes were set on the serial device.
|
||||
@retval RETURN_UNSUPPORTED The serial device does not support this operation.
|
||||
@retval RETURN_INVALID_PARAMETER One or more of the attributes has an unsupported value.
|
||||
@retval RETURN_DEVICE_ERROR The serial device is not functioning correctly.
|
||||
@retval RETURN_SUCCESS The new attributes were set on the serial
|
||||
device.
|
||||
@retval RETURN_UNSUPPORTED The serial device does not support this
|
||||
operation.
|
||||
@retval RETURN_INVALID_PARAMETER One or more of the attributes has an
|
||||
unsupported value.
|
||||
@retval RETURN_DEVICE_ERROR The serial device is not functioning
|
||||
correctly.
|
||||
|
||||
**/
|
||||
RETURN_STATUS
|
||||
EFIAPI
|
||||
SerialPortSetAttributes (
|
||||
IN OUT UINT64 *BaudRate,
|
||||
IN OUT UINT32 *ReceiveFifoDepth,
|
||||
IN OUT UINT32 *Timeout,
|
||||
IN OUT EFI_PARITY_TYPE *Parity,
|
||||
IN OUT UINT8 *DataBits,
|
||||
IN OUT EFI_STOP_BITS_TYPE *StopBits
|
||||
)
|
||||
SerialPortSetAttributes(
|
||||
IN OUT UINT64 *BaudRate, IN OUT UINT32 *ReceiveFifoDepth,
|
||||
IN OUT UINT32 *Timeout, IN OUT EFI_PARITY_TYPE *Parity,
|
||||
IN OUT UINT8 *DataBits, IN OUT EFI_STOP_BITS_TYPE *StopBits)
|
||||
{
|
||||
return RETURN_UNSUPPORTED;
|
||||
}
|
||||
|
||||
|
@ -10,6 +10,9 @@
|
||||
|
||||
**/
|
||||
|
||||
#include <Guid/EventGroup.h>
|
||||
#include <Guid/SerialPortLibVendor.h>
|
||||
#include <Guid/TtyTerm.h>
|
||||
#include <IndustryStandard/Pci22.h>
|
||||
#include <Library/BootLogoLib.h>
|
||||
#include <Library/CapsuleLib.h>
|
||||
@ -26,54 +29,48 @@
|
||||
#include <Protocol/PciIo.h>
|
||||
#include <Protocol/PciRootBridgeIo.h>
|
||||
#include <Protocol/PlatformBootManager.h>
|
||||
#include <Guid/EventGroup.h>
|
||||
#include <Guid/TtyTerm.h>
|
||||
#include <Guid/SerialPortLibVendor.h>
|
||||
|
||||
#include "PlatformBm.h"
|
||||
|
||||
#define DP_NODE_LEN(Type) \
|
||||
{ \
|
||||
(UINT8)sizeof(Type), (UINT8)(sizeof(Type) >> 8) \
|
||||
}
|
||||
|
||||
|
||||
#define DP_NODE_LEN(Type) { (UINT8)sizeof (Type), (UINT8)(sizeof (Type) >> 8) }
|
||||
|
||||
#pragma pack (1)
|
||||
#pragma pack(1)
|
||||
typedef struct {
|
||||
VENDOR_DEVICE_PATH SerialDxe;
|
||||
UART_DEVICE_PATH Uart;
|
||||
VENDOR_DEFINED_DEVICE_PATH TermType;
|
||||
EFI_DEVICE_PATH_PROTOCOL End;
|
||||
} PLATFORM_SERIAL_CONSOLE;
|
||||
#pragma pack ()
|
||||
#pragma pack()
|
||||
|
||||
STATIC PLATFORM_SERIAL_CONSOLE mSerialConsole = {
|
||||
//
|
||||
// VENDOR_DEVICE_PATH SerialDxe
|
||||
//
|
||||
{
|
||||
{ HARDWARE_DEVICE_PATH, HW_VENDOR_DP, DP_NODE_LEN (VENDOR_DEVICE_PATH) },
|
||||
EDKII_SERIAL_PORT_LIB_VENDOR_GUID
|
||||
},
|
||||
{{HARDWARE_DEVICE_PATH, HW_VENDOR_DP, DP_NODE_LEN(VENDOR_DEVICE_PATH)},
|
||||
EDKII_SERIAL_PORT_LIB_VENDOR_GUID},
|
||||
|
||||
//
|
||||
// UART_DEVICE_PATH Uart
|
||||
//
|
||||
{
|
||||
{ MESSAGING_DEVICE_PATH, MSG_UART_DP, DP_NODE_LEN (UART_DEVICE_PATH) },
|
||||
{MESSAGING_DEVICE_PATH, MSG_UART_DP, DP_NODE_LEN(UART_DEVICE_PATH)},
|
||||
0, // Reserved
|
||||
FixedPcdGet64 (PcdUartDefaultBaudRate), // BaudRate
|
||||
FixedPcdGet8 (PcdUartDefaultDataBits), // DataBits
|
||||
FixedPcdGet8 (PcdUartDefaultParity), // Parity
|
||||
FixedPcdGet8 (PcdUartDefaultStopBits) // StopBits
|
||||
FixedPcdGet64(PcdUartDefaultBaudRate), // BaudRate
|
||||
FixedPcdGet8(PcdUartDefaultDataBits), // DataBits
|
||||
FixedPcdGet8(PcdUartDefaultParity), // Parity
|
||||
FixedPcdGet8(PcdUartDefaultStopBits) // StopBits
|
||||
},
|
||||
|
||||
//
|
||||
// VENDOR_DEFINED_DEVICE_PATH TermType
|
||||
//
|
||||
{
|
||||
{
|
||||
MESSAGING_DEVICE_PATH, MSG_VENDOR_DP,
|
||||
DP_NODE_LEN (VENDOR_DEFINED_DEVICE_PATH)
|
||||
}
|
||||
{MESSAGING_DEVICE_PATH, MSG_VENDOR_DP,
|
||||
DP_NODE_LEN(VENDOR_DEFINED_DEVICE_PATH)}
|
||||
//
|
||||
// Guid to be filled in dynamically
|
||||
//
|
||||
@ -82,29 +79,23 @@ STATIC PLATFORM_SERIAL_CONSOLE mSerialConsole = {
|
||||
//
|
||||
// EFI_DEVICE_PATH_PROTOCOL End
|
||||
//
|
||||
{
|
||||
END_DEVICE_PATH_TYPE, END_ENTIRE_DEVICE_PATH_SUBTYPE,
|
||||
DP_NODE_LEN (EFI_DEVICE_PATH_PROTOCOL)
|
||||
}
|
||||
};
|
||||
{END_DEVICE_PATH_TYPE, END_ENTIRE_DEVICE_PATH_SUBTYPE,
|
||||
DP_NODE_LEN(EFI_DEVICE_PATH_PROTOCOL)}};
|
||||
|
||||
|
||||
#pragma pack (1)
|
||||
#pragma pack(1)
|
||||
typedef struct {
|
||||
USB_CLASS_DEVICE_PATH Keyboard;
|
||||
EFI_DEVICE_PATH_PROTOCOL End;
|
||||
} PLATFORM_USB_KEYBOARD;
|
||||
#pragma pack ()
|
||||
#pragma pack()
|
||||
|
||||
STATIC PLATFORM_USB_KEYBOARD mUsbKeyboard = {
|
||||
//
|
||||
// USB_CLASS_DEVICE_PATH Keyboard
|
||||
//
|
||||
{
|
||||
{
|
||||
MESSAGING_DEVICE_PATH, MSG_USB_CLASS_DP,
|
||||
DP_NODE_LEN (USB_CLASS_DEVICE_PATH)
|
||||
},
|
||||
{MESSAGING_DEVICE_PATH, MSG_USB_CLASS_DP,
|
||||
DP_NODE_LEN(USB_CLASS_DEVICE_PATH)},
|
||||
0xFFFF, // VendorId: any
|
||||
0xFFFF, // ProductId: any
|
||||
3, // DeviceClass: HID
|
||||
@ -115,12 +106,8 @@ STATIC PLATFORM_USB_KEYBOARD mUsbKeyboard = {
|
||||
//
|
||||
// EFI_DEVICE_PATH_PROTOCOL End
|
||||
//
|
||||
{
|
||||
END_DEVICE_PATH_TYPE, END_ENTIRE_DEVICE_PATH_SUBTYPE,
|
||||
DP_NODE_LEN (EFI_DEVICE_PATH_PROTOCOL)
|
||||
}
|
||||
};
|
||||
|
||||
{END_DEVICE_PATH_TYPE, END_ENTIRE_DEVICE_PATH_SUBTYPE,
|
||||
DP_NODE_LEN(EFI_DEVICE_PATH_PROTOCOL)}};
|
||||
|
||||
/**
|
||||
Check if the handle satisfies a particular condition.
|
||||
@ -133,13 +120,8 @@ STATIC PLATFORM_USB_KEYBOARD mUsbKeyboard = {
|
||||
@retval FALSE Otherwise. This includes the case when the condition could not
|
||||
be fully evaluated due to an error.
|
||||
**/
|
||||
typedef
|
||||
BOOLEAN
|
||||
(EFIAPI *FILTER_FUNCTION) (
|
||||
IN EFI_HANDLE Handle,
|
||||
IN CONST CHAR16 *ReportText
|
||||
);
|
||||
|
||||
typedef BOOLEAN(EFIAPI *FILTER_FUNCTION)(
|
||||
IN EFI_HANDLE Handle, IN CONST CHAR16 *ReportText);
|
||||
|
||||
/**
|
||||
Process a handle.
|
||||
@ -148,12 +130,8 @@ BOOLEAN
|
||||
@param[in] ReportText A caller-allocated string passed in for reporting
|
||||
purposes. It must never be NULL.
|
||||
**/
|
||||
typedef
|
||||
VOID
|
||||
(EFIAPI *CALLBACK_FUNCTION) (
|
||||
IN EFI_HANDLE Handle,
|
||||
IN CONST CHAR16 *ReportText
|
||||
);
|
||||
typedef VOID(EFIAPI *CALLBACK_FUNCTION)(
|
||||
IN EFI_HANDLE Handle, IN CONST CHAR16 *ReportText);
|
||||
|
||||
/**
|
||||
Locate all handles that carry the specified protocol, filter them with a
|
||||
@ -169,39 +147,35 @@ VOID
|
||||
clears the filter.
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
FilterAndProcess (
|
||||
IN EFI_GUID *ProtocolGuid,
|
||||
IN FILTER_FUNCTION Filter OPTIONAL,
|
||||
IN CALLBACK_FUNCTION Process
|
||||
)
|
||||
VOID FilterAndProcess(
|
||||
IN EFI_GUID *ProtocolGuid, IN FILTER_FUNCTION Filter OPTIONAL,
|
||||
IN CALLBACK_FUNCTION Process)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_HANDLE *Handles;
|
||||
UINTN NoHandles;
|
||||
UINTN Idx;
|
||||
|
||||
Status = gBS->LocateHandleBuffer (ByProtocol, ProtocolGuid,
|
||||
NULL /* SearchKey */, &NoHandles, &Handles);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->LocateHandleBuffer(
|
||||
ByProtocol, ProtocolGuid, NULL /* SearchKey */, &NoHandles, &Handles);
|
||||
if (EFI_ERROR(Status)) {
|
||||
//
|
||||
// This is not an error, just an informative condition.
|
||||
//
|
||||
DEBUG ((EFI_D_VERBOSE, "%a: %g: %r\n", __FUNCTION__, ProtocolGuid,
|
||||
Status));
|
||||
DEBUG((EFI_D_VERBOSE, "%a: %g: %r\n", __FUNCTION__, ProtocolGuid, Status));
|
||||
return;
|
||||
}
|
||||
|
||||
ASSERT (NoHandles > 0);
|
||||
ASSERT(NoHandles > 0);
|
||||
for (Idx = 0; Idx < NoHandles; ++Idx) {
|
||||
CHAR16 *DevicePathText;
|
||||
CHAR16 * DevicePathText;
|
||||
STATIC CHAR16 Fallback[] = L"<device path unavailable>";
|
||||
|
||||
//
|
||||
// The ConvertDevicePathToText() function handles NULL input transparently.
|
||||
//
|
||||
DevicePathText = ConvertDevicePathToText (
|
||||
DevicePathFromHandle (Handles[Idx]),
|
||||
DevicePathText = ConvertDevicePathToText(
|
||||
DevicePathFromHandle(Handles[Idx]),
|
||||
FALSE, // DisplayOnly
|
||||
FALSE // AllowShortcuts
|
||||
);
|
||||
@ -209,220 +183,183 @@ FilterAndProcess (
|
||||
DevicePathText = Fallback;
|
||||
}
|
||||
|
||||
if (Filter == NULL || Filter (Handles[Idx], DevicePathText)) {
|
||||
Process (Handles[Idx], DevicePathText);
|
||||
if (Filter == NULL || Filter(Handles[Idx], DevicePathText)) {
|
||||
Process(Handles[Idx], DevicePathText);
|
||||
}
|
||||
|
||||
if (DevicePathText != Fallback) {
|
||||
FreePool (DevicePathText);
|
||||
FreePool(DevicePathText);
|
||||
}
|
||||
}
|
||||
gBS->FreePool (Handles);
|
||||
gBS->FreePool(Handles);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
This FILTER_FUNCTION checks if a handle corresponds to a PCI display device.
|
||||
**/
|
||||
STATIC
|
||||
BOOLEAN
|
||||
EFIAPI
|
||||
IsPciDisplay (
|
||||
IN EFI_HANDLE Handle,
|
||||
IN CONST CHAR16 *ReportText
|
||||
)
|
||||
IsPciDisplay(IN EFI_HANDLE Handle, IN CONST CHAR16 *ReportText)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_PCI_IO_PROTOCOL *PciIo;
|
||||
PCI_TYPE00 Pci;
|
||||
|
||||
Status = gBS->HandleProtocol (Handle, &gEfiPciIoProtocolGuid,
|
||||
(VOID**)&PciIo);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->HandleProtocol(Handle, &gEfiPciIoProtocolGuid, (VOID **)&PciIo);
|
||||
if (EFI_ERROR(Status)) {
|
||||
//
|
||||
// This is not an error worth reporting.
|
||||
//
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
Status = PciIo->Pci.Read (PciIo, EfiPciIoWidthUint32, 0 /* Offset */,
|
||||
sizeof Pci / sizeof (UINT32), &Pci);
|
||||
if (EFI_ERROR (Status)) {
|
||||
DEBUG ((EFI_D_ERROR, "%a: %s: %r\n", __FUNCTION__, ReportText, Status));
|
||||
Status = PciIo->Pci.Read(
|
||||
PciIo, EfiPciIoWidthUint32, 0 /* Offset */, sizeof Pci / sizeof(UINT32),
|
||||
&Pci);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG((EFI_D_ERROR, "%a: %s: %r\n", __FUNCTION__, ReportText, Status));
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return IS_PCI_DISPLAY (&Pci);
|
||||
return IS_PCI_DISPLAY(&Pci);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
This CALLBACK_FUNCTION attempts to connect a handle non-recursively, asking
|
||||
the matching driver to produce all first-level child handles.
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
EFIAPI
|
||||
Connect (
|
||||
IN EFI_HANDLE Handle,
|
||||
IN CONST CHAR16 *ReportText
|
||||
)
|
||||
VOID EFIAPI Connect(IN EFI_HANDLE Handle, IN CONST CHAR16 *ReportText)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
Status = gBS->ConnectController (
|
||||
Status = gBS->ConnectController(
|
||||
Handle, // ControllerHandle
|
||||
NULL, // DriverImageHandle
|
||||
NULL, // RemainingDevicePath -- produce all children
|
||||
FALSE // Recursive
|
||||
);
|
||||
DEBUG ((EFI_ERROR (Status) ? EFI_D_ERROR : EFI_D_VERBOSE, "%a: %s: %r\n",
|
||||
DEBUG(
|
||||
(EFI_ERROR(Status) ? EFI_D_ERROR : EFI_D_VERBOSE, "%a: %s: %r\n",
|
||||
__FUNCTION__, ReportText, Status));
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
This CALLBACK_FUNCTION retrieves the EFI_DEVICE_PATH_PROTOCOL from the
|
||||
handle, and adds it to ConOut and ErrOut.
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
EFIAPI
|
||||
AddOutput (
|
||||
IN EFI_HANDLE Handle,
|
||||
IN CONST CHAR16 *ReportText
|
||||
)
|
||||
VOID EFIAPI AddOutput(IN EFI_HANDLE Handle, IN CONST CHAR16 *ReportText)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
|
||||
|
||||
DevicePath = DevicePathFromHandle (Handle);
|
||||
DevicePath = DevicePathFromHandle(Handle);
|
||||
if (DevicePath == NULL) {
|
||||
DEBUG ((EFI_D_ERROR, "%a: %s: handle %p: device path not found\n",
|
||||
DEBUG(
|
||||
(EFI_D_ERROR, "%a: %s: handle %p: device path not found\n",
|
||||
__FUNCTION__, ReportText, Handle));
|
||||
return;
|
||||
}
|
||||
|
||||
Status = EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
|
||||
if (EFI_ERROR (Status)) {
|
||||
DEBUG ((EFI_D_ERROR, "%a: %s: adding to ConOut: %r\n", __FUNCTION__,
|
||||
Status = EfiBootManagerUpdateConsoleVariable(ConOut, DevicePath, NULL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG(
|
||||
(EFI_D_ERROR, "%a: %s: adding to ConOut: %r\n", __FUNCTION__,
|
||||
ReportText, Status));
|
||||
return;
|
||||
}
|
||||
|
||||
Status = EfiBootManagerUpdateConsoleVariable (ErrOut, DevicePath, NULL);
|
||||
if (EFI_ERROR (Status)) {
|
||||
DEBUG ((EFI_D_ERROR, "%a: %s: adding to ErrOut: %r\n", __FUNCTION__,
|
||||
Status = EfiBootManagerUpdateConsoleVariable(ErrOut, DevicePath, NULL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG(
|
||||
(EFI_D_ERROR, "%a: %s: adding to ErrOut: %r\n", __FUNCTION__,
|
||||
ReportText, Status));
|
||||
return;
|
||||
}
|
||||
|
||||
DEBUG ((EFI_D_VERBOSE, "%a: %s: added to ConOut and ErrOut\n", __FUNCTION__,
|
||||
DEBUG(
|
||||
(EFI_D_VERBOSE, "%a: %s: added to ConOut and ErrOut\n", __FUNCTION__,
|
||||
ReportText));
|
||||
}
|
||||
|
||||
STATIC
|
||||
UINT16
|
||||
PlatformRegisterFvBootOption (
|
||||
CONST EFI_GUID *FileGuid,
|
||||
CHAR16 *Description,
|
||||
UINT32 Attributes
|
||||
)
|
||||
PlatformRegisterFvBootOption(
|
||||
CONST EFI_GUID *FileGuid, CHAR16 *Description, UINT32 Attributes)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
INTN OptionIndex;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION NewOption;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION *BootOptions;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION * BootOptions;
|
||||
UINTN BootOptionCount;
|
||||
MEDIA_FW_VOL_FILEPATH_DEVICE_PATH FileNode;
|
||||
EFI_LOADED_IMAGE_PROTOCOL *LoadedImage;
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
|
||||
EFI_LOADED_IMAGE_PROTOCOL * LoadedImage;
|
||||
EFI_DEVICE_PATH_PROTOCOL * DevicePath;
|
||||
UINT16 OptionNumber;
|
||||
|
||||
Status = gBS->HandleProtocol (
|
||||
gImageHandle,
|
||||
&gEfiLoadedImageProtocolGuid,
|
||||
(VOID **) &LoadedImage
|
||||
);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
Status = gBS->HandleProtocol(
|
||||
gImageHandle, &gEfiLoadedImageProtocolGuid, (VOID **)&LoadedImage);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
EfiInitializeFwVolDevicepathNode (&FileNode, FileGuid);
|
||||
DevicePath = DevicePathFromHandle (LoadedImage->DeviceHandle);
|
||||
ASSERT (DevicePath != NULL);
|
||||
DevicePath = AppendDevicePathNode (
|
||||
DevicePath,
|
||||
(EFI_DEVICE_PATH_PROTOCOL *) &FileNode
|
||||
);
|
||||
ASSERT (DevicePath != NULL);
|
||||
EfiInitializeFwVolDevicepathNode(&FileNode, FileGuid);
|
||||
DevicePath = DevicePathFromHandle(LoadedImage->DeviceHandle);
|
||||
ASSERT(DevicePath != NULL);
|
||||
DevicePath =
|
||||
AppendDevicePathNode(DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&FileNode);
|
||||
ASSERT(DevicePath != NULL);
|
||||
|
||||
Status = EfiBootManagerInitializeLoadOption (
|
||||
&NewOption,
|
||||
LoadOptionNumberUnassigned,
|
||||
LoadOptionTypeBoot,
|
||||
Attributes,
|
||||
Description,
|
||||
DevicePath,
|
||||
NULL,
|
||||
0
|
||||
);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
FreePool (DevicePath);
|
||||
Status = EfiBootManagerInitializeLoadOption(
|
||||
&NewOption, LoadOptionNumberUnassigned, LoadOptionTypeBoot, Attributes,
|
||||
Description, DevicePath, NULL, 0);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
FreePool(DevicePath);
|
||||
|
||||
BootOptions = EfiBootManagerGetLoadOptions (
|
||||
&BootOptionCount, LoadOptionTypeBoot
|
||||
);
|
||||
BootOptions =
|
||||
EfiBootManagerGetLoadOptions(&BootOptionCount, LoadOptionTypeBoot);
|
||||
|
||||
OptionIndex = EfiBootManagerFindLoadOption (
|
||||
&NewOption, BootOptions, BootOptionCount
|
||||
);
|
||||
OptionIndex =
|
||||
EfiBootManagerFindLoadOption(&NewOption, BootOptions, BootOptionCount);
|
||||
|
||||
if (OptionIndex == -1) {
|
||||
Status = EfiBootManagerAddLoadOptionVariable (&NewOption, MAX_UINTN);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
Status = EfiBootManagerAddLoadOptionVariable(&NewOption, MAX_UINTN);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
}
|
||||
OptionNumber = NewOption.OptionNumber;
|
||||
EfiBootManagerFreeLoadOption (&NewOption);
|
||||
EfiBootManagerFreeLoadOptions (BootOptions, BootOptionCount);
|
||||
EfiBootManagerFreeLoadOption(&NewOption);
|
||||
EfiBootManagerFreeLoadOptions(BootOptions, BootOptionCount);
|
||||
return OptionNumber;
|
||||
}
|
||||
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
GetPlatformOptions (
|
||||
VOID
|
||||
)
|
||||
VOID GetPlatformOptions(VOID)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION *CurrentBootOptions;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION *BootOptions;
|
||||
EFI_INPUT_KEY *BootKeys;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION * CurrentBootOptions;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION * BootOptions;
|
||||
EFI_INPUT_KEY * BootKeys;
|
||||
PLATFORM_BOOT_MANAGER_PROTOCOL *PlatformBootManager;
|
||||
UINTN CurrentBootOptionCount;
|
||||
UINTN Index;
|
||||
UINTN BootCount;
|
||||
|
||||
Status = gBS->LocateProtocol (&gPlatformBootManagerProtocolGuid, NULL,
|
||||
(VOID **)&PlatformBootManager);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = gBS->LocateProtocol(
|
||||
&gPlatformBootManagerProtocolGuid, NULL, (VOID **)&PlatformBootManager);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return;
|
||||
}
|
||||
Status = PlatformBootManager->GetPlatformBootOptionsAndKeys (
|
||||
&BootCount,
|
||||
&BootOptions,
|
||||
&BootKeys
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = PlatformBootManager->GetPlatformBootOptionsAndKeys(
|
||||
&BootCount, &BootOptions, &BootKeys);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return;
|
||||
}
|
||||
//
|
||||
// Fetch the existent boot options. If there are none, CurrentBootCount
|
||||
// will be zeroed.
|
||||
//
|
||||
CurrentBootOptions = EfiBootManagerGetLoadOptions (
|
||||
&CurrentBootOptionCount,
|
||||
LoadOptionTypeBoot
|
||||
);
|
||||
CurrentBootOptions =
|
||||
EfiBootManagerGetLoadOptions(&CurrentBootOptionCount, LoadOptionTypeBoot);
|
||||
//
|
||||
// Process the platform boot options.
|
||||
//
|
||||
@ -437,27 +374,24 @@ GetPlatformOptions (
|
||||
// that EfiBootManagerFindLoadOption() deals fine with (CurrentBootOptions
|
||||
// == NULL) if (CurrentBootCount == 0).
|
||||
//
|
||||
Match = EfiBootManagerFindLoadOption (
|
||||
&BootOptions[Index],
|
||||
CurrentBootOptions,
|
||||
CurrentBootOptionCount
|
||||
);
|
||||
Match = EfiBootManagerFindLoadOption(
|
||||
&BootOptions[Index], CurrentBootOptions, CurrentBootOptionCount);
|
||||
if (Match >= 0) {
|
||||
BootOptionNumber = CurrentBootOptions[Match].OptionNumber;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
//
|
||||
// Add the platform boot options as a new one, at the end of the boot
|
||||
// order. Note that if the platform provided this boot option with an
|
||||
// unassigned option number, then the below function call will assign a
|
||||
// number.
|
||||
//
|
||||
Status = EfiBootManagerAddLoadOptionVariable (
|
||||
&BootOptions[Index],
|
||||
MAX_UINTN
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
DEBUG ((DEBUG_ERROR, "%a: failed to register \"%s\": %r\n",
|
||||
__FUNCTION__, BootOptions[Index].Description, Status));
|
||||
Status =
|
||||
EfiBootManagerAddLoadOptionVariable(&BootOptions[Index], MAX_UINTN);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG(
|
||||
(DEBUG_ERROR, "%a: failed to register \"%s\": %r\n", __FUNCTION__,
|
||||
BootOptions[Index].Description, Status));
|
||||
continue;
|
||||
}
|
||||
BootOptionNumber = BootOptions[Index].OptionNumber;
|
||||
@ -470,31 +404,21 @@ GetPlatformOptions (
|
||||
continue;
|
||||
}
|
||||
|
||||
Status = EfiBootManagerAddKeyOptionVariable (
|
||||
NULL,
|
||||
BootOptionNumber,
|
||||
0,
|
||||
&BootKeys[Index],
|
||||
NULL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
DEBUG ((DEBUG_ERROR, "%a: failed to register hotkey for \"%s\": %r\n",
|
||||
Status = EfiBootManagerAddKeyOptionVariable(
|
||||
NULL, BootOptionNumber, 0, &BootKeys[Index], NULL);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG(
|
||||
(DEBUG_ERROR, "%a: failed to register hotkey for \"%s\": %r\n",
|
||||
__FUNCTION__, BootOptions[Index].Description, Status));
|
||||
}
|
||||
}
|
||||
EfiBootManagerFreeLoadOptions (CurrentBootOptions, CurrentBootOptionCount);
|
||||
EfiBootManagerFreeLoadOptions (BootOptions, BootCount);
|
||||
FreePool (BootKeys);
|
||||
EfiBootManagerFreeLoadOptions(CurrentBootOptions, CurrentBootOptionCount);
|
||||
EfiBootManagerFreeLoadOptions(BootOptions, BootCount);
|
||||
FreePool(BootKeys);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
PlatformRegisterOptionsAndKeys (
|
||||
VOID
|
||||
)
|
||||
VOID PlatformRegisterOptionsAndKeys(VOID)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_INPUT_KEY Enter;
|
||||
@ -502,15 +426,15 @@ PlatformRegisterOptionsAndKeys (
|
||||
EFI_INPUT_KEY Esc;
|
||||
EFI_BOOT_MANAGER_LOAD_OPTION BootOption;
|
||||
|
||||
GetPlatformOptions ();
|
||||
GetPlatformOptions();
|
||||
|
||||
//
|
||||
// Register ENTER as CONTINUE key
|
||||
//
|
||||
Enter.ScanCode = SCAN_NULL;
|
||||
Enter.UnicodeChar = CHAR_CARRIAGE_RETURN;
|
||||
Status = EfiBootManagerRegisterContinueKeyOption (0, &Enter, NULL);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
Status = EfiBootManagerRegisterContinueKeyOption(0, &Enter, NULL);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
|
||||
//
|
||||
// Map UP and ESC to Boot Manager Menu or SimpleInitGUI
|
||||
@ -519,36 +443,31 @@ PlatformRegisterOptionsAndKeys (
|
||||
UP.UnicodeChar = CHAR_NULL;
|
||||
Esc.ScanCode = SCAN_ESC;
|
||||
Esc.UnicodeChar = CHAR_NULL;
|
||||
Status = EfiBootManagerGetBootManagerMenu (&BootOption);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
#ifdef ENABLE_SIMPLE_INIT
|
||||
Status = EfiBootManagerGetBootManagerMenu(&BootOption);
|
||||
ASSERT_EFI_ERROR(Status);
|
||||
#ifdef ENABLE_SIMPLE_INIT
|
||||
//
|
||||
// Search all boot options
|
||||
//
|
||||
EfiBootManagerRefreshAllBootOption ();
|
||||
EfiBootManagerRefreshAllBootOption();
|
||||
|
||||
//
|
||||
// Register Simple Init GUI APP
|
||||
//
|
||||
UINT16 OptionSimpleInit = PlatformRegisterFvBootOption (
|
||||
&gSimpleInitFileGuid, L"Simple Init", LOAD_OPTION_ACTIVE
|
||||
);
|
||||
Status = EfiBootManagerAddKeyOptionVariable (
|
||||
NULL, (UINT16) OptionSimpleInit, 0, &UP, NULL
|
||||
);
|
||||
#else
|
||||
Status = EfiBootManagerAddKeyOptionVariable (
|
||||
NULL, (UINT16) BootOption.OptionNumber, 0, &UP, NULL
|
||||
);
|
||||
#endif
|
||||
ASSERT (Status == EFI_SUCCESS || Status == EFI_ALREADY_STARTED);
|
||||
Status = EfiBootManagerAddKeyOptionVariable (
|
||||
NULL, (UINT16) BootOption.OptionNumber, 0, &Esc, NULL
|
||||
);
|
||||
ASSERT (Status == EFI_SUCCESS || Status == EFI_ALREADY_STARTED);
|
||||
UINT16 OptionSimpleInit = PlatformRegisterFvBootOption(
|
||||
&gSimpleInitFileGuid, L"Simple Init", LOAD_OPTION_ACTIVE);
|
||||
Status = EfiBootManagerAddKeyOptionVariable(
|
||||
NULL, (UINT16)OptionSimpleInit, 0, &UP, NULL);
|
||||
#else
|
||||
Status = EfiBootManagerAddKeyOptionVariable(
|
||||
NULL, (UINT16)BootOption.OptionNumber, 0, &UP, NULL);
|
||||
#endif
|
||||
ASSERT(Status == EFI_SUCCESS || Status == EFI_ALREADY_STARTED);
|
||||
Status = EfiBootManagerAddKeyOptionVariable(
|
||||
NULL, (UINT16)BootOption.OptionNumber, 0, &Esc, NULL);
|
||||
ASSERT(Status == EFI_SUCCESS || Status == EFI_ALREADY_STARTED);
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// BDS Platform Functions
|
||||
//
|
||||
@ -563,134 +482,127 @@ PlatformRegisterOptionsAndKeys (
|
||||
> Authentication action: 1. connect Auth devices;
|
||||
> 2. Identify auto logon user.
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
PlatformBootManagerBeforeConsole (
|
||||
VOID
|
||||
)
|
||||
VOID EFIAPI PlatformBootManagerBeforeConsole(VOID)
|
||||
{
|
||||
//
|
||||
// Signal EndOfDxe PI Event
|
||||
//
|
||||
EfiEventGroupSignal (&gEfiEndOfDxeEventGroupGuid);
|
||||
EfiEventGroupSignal(&gEfiEndOfDxeEventGroupGuid);
|
||||
|
||||
//
|
||||
// Dispatch deferred images after EndOfDxe event.
|
||||
//
|
||||
EfiBootManagerDispatchDeferredImages ();
|
||||
EfiBootManagerDispatchDeferredImages();
|
||||
|
||||
//
|
||||
// Locate the PCI root bridges and make the PCI bus driver connect each,
|
||||
// non-recursively. This will produce a number of child handles with PciIo on
|
||||
// them.
|
||||
//
|
||||
FilterAndProcess (&gEfiPciRootBridgeIoProtocolGuid, NULL, Connect);
|
||||
FilterAndProcess(&gEfiPciRootBridgeIoProtocolGuid, NULL, Connect);
|
||||
|
||||
//
|
||||
// Find all display class PCI devices (using the handles from the previous
|
||||
// step), and connect them non-recursively. This should produce a number of
|
||||
// child handles with GOPs on them.
|
||||
//
|
||||
FilterAndProcess (&gEfiPciIoProtocolGuid, IsPciDisplay, Connect);
|
||||
FilterAndProcess(&gEfiPciIoProtocolGuid, IsPciDisplay, Connect);
|
||||
|
||||
//
|
||||
// Now add the device path of all handles with GOP on them to ConOut and
|
||||
// ErrOut.
|
||||
//
|
||||
FilterAndProcess (&gEfiGraphicsOutputProtocolGuid, NULL, AddOutput);
|
||||
FilterAndProcess(&gEfiGraphicsOutputProtocolGuid, NULL, AddOutput);
|
||||
|
||||
//
|
||||
// Add the hardcoded short-form USB keyboard device path to ConIn.
|
||||
//
|
||||
EfiBootManagerUpdateConsoleVariable (ConIn,
|
||||
(EFI_DEVICE_PATH_PROTOCOL *)&mUsbKeyboard, NULL);
|
||||
EfiBootManagerUpdateConsoleVariable(
|
||||
ConIn, (EFI_DEVICE_PATH_PROTOCOL *)&mUsbKeyboard, NULL);
|
||||
|
||||
EFI_HANDLE *handles;
|
||||
EFI_HANDLE * handles;
|
||||
UINTN NoHandles;
|
||||
EFI_DEVICE_PATH_PROTOCOL *devicehandle;
|
||||
/*CHAR16 *devicepathtxt;*/
|
||||
//EfiBootManagerUpdateConsoleVariable(ConIn,
|
||||
// EfiBootManagerUpdateConsoleVariable(ConIn,
|
||||
// (EFI_DEVICE_PATH_PROTOCOL*)&gQcomKeypadDeviceGuid, NULL);
|
||||
gBS->LocateHandleBuffer(ByProtocol,&gEfiSimpleTextInputExProtocolGuid,NULL, &NoHandles,&handles);
|
||||
gBS->LocateHandleBuffer(
|
||||
ByProtocol, &gEfiSimpleTextInputExProtocolGuid, NULL, &NoHandles,
|
||||
&handles);
|
||||
devicehandle = DevicePathFromHandle(handles[1]);
|
||||
EfiBootManagerUpdateConsoleVariable (ConIn,
|
||||
devicehandle, NULL);/*
|
||||
EfiBootManagerUpdateConsoleVariable(
|
||||
ConIn, devicehandle, NULL); /*
|
||||
devicepathtxt = ConvertDevicePathToText(devicehandle,TRUE,TRUE);
|
||||
DEBUG((DEBUG_ERROR,"There are %s handles\n",devicepathtxt));
|
||||
ASSERT(0);*/
|
||||
|
||||
|
||||
|
||||
|
||||
//
|
||||
// Add the hardcoded serial console device path to ConIn, ConOut, ErrOut.
|
||||
//
|
||||
ASSERT (FixedPcdGet8 (PcdDefaultTerminalType) == 4);
|
||||
CopyGuid (&mSerialConsole.TermType.Guid, &gEfiTtyTermGuid);
|
||||
ASSERT(FixedPcdGet8(PcdDefaultTerminalType) == 4);
|
||||
CopyGuid(&mSerialConsole.TermType.Guid, &gEfiTtyTermGuid);
|
||||
|
||||
EfiBootManagerUpdateConsoleVariable (ConIn,
|
||||
(EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
|
||||
EfiBootManagerUpdateConsoleVariable (ConOut,
|
||||
(EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
|
||||
EfiBootManagerUpdateConsoleVariable (ErrOut,
|
||||
(EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
|
||||
EfiBootManagerUpdateConsoleVariable(
|
||||
ConIn, (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
|
||||
EfiBootManagerUpdateConsoleVariable(
|
||||
ConOut, (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
|
||||
EfiBootManagerUpdateConsoleVariable(
|
||||
ErrOut, (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
|
||||
|
||||
//
|
||||
// Register platform-specific boot options and keyboard shortcuts.
|
||||
//
|
||||
PlatformRegisterOptionsAndKeys ();
|
||||
PlatformRegisterOptionsAndKeys();
|
||||
}
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
HandleCapsules (
|
||||
VOID
|
||||
)
|
||||
VOID HandleCapsules(VOID)
|
||||
{
|
||||
ESRT_MANAGEMENT_PROTOCOL *EsrtManagement;
|
||||
EFI_PEI_HOB_POINTERS HobPointer;
|
||||
EFI_CAPSULE_HEADER *CapsuleHeader;
|
||||
EFI_CAPSULE_HEADER * CapsuleHeader;
|
||||
BOOLEAN NeedReset;
|
||||
EFI_STATUS Status;
|
||||
|
||||
DEBUG ((DEBUG_INFO, "%a: processing capsules ...\n", __FUNCTION__));
|
||||
DEBUG((DEBUG_INFO, "%a: processing capsules ...\n", __FUNCTION__));
|
||||
|
||||
Status = gBS->LocateProtocol (&gEsrtManagementProtocolGuid, NULL,
|
||||
(VOID **)&EsrtManagement);
|
||||
if (!EFI_ERROR (Status)) {
|
||||
EsrtManagement->SyncEsrtFmp ();
|
||||
Status = gBS->LocateProtocol(
|
||||
&gEsrtManagementProtocolGuid, NULL, (VOID **)&EsrtManagement);
|
||||
if (!EFI_ERROR(Status)) {
|
||||
EsrtManagement->SyncEsrtFmp();
|
||||
}
|
||||
|
||||
//
|
||||
// Find all capsule images from hob
|
||||
//
|
||||
HobPointer.Raw = GetHobList ();
|
||||
HobPointer.Raw = GetHobList();
|
||||
NeedReset = FALSE;
|
||||
while ((HobPointer.Raw = GetNextHob (EFI_HOB_TYPE_UEFI_CAPSULE,
|
||||
HobPointer.Raw)) != NULL) {
|
||||
while ((HobPointer.Raw =
|
||||
GetNextHob(EFI_HOB_TYPE_UEFI_CAPSULE, HobPointer.Raw)) != NULL) {
|
||||
CapsuleHeader = (VOID *)(UINTN)HobPointer.Capsule->BaseAddress;
|
||||
|
||||
Status = ProcessCapsuleImage (CapsuleHeader);
|
||||
if (EFI_ERROR (Status)) {
|
||||
DEBUG ((DEBUG_ERROR, "%a: failed to process capsule %p - %r\n",
|
||||
__FUNCTION__, CapsuleHeader, Status));
|
||||
Status = ProcessCapsuleImage(CapsuleHeader);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG(
|
||||
(DEBUG_ERROR, "%a: failed to process capsule %p - %r\n", __FUNCTION__,
|
||||
CapsuleHeader, Status));
|
||||
return;
|
||||
}
|
||||
|
||||
NeedReset = TRUE;
|
||||
HobPointer.Raw = GET_NEXT_HOB (HobPointer);
|
||||
HobPointer.Raw = GET_NEXT_HOB(HobPointer);
|
||||
}
|
||||
|
||||
if (NeedReset) {
|
||||
DEBUG ((DEBUG_WARN, "%a: capsule update successful, resetting ...\n",
|
||||
DEBUG(
|
||||
(DEBUG_WARN, "%a: capsule update successful, resetting ...\n",
|
||||
__FUNCTION__));
|
||||
|
||||
gRT->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL);
|
||||
gRT->ResetSystem(EfiResetCold, EFI_SUCCESS, 0, NULL);
|
||||
CpuDeadLoop();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#define VERSION_STRING_PREFIX L"Tianocore/EDK2 firmware version "
|
||||
|
||||
/**
|
||||
@ -704,11 +616,7 @@ HandleCapsules (
|
||||
> Dispatch additional option roms
|
||||
> Special boot: e.g.: USB boot, enter UI
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
PlatformBootManagerAfterConsole (
|
||||
VOID
|
||||
)
|
||||
VOID EFIAPI PlatformBootManagerAfterConsole(VOID)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput;
|
||||
@ -716,40 +624,43 @@ PlatformBootManagerAfterConsole (
|
||||
UINTN PosX;
|
||||
UINTN PosY;
|
||||
|
||||
FirmwareVerLength = StrLen (PcdGetPtr (PcdFirmwareVersionString));
|
||||
FirmwareVerLength = StrLen(PcdGetPtr(PcdFirmwareVersionString));
|
||||
|
||||
//
|
||||
// Show the splash screen.
|
||||
//
|
||||
Status = BootLogoEnableLogo ();
|
||||
if (EFI_ERROR (Status)) {
|
||||
Status = BootLogoEnableLogo();
|
||||
if (EFI_ERROR(Status)) {
|
||||
if (FirmwareVerLength > 0) {
|
||||
Print (VERSION_STRING_PREFIX L"%s\n",
|
||||
PcdGetPtr (PcdFirmwareVersionString));
|
||||
Print(VERSION_STRING_PREFIX L"%s\n", PcdGetPtr(PcdFirmwareVersionString));
|
||||
}
|
||||
#ifdef ENABLE_SIMPLE_INIT
|
||||
Print (L"Press any side button for SimpleInitGUI");
|
||||
#else
|
||||
Print (L"Press any side button for Boot Options");
|
||||
#endif
|
||||
} else if (FirmwareVerLength > 0) {
|
||||
Status = gBS->HandleProtocol (gST->ConsoleOutHandle,
|
||||
&gEfiGraphicsOutputProtocolGuid, (VOID **)&GraphicsOutput);
|
||||
if (!EFI_ERROR (Status)) {
|
||||
#ifdef ENABLE_SIMPLE_INIT
|
||||
Print(L"Press any side button for SimpleInitGUI");
|
||||
#else
|
||||
Print(L"Press any side button for Boot Options");
|
||||
#endif
|
||||
}
|
||||
else if (FirmwareVerLength > 0) {
|
||||
Status = gBS->HandleProtocol(
|
||||
gST->ConsoleOutHandle, &gEfiGraphicsOutputProtocolGuid,
|
||||
(VOID **)&GraphicsOutput);
|
||||
if (!EFI_ERROR(Status)) {
|
||||
PosX = (GraphicsOutput->Mode->Info->HorizontalResolution -
|
||||
(StrLen (VERSION_STRING_PREFIX) + FirmwareVerLength) *
|
||||
EFI_GLYPH_WIDTH) / 2;
|
||||
(StrLen(VERSION_STRING_PREFIX) + FirmwareVerLength) *
|
||||
EFI_GLYPH_WIDTH) /
|
||||
2;
|
||||
PosY = 0;
|
||||
|
||||
PrintXY (PosX, PosY, NULL, NULL, VERSION_STRING_PREFIX L"%s",
|
||||
PcdGetPtr (PcdFirmwareVersionString));
|
||||
PrintXY(
|
||||
PosX, PosY, NULL, NULL, VERSION_STRING_PREFIX L"%s",
|
||||
PcdGetPtr(PcdFirmwareVersionString));
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Connect the rest of the devices.
|
||||
//
|
||||
EfiBootManagerConnectAll ();
|
||||
EfiBootManagerConnectAll();
|
||||
|
||||
//
|
||||
// On ARM, there is currently no reason to use the phased capsule
|
||||
@ -758,34 +669,31 @@ PlatformBootManagerAfterConsole (
|
||||
// when the console is up and we can actually give the user some
|
||||
// feedback about what is going on.
|
||||
//
|
||||
HandleCapsules ();
|
||||
HandleCapsules();
|
||||
|
||||
//
|
||||
// Enumerate all possible boot options.
|
||||
//
|
||||
EfiBootManagerRefreshAllBootOption ();
|
||||
EfiBootManagerRefreshAllBootOption();
|
||||
|
||||
//
|
||||
// Register UEFI Shell
|
||||
//
|
||||
PlatformRegisterFvBootOption (
|
||||
&gUefiShellFileGuid, L"UEFI Shell", LOAD_OPTION_ACTIVE
|
||||
);
|
||||
PlatformRegisterFvBootOption(
|
||||
&gUefiShellFileGuid, L"UEFI Shell", LOAD_OPTION_ACTIVE);
|
||||
|
||||
//
|
||||
// Register Mass Storage App
|
||||
//
|
||||
PlatformRegisterFvBootOption (
|
||||
&gUsbfnMsdAppFileGuid, L"Mass Storage", LOAD_OPTION_ACTIVE
|
||||
);
|
||||
PlatformRegisterFvBootOption(
|
||||
&gUsbfnMsdAppFileGuid, L"Mass Storage", LOAD_OPTION_ACTIVE);
|
||||
|
||||
#ifdef AB_SLOTS_SUPPORT
|
||||
//
|
||||
// Register Switch Slots App
|
||||
//
|
||||
PlatformRegisterFvBootOption (
|
||||
&gSwitchSlotsAppFileGuid, L"Reboot to other slot", LOAD_OPTION_ACTIVE
|
||||
);
|
||||
PlatformRegisterFvBootOption(
|
||||
&gSwitchSlotsAppFileGuid, L"Reboot to other slot", LOAD_OPTION_ACTIVE);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -795,36 +703,28 @@ PlatformBootManagerAfterConsole (
|
||||
|
||||
@param TimeoutRemain The remaining timeout.
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
PlatformBootManagerWaitCallback (
|
||||
UINT16 TimeoutRemain
|
||||
)
|
||||
VOID EFIAPI PlatformBootManagerWaitCallback(UINT16 TimeoutRemain)
|
||||
{
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL_UNION Black;
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL_UNION White;
|
||||
UINT16 Timeout;
|
||||
EFI_STATUS Status;
|
||||
|
||||
Timeout = PcdGet16 (PcdPlatformBootTimeOut);
|
||||
Timeout = PcdGet16(PcdPlatformBootTimeOut);
|
||||
|
||||
Black.Raw = 0x00000000;
|
||||
White.Raw = 0x00FFFFFF;
|
||||
|
||||
Status = BootLogoUpdateProgress (
|
||||
White.Pixel,
|
||||
Black.Pixel,
|
||||
#ifdef ENABLE_SIMPLE_INIT
|
||||
Status = BootLogoUpdateProgress(
|
||||
White.Pixel, Black.Pixel,
|
||||
#ifdef ENABLE_SIMPLE_INIT
|
||||
L"Press any side button for SimpleInitGUI",
|
||||
#else
|
||||
#else
|
||||
L"Press any side button for Boot Options",
|
||||
#endif
|
||||
White.Pixel,
|
||||
(Timeout - TimeoutRemain) * 100 / Timeout,
|
||||
0
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
Print (L".");
|
||||
#endif
|
||||
White.Pixel, (Timeout - TimeoutRemain) * 100 / Timeout, 0);
|
||||
if (EFI_ERROR(Status)) {
|
||||
Print(L".");
|
||||
}
|
||||
}
|
||||
|
||||
@ -835,11 +735,4 @@ PlatformBootManagerWaitCallback (
|
||||
|
||||
If this function returns, BDS attempts to enter an infinite loop.
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
PlatformBootManagerUnableToBoot (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
return;
|
||||
}
|
||||
VOID EFIAPI PlatformBootManagerUnableToBoot(VOID) { return; }
|
||||
|
@ -41,9 +41,7 @@
|
||||
@retval EFI_UNSUPPORTED Logo not found
|
||||
**/
|
||||
EFI_STATUS
|
||||
EnableQuietBoot (
|
||||
IN EFI_GUID *LogoFile
|
||||
);
|
||||
EnableQuietBoot(IN EFI_GUID *LogoFile);
|
||||
|
||||
/**
|
||||
Use SystemTable Conout to turn on video based Simple Text Out consoles. The
|
||||
@ -53,8 +51,6 @@ EnableQuietBoot (
|
||||
@retval EFI_SUCCESS UGA devices are back in text mode and synced up.
|
||||
**/
|
||||
EFI_STATUS
|
||||
DisableQuietBoot (
|
||||
VOID
|
||||
);
|
||||
DisableQuietBoot(VOID);
|
||||
|
||||
#endif // _PLATFORM_BM_H_
|
||||
|
@ -1,16 +1,17 @@
|
||||
/** @file
|
||||
*
|
||||
* Copyright (c) 2018, Linaro Limited. 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.
|
||||
*
|
||||
**/
|
||||
*
|
||||
* Copyright (c) 2018, Linaro Limited. 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.
|
||||
*
|
||||
**/
|
||||
|
||||
#include <Library/ArmPlatformLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
@ -20,14 +21,12 @@
|
||||
#include <Ppi/ArmMpCoreInfo.h>
|
||||
|
||||
ARM_CORE_INFO mHiKey960InfoTable[] = {
|
||||
{
|
||||
// Cluster 0, Core 0
|
||||
{// Cluster 0, Core 0
|
||||
0x0, 0x0,
|
||||
|
||||
// MP Core MailBox Set/Get/Clear Addresses and Clear Value
|
||||
(UINT64)0xFFFFFFFF
|
||||
},
|
||||
/*
|
||||
(UINT64)0xFFFFFFFF},
|
||||
/*
|
||||
{
|
||||
// Cluster 0, Core 1
|
||||
0x0, 0x1,
|
||||
@ -77,7 +76,7 @@ ARM_CORE_INFO mHiKey960InfoTable[] = {
|
||||
// MP Core MailBox Set/Get/Clear Addresses and Clear Value
|
||||
(UINT64)0xFFFFFFFF
|
||||
}
|
||||
*/
|
||||
*/
|
||||
};
|
||||
|
||||
/**
|
||||
@ -89,33 +88,20 @@ ARM_CORE_INFO mHiKey960InfoTable[] = {
|
||||
|
||||
**/
|
||||
EFI_BOOT_MODE
|
||||
ArmPlatformGetBootMode (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
return BOOT_WITH_FULL_CONFIGURATION;
|
||||
}
|
||||
ArmPlatformGetBootMode(VOID) { return BOOT_WITH_FULL_CONFIGURATION; }
|
||||
|
||||
/**
|
||||
Initialize controllers that must setup in the normal world
|
||||
|
||||
This function is called by the ArmPlatformPkg/Pei or ArmPlatformPkg/Pei/PlatformPeim
|
||||
in the PEI phase.
|
||||
This function is called by the ArmPlatformPkg/Pei or
|
||||
ArmPlatformPkg/Pei/PlatformPeim in the PEI phase.
|
||||
|
||||
**/
|
||||
RETURN_STATUS
|
||||
ArmPlatformInitialize (
|
||||
IN UINTN MpId
|
||||
)
|
||||
{
|
||||
return RETURN_SUCCESS;
|
||||
}
|
||||
ArmPlatformInitialize(IN UINTN MpId) { return RETURN_SUCCESS; }
|
||||
|
||||
EFI_STATUS
|
||||
PrePeiCoreGetMpCoreInfo (
|
||||
OUT UINTN *CoreCount,
|
||||
OUT ARM_CORE_INFO **ArmCoreTable
|
||||
)
|
||||
PrePeiCoreGetMpCoreInfo(OUT UINTN *CoreCount, OUT ARM_CORE_INFO **ArmCoreTable)
|
||||
{
|
||||
// Only support one cluster
|
||||
*CoreCount = sizeof(mHiKey960InfoTable) / sizeof(ARM_CORE_INFO);
|
||||
@ -123,23 +109,16 @@ PrePeiCoreGetMpCoreInfo (
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
// Needs to be declared in the file. Otherwise gArmMpCoreInfoPpiGuid is undefined in the contect of PrePeiCore
|
||||
// Needs to be declared in the file. Otherwise gArmMpCoreInfoPpiGuid is
|
||||
// undefined in the contect of PrePeiCore
|
||||
EFI_GUID mArmMpCoreInfoPpiGuid = ARM_MP_CORE_INFO_PPI_GUID;
|
||||
ARM_MP_CORE_INFO_PPI mMpCoreInfoPpi = { PrePeiCoreGetMpCoreInfo };
|
||||
ARM_MP_CORE_INFO_PPI mMpCoreInfoPpi = {PrePeiCoreGetMpCoreInfo};
|
||||
|
||||
EFI_PEI_PPI_DESCRIPTOR gPlatformPpiTable[] = {
|
||||
{
|
||||
EFI_PEI_PPI_DESCRIPTOR_PPI,
|
||||
&mArmMpCoreInfoPpiGuid,
|
||||
&mMpCoreInfoPpi
|
||||
}
|
||||
};
|
||||
{EFI_PEI_PPI_DESCRIPTOR_PPI, &mArmMpCoreInfoPpiGuid, &mMpCoreInfoPpi}};
|
||||
|
||||
VOID
|
||||
ArmPlatformGetPlatformPpiList (
|
||||
OUT UINTN *PpiListSize,
|
||||
OUT EFI_PEI_PPI_DESCRIPTOR **PpiList
|
||||
)
|
||||
VOID ArmPlatformGetPlatformPpiList(
|
||||
OUT UINTN *PpiListSize, OUT EFI_PEI_PPI_DESCRIPTOR **PpiList)
|
||||
{
|
||||
*PpiListSize = sizeof(gPlatformPpiTable);
|
||||
*PpiList = gPlatformPpiTable;
|
||||
|
@ -1,70 +1,58 @@
|
||||
/** @file
|
||||
*
|
||||
* Copyright (c) 2011, ARM Limited. All rights reserved.
|
||||
* Copyright (c) 2019, RUIKAI LIU and MR TUNNEL. 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.
|
||||
*
|
||||
**/
|
||||
*
|
||||
* Copyright (c) 2011, ARM Limited. All rights reserved.
|
||||
* Copyright (c) 2019, RUIKAI LIU and MR TUNNEL. 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.
|
||||
*
|
||||
**/
|
||||
|
||||
#include <Configuration/DeviceMemoryMap.h>
|
||||
#include <Library/ArmPlatformLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/HobLib.h>
|
||||
#include <Configuration/DeviceMemoryMap.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
/**
|
||||
Return the Virtual Memory Map of your platform
|
||||
This Virtual Memory Map is used by MemoryInitPei Module to initialize the MMU on your platform.
|
||||
@param[out] VirtualMemoryMap Array of ARM_MEMORY_REGION_DESCRIPTOR describing a Physical-to-
|
||||
Virtual Memory mapping. This array must be ended by a zero-filled
|
||||
entry
|
||||
This Virtual Memory Map is used by MemoryInitPei Module to initialize the MMU
|
||||
on your platform.
|
||||
@param[out] VirtualMemoryMap Array of ARM_MEMORY_REGION_DESCRIPTOR
|
||||
describing a Physical-to- Virtual Memory mapping. This array must be ended by a
|
||||
zero-filled entry
|
||||
**/
|
||||
|
||||
STATIC
|
||||
VOID
|
||||
AddHob
|
||||
(
|
||||
ARM_MEMORY_REGION_DESCRIPTOR_EX Desc
|
||||
)
|
||||
VOID AddHob(ARM_MEMORY_REGION_DESCRIPTOR_EX Desc)
|
||||
{
|
||||
BuildResourceDescriptorHob(
|
||||
Desc.ResourceType,
|
||||
Desc.ResourceAttribute,
|
||||
Desc.Address,
|
||||
Desc.Length
|
||||
);
|
||||
Desc.ResourceType, Desc.ResourceAttribute, Desc.Address, Desc.Length);
|
||||
|
||||
BuildMemoryAllocationHob(
|
||||
Desc.Address,
|
||||
Desc.Length,
|
||||
Desc.MemoryType
|
||||
);
|
||||
BuildMemoryAllocationHob(Desc.Address, Desc.Length, Desc.MemoryType);
|
||||
}
|
||||
|
||||
VOID
|
||||
ArmPlatformGetVirtualMemoryMap (
|
||||
IN ARM_MEMORY_REGION_DESCRIPTOR** VirtualMemoryMap
|
||||
)
|
||||
VOID ArmPlatformGetVirtualMemoryMap(
|
||||
IN ARM_MEMORY_REGION_DESCRIPTOR **VirtualMemoryMap)
|
||||
{
|
||||
//TO-DO:ADD MEMORY MAP HERE
|
||||
ARM_MEMORY_REGION_DESCRIPTOR* MemoryDescriptor;
|
||||
// TO-DO:ADD MEMORY MAP HERE
|
||||
ARM_MEMORY_REGION_DESCRIPTOR *MemoryDescriptor;
|
||||
UINTN Index = 0;
|
||||
|
||||
MemoryDescriptor = (ARM_MEMORY_REGION_DESCRIPTOR*)AllocatePages
|
||||
(EFI_SIZE_TO_PAGES (sizeof (ARM_MEMORY_REGION_DESCRIPTOR) *
|
||||
MemoryDescriptor =
|
||||
(ARM_MEMORY_REGION_DESCRIPTOR *)AllocatePages(EFI_SIZE_TO_PAGES(
|
||||
sizeof(ARM_MEMORY_REGION_DESCRIPTOR) *
|
||||
MAX_ARM_MEMORY_REGION_DESCRIPTOR_COUNT));
|
||||
|
||||
// Run through each memory descriptor
|
||||
while (gDeviceMemoryDescriptorEx[Index].Address != (EFI_PHYSICAL_ADDRESS)0xFFFFFFFF)
|
||||
{
|
||||
switch (gDeviceMemoryDescriptorEx[Index].HobOption)
|
||||
{
|
||||
while (gDeviceMemoryDescriptorEx[Index].Address !=
|
||||
(EFI_PHYSICAL_ADDRESS)0xFFFFFFFF) {
|
||||
switch (gDeviceMemoryDescriptorEx[Index].HobOption) {
|
||||
case AddMem:
|
||||
case AddDev:
|
||||
AddHob(gDeviceMemoryDescriptorEx[Index]);
|
||||
@ -77,10 +65,13 @@ ArmPlatformGetVirtualMemoryMap (
|
||||
update:
|
||||
ASSERT(Index < MAX_ARM_MEMORY_REGION_DESCRIPTOR_COUNT);
|
||||
|
||||
MemoryDescriptor[Index].PhysicalBase = gDeviceMemoryDescriptorEx[Index].Address;
|
||||
MemoryDescriptor[Index].VirtualBase = gDeviceMemoryDescriptorEx[Index].Address;
|
||||
MemoryDescriptor[Index].PhysicalBase =
|
||||
gDeviceMemoryDescriptorEx[Index].Address;
|
||||
MemoryDescriptor[Index].VirtualBase =
|
||||
gDeviceMemoryDescriptorEx[Index].Address;
|
||||
MemoryDescriptor[Index].Length = gDeviceMemoryDescriptorEx[Index].Length;
|
||||
MemoryDescriptor[Index].Attributes = gDeviceMemoryDescriptorEx[Index].ArmAttributes;
|
||||
MemoryDescriptor[Index].Attributes =
|
||||
gDeviceMemoryDescriptorEx[Index].ArmAttributes;
|
||||
|
||||
Index++;
|
||||
}
|
||||
@ -93,5 +84,5 @@ ArmPlatformGetVirtualMemoryMap (
|
||||
ASSERT(Index <= MAX_ARM_MEMORY_REGION_DESCRIPTOR_COUNT);
|
||||
|
||||
*VirtualMemoryMap = &MemoryDescriptor[0];
|
||||
//ASSERT(0);
|
||||
// ASSERT(0);
|
||||
}
|
Loading…
Reference in New Issue
Block a user