之前的《Shell 下读取 VBT》【参考1】给出了一个读取VBT 的方法。Simon 留言表示可以使用 PLATFORM_GOP_POLICY_PROTOCOL提供的 GetVbtData 。可以在\Vlv2DeviceRefCodePkg\ValleyView2Soc\NorthCluster\Include\Protocol\PlatformGopPolicy.h 中看到如下定义:
#define EFI_PLATFORM_GOP_POLICY_PROTOCOL_GUID \
{ 0xec2e931b, 0x3281, 0x48a5, 0x81, 0x7, 0xdf, 0x8a, 0x8b, 0xed, 0x3c, 0x5d }
#define PLATFORM_GOP_POLICY_PROTOCOL_REVISION_01 0x01
#define PLATFORM_GOP_POLICY_PROTOCOL_REVISION_02 x0222
#pragma pack(1)
typedef enum {
LidClosed,
LidOpen,
LidStatusMax
} LID_STATUS;
typedef enum {
Docked,
UnDocked,
DockStatusMax
} DOCK_STATUS;
typedef
EFI_STATUS
(EFIAPI *GET_PLATFORM_LID_STATUS) (
OUT LID_STATUS *CurrentLidStatus
);
typedef
EFI_STATUS
(EFIAPI *GET_VBT_DATA) (
OUT EFI_PHYSICAL_ADDRESS *VbtAddress,
OUT UINT32 *VbtSize
);
#pragma pack()
typedef struct _PLATFORM_GOP_POLICY_PROTOCOL {
UINT32 Revision;
GET_PLATFORM_LID_STATUS GetPlatformLidStatus;
GET_VBT_DATA GetVbtData;
} PLATFORM_GOP_POLICY_PROTOCOL;
根据上述定义编写代码,首先搜索 PLATFORM_GOP_POLICY_PROTOCOL ,然后调用它提供的GetVbtData 函数。
/** @file
A simple, basic, EDK II native, "hello" application to verify that
we can build applications without LibC.
Copyright (c) 2010 - 2011, 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.
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 <Uefi.h>
#include <Library/UefiLib.h>
#include <Library/ShellCEntryLib.h>
#include <Protocol/SimpleFileSystem.h>
#include <Library/UefiBootServicesTableLib.h> //global gST gBS gImageHandle
#include <Library/ShellLib.h>
#include <Library/IoLib.h>
#include "PlatformGopPolicy.h"
EFI_GUID gPlatformGOPPolicyGuid =
{ 0xec2e931b, 0x3281, 0x48a5,
{ 0x81, 0x07, 0xdf, 0x8a, 0x8b, 0xed, 0x3c, 0x5d } };
//
//Save memory address to a file
//
EFI_STATUS
SaveToFile(
IN UINT8 *FileData,
IN UINTN FileDataLength)
{
EFI_STATUS Status;
EFI_FILE_PROTOCOL *FileHandle;
UINTN BufferSize;
EFI_FILE_PROTOCOL *Root;
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL *SimpleFileSystem;
Status = gBS->LocateProtocol(
&gEfiSimpleFileSystemProtocolGuid,
NULL,
(VOID **)&SimpleFileSystem);
if (EFI_ERROR(Status)) {
Print(L"Cannot find EFI_SIMPLE_FILE_SYSTEM_PROTOCOL \r\n");
return Status;
}
Status = SimpleFileSystem->OpenVolume(SimpleFileSystem, &Root);
if (EFI_ERROR(Status)) {
Print(L"OpenVolume error \r\n");
return Status;
}
Status = Root->Open(
Root,
&FileHandle,
L"dumpvbt.bin",
EFI_FILE_MODE_READ |
EFI_FILE_MODE_WRITE |
EFI_FILE_MODE_CREATE,
0);
if (EFI_ERROR(Status)){
Print(L"Error Open NULL [%r]\n",Status);
return Status;
}
BufferSize = FileDataLength;
Status = FileHandle->Write(FileHandle, &BufferSize, FileData);
if (EFI_ERROR(Status)){
Print(L"Error write [%r]\n",Status);
return Status;
}
else Print(L"VBT has been saved to 'dumpvbt.bin' \n");
FileHandle->Close(FileHandle);
return Status;
}
/***
Print a welcoming message.
Establishes the main structure of the application.
@retval 0 The application exited normally.
@retval Other An error occurred.
***/
INTN
EFIAPI
ShellAppMain (
IN UINTN Argc,
IN CHAR16 **Argv
)
{
PLATFORM_GOP_POLICY_PROTOCOL *mPlatformGopPolicyProtocl;
EFI_STATUS Status;
EFI_PHYSICAL_ADDRESS VbtAddress;
UINT32 VbtSize;
Print(L"*************************************************\n");
Print(L"* VBT dump tool By Platform GOP Policy Protocol *\n");
Print(L"* May 4th 2019 *\n");
Print(L"* Powered by www.lab-z.com *\n");
Print(L"*************************************************\n");
//
// Locate the Cpu Arch Protocol.
//
Status = gBS->LocateProtocol(
&gPlatformGOPPolicyGuid,
NULL,
&mPlatformGopPolicyProtocl);
if (EFI_ERROR (Status)) {
Print(L"Can't find EFI_PLATFORM_GOP_POLICY_PROTOCOL_\n");
return Status;
}
mPlatformGopPolicyProtocl->GetVbtData(&VbtAddress,&VbtSize);
SaveToFile((UINT8 *)VbtAddress,VbtSize);
return(0);
}
在 Shell 下运行之后会生成dumpvbt.bin ,内容就是当前使用的 VBT。
完整的代码和 EFI 文件下载:
这个方法和之前相比优点是避免了计算便宜之类的问题更加简单明确,可以在一定程度上克服不同Chipset之间的差别;缺点是:并非公开的 Protcol 在使用的时候可能存在一定风险。
最后,再次感谢 Simon 先生的建议。
参考:
1. http://www.lab-z.com/stu175vbt/ Step to UEFI (175)Shell 下读取 VBT