Reviewed-by: Jaben Carsey <***@intel.com>
>-----Original Message-----
>From: Zeng, Star
>Sent: Tuesday, June 30, 2015 2:02 AM
>To: edk2-***@lists.sourceforge.net
>Cc: Carsey, Jaben
>Subject: [PATCH V4 21/21] SecurityPkg: Delete Auth Variable driver
>Importance: High
>
>1. Delete TpmMeasurementLib LibraryClass from SecurityPkg after it moved to MdeModulePkg.
>2. Update DxeTpmMeasurementLib.inf to include MdeModulePkg.dec.
>3. Delete authenticated variable definition from AuthenticatedVariableFormat.h after
>them moved to VariableFormat.h.
>4. Replace VARIABLE_HEADER with AUTHENTICATED_VARIABLE_HEADER in EsalVariableDxeSal.
>5. Delete VariableInfo from SecurityPkg after it merged to VariableInfo in MdeModulePkg.
>6. Delete VariablePei from SecurityPkg after it merged to VariablePei in MdeModulePkg.
>7. Delete Auth Variable driver from SecurityPkg after it merged to Variable driver in
>MdeModulePkg.
>8. Also update PACKAGE_GUID and PACKAGE_VERSION in SecurityPkg.dec after the deletion
>of authenticated variable definition, VariableInfo, VariablePei and Auth Variable
>driver from SecurityPkg; update PLATFORM_VERSION in SecurityPkg.dsc.
>
>Cc: Jaben Carsey <***@intel.com>
>Contributed-under: TianoCore Contribution Agreement 1.0
>Signed-off-by: Star Zeng <***@intel.com>
>Reviewed-by: Jiewen Yao <***@intel.com>
>Reviewed-by: Liming Gao <***@intel.com>
>---
> .../Application/VariableInfo/VariableInfo.c | 265 --
> .../Application/VariableInfo/VariableInfo.inf | 63 -
> .../Application/VariableInfo/VariableInfo.uni | Bin 2902 -> 0 bytes
> .../Application/VariableInfo/VariableInfoExtra.uni | Bin 1360 -> 0 bytes
> .../Include/Guid/AuthenticatedVariableFormat.h | 201 +-
> SecurityPkg/Include/Library/TpmMeasurementLib.h | 44 -
> .../DxeTpmMeasurementLib/DxeTpmMeasurementLib.inf | 5 +-
> SecurityPkg/SecurityPkg.dec | 12 +-
> SecurityPkg/SecurityPkg.dsc | 7 +-
> .../EsalVariableDxeSal/AuthService.c | 42 +-
> .../EsalVariableDxeSal/Variable.c | 220 +-
> .../EsalVariableDxeSal/Variable.h | 18 +-
> .../VariableAuthenticated/Pei/PeiVariableAuth.uni | Bin 2170 -> 0 bytes
> .../VariableAuthenticated/Pei/PeiVariableExtra.uni | Bin 1348 -> 0 bytes
> SecurityPkg/VariableAuthenticated/Pei/Variable.c | 1087 -----
> SecurityPkg/VariableAuthenticated/Pei/Variable.h | 148 -
> .../VariableAuthenticated/Pei/VariablePei.inf | 73 -
> .../VariableAuthenticated/RuntimeDxe/AuthService.c | 2532 ------------
> .../VariableAuthenticated/RuntimeDxe/AuthService.h | 360 --
> .../VariableAuthenticated/RuntimeDxe/Measurement.c | 255 --
> .../VariableAuthenticated/RuntimeDxe/Reclaim.c | 161 -
> .../VariableAuthenticated/RuntimeDxe/VarCheck.c | 1264 ------
> .../VariableAuthenticated/RuntimeDxe/Variable.c | 4170 --------------------
> .../VariableAuthenticated/RuntimeDxe/Variable.h | 836 ----
> .../RuntimeDxe/VariableAuthRuntimeDxe.uni | Bin 3204 -> 0 bytes
> .../RuntimeDxe/VariableAuthSmm.uni | Bin 4488 -> 0 bytes
> .../RuntimeDxe/VariableAuthSmmRuntimeDxe.uni | Bin 3320 -> 0 bytes
> .../VariableAuthenticated/RuntimeDxe/VariableDxe.c | 530 ---
> .../RuntimeDxe/VariableRuntimeDxe.inf | 158 -
> .../RuntimeDxe/VariableRuntimeDxeExtra.uni | Bin 1376 -> 0 bytes
> .../VariableAuthenticated/RuntimeDxe/VariableSmm.c | 988 -----
> .../RuntimeDxe/VariableSmm.inf | 165 -
> .../RuntimeDxe/VariableSmmExtra.uni | Bin 1332 -> 0 bytes
> .../RuntimeDxe/VariableSmmRuntimeDxe.c | 1118 ------
> .../RuntimeDxe/VariableSmmRuntimeDxe.inf | 102 -
> .../RuntimeDxe/VariableSmmRuntimeDxeExtra.uni | Bin 1390 -> 0 bytes
> 36 files changed, 169 insertions(+), 14655 deletions(-)
> delete mode 100644 SecurityPkg/Application/VariableInfo/VariableInfo.c
> delete mode 100644 SecurityPkg/Application/VariableInfo/VariableInfo.inf
> delete mode 100644 SecurityPkg/Application/VariableInfo/VariableInfo.uni
> delete mode 100644 SecurityPkg/Application/VariableInfo/VariableInfoExtra.uni
> delete mode 100644 SecurityPkg/Include/Library/TpmMeasurementLib.h
> delete mode 100644 SecurityPkg/VariableAuthenticated/Pei/PeiVariableAuth.uni
> delete mode 100644 SecurityPkg/VariableAuthenticated/Pei/PeiVariableExtra.uni
> delete mode 100644 SecurityPkg/VariableAuthenticated/Pei/Variable.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/Pei/Variable.h
> delete mode 100644 SecurityPkg/VariableAuthenticated/Pei/VariablePei.inf
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.h
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/Measurement.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/Reclaim.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VarCheck.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.h
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthRuntimeDxe.uni
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthSmm.uni
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthSmmRuntimeDxe.uni
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableDxe.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxe.inf
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxeExtra.uni
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.inf
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmExtra.uni
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.c
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.inf
> delete mode 100644 SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxeExtra.uni
>
>diff --git a/SecurityPkg/Application/VariableInfo/VariableInfo.c b/SecurityPkg/Application/VariableInfo/VariableInfo.c
>deleted file mode 100644
>index 0c1ee4b..0000000
>--- a/SecurityPkg/Application/VariableInfo/VariableInfo.c
>+++ /dev/null
>@@ -1,265 +0,0 @@
>-/** @file
>- If the Variable services have PcdVariableCollectStatistics set to TRUE then
>- this utility will print out the statistics information. You can use console
>- redirection to capture the data.
>-
>-Copyright (c) 2009 - 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.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 <Uefi.h>
>-#include <Library/UefiLib.h>
>-#include <Library/UefiApplicationEntryPoint.h>
>-#include <Library/BaseMemoryLib.h>
>-
>-#include <Library/BaseLib.h>
>-#include <Library/MemoryAllocationLib.h>
>-#include <Library/DebugLib.h>
>-#include <Library/UefiBootServicesTableLib.h>
>-
>-#include <Guid/AuthenticatedVariableFormat.h>
>-#include <Guid/SmmVariableCommon.h>
>-#include <Protocol/SmmCommunication.h>
>-#include <Protocol/SmmVariable.h>
>-
>-extern EFI_GUID gEfiVariableGuid;
>-EFI_SMM_COMMUNICATION_PROTOCOL *mSmmCommunication = NULL;
>-
>-/**
>-
>- This function get the variable statistics data from SMM variable driver.
>-
>- @param[in, out] SmmCommunicateHeader In input, a pointer to a collection of data that will
>- be passed into an SMM environment. In output, a pointer
>- to a collection of data that comes from an SMM environment.
>- @param[in, out] SmmCommunicateSize The size of the SmmCommunicateHeader.
>-
>- @retval EFI_SUCCESS Get the statistics data information.
>- @retval EFI_NOT_FOUND Not found.
>- @retval EFI_BUFFER_TO_SMALL DataSize is too small for the result.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-GetVariableStatisticsData (
>- IN OUT EFI_SMM_COMMUNICATE_HEADER *SmmCommunicateHeader,
>- IN OUT UINTN *SmmCommunicateSize
>- )
>-{
>- EFI_STATUS Status;
>- SMM_VARIABLE_COMMUNICATE_HEADER *SmmVariableFunctionHeader;
>-
>- CopyGuid (&SmmCommunicateHeader->HeaderGuid, &gEfiSmmVariableProtocolGuid);
>- SmmCommunicateHeader->MessageLength = *SmmCommunicateSize - OFFSET_OF (EFI_SMM_COMMUNICATE_HEADER, Data);
>-
>- SmmVariableFunctionHeader = (SMM_VARIABLE_COMMUNICATE_HEADER *) &SmmCommunicateHeader->Data[0];
>- SmmVariableFunctionHeader->Function = SMM_VARIABLE_FUNCTION_GET_STATISTICS;
>-
>- Status = mSmmCommunication->Communicate (mSmmCommunication, SmmCommunicateHeader, SmmCommunicateSize);
>- ASSERT_EFI_ERROR (Status);
>-
>- Status = SmmVariableFunctionHeader->ReturnStatus;
>- return Status;
>-}
>-
>-
>-/**
>-
>- This function get and print the variable statistics data from SMM variable driver.
>-
>- @retval EFI_SUCCESS Print the statistics information successfully.
>- @retval EFI_NOT_FOUND Not found the statistics information.
>-
>-**/
>-EFI_STATUS
>-PrintInfoFromSmm (
>- VOID
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_INFO_ENTRY *VariableInfo;
>- EFI_SMM_COMMUNICATE_HEADER *CommBuffer;
>- UINTN RealCommSize;
>- UINTN CommSize;
>- SMM_VARIABLE_COMMUNICATE_HEADER *FunctionHeader;
>- EFI_SMM_VARIABLE_PROTOCOL *Smmvariable;
>-
>-
>- Status = gBS->LocateProtocol (&gEfiSmmVariableProtocolGuid, NULL, (VOID **) &Smmvariable);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- Status = gBS->LocateProtocol (&gEfiSmmCommunicationProtocolGuid, NULL, (VOID **) &mSmmCommunication);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- CommSize = SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE;
>- RealCommSize = CommSize;
>- CommBuffer = AllocateZeroPool (CommSize);
>- ASSERT (CommBuffer != NULL);
>-
>- Print (L"Non-Volatile SMM Variables:\n");
>- do {
>- Status = GetVariableStatisticsData (CommBuffer, &CommSize);
>- if (Status == EFI_BUFFER_TOO_SMALL) {
>- FreePool (CommBuffer);
>- CommBuffer = AllocateZeroPool (CommSize);
>- ASSERT (CommBuffer != NULL);
>- RealCommSize = CommSize;
>- Status = GetVariableStatisticsData (CommBuffer, &CommSize);
>- }
>-
>- if (EFI_ERROR (Status) || (CommSize <= SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE))
>{
>- break;
>- }
>-
>- if (CommSize < RealCommSize) {
>- CommSize = RealCommSize;
>- }
>-
>- FunctionHeader = (SMM_VARIABLE_COMMUNICATE_HEADER *) CommBuffer->Data;
>- VariableInfo = (VARIABLE_INFO_ENTRY *) FunctionHeader->Data;
>-
>- if (!VariableInfo->Volatile) {
>- Print (
>- L"%g R%03d(%03d) W%03d D%03d:%s\n",
>- &VariableInfo->VendorGuid,
>- VariableInfo->ReadCount,
>- VariableInfo->CacheCount,
>- VariableInfo->WriteCount,
>- VariableInfo->DeleteCount,
>- (CHAR16 *)(VariableInfo + 1)
>- );
>- }
>- } while (TRUE);
>-
>- Print (L"Volatile SMM Variables:\n");
>- ZeroMem (CommBuffer, CommSize);
>- do {
>- Status = GetVariableStatisticsData (CommBuffer, &CommSize);
>- if (Status == EFI_BUFFER_TOO_SMALL) {
>- FreePool (CommBuffer);
>- CommBuffer = AllocateZeroPool (CommSize);
>- ASSERT (CommBuffer != NULL);
>- RealCommSize = CommSize;
>- Status = GetVariableStatisticsData (CommBuffer, &CommSize);
>- }
>-
>- if (EFI_ERROR (Status) || (CommSize <= SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE))
>{
>- break;
>- }
>-
>- if (CommSize < RealCommSize) {
>- CommSize = RealCommSize;
>- }
>-
>- FunctionHeader = (SMM_VARIABLE_COMMUNICATE_HEADER *) CommBuffer->Data;
>- VariableInfo = (VARIABLE_INFO_ENTRY *) FunctionHeader->Data;
>-
>- if (VariableInfo->Volatile) {
>- Print (
>- L"%g R%03d(%03d) W%03d D%03d:%s\n",
>- &VariableInfo->VendorGuid,
>- VariableInfo->ReadCount,
>- VariableInfo->CacheCount,
>- VariableInfo->WriteCount,
>- VariableInfo->DeleteCount,
>- (CHAR16 *)(VariableInfo + 1)
>- );
>- }
>- } while (TRUE);
>-
>- FreePool (CommBuffer);
>- return Status;
>-}
>-
>-/**
>- The user Entry Point for Application. The user code starts with this function
>- as the real entry point for the image goes into a library that calls this
>- function.
>-
>- @param[in] ImageHandle The firmware allocated handle for the EFI image.
>- @param[in] SystemTable A pointer to the EFI System Table.
>-
>- @retval EFI_SUCCESS The entry point is executed successfully.
>- @retval other Some error occurs when executing this entry point.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-UefiMain (
>- IN EFI_HANDLE ImageHandle,
>- IN EFI_SYSTEM_TABLE *SystemTable
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_INFO_ENTRY *VariableInfo;
>- VARIABLE_INFO_ENTRY *Entry;
>-
>- Status = EfiGetSystemConfigurationTable (&gEfiVariableGuid, (VOID **)&Entry);
>- if (EFI_ERROR (Status) || (Entry == NULL)) {
>- Status = EfiGetSystemConfigurationTable (&gEfiAuthenticatedVariableGuid, (VOID **)&Entry);
>- }
>-
>- if (EFI_ERROR (Status) || (Entry == NULL)) {
>- Status = PrintInfoFromSmm ();
>- if (!EFI_ERROR (Status)) {
>- return Status;
>- }
>- }
>-
>- if (!EFI_ERROR (Status) && (Entry != NULL)) {
>- Print (L"Non-Volatile EFI Variables:\n");
>- VariableInfo = Entry;
>- do {
>- if (!VariableInfo->Volatile) {
>- Print (
>- L"%g R%03d(%03d) W%03d D%03d:%s\n",
>- &VariableInfo->VendorGuid,
>- VariableInfo->ReadCount,
>- VariableInfo->CacheCount,
>- VariableInfo->WriteCount,
>- VariableInfo->DeleteCount,
>- VariableInfo->Name
>- );
>- }
>-
>- VariableInfo = VariableInfo->Next;
>- } while (VariableInfo != NULL);
>-
>- Print (L"Volatile EFI Variables:\n");
>- VariableInfo = Entry;
>- do {
>- if (VariableInfo->Volatile) {
>- Print (
>- L"%g R%03d(%03d) W%03d D%03d:%s\n",
>- &VariableInfo->VendorGuid,
>- VariableInfo->ReadCount,
>- VariableInfo->CacheCount,
>- VariableInfo->WriteCount,
>- VariableInfo->DeleteCount,
>- VariableInfo->Name
>- );
>- }
>- VariableInfo = VariableInfo->Next;
>- } while (VariableInfo != NULL);
>-
>- } else {
>- Print (L"Warning: Variable Dxe driver doesn't enable the feature of statistical information!\n");
>- Print (L"If you want to see this info, please:\n");
>- Print (L" 1. Set PcdVariableCollectStatistics as TRUE\n");
>- Print (L" 2. Rebuild Variable Dxe driver\n");
>- Print (L" 3. Run \"VariableInfo\" cmd again\n");
>- }
>-
>- return Status;
>-}
>diff --git a/SecurityPkg/Application/VariableInfo/VariableInfo.inf b/SecurityPkg/Application/VariableInfo/VariableInfo.inf
>deleted file mode 100644
>index d4a771a..0000000
>--- a/SecurityPkg/Application/VariableInfo/VariableInfo.inf
>+++ /dev/null
>@@ -1,63 +0,0 @@
>-## @file
>-# A shell application that displays statistical information about variable usage
>-#
>-# This application can display statistical information about variable usage for SMM variable
>-# driver and non-SMM variable driver.
>-# Note that if Variable Dxe driver doesn't enable the feature by setting PcdVariableCollectStatistics
>-# as TRUE, the application will not display variable statistical information.
>-#
>-# Copyright (c) 2009 - 2014, 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
>-# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
>-# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
>-#
>-##
>-
>-[Defines]
>- INF_VERSION = 0x00010005
>- BASE_NAME = VariableInfo
>- MODULE_UNI_FILE = VariableInfo.uni
>- FILE_GUID = B9EF901F-A2A2-4fc8-8D2B-3A2E07B301CC
>- MODULE_TYPE = UEFI_APPLICATION
>- VERSION_STRING = 1.0
>- ENTRY_POINT = UefiMain
>-
>-#
>-# The following information is for reference only and not required by the build tools.
>-#
>-# VALID_ARCHITECTURES = IA32 X64 IPF EBC
>-#
>-
>-[Sources]
>- VariableInfo.c
>-
>-
>-[Packages]
>- MdePkg/MdePkg.dec
>- MdeModulePkg/MdeModulePkg.dec
>- SecurityPkg/SecurityPkg.dec
>-
>-[LibraryClasses]
>- UefiApplicationEntryPoint
>- UefiLib
>- UefiBootServicesTableLib
>- BaseMemoryLib
>- MemoryAllocationLib
>-
>-[Protocols]
>- gEfiSmmCommunicationProtocolGuid ## SOMETIMES_CONSUMES
>-
>- ## UNDEFINED # Used to do smm communication
>- ## SOMETIMES_CONSUMES
>- gEfiSmmVariableProtocolGuid
>-
>-[Guids]
>- gEfiAuthenticatedVariableGuid ## SOMETIMES_CONSUMES ## SystemTable
>- gEfiVariableGuid ## CONSUMES ## SystemTable
>-
>-[UserExtensions.TianoCore."ExtraFiles"]
>- VariableInfoExtra.uni
>-
>\ No newline at end of file
>diff --git a/SecurityPkg/Application/VariableInfo/VariableInfo.uni b/SecurityPkg/Application/VariableInfo/VariableInfo.uni
>deleted file mode 100644
>index e2f214b6150a43fb3ea329d33e48474a7d29d8fc..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 2902
>zcmdUxTW=FV42AuS#D5sI4_wqHfOr8RL`nlhKvJa%El*W$Z6l>kwAu9X=Yj8dl1wf{
>z&<CWV)$YuCJofRiJ-a`D6s>51`zcqjcXn!h8(7aC+***@CoD{+tQ9NB;?Sj$FS1N1t~
>zbH<@vBG1v$d$2CDvFo(#mYMeFQ(evCPTA_S^OXIWT`bvZSsUrZtzEH_p(&Y=1>|Gi
>z&K6K6v<*<m`(~U%ExgMp{~g9KjWF1uedP+a8c{;u^+>OXEb|C1K^Z_RhIcpaS1e*E
>z?kg<huFB5bIZN5;gD2RxHCFfS#x)mh$?_2C82^tv8$D(z6SAs|obpueC*aU~o4kwB
>z9x~<ol57P#pklgfp5Nm^mDOW4C&txE885`s^2|***@ZcQuO4mM{9HdW;{-ecX0#r5i3
>z&&***@QB^sF+***@psbw1k^DX;z9)<?>>1Z9X1mk3=l0TLslb!6rOuFr3>$i;E-SE7
>zn#PlCtJ=l8_|Civx>m3^wg*pd=j<hPsYgcW4?!p&7g$kesNxc<9Z(Nh8~NJpJeRRw
>z<xibCz<08*epMC3GeQ+***@Q6uiahOX?Zs&N2#***@t6q7*XC`rwVH
>zkXDCY-?M#tRMbAwFKBeI5wRq!*M44fcnaNew0-ntQMTfl63>j>qi*~86#XhM4YXn}
>zOr{wU<{NgeVp`@U_}Qm^X;1g-<ckq1^9if!C?^xI{bW{!#dxHjd2|J$&&X$Sh5Ip*
>zHnDW6xn=JKtekTvFAe)dZ>d}BR<n;hOMYrqU^2j^Ms;9?`f4&OJHJh<GM15xiD)5l
>zU!k7MXdJrb8Z*_go?DEvE2~?Kd;YGsodrxstjlW6Jq9~MtM16E$SYWtjhcI}^Cs+)
>z$!7yy>Bwu;`hc#ye`oy6ijeCpDNnt`D9Uy`x09?_;NpO4lFxm*Y{uJc4E`l8x?D2d
>z+b|z%CZ2<lzY{Fgu+hX?*-k(tzQk+^***@8sbZvXL$kv3K)psy>CG28LNX4m6vHSVW
>z-kNjscf6>o4q-$***@3{FhFY3|%?eAdu>z>ZgyZ#jf>ijN$1IO^b>ia(Y4Tym;
>L$nM);K&tCs^3CL<
>
>diff --git a/SecurityPkg/Application/VariableInfo/VariableInfoExtra.uni b/SecurityPkg/Application/VariableInfo/VariableInfoExtra.uni
>deleted file mode 100644
>index b7fd354c459bbe399b3f4476ac90e64ffd83ec19..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 1360
>zcmZ9MTW=Ck6ovP*iT`0zU(~eV?a3G;*ik3e4xwQ6iEt~Ogfe8HRs8YlxAvI}5W>0a
>z%i8O#v(Nnd+qSkv{GaoS?1SA{W=osfV|#>EzV9}+0_)f&?n!J#***@af*G3_YXNU
>zY*)7R=#?#O!+uP(>>r6;;hXzdp;vS8uWjeK3%eyUvZtUwV}4~X?4`YCbyn}**ePpq
>z5$2M$DipT%af~(diY+`H{EE;i0=AeH<ZbvD_P{u^mc6sC_3eFq_J-X6Mwy>yO?(bY
>z!O8AGsm`}0V($AXtaE&8_wC4&77-S)Qax$81g*iB!pfGCQ&***@d
>z)r~}UPlmh&85NUI>&{tMC}O6_tky?L<lJYI*X0h+*<T!RX}JD!EvAfOcX-+i4nh=%
>zpqFZG*z432c<$eeRMn|(u!kEG=ikH}b2`)|Xt^V5Qs(ES0%Ek?(^Y-6<tE;GFXya+
>zwu&!Y=@zFixS#fs_8Tk{n9u0B!|E+iZuvKg4D5@=u<6k~seNYb*f;hGN=***@d4M&c
>zzlN-0****@_%rW)|TR>>EPw3~Eh$}}<S*edTo-hkns3*)_-)nce$LSisP*blM*)>sp
>zXLgA_0aX~OSMReEciB{PK&)a^HAH<***@Hwpf5ju_dVg_QC7dF*A2m*co}fjKZc@#2
>zURkAEHAnvKX}evvCw0GscN4T5mFo6D>DMP1ft`Xn1V6SByrjJDA|UCF2<4u6;k}~!
>oKO<iJ6eBg&mFh%&OZ5K2JJstu{`Q40PWbwD=z%r)LaF}$0qSPb+yDRo
>
>diff --git a/SecurityPkg/Include/Guid/AuthenticatedVariableFormat.h b/SecurityPkg/Include/Guid/AuthenticatedVariableFormat.h
>index c7cd34a..1f007cf 100644
>--- a/SecurityPkg/Include/Guid/AuthenticatedVariableFormat.h
>+++ b/SecurityPkg/Include/Guid/AuthenticatedVariableFormat.h
>@@ -1,16 +1,17 @@
> /** @file
>- The variable data structures are related to EDKII-specific
>+ The variable data structures are related to EDKII-specific
> implementation of UEFI authenticated variables.
>- AuthenticatedVariableFormat.h defines variable data headers
>- and variable storage region headers.
>-
>-Copyright (c) 2009 - 2013, 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
>+ AuthenticatedVariableFormat.h defines variable data headers
>+ and variable storage region headers that has been moved to
>+ VariableFormat.h.
>+
>+Copyright (c) 2009 - 2015, 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
>
>-THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
>+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
> WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
>
> **/
>@@ -18,14 +19,11 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
> #ifndef __AUTHENTICATED_VARIABLE_FORMAT_H__
> #define __AUTHENTICATED_VARIABLE_FORMAT_H__
>
>-#define EFI_AUTHENTICATED_VARIABLE_GUID \
>- { 0xaaf32c78, 0x947b, 0x439a, { 0xa1, 0x80, 0x2e, 0x14, 0x4e, 0xc3, 0x77, 0x92 } }
>+#include <Guid/VariableFormat.h>
>
> #define EFI_SECURE_BOOT_ENABLE_DISABLE \
> { 0xf0a30bc7, 0xaf08, 0x4556, { 0x99, 0xc4, 0x0, 0x10, 0x9, 0xc9, 0x3a, 0x44 } }
>
>-
>-extern EFI_GUID gEfiAuthenticatedVariableGuid;
> extern EFI_GUID gEfiSecureBootEnableDisableGuid;
> extern EFI_GUID gEfiCertDbGuid;
> extern EFI_GUID gEfiCustomModeEnableGuid;
>@@ -36,6 +34,10 @@ extern EFI_GUID gEfiVendorKeysNvGuid;
> /// This variable is used for allowing a physically present user to disable
> /// Secure Boot via firmware setup without the possession of PKpriv.
> ///
>+/// GUID: gEfiSecureBootEnableDisableGuid
>+///
>+/// Format: UINT8
>+///
> #define EFI_SECURE_BOOT_ENABLE_NAME L"SecureBootEnable"
> #define SECURE_BOOT_ENABLE 1
> #define SECURE_BOOT_DISABLE 0
>@@ -48,6 +50,10 @@ extern EFI_GUID gEfiVendorKeysNvGuid;
> /// Can enroll or delete KEK without existing PK's private key.
> /// Can enroll or delete signature from DB/DBX without KEK's private key.
> ///
>+/// GUID: gEfiCustomModeEnableGuid
>+///
>+/// Format: UINT8
>+///
> #define EFI_CUSTOM_MODE_NAME L"CustomMode"
> #define CUSTOM_SECURE_BOOT_MODE 1
> #define STANDARD_SECURE_BOOT_MODE 0
>@@ -58,173 +64,12 @@ extern EFI_GUID gEfiVendorKeysNvGuid;
> /// the platform vendor has used a mechanism not defined by the UEFI Specification to
> /// transition the system to setup mode or to update secure boot keys.
> ///
>+/// GUID: gEfiVendorKeysNvGuid
>+///
>+/// Format: UINT8
>+///
> #define EFI_VENDOR_KEYS_NV_VARIABLE_NAME L"VendorKeysNv"
> #define VENDOR_KEYS_VALID 1
> #define VENDOR_KEYS_MODIFIED 0
>
>-///
>-/// Alignment of variable name and data, according to the architecture:
>-/// * For IA-32 and Intel(R) 64 architectures: 1.
>-/// * For IA-64 architecture: 8.
>-///
>-#if defined (MDE_CPU_IPF)
>-#define ALIGNMENT 8
>-#else
>-#define ALIGNMENT 1
>-#endif
>-
>-//
>-// GET_PAD_SIZE calculates the miminal pad bytes needed to make the current pad size satisfy the alignment requirement.
>-//
>-#if (ALIGNMENT == 1)
>-#define GET_PAD_SIZE(a) (0)
>-#else
>-#define GET_PAD_SIZE(a) (((~a) + 1) & (ALIGNMENT - 1))
>-#endif
>-
>-///
>-/// Alignment of Variable Data Header in Variable Store region.
>-///
>-#define HEADER_ALIGNMENT 4
>-#define HEADER_ALIGN(Header) (((UINTN) (Header) + HEADER_ALIGNMENT - 1) & (~(HEADER_ALIGNMENT - 1)))
>-
>-///
>-/// Status of Variable Store Region.
>-///
>-typedef enum {
>- EfiRaw,
>- EfiValid,
>- EfiInvalid,
>- EfiUnknown
>-} VARIABLE_STORE_STATUS;
>-
>-#pragma pack(1)
>-
>-#define VARIABLE_STORE_SIGNATURE EFI_AUTHENTICATED_VARIABLE_GUID
>-
>-///
>-/// Variable Store Header Format and State.
>-///
>-#define VARIABLE_STORE_FORMATTED 0x5a
>-#define VARIABLE_STORE_HEALTHY 0xfe
>-
>-///
>-/// Variable Store region header.
>-///
>-typedef struct {
>- ///
>- /// Variable store region signature.
>- ///
>- EFI_GUID Signature;
>- ///
>- /// Size of entire variable store,
>- /// including size of variable store header but not including the size of FvHeader.
>- ///
>- UINT32 Size;
>- ///
>- /// Variable region format state.
>- ///
>- UINT8 Format;
>- ///
>- /// Variable region healthy state.
>- ///
>- UINT8 State;
>- UINT16 Reserved;
>- UINT32 Reserved1;
>-} VARIABLE_STORE_HEADER;
>-
>-///
>-/// Variable data start flag.
>-///
>-#define VARIABLE_DATA 0x55AA
>-
>-///
>-/// Variable State flags.
>-///
>-#define VAR_IN_DELETED_TRANSITION 0xfe ///< Variable is in obsolete transition.
>-#define VAR_DELETED 0xfd ///< Variable is obsolete.
>-#define VAR_HEADER_VALID_ONLY 0x7f ///< Variable header has been valid.
>-#define VAR_ADDED 0x3f ///< Variable has been completely added.
>-
>-///
>-/// Variable Attribute combinations.
>-///
>-#define VARIABLE_ATTRIBUTE_NV_BS (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_BS_RT (EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS)
>-#define VARIABLE_ATTRIBUTE_AT_AW (EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS |
>EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT (VARIABLE_ATTRIBUTE_BS_RT | EFI_VARIABLE_NON_VOLATILE)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_HR (VARIABLE_ATTRIBUTE_NV_BS_RT | EFI_VARIABLE_HARDWARE_ERROR_RECORD)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_AT (VARIABLE_ATTRIBUTE_NV_BS_RT |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_AW (VARIABLE_ATTRIBUTE_NV_BS_RT |
>EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_HR_AT_AW (VARIABLE_ATTRIBUTE_NV_BS_RT_HR | VARIABLE_ATTRIBUTE_AT_AW)
>-
>-/// Single Variable Data Header Structure.
>-///
>-typedef struct {
>- ///
>- /// Variable Data Start Flag.
>- ///
>- UINT16 StartId;
>- ///
>- /// Variable State defined above.
>- ///
>- UINT8 State;
>- UINT8 Reserved;
>- ///
>- /// Attributes of variable defined in UEFI specification.
>- ///
>- UINT32 Attributes;
>- ///
>- /// Associated monotonic count value against replay attack.
>- ///
>- UINT64 MonotonicCount;
>- ///
>- /// Associated TimeStamp value against replay attack.
>- ///
>- EFI_TIME TimeStamp;
>- ///
>- /// Index of associated public key in database.
>- ///
>- UINT32 PubKeyIndex;
>- ///
>- /// Size of variable null-terminated Unicode string name.
>- ///
>- UINT32 NameSize;
>- ///
>- /// Size of the variable data without this header.
>- ///
>- UINT32 DataSize;
>- ///
>- /// A unique identifier for the vendor that produces and consumes this varaible.
>- ///
>- EFI_GUID VendorGuid;
>-} VARIABLE_HEADER;
>-
>-typedef struct {
>- EFI_GUID *Guid;
>- CHAR16 *Name;
>- UINTN VariableSize;
>-} VARIABLE_ENTRY_CONSISTENCY;
>-
>-#pragma pack()
>-
>-typedef struct _VARIABLE_INFO_ENTRY VARIABLE_INFO_ENTRY;
>-
>-///
>-/// This structure contains the variable list that is put in EFI system table.
>-/// The variable driver collects all variables that were used at boot service time and produces this list.
>-/// This is an optional feature to dump all used variables in shell environment.
>-///
>-struct _VARIABLE_INFO_ENTRY {
>- VARIABLE_INFO_ENTRY *Next; ///< Pointer to next entry.
>- EFI_GUID VendorGuid; ///< Guid of Variable.
>- CHAR16 *Name; ///< Name of Variable.
>- UINT32 Attributes; ///< Attributes of variable defined in UEFI spec.
>- UINT32 ReadCount; ///< Number of times to read this variable.
>- UINT32 WriteCount; ///< Number of times to write this variable.
>- UINT32 DeleteCount; ///< Number of times to delete this variable.
>- UINT32 CacheCount; ///< Number of times that cache hits this variable.
>- BOOLEAN Volatile; ///< TRUE if volatile, FALSE if non-volatile.
>-};
>-
> #endif // __AUTHENTICATED_VARIABLE_FORMAT_H__
>diff --git a/SecurityPkg/Include/Library/TpmMeasurementLib.h b/SecurityPkg/Include/Library/TpmMeasurementLib.h
>deleted file mode 100644
>index 45542f4..0000000
>--- a/SecurityPkg/Include/Library/TpmMeasurementLib.h
>+++ /dev/null
>@@ -1,44 +0,0 @@
>-/** @file
>- This library is used by other modules to measure data to TPM.
>-
>-Copyright (c) 2012, 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
>-
>-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 _TPM_MEASUREMENT_LIB_H_
>-#define _TPM_MEASUREMENT_LIB_H_
>-
>-/**
>- Tpm measure and log data, and extend the measurement result into a specific PCR.
>-
>- @param[in] PcrIndex PCR Index.
>- @param[in] EventType Event type.
>- @param[in] EventLog Measurement event log.
>- @param[in] LogLen Event log length in bytes.
>- @param[in] HashData The start of the data buffer to be hashed, extended.
>- @param[in] HashDataLen The length, in bytes, of the buffer referenced by HashData
>-
>- @retval EFI_SUCCESS Operation completed successfully.
>- @retval EFI_UNSUPPORTED TPM device not available.
>- @retval EFI_OUT_OF_RESOURCES Out of memory.
>- @retval EFI_DEVICE_ERROR The operation was unsuccessful.
>-**/
>-EFI_STATUS
>-EFIAPI
>-TpmMeasureAndLogData (
>- IN UINT32 PcrIndex,
>- IN UINT32 EventType,
>- IN VOID *EventLog,
>- IN UINT32 LogLen,
>- IN VOID *HashData,
>- IN UINT64 HashDataLen
>- );
>-
>-#endif
>diff --git a/SecurityPkg/Library/DxeTpmMeasurementLib/DxeTpmMeasurementLib.inf
>b/SecurityPkg/Library/DxeTpmMeasurementLib/DxeTpmMeasurementLib.inf
>index d99e48c..4c61d9a 100644
>--- a/SecurityPkg/Library/DxeTpmMeasurementLib/DxeTpmMeasurementLib.inf
>+++ b/SecurityPkg/Library/DxeTpmMeasurementLib/DxeTpmMeasurementLib.inf
>@@ -1,10 +1,10 @@
> ## @file
> # Provides TPM measurement functions for TPM1.2 and TPM 2.0
> #
>-# This library provides TpmMeasureAndLogData() to to measure and log data, and
>+# This library provides TpmMeasureAndLogData() to measure and log data, and
> # extend the measurement result into a specific PCR.
> #
>-# Copyright (c) 2012 - 2014, Intel Corporation. All rights reserved.<BR>
>+# Copyright (c) 2012 - 2015, 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
>@@ -34,6 +34,7 @@ [Sources]
>
> [Packages]
> MdePkg/MdePkg.dec
>+ MdeModulePkg/MdeModulePkg.dec
> SecurityPkg/SecurityPkg.dec
>
> [LibraryClasses]
>diff --git a/SecurityPkg/SecurityPkg.dec b/SecurityPkg/SecurityPkg.dec
>index 25ec7d0..b0ef20b 100644
>--- a/SecurityPkg/SecurityPkg.dec
>+++ b/SecurityPkg/SecurityPkg.dec
>@@ -20,8 +20,8 @@ [Defines]
> DEC_SPECIFICATION = 0x00010005
> PACKAGE_NAME = SecurityPkg
> PACKAGE_UNI_FILE = SecurityPkg.uni
>- PACKAGE_GUID = 24369CAC-6AA6-4fb8-88DB-90BF061668AD
>- PACKAGE_VERSION = 0.94
>+ PACKAGE_GUID = 4EFC4F66-6219-4427-B780-FB99F470767F
>+ PACKAGE_VERSION = 0.95
>
> [Includes]
> Include
>@@ -62,10 +62,6 @@ [LibraryClasses]
> ## @libraryclass Provides TPM Interface Specification (TIS) interfaces for TPM command.
> #
> TpmCommLib|Include/Library/TpmCommLib.h
>-
>- ## @libraryclass Provides common interfaces about TPM measurement for other modules.
>- #
>- TpmMeasurementLib|Include/Library/TpmMeasurementLib.h
>
> ## @libraryclass Provides interfaces to handle TPM 2.0 request.
> #
>@@ -80,10 +76,6 @@ [Guids]
> # Include/Guid/SecurityPkgTokenSpace.h
> gEfiSecurityPkgTokenSpaceGuid = { 0xd3fb176, 0x9569, 0x4d51, { 0xa3, 0xef, 0x7d, 0x61, 0xc6, 0x4f, 0xea, 0xba }}
>
>- ## Guid acted as the authenticated variable store header's signature, and to specify the variable list entries put in the EFI system
>table.
>- # Include/Guid/AuthenticatedVariableFormat.h
>- gEfiAuthenticatedVariableGuid = { 0xaaf32c78, 0x947b, 0x439a, { 0xa1, 0x80, 0x2e, 0x14, 0x4e, 0xc3, 0x77, 0x92 } }
>-
> ## GUID used to "SecureBootEnable" variable for the Secure Boot feature enable/disable.
> # This variable is used for allowing a physically present user to disable Secure Boot via firmware setup without the possession of
>PKpriv.
> # Include/Guid/AuthenticatedVariableFormat.h
>diff --git a/SecurityPkg/SecurityPkg.dsc b/SecurityPkg/SecurityPkg.dsc
>index fd74ec1..fa94d90 100644
>--- a/SecurityPkg/SecurityPkg.dsc
>+++ b/SecurityPkg/SecurityPkg.dsc
>@@ -15,7 +15,7 @@
> [Defines]
> PLATFORM_NAME = SecurityPkg
> PLATFORM_GUID = B2C4614D-AE76-47ba-B876-5988BFED064F
>- PLATFORM_VERSION = 0.94
>+ PLATFORM_VERSION = 0.95
> DSC_SPECIFICATION = 0x00010005
> OUTPUT_DIRECTORY = Build/SecurityPkg
> SUPPORTED_ARCHITECTURES = IA32|IPF|X64|EBC
>@@ -126,7 +126,6 @@ [PcdsDynamicDefault.common.DEFAULT]
> gEfiSecurityPkgTokenSpaceGuid.PcdTpmScrtmPolicy|1
>
> [Components]
>- SecurityPkg/VariableAuthenticated/Pei/VariablePei.inf
> SecurityPkg/Library/DxeImageVerificationLib/DxeImageVerificationLib.inf
> #SecurityPkg/Library/DxeDeferImageLoadLib/DxeDeferImageLoadLib.inf
> SecurityPkg/Library/DxeImageAuthenticationStatusLib/DxeImageAuthenticationStatusLib.inf
>@@ -136,7 +135,6 @@ [Components]
> #
> # Application
> #
>- SecurityPkg/Application/VariableInfo/VariableInfo.inf
> SecurityPkg/Application/RngTest/RngTest.inf
>
> #
>@@ -182,7 +180,6 @@ [Components.IA32, Components.X64, Components.IPF]
> # SecurityPkg/UserIdentification/PwdCredentialProviderDxe/PwdCredentialProviderDxe.inf
> # SecurityPkg/UserIdentification/UsbCredentialProviderDxe/UsbCredentialProviderDxe.inf
> SecurityPkg/VariableAuthenticated/SecureBootConfigDxe/SecureBootConfigDxe.inf
>- SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxe.inf
>
> #
> # TPM
>@@ -237,8 +234,6 @@ [Components.IA32, Components.X64, Components.IPF]
> SecurityPkg/Pkcs7Verify/Pkcs7VerifyDxe/Pkcs7VerifyDxe.inf
>
> [Components.IA32, Components.X64]
>- SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.inf
>- SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.inf
> SecurityPkg/Tcg/TcgSmm/TcgSmm.inf
> SecurityPkg/Tcg/TrEESmm/TrEESmm.inf
> #
>diff --git a/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/AuthService.c
>b/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/AuthService.c
>index 45d5cfe..490a8b3 100644
>--- a/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/AuthService.c
>+++ b/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/AuthService.c
>@@ -39,16 +39,16 @@ AutenticatedVariableServiceInitialize (
> VOID
> )
> {
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK Variable;
>- UINT8 VarValue;
>- UINT32 VarAttr;
>- UINTN DataSize;
>- UINTN CtxSize;
>- VARIABLE_HEADER VariableHeader;
>- BOOLEAN Valid;
>+ EFI_STATUS Status;
>+ VARIABLE_POINTER_TRACK Variable;
>+ UINT8 VarValue;
>+ UINT32 VarAttr;
>+ UINTN DataSize;
>+ UINTN CtxSize;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ BOOLEAN Valid;
>
>- ZeroMem (&VariableHeader, sizeof (VARIABLE_HEADER));
>+ ZeroMem (&VariableHeader, sizeof (AUTHENTICATED_VARIABLE_HEADER));
>
> mVariableModuleGlobal->AuthenticatedVariableGuid[Physical] = &gEfiAuthenticatedVariableGuid;
> mVariableModuleGlobal->CertRsa2048Sha256Guid[Physical] = &gEfiCertRsa2048Sha256Guid;
>@@ -477,16 +477,16 @@ ProcessVarWithPk (
> IN BOOLEAN IsPk
> )
> {
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK PkVariable;
>- EFI_SIGNATURE_LIST *OldPkList;
>- EFI_SIGNATURE_DATA *OldPkData;
>- EFI_VARIABLE_AUTHENTICATION *CertData;
>- VARIABLE_HEADER VariableHeader;
>- BOOLEAN Valid;
>+ EFI_STATUS Status;
>+ VARIABLE_POINTER_TRACK PkVariable;
>+ EFI_SIGNATURE_LIST *OldPkList;
>+ EFI_SIGNATURE_DATA *OldPkData;
>+ EFI_VARIABLE_AUTHENTICATION *CertData;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ BOOLEAN Valid;
>
> OldPkList = NULL;
>- ZeroMem (&VariableHeader, sizeof (VARIABLE_HEADER));
>+ ZeroMem (&VariableHeader, sizeof (AUTHENTICATED_VARIABLE_HEADER));
>
> if ((Attributes & EFI_VARIABLE_NON_VOLATILE) == 0) {
> //
>@@ -622,11 +622,11 @@ ProcessVarWithKek (
> EFI_CERT_BLOCK_RSA_2048_SHA256 *CertBlock;
> BOOLEAN IsFound;
> UINT32 Index;
>- VARIABLE_HEADER VariableHeader;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
> BOOLEAN Valid;
>
> KekList = NULL;
>- ZeroMem (&VariableHeader, sizeof (VARIABLE_HEADER));
>+ ZeroMem (&VariableHeader, sizeof (AUTHENTICATED_VARIABLE_HEADER));
>
> if (mPlatformMode == USER_MODE) {
> if ((Attributes & EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) == 0) {
>@@ -771,7 +771,7 @@ VerifyVariable (
> UINT8 *PubKey;
> EFI_VARIABLE_AUTHENTICATION *CertData;
> EFI_CERT_BLOCK_RSA_2048_SHA256 *CertBlock;
>- VARIABLE_HEADER VariableHeader;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
> BOOLEAN Valid;
>
> CertData = NULL;
>@@ -786,7 +786,7 @@ VerifyVariable (
> //
> // Determine if first time SetVariable with the EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS.
> //
>- ZeroMem (&VariableHeader, sizeof (VARIABLE_HEADER));
>+ ZeroMem (&VariableHeader, sizeof (AUTHENTICATED_VARIABLE_HEADER));
> if (Variable->CurrPtr != 0x0) {
> Valid = IsValidVariableHeader (
> Variable->CurrPtr,
>diff --git a/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.c
>b/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.c
>index 0b2775d..f08adf0 100644
>--- a/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.c
>+++ b/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.c
>@@ -347,7 +347,7 @@ GetVarStoreHeader (
> FALSE - Variable is non-volatile.
> @param[in] Global Pointer to VARAIBLE_GLOBAL structure.
> @param[in] Instance Instance of FV Block services.
>- @param[out] VariableHeader Pointer to VARIABLE_HEADER for output.
>+ @param[out] VariableHeader Pointer to AUTHENTICATED_VARIABLE_HEADER for output.
>
> @retval TRUE Variable header is valid.
> @retval FALSE Variable header is not valid.
>@@ -355,15 +355,15 @@ GetVarStoreHeader (
> **/
> BOOLEAN
> IsValidVariableHeader (
>- IN EFI_PHYSICAL_ADDRESS VariableAddress,
>- IN BOOLEAN Volatile,
>- IN VARIABLE_GLOBAL *Global,
>- IN UINTN Instance,
>- OUT VARIABLE_HEADER *VariableHeader OPTIONAL
>+ IN EFI_PHYSICAL_ADDRESS VariableAddress,
>+ IN BOOLEAN Volatile,
>+ IN VARIABLE_GLOBAL *Global,
>+ IN UINTN Instance,
>+ OUT AUTHENTICATED_VARIABLE_HEADER *VariableHeader OPTIONAL
> )
> {
>- EFI_STATUS Status;
>- VARIABLE_HEADER LocalVariableHeader;
>+ EFI_STATUS Status;
>+ AUTHENTICATED_VARIABLE_HEADER LocalVariableHeader;
>
> Status = AccessVariableStore (
> FALSE,
>@@ -371,7 +371,7 @@ IsValidVariableHeader (
> Volatile,
> Instance,
> VariableAddress,
>- sizeof (VARIABLE_HEADER),
>+ sizeof (AUTHENTICATED_VARIABLE_HEADER),
> &LocalVariableHeader
> );
>
>@@ -380,7 +380,7 @@ IsValidVariableHeader (
> }
>
> if (VariableHeader != NULL) {
>- CopyMem (VariableHeader, &LocalVariableHeader, sizeof (VARIABLE_HEADER));
>+ CopyMem (VariableHeader, &LocalVariableHeader, sizeof (AUTHENTICATED_VARIABLE_HEADER));
> }
>
> return TRUE;
>@@ -439,7 +439,7 @@ GetVariableStoreStatus (
> **/
> UINTN
> NameSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>+ IN AUTHENTICATED_VARIABLE_HEADER *Variable
> )
> {
> if (Variable->State == (UINT8) (-1) ||
>@@ -465,7 +465,7 @@ NameSizeOfVariable (
> **/
> UINTN
> DataSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>+ IN AUTHENTICATED_VARIABLE_HEADER *Variable
> )
> {
> if (Variable->State == (UINT8) -1 ||
>@@ -500,10 +500,10 @@ GetVariableNamePtr (
> OUT CHAR16 *VariableName
> )
> {
>- EFI_STATUS Status;
>- EFI_PHYSICAL_ADDRESS Address;
>- VARIABLE_HEADER VariableHeader;
>- BOOLEAN IsValid;
>+ EFI_STATUS Status;
>+ EFI_PHYSICAL_ADDRESS Address;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ BOOLEAN IsValid;
>
> IsValid = IsValidVariableHeader (VariableAddress, Volatile, Global, Instance, &VariableHeader);
> ASSERT (IsValid);
>@@ -511,7 +511,7 @@ GetVariableNamePtr (
> //
> // Name area follows variable header.
> //
>- Address = VariableAddress + sizeof (VARIABLE_HEADER);
>+ Address = VariableAddress + sizeof (AUTHENTICATED_VARIABLE_HEADER);
>
> Status = AccessVariableStore (
> FALSE,
>@@ -548,10 +548,10 @@ GetVariableDataPtr (
> OUT CHAR16 *VariableData
> )
> {
>- EFI_STATUS Status;
>- EFI_PHYSICAL_ADDRESS Address;
>- VARIABLE_HEADER VariableHeader;
>- BOOLEAN IsValid;
>+ EFI_STATUS Status;
>+ EFI_PHYSICAL_ADDRESS Address;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ BOOLEAN IsValid;
>
> IsValid = IsValidVariableHeader (VariableAddress, Volatile, Global, Instance, &VariableHeader);
> ASSERT (IsValid);
>@@ -560,7 +560,7 @@ GetVariableDataPtr (
> // Data area follows variable name.
> // Be careful about pad size for alignment
> //
>- Address = VariableAddress + sizeof (VARIABLE_HEADER);
>+ Address = VariableAddress + sizeof (AUTHENTICATED_VARIABLE_HEADER);
> Address += NameSizeOfVariable (&VariableHeader);
> Address += GET_PAD_SIZE (NameSizeOfVariable (&VariableHeader));
>
>@@ -601,8 +601,8 @@ GetNextVariablePtr (
> IN UINTN Instance
> )
> {
>- EFI_PHYSICAL_ADDRESS Address;
>- VARIABLE_HEADER VariableHeader;
>+ EFI_PHYSICAL_ADDRESS Address;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>
> if (!IsValidVariableHeader (VariableAddress, Volatile, Global, Instance, &VariableHeader)) {
> return 0x0;
>@@ -611,7 +611,7 @@ GetNextVariablePtr (
> //
> // Header of next variable follows data area of this variable
> //
>- Address = VariableAddress + sizeof (VARIABLE_HEADER);
>+ Address = VariableAddress + sizeof (AUTHENTICATED_VARIABLE_HEADER);
> Address += NameSizeOfVariable (&VariableHeader);
> Address += GET_PAD_SIZE (NameSizeOfVariable (&VariableHeader));
> Address += DataSizeOfVariable (&VariableHeader);
>@@ -964,14 +964,14 @@ FindVariable (
> IN UINTN Instance
> )
> {
>- EFI_PHYSICAL_ADDRESS Variable[2];
>- EFI_PHYSICAL_ADDRESS InDeletedVariable;
>- EFI_PHYSICAL_ADDRESS VariableStoreHeader[2];
>- UINTN InDeletedStorageIndex;
>- UINTN Index;
>- CHAR16 LocalVariableName[MAX_NAME_SIZE];
>- BOOLEAN Volatile;
>- VARIABLE_HEADER VariableHeader;
>+ EFI_PHYSICAL_ADDRESS Variable[2];
>+ EFI_PHYSICAL_ADDRESS InDeletedVariable;
>+ EFI_PHYSICAL_ADDRESS VariableStoreHeader[2];
>+ UINTN InDeletedStorageIndex;
>+ UINTN Index;
>+ CHAR16 LocalVariableName[MAX_NAME_SIZE];
>+ BOOLEAN Volatile;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>
> //
> // 0: Volatile, 1: Non-Volatile
>@@ -1120,24 +1120,24 @@ Reclaim (
> IN EFI_PHYSICAL_ADDRESS UpdatingVariable
> )
> {
>- EFI_PHYSICAL_ADDRESS Variable;
>- EFI_PHYSICAL_ADDRESS AddedVariable;
>- EFI_PHYSICAL_ADDRESS NextVariable;
>- EFI_PHYSICAL_ADDRESS NextAddedVariable;
>- VARIABLE_STORE_HEADER VariableStoreHeader;
>- VARIABLE_HEADER VariableHeader;
>- VARIABLE_HEADER AddedVariableHeader;
>- CHAR16 VariableName[MAX_NAME_SIZE];
>- CHAR16 AddedVariableName[MAX_NAME_SIZE];
>- UINT8 *ValidBuffer;
>- UINTN MaximumBufferSize;
>- UINTN VariableSize;
>- UINTN NameSize;
>- UINT8 *CurrPtr;
>- BOOLEAN FoundAdded;
>- EFI_STATUS Status;
>- VARIABLE_GLOBAL *VariableGlobal;
>- UINT32 Instance;
>+ EFI_PHYSICAL_ADDRESS Variable;
>+ EFI_PHYSICAL_ADDRESS AddedVariable;
>+ EFI_PHYSICAL_ADDRESS NextVariable;
>+ EFI_PHYSICAL_ADDRESS NextAddedVariable;
>+ VARIABLE_STORE_HEADER VariableStoreHeader;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ AUTHENTICATED_VARIABLE_HEADER AddedVariableHeader;
>+ CHAR16 VariableName[MAX_NAME_SIZE];
>+ CHAR16 AddedVariableName[MAX_NAME_SIZE];
>+ UINT8 *ValidBuffer;
>+ UINTN MaximumBufferSize;
>+ UINTN VariableSize;
>+ UINTN NameSize;
>+ UINT8 *CurrPtr;
>+ BOOLEAN FoundAdded;
>+ EFI_STATUS Status;
>+ VARIABLE_GLOBAL *VariableGlobal;
>+ UINT32 Instance;
>
> VariableGlobal = &Global->VariableGlobal[VirtualMode];
> Instance = Global->FvbInstance;
>@@ -1200,9 +1200,9 @@ Reclaim (
> VariableSize = NextVariable - Variable;
> CopyMem (CurrPtr, (UINT8 *) Variable, VariableSize);
> CurrPtr += VariableSize;
>- if ((!IsVolatile) && ((((VARIABLE_HEADER*)Variable)->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) ==
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>+ if ((!IsVolatile) && ((((AUTHENTICATED_VARIABLE_HEADER*)Variable)->Attributes &
>EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
> Global->HwErrVariableTotalSize += VariableSize;
>- } else if ((!IsVolatile) && ((((VARIABLE_HEADER*)Variable)->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) !=
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>+ } else if ((!IsVolatile) && ((((AUTHENTICATED_VARIABLE_HEADER*)Variable)->Attributes &
>EFI_VARIABLE_HARDWARE_ERROR_RECORD) != EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
> Global->CommonVariableTotalSize += VariableSize;
> }
> }
>@@ -1254,12 +1254,12 @@ Reclaim (
> // 1. No valid instance of this variable exists.
> // 2. It is not the variable that is going to be updated.
> //
>- ((VARIABLE_HEADER *) CurrPtr)->State = VAR_ADDED;
>+ ((AUTHENTICATED_VARIABLE_HEADER *) CurrPtr)->State = VAR_ADDED;
> }
> CurrPtr += VariableSize;
>- if ((!IsVolatile) && ((((VARIABLE_HEADER*)Variable)->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) ==
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>+ if ((!IsVolatile) && ((((AUTHENTICATED_VARIABLE_HEADER*)Variable)->Attributes &
>EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
> Global->HwErrVariableTotalSize += VariableSize;
>- } else if ((!IsVolatile) && ((((VARIABLE_HEADER*)Variable)->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) !=
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>+ } else if ((!IsVolatile) && ((((AUTHENTICATED_VARIABLE_HEADER*)Variable)->Attributes &
>EFI_VARIABLE_HARDWARE_ERROR_RECORD) != EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
> Global->CommonVariableTotalSize += VariableSize;
> }
> }
>@@ -1729,7 +1729,7 @@ AutoUpdateLangVariable(
> VariableGlobal,
> Variable.Volatile,
> Instance,
>- (UINTN) &(((VARIABLE_HEADER *)Variable.CurrPtr)->DataSize),
>+ (UINTN) &(((AUTHENTICATED_VARIABLE_HEADER *)Variable.CurrPtr)->DataSize),
> sizeof (DataSize),
> &DataSize
> );
>@@ -1865,15 +1865,15 @@ UpdateVariable (
> )
> {
> EFI_STATUS Status;
>- VARIABLE_HEADER *NextVariable;
>+ AUTHENTICATED_VARIABLE_HEADER *NextVariable;
> UINTN VarNameOffset;
> UINTN VarDataOffset;
> UINTN VarNameSize;
> UINTN VarSize;
> BOOLEAN Volatile;
> UINT8 State;
>- VARIABLE_HEADER VariableHeader;
>- VARIABLE_HEADER *NextVariableHeader;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ AUTHENTICATED_VARIABLE_HEADER *NextVariableHeader;
> BOOLEAN Valid;
> BOOLEAN Reclaimed;
> VARIABLE_STORE_HEADER VariableStoreHeader;
>@@ -1930,7 +1930,7 @@ UpdateVariable (
> VariableGlobal,
> Variable->Volatile,
> Instance,
>- (UINTN) &(((VARIABLE_HEADER *)Variable->CurrPtr)->State),
>+ (UINTN) &(((AUTHENTICATED_VARIABLE_HEADER *)Variable->CurrPtr)->State),
> sizeof (UINT8),
> &State
> );
>@@ -1946,7 +1946,7 @@ UpdateVariable (
> // then return to the caller immediately.
> //
> if (DataSizeOfVariable (&VariableHeader) == DataSize) {
>- NextVariable = (VARIABLE_HEADER *)GetEndPointer (VariableGlobal->VolatileVariableBase, TRUE, VariableGlobal, Instance);
>+ NextVariable = (AUTHENTICATED_VARIABLE_HEADER *)GetEndPointer (VariableGlobal->VolatileVariableBase, TRUE,
>VariableGlobal, Instance);
> GetVariableDataPtr (Variable->CurrPtr, Variable->Volatile, VariableGlobal, Instance, (CHAR16 *) NextVariable);
> if (CompareMem (Data, (VOID *) NextVariable, DataSize) == 0) {
> UpdateVariableInfo (VariableName, VendorGuid, Volatile, FALSE, TRUE, FALSE, FALSE);
>@@ -1968,7 +1968,7 @@ UpdateVariable (
> VariableGlobal,
> Variable->Volatile,
> Instance,
>- (UINTN) &(((VARIABLE_HEADER *)Variable->CurrPtr)->State),
>+ (UINTN) &(((AUTHENTICATED_VARIABLE_HEADER *)Variable->CurrPtr)->State),
> sizeof (UINT8),
> &State
> );
>@@ -2007,9 +2007,9 @@ UpdateVariable (
> // Tricky part: Use scratch data area at the end of volatile variable store
> // as a temporary storage.
> //
>- NextVariable = (VARIABLE_HEADER *)GetEndPointer (VariableGlobal->VolatileVariableBase, TRUE, VariableGlobal, Instance);
>+ NextVariable = (AUTHENTICATED_VARIABLE_HEADER *)GetEndPointer (VariableGlobal->VolatileVariableBase, TRUE,
>VariableGlobal, Instance);
> ScratchSize = MAX (PcdGet32 (PcdMaxVariableSize), PcdGet32 (PcdMaxHardwareErrorVariableSize));
>- NextVariableHeader = (VARIABLE_HEADER *) NextVariable;
>+ NextVariableHeader = (AUTHENTICATED_VARIABLE_HEADER *) NextVariable;
>
> SetMem (NextVariableHeader, ScratchSize, 0xff);
>
>@@ -2018,7 +2018,7 @@ UpdateVariable (
> NextVariableHeader->PubKeyIndex = KeyIndex;
> NextVariableHeader->MonotonicCount = MonotonicCount;
> NextVariableHeader->Reserved = 0;
>- VarNameOffset = sizeof (VARIABLE_HEADER);
>+ VarNameOffset = sizeof (AUTHENTICATED_VARIABLE_HEADER);
> VarNameSize = StrSize (VariableName);
> CopyMem (
> (UINT8 *) ((UINTN)NextVariable + VarNameOffset),
>@@ -2096,7 +2096,7 @@ UpdateVariable (
> FALSE,
> Instance,
> VariableGlobal->NonVolatileVariableBase + Global->NonVolatileLastVariableOffset,
>- sizeof (VARIABLE_HEADER),
>+ sizeof (AUTHENTICATED_VARIABLE_HEADER),
> (UINT8 *) NextVariable
> );
>
>@@ -2114,7 +2114,7 @@ UpdateVariable (
> FALSE,
> Instance,
> VariableGlobal->NonVolatileVariableBase + Global->NonVolatileLastVariableOffset,
>- sizeof (VARIABLE_HEADER),
>+ sizeof (AUTHENTICATED_VARIABLE_HEADER),
> (UINT8 *) NextVariable
> );
>
>@@ -2129,9 +2129,9 @@ UpdateVariable (
> VariableGlobal,
> FALSE,
> Instance,
>- VariableGlobal->NonVolatileVariableBase + Global->NonVolatileLastVariableOffset + sizeof (VARIABLE_HEADER),
>- (UINT32) VarSize - sizeof (VARIABLE_HEADER),
>- (UINT8 *) NextVariable + sizeof (VARIABLE_HEADER)
>+ VariableGlobal->NonVolatileVariableBase + Global->NonVolatileLastVariableOffset + sizeof
>(AUTHENTICATED_VARIABLE_HEADER),
>+ (UINT32) VarSize - sizeof (AUTHENTICATED_VARIABLE_HEADER),
>+ (UINT8 *) NextVariable + sizeof (AUTHENTICATED_VARIABLE_HEADER)
> );
>
> if (EFI_ERROR (Status)) {
>@@ -2147,7 +2147,7 @@ UpdateVariable (
> FALSE,
> Instance,
> VariableGlobal->NonVolatileVariableBase + Global->NonVolatileLastVariableOffset,
>- sizeof (VARIABLE_HEADER),
>+ sizeof (AUTHENTICATED_VARIABLE_HEADER),
> (UINT8 *) NextVariable
> );
>
>@@ -2212,7 +2212,7 @@ UpdateVariable (
> // has already been eliminated, so no need to delete it.
> //
> if (!Reclaimed && !EFI_ERROR (Status) && Variable->CurrPtr != 0) {
>- State = ((VARIABLE_HEADER *)Variable->CurrPtr)->State;
>+ State = ((AUTHENTICATED_VARIABLE_HEADER *)Variable->CurrPtr)->State;
> State &= VAR_DELETED;
>
> Status = AccessVariableStore (
>@@ -2220,7 +2220,7 @@ UpdateVariable (
> VariableGlobal,
> Variable->Volatile,
> Instance,
>- (UINTN) &(((VARIABLE_HEADER *)Variable->CurrPtr)->State),
>+ (UINTN) &(((AUTHENTICATED_VARIABLE_HEADER *)Variable->CurrPtr)->State),
> sizeof (UINT8),
> &State
> );
>@@ -2277,13 +2277,13 @@ EsalGetVariable (
> IN ESAL_VARIABLE_GLOBAL *Global
> )
> {
>- VARIABLE_POINTER_TRACK Variable;
>- UINTN VarDataSize;
>- EFI_STATUS Status;
>- VARIABLE_HEADER VariableHeader;
>- BOOLEAN Valid;
>- VARIABLE_GLOBAL *VariableGlobal;
>- UINT32 Instance;
>+ VARIABLE_POINTER_TRACK Variable;
>+ UINTN VarDataSize;
>+ EFI_STATUS Status;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ BOOLEAN Valid;
>+ VARIABLE_GLOBAL *VariableGlobal;
>+ UINT32 Instance;
>
> if (VariableName == NULL || VendorGuid == NULL || DataSize == NULL) {
> return EFI_INVALID_PARAMETER;
>@@ -2400,12 +2400,12 @@ EsalGetNextVariableName (
> IN ESAL_VARIABLE_GLOBAL *Global
> )
> {
>- VARIABLE_POINTER_TRACK Variable;
>- UINTN VarNameSize;
>- EFI_STATUS Status;
>- VARIABLE_HEADER VariableHeader;
>- VARIABLE_GLOBAL *VariableGlobal;
>- UINT32 Instance;
>+ VARIABLE_POINTER_TRACK Variable;
>+ UINTN VarNameSize;
>+ EFI_STATUS Status;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ VARIABLE_GLOBAL *VariableGlobal;
>+ UINT32 Instance;
>
> if (VariableNameSize == NULL || VariableName == NULL || VendorGuid == NULL) {
> return EFI_INVALID_PARAMETER;
>@@ -2607,7 +2607,7 @@ EsalSetVariable (
> // For variable for hardware error record, the size of the VariableName, including the Unicode Null
> // in bytes plus the DataSize is limited to maximum size of PcdGet32(PcdMaxHardwareErrorVariableSize) bytes.
> //
>- if (StrSize (VariableName) + PayloadSize > PcdGet32(PcdMaxHardwareErrorVariableSize) - sizeof (VARIABLE_HEADER)) {
>+ if (StrSize (VariableName) + PayloadSize > PcdGet32(PcdMaxHardwareErrorVariableSize) - sizeof
>(AUTHENTICATED_VARIABLE_HEADER)) {
> return EFI_INVALID_PARAMETER;
> }
> //
>@@ -2623,7 +2623,7 @@ EsalSetVariable (
> // For variable not for hardware error record, the size of the VariableName, including the
> // Unicode Null in bytes plus the DataSize is limited to maximum size of PcdGet32(PcdMaxVariableSize) bytes.
> //
>- if (StrSize (VariableName) + PayloadSize > PcdGet32(PcdMaxVariableSize) - sizeof (VARIABLE_HEADER)) {
>+ if (StrSize (VariableName) + PayloadSize > PcdGet32(PcdMaxVariableSize) - sizeof (AUTHENTICATED_VARIABLE_HEADER)) {
> return EFI_INVALID_PARAMETER;
> }
> }
>@@ -2746,17 +2746,17 @@ EsalQueryVariableInfo (
> IN ESAL_VARIABLE_GLOBAL *Global
> )
> {
>- EFI_PHYSICAL_ADDRESS Variable;
>- EFI_PHYSICAL_ADDRESS NextVariable;
>- UINT64 VariableSize;
>- EFI_PHYSICAL_ADDRESS VariableStoreHeaderAddress;
>- BOOLEAN Volatile;
>- VARIABLE_STORE_HEADER VarStoreHeader;
>- VARIABLE_HEADER VariableHeader;
>- UINT64 CommonVariableTotalSize;
>- UINT64 HwErrVariableTotalSize;
>- VARIABLE_GLOBAL *VariableGlobal;
>- UINT32 Instance;
>+ EFI_PHYSICAL_ADDRESS Variable;
>+ EFI_PHYSICAL_ADDRESS NextVariable;
>+ UINT64 VariableSize;
>+ EFI_PHYSICAL_ADDRESS VariableStoreHeaderAddress;
>+ BOOLEAN Volatile;
>+ VARIABLE_STORE_HEADER VarStoreHeader;
>+ AUTHENTICATED_VARIABLE_HEADER VariableHeader;
>+ UINT64 CommonVariableTotalSize;
>+ UINT64 HwErrVariableTotalSize;
>+ VARIABLE_GLOBAL *VariableGlobal;
>+ UINT32 Instance;
>
> CommonVariableTotalSize = 0;
> HwErrVariableTotalSize = 0;
>@@ -2818,7 +2818,7 @@ EsalQueryVariableInfo (
> //
> if ((Attributes & (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) == (EFI_VARIABLE_NON_VOLATILE
>| EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
> *MaximumVariableStorageSize = PcdGet32(PcdHwErrStorageSize);
>- *MaximumVariableSize = PcdGet32(PcdMaxHardwareErrorVariableSize) - sizeof (VARIABLE_HEADER);
>+ *MaximumVariableSize = PcdGet32(PcdMaxHardwareErrorVariableSize) - sizeof (AUTHENTICATED_VARIABLE_HEADER);
> } else {
> if ((Attributes & EFI_VARIABLE_NON_VOLATILE) != 0) {
> ASSERT (PcdGet32(PcdHwErrStorageSize) < VarStoreHeader.Size);
>@@ -2828,7 +2828,7 @@ EsalQueryVariableInfo (
> //
> // Let *MaximumVariableSize be PcdGet32(PcdMaxVariableSize) with the exception of the variable header size.
> //
>- *MaximumVariableSize = PcdGet32(PcdMaxVariableSize) - sizeof (VARIABLE_HEADER);
>+ *MaximumVariableSize = PcdGet32(PcdMaxVariableSize) - sizeof (AUTHENTICATED_VARIABLE_HEADER);
> }
>
> //
>@@ -2882,10 +2882,10 @@ EsalQueryVariableInfo (
> *RemainingVariableStorageSize = *MaximumVariableStorageSize - CommonVariableTotalSize;
> }
>
>- if (*RemainingVariableStorageSize < sizeof (VARIABLE_HEADER)) {
>+ if (*RemainingVariableStorageSize < sizeof (AUTHENTICATED_VARIABLE_HEADER)) {
> *MaximumVariableSize = 0;
>- } else if ((*RemainingVariableStorageSize - sizeof (VARIABLE_HEADER)) < *MaximumVariableSize) {
>- *MaximumVariableSize = *RemainingVariableStorageSize - sizeof (VARIABLE_HEADER);
>+ } else if ((*RemainingVariableStorageSize - sizeof (AUTHENTICATED_VARIABLE_HEADER)) < *MaximumVariableSize) {
>+ *MaximumVariableSize = *RemainingVariableStorageSize - sizeof (AUTHENTICATED_VARIABLE_HEADER);
> }
>
> ReleaseLockOnlyAtBootTime (&VariableGlobal->VariableServicesLock);
>@@ -2955,7 +2955,7 @@ FlushHob2Nv (
> EFI_STATUS Status;
> VOID *GuidHob;
> VARIABLE_STORE_HEADER *VariableStoreHeader;
>- VARIABLE_HEADER *VariableHeader;
>+ AUTHENTICATED_VARIABLE_HEADER *VariableHeader;
> //
> // Get HOB variable store.
> //
>@@ -2970,11 +2970,11 @@ FlushHob2Nv (
> //
> // Flush the HOB variable to NV Variable storage.
> //
>- for ( VariableHeader = (VARIABLE_HEADER *) HEADER_ALIGN (VariableStoreHeader + 1)
>- ; (VariableHeader < (VARIABLE_HEADER *) HEADER_ALIGN ((UINTN) VariableStoreHeader + VariableStoreHeader->Size)
>+ for ( VariableHeader = (AUTHENTICATED_VARIABLE_HEADER *) HEADER_ALIGN (VariableStoreHeader + 1)
>+ ; (VariableHeader < (AUTHENTICATED_VARIABLE_HEADER *) HEADER_ALIGN ((UINTN) VariableStoreHeader +
>VariableStoreHeader->Size)
> &&
> (VariableHeader->StartId == VARIABLE_DATA))
>- ; VariableHeader = (VARIABLE_HEADER *) HEADER_ALIGN ((UINTN) (VariableHeader + 1)
>+ ; VariableHeader = (AUTHENTICATED_VARIABLE_HEADER *) HEADER_ALIGN ((UINTN) (VariableHeader + 1)
> + VariableHeader->NameSize + GET_PAD_SIZE (VariableHeader->NameSize)
> + VariableHeader->DataSize + GET_PAD_SIZE (VariableHeader->DataSize)
> )
>@@ -3198,7 +3198,7 @@ VariableCommonInitialize (
> Instance
> );
> VariableSize = NextVariable - Variable;
>- if ((((VARIABLE_HEADER *)Variable)->Attributes & (EFI_VARIABLE_NON_VOLATILE |
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) == (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>+ if ((((AUTHENTICATED_VARIABLE_HEADER *)Variable)->Attributes & (EFI_VARIABLE_NON_VOLATILE |
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) == (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
> mVariableModuleGlobal->HwErrVariableTotalSize += VariableSize;
> } else {
> mVariableModuleGlobal->CommonVariableTotalSize += VariableSize;
>diff --git a/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.h
>b/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.h
>index 5e6690e..b32ef74 100644
>--- a/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.h
>+++ b/SecurityPkg/VariableAuthenticated/EsalVariableDxeSal/Variable.h
>@@ -1,7 +1,7 @@
> /** @file
> Internal header file for Extended SAL variable service module.
>
>-Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>
>+Copyright (c) 2009 - 2015, 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
>@@ -66,7 +66,7 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
> /// The maximum size of the public key database, restricted by maximum individal EFI
> /// varible size, and excluding the variable header and name size.
> ///
>-#define MAX_KEYDB_SIZE (FixedPcdGet32 (PcdMaxVariableSize) - sizeof (VARIABLE_HEADER) - AUTHVAR_KEYDB_NAME_SIZE)
>+#define MAX_KEYDB_SIZE (FixedPcdGet32 (PcdMaxVariableSize) - sizeof (AUTHENTICATED_VARIABLE_HEADER) -
>AUTHVAR_KEYDB_NAME_SIZE)
> #define MAX_KEY_NUM (MAX_KEYDB_SIZE / EFI_CERT_TYPE_RSA2048_SIZE)
>
> ///
>@@ -432,7 +432,7 @@ GetVariableDataPtr (
> **/
> UINTN
> DataSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>+ IN AUTHENTICATED_VARIABLE_HEADER *Variable
> );
>
> /**
>@@ -479,7 +479,7 @@ UpdateVariable (
> FALSE - Variable is non-volatile.
> @param[in] Global Pointer to VARAIBLE_GLOBAL structure.
> @param[in] Instance Instance of FV Block services.
>- @param[out] VariableHeader Pointer to VARIABLE_HEADER for output.
>+ @param[out] VariableHeader Pointer to AUTHENTICATED_VARIABLE_HEADER for output.
>
> @retval TRUE Variable header is valid.
> @retval FALSE Variable header is not valid.
>@@ -487,11 +487,11 @@ UpdateVariable (
> **/
> BOOLEAN
> IsValidVariableHeader (
>- IN EFI_PHYSICAL_ADDRESS VariableAddress,
>- IN BOOLEAN Volatile,
>- IN VARIABLE_GLOBAL *Global,
>- IN UINTN Instance,
>- OUT VARIABLE_HEADER *VariableHeader OPTIONAL
>+ IN EFI_PHYSICAL_ADDRESS VariableAddress,
>+ IN BOOLEAN Volatile,
>+ IN VARIABLE_GLOBAL *Global,
>+ IN UINTN Instance,
>+ OUT AUTHENTICATED_VARIABLE_HEADER *VariableHeader OPTIONAL
> );
>
> /**
>diff --git a/SecurityPkg/VariableAuthenticated/Pei/PeiVariableAuth.uni
>b/SecurityPkg/VariableAuthenticated/Pei/PeiVariableAuth.uni
>deleted file mode 100644
>index 0fdc8055076e5d6a3192b48ac0138055032bc440..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 2170
>zcmds&NpBND5QXcE#D5q$7eI*(5f>0b*u=mn5L;ddoTBlPWF&8lZ6JRh_+GVV#*Q4p
>zHE85ss;ggBzk1#N{i|j*i}*d^i|mbET51y;+e3SRRco<LZQ-^l_L;40iM7Kxv5~c~
>zOzZ~BXXY8Z6C1d9WL<nR`;KkMNV_unZ??vw(Fn`H_qMG`***@MKTvm&8iIn)u$}
>zb9dxqEA}x6ZN9iTM|qx}UE`^2rZy+mdXsH>ug_WCbJDk*Zvnrm$`z+xapp(V;xYZP
>zJ>`4B=x8&0X3y=AaqKl7!%AdA$iPsWus>xqvnnffuZt?0W9Ri<ZmO>OR_&EF(8}vQ
>z*_CxzfHEgT#h8MfYhXprW1kPndhYen+6^&h_^X1-N-C4?q?5AFQloZHSd;#wr=YnU
>zU%N-{lb}-RXF{8+cg+s1W?<x*gjiEoPmZF@<e3)yh>1BjsodA#E}Ss`xRXnn>krrD
>zkXEPPJ#9)3LR1bxw~D2^p;Hgg?{;0ps!o0Bx>gO9^H18_IqmWixYRu!Z1&GV2zOB&
>zm$^zuD>U)a-v=oya4Y}JnXYpBjQZ4WalgbeAoCHL+l^iY<(gj^rDq>_6LgC^yfN=-
>z>;68(Fd4z6`X1I8ef1eNo!`El(KoS2*aAYyeT<%)cyt}P#Yj3<TcH=OP%HEepKErw
>zmD4%vLT!1($j<TVcxGqVV^D?B^5`9A%3U_a?BOdPMGao>@KyA$^rx&SbKO6^gdumG
>zqG?|WoDyAcWg9gq<_Whf=***@fmrcKeLNnp+1pY2SYJt%Qt!WozB)-IK9kzO8
>zaMyR>w?$ZMG<)T$krIx;Ql=HMyU+g|m4dy0V@|s3!kIMLE^57xy}vW3Tl_!%N0prZ
>***@Bjb+
>
>diff --git a/SecurityPkg/VariableAuthenticated/Pei/PeiVariableExtra.uni
>b/SecurityPkg/VariableAuthenticated/Pei/PeiVariableExtra.uni
>deleted file mode 100644
>index c9f171b0662cfdc5ffea376b12c02dadce55082e..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 1348
>zcmZXUTW`}q5QXO%iT_}g7eKAU?Fk`7Lk(DzI!Y4?Pf>17Ev0efB!%$ff$z-vLW&~q
>z?##}dIeT_Ce|~qYV-ep|ev!SiYs+nEb9-***@M^DzmD^VvTgg1OiSI{tZiP*;mw0~>
>zGb8rWwjQ;zg>A6MwsQY_Vpr_VeXOzTIWq09ZST1YyCE{N$Dlu9eqqn-xxHj{(pazT
>zm~~oVE?Enq1ViJP{M;+X?3}_-5n>;(#jJ$OhOe|c=N{V|>ssI5HYab{4Pcb}***@i
>zps2<zDE0ZaM9kfu!n$B@?R$Ijq(y{BtW-}LE<tPYrL3~0<doIQnMuzYU)i&&!X0bf
>zQF{|RGPGNgQ8Nj(Zk=_FB4&!r8-1ii!JW5xUGDG<`}}}Q%k_tAF=Z6H!_($)5TZB)
>zy;N(1ty52I*VNU$NL8Ks8h^MUasElneNKnE1TFVOO{)9?gwSWwxaF!o+Hw=Gy_3~p
>zL0iR_u5`@lOYWz0Px}p?3Cw5o++p<?lpDUb%D_HZ0-GM)li5ecQ~QFQqGW`***@7O
>z`fJE4aeaq&!JOci5&@yrKBb=%A}$>{W2HXUc*HDRp&l`J-IjIy52q{kg_?QA$gYU$
>zJF^S?DX7B8ym}u?+~rfv0kMiv)e!Z8SXKYd{Fxmw*ZWJVD&Z7~eQR)9^b{?6bdzeH
>zS=?}J_0vC3$Nlm>YWgL-o1opOQnv?6zd6AO><rW)_=%0+CFOM&0ZDH}C_Cnb_loZS
>hgn02&jMP+DsuT79r1uxzsb1gz|9PsPlBL}G`wLwR(0>2`
>
>diff --git a/SecurityPkg/VariableAuthenticated/Pei/Variable.c b/SecurityPkg/VariableAuthenticated/Pei/Variable.c
>deleted file mode 100644
>index 7ee8b88..0000000
>--- a/SecurityPkg/VariableAuthenticated/Pei/Variable.c
>+++ /dev/null
>@@ -1,1087 +0,0 @@
>-/** @file
>- Implement ReadOnly Variable Services required by PEIM and install PEI
>- ReadOnly Varaiable2 PPI. These services operates the non-volatile
>- storage space.
>-
>-Copyright (c) 2009 - 2014, 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
>-
>-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 "Variable.h"
>-
>-//
>-// Module globals
>-//
>-EFI_PEI_READ_ONLY_VARIABLE2_PPI mVariablePpi = {
>- PeiGetVariable,
>- PeiGetNextVariableName
>-};
>-
>-EFI_PEI_PPI_DESCRIPTOR mPpiListVariable = {
>- (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),
>- &gEfiPeiReadOnlyVariable2PpiGuid,
>- &mVariablePpi
>-};
>-
>-/**
>- Provide the functionality of the variable services.
>-
>- @param FileHandle Handle of the file being invoked.
>- Type EFI_PEI_FILE_HANDLE is defined in FfsFindNextFile().
>- @param PeiServices General purpose services available to every PEIM.
>-
>- @retval EFI_SUCCESS If the interface could be successfully installed
>- @retval Others Returned from PeiServicesInstallPpi()
>-**/
>-EFI_STATUS
>-EFIAPI
>-PeimInitializeVariableServices (
>- IN EFI_PEI_FILE_HANDLE FileHandle,
>- IN CONST EFI_PEI_SERVICES **PeiServices
>- )
>-{
>- return PeiServicesInstallPpi (&mPpiListVariable);
>-}
>-
>-/**
>-
>- Gets the pointer to the first variable header in given variable store area.
>-
>- @param VarStoreHeader Pointer to the Variable Store Header.
>-
>- @return Pointer to the first variable header
>-
>-**/
>-VARIABLE_HEADER *
>-GetStartPointer (
>- IN VARIABLE_STORE_HEADER *VarStoreHeader
>- )
>-{
>- //
>- // The end of variable store
>- //
>- return (VARIABLE_HEADER *) HEADER_ALIGN (VarStoreHeader + 1);
>-}
>-
>-
>-/**
>- This code gets the pointer to the last variable memory pointer byte.
>-
>- @param VarStoreHeader Pointer to the Variable Store Header.
>-
>- @return VARIABLE_HEADER* pointer to last unavailable Variable Header.
>-
>-**/
>-VARIABLE_HEADER *
>-GetEndPointer (
>- IN VARIABLE_STORE_HEADER *VarStoreHeader
>- )
>-{
>- //
>- // The end of variable store
>- //
>- return (VARIABLE_HEADER *) HEADER_ALIGN ((UINTN) VarStoreHeader + VarStoreHeader->Size);
>-}
>-
>-
>-/**
>- This code checks if variable header is valid or not.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @retval TRUE Variable header is valid.
>- @retval FALSE Variable header is not valid.
>-
>-**/
>-BOOLEAN
>-IsValidVariableHeader (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- if (Variable == NULL || Variable->StartId != VARIABLE_DATA ) {
>- return FALSE;
>- }
>-
>- return TRUE;
>-}
>-
>-
>-/**
>- This code gets the size of name of variable.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Size of variable in bytes in type UINTN.
>-
>-**/
>-UINTN
>-NameSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- if (Variable->State == (UINT8) (-1) ||
>- Variable->DataSize == (UINT32) (-1) ||
>- Variable->NameSize == (UINT32) (-1) ||
>- Variable->Attributes == (UINT32) (-1)) {
>- return 0;
>- }
>- return (UINTN) Variable->NameSize;
>-}
>-
>-
>-/**
>- This code gets the size of data of variable.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Size of variable in bytes in type UINTN.
>-
>-**/
>-UINTN
>-DataSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- if (Variable->State == (UINT8) (-1) ||
>- Variable->DataSize == (UINT32) (-1) ||
>- Variable->NameSize == (UINT32) (-1) ||
>- Variable->Attributes == (UINT32) (-1)) {
>- return 0;
>- }
>- return (UINTN) Variable->DataSize;
>-}
>-
>-/**
>- This code gets the pointer to the variable name.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return A CHAR16* pointer to Variable Name.
>-
>-**/
>-CHAR16 *
>-GetVariableNamePtr (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- return (CHAR16 *) (Variable + 1);
>-}
>-
>-
>-/**
>- This code gets the pointer to the variable data.
>-
>- @param Variable Pointer to the Variable Header.
>- @param VariableHeader Pointer to the Variable Header that has consecutive content.
>-
>- @return A UINT8* pointer to Variable Data.
>-
>-**/
>-UINT8 *
>-GetVariableDataPtr (
>- IN VARIABLE_HEADER *Variable,
>- IN VARIABLE_HEADER *VariableHeader
>- )
>-{
>- UINTN Value;
>-
>- //
>- // Be careful about pad size for alignment
>- //
>- Value = (UINTN) GetVariableNamePtr (Variable);
>- Value += NameSizeOfVariable (VariableHeader);
>- Value += GET_PAD_SIZE (NameSizeOfVariable (VariableHeader));
>-
>- return (UINT8 *) Value;
>-}
>-
>-
>-/**
>- This code gets the pointer to the next variable header.
>-
>- @param StoreInfo Pointer to variable store info structure.
>- @param Variable Pointer to the Variable Header.
>- @param VariableHeader Pointer to the Variable Header that has consecutive content.
>-
>- @return A VARIABLE_HEADER* pointer to next variable header.
>-
>-**/
>-VARIABLE_HEADER *
>-GetNextVariablePtr (
>- IN VARIABLE_STORE_INFO *StoreInfo,
>- IN VARIABLE_HEADER *Variable,
>- IN VARIABLE_HEADER *VariableHeader
>- )
>-{
>- EFI_PHYSICAL_ADDRESS TargetAddress;
>- EFI_PHYSICAL_ADDRESS SpareAddress;
>- UINTN Value;
>-
>- Value = (UINTN) GetVariableDataPtr (Variable, VariableHeader);
>- Value += DataSizeOfVariable (VariableHeader);
>- Value += GET_PAD_SIZE (DataSizeOfVariable (VariableHeader));
>- //
>- // Be careful about pad size for alignment
>- //
>- Value = HEADER_ALIGN (Value);
>-
>- if (StoreInfo->FtwLastWriteData != NULL) {
>- TargetAddress = StoreInfo->FtwLastWriteData->TargetAddress;
>- SpareAddress = StoreInfo->FtwLastWriteData->SpareAddress;
>- if (((UINTN) Variable < (UINTN) TargetAddress) && (Value >= (UINTN) TargetAddress)) {
>- //
>- // Next variable is in spare block.
>- //
>- Value = (UINTN) SpareAddress + (Value - (UINTN) TargetAddress);
>- }
>- }
>-
>- return (VARIABLE_HEADER *) Value;
>-}
>-
>-/**
>- Get variable store status.
>-
>- @param VarStoreHeader Pointer to the Variable Store Header.
>-
>- @retval EfiRaw Variable store is raw
>- @retval EfiValid Variable store is valid
>- @retval EfiInvalid Variable store is invalid
>-
>-**/
>-VARIABLE_STORE_STATUS
>-GetVariableStoreStatus (
>- IN VARIABLE_STORE_HEADER *VarStoreHeader
>- )
>-{
>- if (CompareGuid (&VarStoreHeader->Signature, &gEfiAuthenticatedVariableGuid) &&
>- VarStoreHeader->Format == VARIABLE_STORE_FORMATTED &&
>- VarStoreHeader->State == VARIABLE_STORE_HEALTHY
>- ) {
>-
>- return EfiValid;
>- }
>-
>- if (((UINT32 *)(&VarStoreHeader->Signature))[0] == 0xffffffff &&
>- ((UINT32 *)(&VarStoreHeader->Signature))[1] == 0xffffffff &&
>- ((UINT32 *)(&VarStoreHeader->Signature))[2] == 0xffffffff &&
>- ((UINT32 *)(&VarStoreHeader->Signature))[3] == 0xffffffff &&
>- VarStoreHeader->Size == 0xffffffff &&
>- VarStoreHeader->Format == 0xff &&
>- VarStoreHeader->State == 0xff
>- ) {
>-
>- return EfiRaw;
>- } else {
>- return EfiInvalid;
>- }
>-}
>-
>-/**
>- Compare two variable names, one of them may be inconsecutive.
>-
>- @param StoreInfo Pointer to variable store info structure.
>- @param Name1 Pointer to one variable name.
>- @param Name2 Pointer to another variable name.
>- @param NameSize Variable name size.
>-
>- @retval TRUE Name1 and Name2 are identical.
>- @retval FALSE Name1 and Name2 are not identical.
>-
>-**/
>-BOOLEAN
>-CompareVariableName (
>- IN VARIABLE_STORE_INFO *StoreInfo,
>- IN CONST CHAR16 *Name1,
>- IN CONST CHAR16 *Name2,
>- IN UINTN NameSize
>- )
>-{
>- EFI_PHYSICAL_ADDRESS TargetAddress;
>- EFI_PHYSICAL_ADDRESS SpareAddress;
>- UINTN PartialNameSize;
>-
>- if (StoreInfo->FtwLastWriteData != NULL) {
>- TargetAddress = StoreInfo->FtwLastWriteData->TargetAddress;
>- SpareAddress = StoreInfo->FtwLastWriteData->SpareAddress;
>- if (((UINTN) Name1 < (UINTN) TargetAddress) && (((UINTN) Name1 + NameSize) > (UINTN) TargetAddress)) {
>- //
>- // Name1 is inconsecutive.
>- //
>- PartialNameSize = (UINTN) TargetAddress - (UINTN) Name1;
>- //
>- // Partial content is in NV storage.
>- //
>- if (CompareMem ((UINT8 *) Name1, (UINT8 *) Name2, PartialNameSize) == 0) {
>- //
>- // Another partial content is in spare block.
>- //
>- if (CompareMem ((UINT8 *) (UINTN) SpareAddress, (UINT8 *) Name2 + PartialNameSize, NameSize - PartialNameSize) == 0) {
>- return TRUE;
>- }
>- }
>- return FALSE;
>- } else if (((UINTN) Name2 < (UINTN) TargetAddress) && (((UINTN) Name2 + NameSize) > (UINTN) TargetAddress)) {
>- //
>- // Name2 is inconsecutive.
>- //
>- PartialNameSize = (UINTN) TargetAddress - (UINTN) Name2;
>- //
>- // Partial content is in NV storage.
>- //
>- if (CompareMem ((UINT8 *) Name2, (UINT8 *) Name1, PartialNameSize) == 0) {
>- //
>- // Another partial content is in spare block.
>- //
>- if (CompareMem ((UINT8 *) (UINTN) SpareAddress, (UINT8 *) Name1 + PartialNameSize, NameSize - PartialNameSize) == 0) {
>- return TRUE;
>- }
>- }
>- return FALSE;
>- }
>- }
>-
>- //
>- // Both Name1 and Name2 are consecutive.
>- //
>- if (CompareMem ((UINT8 *) Name1, (UINT8 *) Name2, NameSize) == 0) {
>- return TRUE;
>- }
>- return FALSE;
>-}
>-
>-/**
>- This function compares a variable with variable entries in database.
>-
>- @param StoreInfo Pointer to variable store info structure.
>- @param Variable Pointer to the variable in our database
>- @param VariableHeader Pointer to the Variable Header that has consecutive content.
>- @param VariableName Name of the variable to compare to 'Variable'
>- @param VendorGuid GUID of the variable to compare to 'Variable'
>- @param PtrTrack Variable Track Pointer structure that contains Variable Information.
>-
>- @retval EFI_SUCCESS Found match variable
>- @retval EFI_NOT_FOUND Variable not found
>-
>-**/
>-EFI_STATUS
>-CompareWithValidVariable (
>- IN VARIABLE_STORE_INFO *StoreInfo,
>- IN VARIABLE_HEADER *Variable,
>- IN VARIABLE_HEADER *VariableHeader,
>- IN CONST CHAR16 *VariableName,
>- IN CONST EFI_GUID *VendorGuid,
>- OUT VARIABLE_POINTER_TRACK *PtrTrack
>- )
>-{
>- VOID *Point;
>-
>- if (VariableName[0] == 0) {
>- PtrTrack->CurrPtr = Variable;
>- return EFI_SUCCESS;
>- } else {
>- //
>- // Don't use CompareGuid function here for performance reasons.
>- // Instead we compare the GUID a UINT32 at a time and branch
>- // on the first failed comparison.
>- //
>- if ((((INT32 *) VendorGuid)[0] == ((INT32 *) &VariableHeader->VendorGuid)[0]) &&
>- (((INT32 *) VendorGuid)[1] == ((INT32 *) &VariableHeader->VendorGuid)[1]) &&
>- (((INT32 *) VendorGuid)[2] == ((INT32 *) &VariableHeader->VendorGuid)[2]) &&
>- (((INT32 *) VendorGuid)[3] == ((INT32 *) &VariableHeader->VendorGuid)[3])
>- ) {
>- ASSERT (NameSizeOfVariable (VariableHeader) != 0);
>- Point = (VOID *) GetVariableNamePtr (Variable);
>- if (CompareVariableName (StoreInfo, VariableName, Point, NameSizeOfVariable (VariableHeader))) {
>- PtrTrack->CurrPtr = Variable;
>- return EFI_SUCCESS;
>- }
>- }
>- }
>-
>- return EFI_NOT_FOUND;
>-}
>-
>-/**
>- Return the variable store header and the store info based on the Index.
>-
>- @param Type The type of the variable store.
>- @param StoreInfo Return the store info.
>-
>- @return Pointer to the variable store header.
>-**/
>-VARIABLE_STORE_HEADER *
>-GetVariableStore (
>- IN VARIABLE_STORE_TYPE Type,
>- OUT VARIABLE_STORE_INFO *StoreInfo
>- )
>-{
>- EFI_HOB_GUID_TYPE *GuidHob;
>- EFI_FIRMWARE_VOLUME_HEADER *FvHeader;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- EFI_PHYSICAL_ADDRESS NvStorageBase;
>- UINT32 NvStorageSize;
>- FAULT_TOLERANT_WRITE_LAST_WRITE_DATA *FtwLastWriteData;
>- UINT32 BackUpOffset;
>-
>- StoreInfo->IndexTable = NULL;
>- StoreInfo->FtwLastWriteData = NULL;
>- VariableStoreHeader = NULL;
>- switch (Type) {
>- case VariableStoreTypeHob:
>- GuidHob = GetFirstGuidHob (&gEfiAuthenticatedVariableGuid);
>- if (GuidHob != NULL) {
>- VariableStoreHeader = (VARIABLE_STORE_HEADER *) GET_GUID_HOB_DATA (GuidHob);
>- }
>- break;
>-
>- case VariableStoreTypeNv:
>- if (GetBootModeHob () != BOOT_IN_RECOVERY_MODE) {
>- //
>- // The content of NV storage for variable is not reliable in recovery boot mode.
>- //
>-
>- NvStorageSize = PcdGet32 (PcdFlashNvStorageVariableSize);
>- NvStorageBase = (EFI_PHYSICAL_ADDRESS) (PcdGet64 (PcdFlashNvStorageVariableBase64) != 0 ?
>- PcdGet64 (PcdFlashNvStorageVariableBase64) :
>- PcdGet32 (PcdFlashNvStorageVariableBase)
>- );
>- //
>- // First let FvHeader point to NV storage base.
>- //
>- FvHeader = (EFI_FIRMWARE_VOLUME_HEADER *) (UINTN) NvStorageBase;
>-
>- //
>- // Check the FTW last write data hob.
>- //
>- BackUpOffset = 0;
>- GuidHob = GetFirstGuidHob (&gEdkiiFaultTolerantWriteGuid);
>- if (GuidHob != NULL) {
>- FtwLastWriteData = (FAULT_TOLERANT_WRITE_LAST_WRITE_DATA *) GET_GUID_HOB_DATA (GuidHob);
>- if (FtwLastWriteData->TargetAddress == NvStorageBase) {
>- //
>- // Let FvHeader point to spare block.
>- //
>- FvHeader = (EFI_FIRMWARE_VOLUME_HEADER *) (UINTN) FtwLastWriteData->SpareAddress;
>- DEBUG ((EFI_D_INFO, "PeiVariable: NV storage is backed up in spare block: 0x%x\n", (UINTN) FtwLastWriteData-
>>SpareAddress));
>- } else if ((FtwLastWriteData->TargetAddress > NvStorageBase) && (FtwLastWriteData->TargetAddress < (NvStorageBase +
>NvStorageSize))) {
>- StoreInfo->FtwLastWriteData = FtwLastWriteData;
>- //
>- // Flash NV storage from the offset is backed up in spare block.
>- //
>- BackUpOffset = (UINT32) (FtwLastWriteData->TargetAddress - NvStorageBase);
>- DEBUG ((EFI_D_INFO, "PeiVariable: High partial NV storage from offset: %x is backed up in spare block: 0x%x\n",
>BackUpOffset, (UINTN) FtwLastWriteData->SpareAddress));
>- //
>- // At least one block data in flash NV storage is still valid, so still leave FvHeader point to NV storage base.
>- //
>- }
>- }
>-
>- //
>- // Check if the Firmware Volume is not corrupted
>- //
>- if ((FvHeader->Signature != EFI_FVH_SIGNATURE) || (!CompareGuid (&gEfiSystemNvDataFvGuid, &FvHeader-
>>FileSystemGuid))) {
>- DEBUG ((EFI_D_ERROR, "Firmware Volume for Variable Store is corrupted\n"));
>- break;
>- }
>-
>- VariableStoreHeader = (VARIABLE_STORE_HEADER *) ((UINT8 *) FvHeader + FvHeader->HeaderLength);
>-
>- GuidHob = GetFirstGuidHob (&gEfiVariableIndexTableGuid);
>- if (GuidHob != NULL) {
>- StoreInfo->IndexTable = GET_GUID_HOB_DATA (GuidHob);
>- } else {
>- //
>- // If it's the first time to access variable region in flash, create a guid hob to record
>- // VAR_ADDED type variable info.
>- // Note that as the resource of PEI phase is limited, only store the limited number of
>- // VAR_ADDED type variables to reduce access time.
>- //
>- StoreInfo->IndexTable = (VARIABLE_INDEX_TABLE *) BuildGuidHob (&gEfiVariableIndexTableGuid, sizeof
>(VARIABLE_INDEX_TABLE));
>- StoreInfo->IndexTable->Length = 0;
>- StoreInfo->IndexTable->StartPtr = GetStartPointer (VariableStoreHeader);
>- StoreInfo->IndexTable->EndPtr = GetEndPointer (VariableStoreHeader);
>- StoreInfo->IndexTable->GoneThrough = 0;
>- }
>- }
>- break;
>-
>- default:
>- ASSERT (FALSE);
>- break;
>- }
>-
>- StoreInfo->VariableStoreHeader = VariableStoreHeader;
>- return VariableStoreHeader;
>-}
>-
>-/**
>- Get variable header that has consecutive content.
>-
>- @param StoreInfo Pointer to variable store info structure.
>- @param Variable Pointer to the Variable Header.
>- @param VariableHeader Pointer to Pointer to the Variable Header that has consecutive content.
>-
>- @retval TRUE Variable header is valid.
>- @retval FALSE Variable header is not valid.
>-
>-**/
>-BOOLEAN
>-GetVariableHeader (
>- IN VARIABLE_STORE_INFO *StoreInfo,
>- IN VARIABLE_HEADER *Variable,
>- OUT VARIABLE_HEADER **VariableHeader
>- )
>-{
>- EFI_PHYSICAL_ADDRESS TargetAddress;
>- EFI_PHYSICAL_ADDRESS SpareAddress;
>- EFI_HOB_GUID_TYPE *GuidHob;
>- UINTN PartialHeaderSize;
>-
>- if (Variable == NULL) {
>- return FALSE;
>- }
>-
>- //
>- // First assume variable header pointed by Variable is consecutive.
>- //
>- *VariableHeader = Variable;
>-
>- if (StoreInfo->FtwLastWriteData != NULL) {
>- TargetAddress = StoreInfo->FtwLastWriteData->TargetAddress;
>- SpareAddress = StoreInfo->FtwLastWriteData->SpareAddress;
>- if (((UINTN) Variable > (UINTN) SpareAddress) &&
>- (((UINTN) Variable - (UINTN) SpareAddress + (UINTN) TargetAddress) >= (UINTN) GetEndPointer (StoreInfo-
>>VariableStoreHeader))) {
>- //
>- // Reach the end of variable store.
>- //
>- return FALSE;
>- }
>- if (((UINTN) Variable < (UINTN) TargetAddress) && (((UINTN) Variable + sizeof (VARIABLE_HEADER)) > (UINTN) TargetAddress)) {
>- //
>- // Variable header pointed by Variable is inconsecutive,
>- // create a guid hob to combine the two partial variable header content together.
>- //
>- GuidHob = GetFirstGuidHob (&gEfiCallerIdGuid);
>- if (GuidHob != NULL) {
>- *VariableHeader = (VARIABLE_HEADER *) GET_GUID_HOB_DATA (GuidHob);
>- } else {
>- *VariableHeader = (VARIABLE_HEADER *) BuildGuidHob (&gEfiCallerIdGuid, sizeof (VARIABLE_HEADER));
>- PartialHeaderSize = (UINTN) TargetAddress - (UINTN) Variable;
>- //
>- // Partial content is in NV storage.
>- //
>- CopyMem ((UINT8 *) *VariableHeader, (UINT8 *) Variable, PartialHeaderSize);
>- //
>- // Another partial content is in spare block.
>- //
>- CopyMem ((UINT8 *) *VariableHeader + PartialHeaderSize, (UINT8 *) (UINTN) SpareAddress, sizeof (VARIABLE_HEADER) -
>PartialHeaderSize);
>- }
>- }
>- } else {
>- if (Variable >= GetEndPointer (StoreInfo->VariableStoreHeader)) {
>- //
>- // Reach the end of variable store.
>- //
>- return FALSE;
>- }
>- }
>-
>- return IsValidVariableHeader (*VariableHeader);
>-}
>-
>-/**
>- Get variable name or data to output buffer.
>-
>- @param StoreInfo Pointer to variable store info structure.
>- @param NameOrData Pointer to the variable name/data that may be inconsecutive.
>- @param Size Variable name/data size.
>- @param Buffer Pointer to output buffer to hold the variable name/data.
>-
>-**/
>-VOID
>-GetVariableNameOrData (
>- IN VARIABLE_STORE_INFO *StoreInfo,
>- IN UINT8 *NameOrData,
>- IN UINTN Size,
>- OUT UINT8 *Buffer
>- )
>-{
>- EFI_PHYSICAL_ADDRESS TargetAddress;
>- EFI_PHYSICAL_ADDRESS SpareAddress;
>- UINTN PartialSize;
>-
>- if (StoreInfo->FtwLastWriteData != NULL) {
>- TargetAddress = StoreInfo->FtwLastWriteData->TargetAddress;
>- SpareAddress = StoreInfo->FtwLastWriteData->SpareAddress;
>- if (((UINTN) NameOrData < (UINTN) TargetAddress) && (((UINTN) NameOrData + Size) > (UINTN) TargetAddress)) {
>- //
>- // Variable name/data is inconsecutive.
>- //
>- PartialSize = (UINTN) TargetAddress - (UINTN) NameOrData;
>- //
>- // Partial content is in NV storage.
>- //
>- CopyMem (Buffer, NameOrData, PartialSize);
>- //
>- // Another partial content is in spare block.
>- //
>- CopyMem (Buffer + PartialSize, (UINT8 *) (UINTN) SpareAddress, Size - PartialSize);
>- return;
>- }
>- }
>-
>- //
>- // Variable name/data is consecutive.
>- //
>- CopyMem (Buffer, NameOrData, Size);
>-}
>-
>-/**
>- Find the variable in the specified variable store.
>-
>- @param StoreInfo Pointer to the store info structure.
>- @param VariableName Name of the variable to be found
>- @param VendorGuid Vendor GUID to be found.
>- @param PtrTrack Variable Track Pointer structure that contains Variable Information.
>-
>- @retval EFI_SUCCESS Variable found successfully
>- @retval EFI_NOT_FOUND Variable not found
>- @retval EFI_INVALID_PARAMETER Invalid variable name
>-
>-**/
>-EFI_STATUS
>-FindVariableEx (
>- IN VARIABLE_STORE_INFO *StoreInfo,
>- IN CONST CHAR16 *VariableName,
>- IN CONST EFI_GUID *VendorGuid,
>- OUT VARIABLE_POINTER_TRACK *PtrTrack
>- )
>-{
>- VARIABLE_HEADER *Variable;
>- VARIABLE_HEADER *LastVariable;
>- VARIABLE_HEADER *MaxIndex;
>- UINTN Index;
>- UINTN Offset;
>- BOOLEAN StopRecord;
>- VARIABLE_HEADER *InDeletedVariable;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- VARIABLE_INDEX_TABLE *IndexTable;
>- VARIABLE_HEADER *VariableHeader;
>-
>- VariableStoreHeader = StoreInfo->VariableStoreHeader;
>-
>- if (VariableStoreHeader == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (GetVariableStoreStatus (VariableStoreHeader) != EfiValid) {
>- return EFI_UNSUPPORTED;
>- }
>-
>- if (~VariableStoreHeader->Size == 0) {
>- return EFI_NOT_FOUND;
>- }
>-
>- IndexTable = StoreInfo->IndexTable;
>- PtrTrack->StartPtr = GetStartPointer (VariableStoreHeader);
>- PtrTrack->EndPtr = GetEndPointer (VariableStoreHeader);
>-
>- InDeletedVariable = NULL;
>-
>- //
>- // No Variable Address equals zero, so 0 as initial value is safe.
>- //
>- MaxIndex = NULL;
>- VariableHeader = NULL;
>-
>- if (IndexTable != NULL) {
>- //
>- // traverse the variable index table to look for varible.
>- // The IndexTable->Index[Index] records the distance of two neighbouring VAR_ADDED type variables.
>- //
>- for (Offset = 0, Index = 0; Index < IndexTable->Length; Index++) {
>- ASSERT (Index < sizeof (IndexTable->Index) / sizeof (IndexTable->Index[0]));
>- Offset += IndexTable->Index[Index];
>- MaxIndex = (VARIABLE_HEADER *) ((UINT8 *) IndexTable->StartPtr + Offset);
>- GetVariableHeader (StoreInfo, MaxIndex, &VariableHeader);
>- if (CompareWithValidVariable (StoreInfo, MaxIndex, VariableHeader, VariableName, VendorGuid, PtrTrack) == EFI_SUCCESS) {
>- if (VariableHeader->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- InDeletedVariable = PtrTrack->CurrPtr;
>- } else {
>- return EFI_SUCCESS;
>- }
>- }
>- }
>-
>- if (IndexTable->GoneThrough != 0) {
>- //
>- // If the table has all the existing variables indexed, return.
>- //
>- PtrTrack->CurrPtr = InDeletedVariable;
>- return (PtrTrack->CurrPtr == NULL) ? EFI_NOT_FOUND : EFI_SUCCESS;
>- }
>- }
>-
>- if (MaxIndex != NULL) {
>- //
>- // HOB exists but the variable cannot be found in HOB
>- // If not found in HOB, then let's start from the MaxIndex we've found.
>- //
>- Variable = GetNextVariablePtr (StoreInfo, MaxIndex, VariableHeader);
>- LastVariable = MaxIndex;
>- } else {
>- //
>- // Start Pointers for the variable.
>- // Actual Data Pointer where data can be written.
>- //
>- Variable = PtrTrack->StartPtr;
>- LastVariable = PtrTrack->StartPtr;
>- }
>-
>- //
>- // Find the variable by walk through variable store
>- //
>- StopRecord = FALSE;
>- while (GetVariableHeader (StoreInfo, Variable, &VariableHeader)) {
>- if (VariableHeader->State == VAR_ADDED || VariableHeader->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- //
>- // Record Variable in VariableIndex HOB
>- //
>- if ((IndexTable != NULL) && !StopRecord) {
>- Offset = (UINTN) Variable - (UINTN) LastVariable;
>- if ((Offset > 0x0FFFF) || (IndexTable->Length == sizeof (IndexTable->Index) / sizeof (IndexTable->Index[0]))) {
>- //
>- // Stop to record if the distance of two neighbouring VAR_ADDED variable is larger than the allowable scope(UINT16),
>- // or the record buffer is full.
>- //
>- StopRecord = TRUE;
>- } else {
>- IndexTable->Index[IndexTable->Length++] = (UINT16) Offset;
>- LastVariable = Variable;
>- }
>- }
>-
>- if (CompareWithValidVariable (StoreInfo, Variable, VariableHeader, VariableName, VendorGuid, PtrTrack) == EFI_SUCCESS) {
>- if (VariableHeader->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- InDeletedVariable = PtrTrack->CurrPtr;
>- } else {
>- return EFI_SUCCESS;
>- }
>- }
>- }
>-
>- Variable = GetNextVariablePtr (StoreInfo, Variable, VariableHeader);
>- }
>- //
>- // If gone through the VariableStore, that means we never find in Firmware any more.
>- //
>- if ((IndexTable != NULL) && !StopRecord) {
>- IndexTable->GoneThrough = 1;
>- }
>-
>- PtrTrack->CurrPtr = InDeletedVariable;
>-
>- return (PtrTrack->CurrPtr == NULL) ? EFI_NOT_FOUND : EFI_SUCCESS;
>-}
>-
>-/**
>- Find the variable in HOB and Non-Volatile variable storages.
>-
>- @param VariableName Name of the variable to be found
>- @param VendorGuid Vendor GUID to be found.
>- @param PtrTrack Variable Track Pointer structure that contains Variable Information.
>- @param StoreInfo Return the store info.
>-
>- @retval EFI_SUCCESS Variable found successfully
>- @retval EFI_NOT_FOUND Variable not found
>- @retval EFI_INVALID_PARAMETER Invalid variable name
>-**/
>-EFI_STATUS
>-FindVariable (
>- IN CONST CHAR16 *VariableName,
>- IN CONST EFI_GUID *VendorGuid,
>- OUT VARIABLE_POINTER_TRACK *PtrTrack,
>- OUT VARIABLE_STORE_INFO *StoreInfo
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_STORE_TYPE Type;
>-
>- if (VariableName[0] != 0 && VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- for (Type = (VARIABLE_STORE_TYPE) 0; Type < VariableStoreTypeMax; Type++) {
>- GetVariableStore (Type, StoreInfo);
>- Status = FindVariableEx (
>- StoreInfo,
>- VariableName,
>- VendorGuid,
>- PtrTrack
>- );
>- if (!EFI_ERROR (Status)) {
>- return Status;
>- }
>- }
>-
>- return EFI_NOT_FOUND;
>-}
>-
>-/**
>- This service retrieves a variable's value using its name and GUID.
>-
>- Read the specified variable from the UEFI variable store. If the Data
>- buffer is too small to hold the contents of the variable, the error
>- EFI_BUFFER_TOO_SMALL is returned and DataSize is set to the required buffer
>- size to obtain the data.
>-
>- @param This A pointer to this instance of the EFI_PEI_READ_ONLY_VARIABLE2_PPI.
>- @param VariableName A pointer to a null-terminated string that is the variable's name.
>- @param VariableGuid A pointer to an EFI_GUID that is the variable's GUID. The combination of
>- VariableGuid and VariableName must be unique.
>- @param Attributes If non-NULL, on return, points to the variable's attributes.
>- @param DataSize On entry, points to the size in bytes of the Data buffer.
>- On return, points to the size of the data returned in Data.
>- @param Data Points to the buffer which will hold the returned variable value.
>-
>- @retval EFI_SUCCESS The variable was read successfully.
>- @retval EFI_NOT_FOUND The variable could not be found.
>- @retval EFI_BUFFER_TOO_SMALL The DataSize is too small for the resulting data.
>- DataSize is updated with the size required for
>- the specified variable.
>- @retval EFI_INVALID_PARAMETER VariableName, VariableGuid, DataSize or Data is NULL.
>- @retval EFI_DEVICE_ERROR The variable could not be retrieved because of a device error.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-PeiGetVariable (
>- IN CONST EFI_PEI_READ_ONLY_VARIABLE2_PPI *This,
>- IN CONST CHAR16 *VariableName,
>- IN CONST EFI_GUID *VariableGuid,
>- OUT UINT32 *Attributes,
>- IN OUT UINTN *DataSize,
>- OUT VOID *Data
>- )
>-{
>- VARIABLE_POINTER_TRACK Variable;
>- UINTN VarDataSize;
>- EFI_STATUS Status;
>- VARIABLE_STORE_INFO StoreInfo;
>- VARIABLE_HEADER *VariableHeader;
>-
>- if (VariableName == NULL || VariableGuid == NULL || DataSize == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- VariableHeader = NULL;
>-
>- //
>- // Find existing variable
>- //
>- Status = FindVariable (VariableName, VariableGuid, &Variable, &StoreInfo);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- GetVariableHeader (&StoreInfo, Variable.CurrPtr, &VariableHeader);
>-
>- //
>- // Get data size
>- //
>- VarDataSize = DataSizeOfVariable (VariableHeader);
>- if (*DataSize >= VarDataSize) {
>- if (Data == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- GetVariableNameOrData (&StoreInfo, GetVariableDataPtr (Variable.CurrPtr, VariableHeader), VarDataSize, Data);
>-
>- if (Attributes != NULL) {
>- *Attributes = VariableHeader->Attributes;
>- }
>-
>- *DataSize = VarDataSize;
>- return EFI_SUCCESS;
>- } else {
>- *DataSize = VarDataSize;
>- return EFI_BUFFER_TOO_SMALL;
>- }
>-}
>-
>-/**
>- Return the next variable name and GUID.
>-
>- This function is called multiple times to retrieve the VariableName
>- and VariableGuid of all variables currently available in the system.
>- On each call, the previous results are passed into the interface,
>- and, on return, the interface returns the data for the next
>- interface. When the entire variable list has been returned,
>- EFI_NOT_FOUND is returned.
>-
>- @param This A pointer to this instance of the EFI_PEI_READ_ONLY_VARIABLE2_PPI.
>-
>- @param VariableNameSize On entry, points to the size of the buffer pointed to by VariableName.
>- On return, the size of the variable name buffer.
>- @param VariableName On entry, a pointer to a null-terminated string that is the variable's name.
>- On return, points to the next variable's null-terminated name string.
>- @param VariableGuid On entry, a pointer to an EFI_GUID that is the variable's GUID.
>- On return, a pointer to the next variable's GUID.
>-
>- @retval EFI_SUCCESS The variable was read successfully.
>- @retval EFI_NOT_FOUND The variable could not be found.
>- @retval EFI_BUFFER_TOO_SMALL The VariableNameSize is too small for the resulting
>- data. VariableNameSize is updated with the size
>- required for the specified variable.
>- @retval EFI_INVALID_PARAMETER VariableName, VariableGuid or
>- VariableNameSize is NULL.
>- @retval EFI_DEVICE_ERROR The variable could not be retrieved because of a device error.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-PeiGetNextVariableName (
>- IN CONST EFI_PEI_READ_ONLY_VARIABLE2_PPI *This,
>- IN OUT UINTN *VariableNameSize,
>- IN OUT CHAR16 *VariableName,
>- IN OUT EFI_GUID *VariableGuid
>- )
>-{
>- VARIABLE_STORE_TYPE Type;
>- VARIABLE_POINTER_TRACK Variable;
>- VARIABLE_POINTER_TRACK VariableInHob;
>- VARIABLE_POINTER_TRACK VariablePtrTrack;
>- UINTN VarNameSize;
>- EFI_STATUS Status;
>- VARIABLE_STORE_HEADER *VariableStoreHeader[VariableStoreTypeMax];
>- VARIABLE_HEADER *VariableHeader;
>- VARIABLE_STORE_INFO StoreInfo;
>- VARIABLE_STORE_INFO StoreInfoForNv;
>- VARIABLE_STORE_INFO StoreInfoForHob;
>-
>- if (VariableName == NULL || VariableGuid == NULL || VariableNameSize == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- VariableHeader = NULL;
>-
>- Status = FindVariable (VariableName, VariableGuid, &Variable, &StoreInfo);
>- if (Variable.CurrPtr == NULL || Status != EFI_SUCCESS) {
>- return Status;
>- }
>-
>- if (VariableName[0] != 0) {
>- //
>- // If variable name is not NULL, get next variable
>- //
>- GetVariableHeader (&StoreInfo, Variable.CurrPtr, &VariableHeader);
>- Variable.CurrPtr = GetNextVariablePtr (&StoreInfo, Variable.CurrPtr, VariableHeader);
>- }
>-
>- VariableStoreHeader[VariableStoreTypeHob] = GetVariableStore (VariableStoreTypeHob, &StoreInfoForHob);
>- VariableStoreHeader[VariableStoreTypeNv] = GetVariableStore (VariableStoreTypeNv, &StoreInfoForNv);
>-
>- while (TRUE) {
>- //
>- // Switch from HOB to Non-Volatile.
>- //
>- while (!GetVariableHeader (&StoreInfo, Variable.CurrPtr, &VariableHeader)) {
>- //
>- // Find current storage index
>- //
>- for (Type = (VARIABLE_STORE_TYPE) 0; Type < VariableStoreTypeMax; Type++) {
>- if ((VariableStoreHeader[Type] != NULL) && (Variable.StartPtr == GetStartPointer (VariableStoreHeader[Type]))) {
>- break;
>- }
>- }
>- ASSERT (Type < VariableStoreTypeMax);
>- //
>- // Switch to next storage
>- //
>- for (Type++; Type < VariableStoreTypeMax; Type++) {
>- if (VariableStoreHeader[Type] != NULL) {
>- break;
>- }
>- }
>- //
>- // Capture the case that
>- // 1. current storage is the last one, or
>- // 2. no further storage
>- //
>- if (Type == VariableStoreTypeMax) {
>- return EFI_NOT_FOUND;
>- }
>- Variable.StartPtr = GetStartPointer (VariableStoreHeader[Type]);
>- Variable.EndPtr = GetEndPointer (VariableStoreHeader[Type]);
>- Variable.CurrPtr = Variable.StartPtr;
>- GetVariableStore (Type, &StoreInfo);
>- }
>-
>- if (VariableHeader->State == VAR_ADDED || VariableHeader->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- if (VariableHeader->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- //
>- // If it is a IN_DELETED_TRANSITION variable,
>- // and there is also a same ADDED one at the same time,
>- // don't return it.
>- //
>- Status = FindVariableEx (
>- &StoreInfo,
>- GetVariableNamePtr (Variable.CurrPtr),
>- &VariableHeader->VendorGuid,
>- &VariablePtrTrack
>- );
>- if (!EFI_ERROR (Status) && VariablePtrTrack.CurrPtr != Variable.CurrPtr) {
>- Variable.CurrPtr = GetNextVariablePtr (&StoreInfo, Variable.CurrPtr, VariableHeader);
>- continue;
>- }
>- }
>-
>- //
>- // Don't return NV variable when HOB overrides it
>- //
>- if ((VariableStoreHeader[VariableStoreTypeHob] != NULL) && (VariableStoreHeader[VariableStoreTypeNv] != NULL) &&
>- (Variable.StartPtr == GetStartPointer (VariableStoreHeader[VariableStoreTypeNv]))
>- ) {
>- Status = FindVariableEx (
>- &StoreInfoForHob,
>- GetVariableNamePtr (Variable.CurrPtr),
>- &VariableHeader->VendorGuid,
>- &VariableInHob
>- );
>- if (!EFI_ERROR (Status)) {
>- Variable.CurrPtr = GetNextVariablePtr (&StoreInfo, Variable.CurrPtr, VariableHeader);
>- continue;
>- }
>- }
>-
>- VarNameSize = NameSizeOfVariable (VariableHeader);
>- ASSERT (VarNameSize != 0);
>-
>- if (VarNameSize <= *VariableNameSize) {
>- GetVariableNameOrData (&StoreInfo, (UINT8 *) GetVariableNamePtr (Variable.CurrPtr), VarNameSize, (UINT8 *)
>VariableName);
>-
>- CopyMem (VariableGuid, &VariableHeader->VendorGuid, sizeof (EFI_GUID));
>-
>- Status = EFI_SUCCESS;
>- } else {
>- Status = EFI_BUFFER_TOO_SMALL;
>- }
>-
>- *VariableNameSize = VarNameSize;
>- //
>- // Variable is found
>- //
>- return Status;
>- } else {
>- Variable.CurrPtr = GetNextVariablePtr (&StoreInfo, Variable.CurrPtr, VariableHeader);
>- }
>- }
>-}
>diff --git a/SecurityPkg/VariableAuthenticated/Pei/Variable.h b/SecurityPkg/VariableAuthenticated/Pei/Variable.h
>deleted file mode 100644
>index 7693522..0000000
>--- a/SecurityPkg/VariableAuthenticated/Pei/Variable.h
>+++ /dev/null
>@@ -1,148 +0,0 @@
>-/** @file
>- The internal header file includes the common header files, defines
>- internal structure and functions used by PeiVariable module.
>-
>-Copyright (c) 2009 - 2013, 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
>-
>-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 _PEI_VARIABLE_H_
>-#define _PEI_VARIABLE_H_
>-
>-#include <PiPei.h>
>-#include <Ppi/ReadOnlyVariable2.h>
>-
>-#include <Library/DebugLib.h>
>-#include <Library/PeimEntryPoint.h>
>-#include <Library/HobLib.h>
>-#include <Library/PcdLib.h>
>-#include <Library/BaseMemoryLib.h>
>-#include <Library/PeiServicesTablePointerLib.h>
>-#include <Library/PeiServicesLib.h>
>-
>-#include <Guid/AuthenticatedVariableFormat.h>
>-#include <Guid/VariableIndexTable.h>
>-#include <Guid/SystemNvDataGuid.h>
>-#include <Guid/FaultTolerantWrite.h>
>-
>-typedef enum {
>- VariableStoreTypeHob,
>- VariableStoreTypeNv,
>- VariableStoreTypeMax
>-} VARIABLE_STORE_TYPE;
>-
>-typedef struct {
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- VARIABLE_INDEX_TABLE *IndexTable;
>- //
>- // If it is not NULL, it means there may be an inconsecutive variable whose
>- // partial content is still in NV storage, but another partial content is backed up
>- // in spare block.
>- //
>- FAULT_TOLERANT_WRITE_LAST_WRITE_DATA *FtwLastWriteData;
>-} VARIABLE_STORE_INFO;
>-
>-//
>-// Functions
>-//
>-/**
>- Provide the functionality of the variable services.
>-
>- @param FileHandle Handle of the file being invoked.
>- Type EFI_PEI_FILE_HANDLE is defined in FfsFindNextFile().
>- @param PeiServices General purpose services available to every PEIM.
>-
>- @retval EFI_SUCCESS If the interface could be successfully installed
>- @retval Others Returned from PeiServicesInstallPpi()
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-PeimInitializeVariableServices (
>- IN EFI_PEI_FILE_HANDLE FileHandle,
>- IN CONST EFI_PEI_SERVICES **PeiServices
>- );
>-
>-/**
>- This service retrieves a variable's value using its name and GUID.
>-
>- Read the specified variable from the UEFI variable store. If the Data
>- buffer is too small to hold the contents of the variable, the error
>- EFI_BUFFER_TOO_SMALL is returned and DataSize is set to the required buffer
>- size to obtain the data.
>-
>- @param This A pointer to this instance of the EFI_PEI_READ_ONLY_VARIABLE2_PPI.
>- @param VariableName A pointer to a null-terminated string that is the variable's name.
>- @param VariableGuid A pointer to an EFI_GUID that is the variable's GUID. The combination of
>- VariableGuid and VariableName must be unique.
>- @param Attributes If non-NULL, on return, points to the variable's attributes.
>- @param DataSize On entry, points to the size in bytes of the Data buffer.
>- On return, points to the size of the data returned in Data.
>- @param Data Points to the buffer which will hold the returned variable value.
>-
>- @retval EFI_SUCCESS The variable was read successfully.
>- @retval EFI_NOT_FOUND The variable could not be found.
>- @retval EFI_BUFFER_TOO_SMALL The DataSize is too small for the resulting data.
>- DataSize is updated with the size required for
>- the specified variable.
>- @retval EFI_INVALID_PARAMETER VariableName, VariableGuid, DataSize or Data is NULL.
>- @retval EFI_DEVICE_ERROR The variable could not be retrieved because of a device error.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-PeiGetVariable (
>- IN CONST EFI_PEI_READ_ONLY_VARIABLE2_PPI *This,
>- IN CONST CHAR16 *VariableName,
>- IN CONST EFI_GUID *VariableGuid,
>- OUT UINT32 *Attributes,
>- IN OUT UINTN *DataSize,
>- OUT VOID *Data
>- );
>-
>-/**
>- Return the next variable name and GUID.
>-
>- This function is called multiple times to retrieve the VariableName
>- and VariableGuid of all variables currently available in the system.
>- On each call, the previous results are passed into the interface,
>- and, on return, the interface returns the data for the next
>- interface. When the entire variable list has been returned,
>- EFI_NOT_FOUND is returned.
>-
>- @param This A pointer to this instance of the EFI_PEI_READ_ONLY_VARIABLE2_PPI.
>-
>- @param VariableNameSize On entry, points to the size of the buffer pointed to by VariableName.
>- @param VariableName On entry, a pointer to a null-terminated string that is the variable's name.
>- On return, points to the next variable's null-terminated name string.
>-
>- @param VariableGuid On entry, a pointer to an UEFI _GUID that is the variable's GUID.
>- On return, a pointer to the next variable's GUID.
>-
>- @retval EFI_SUCCESS The variable was read successfully.
>- @retval EFI_NOT_FOUND The variable could not be found.
>- @retval EFI_BUFFER_TOO_SMALL The VariableNameSize is too small for the resulting
>- data. VariableNameSize is updated with the size
>- required for the specified variable.
>- @retval EFI_INVALID_PARAMETER VariableName, VariableGuid or
>- VariableNameSize is NULL.
>- @retval EFI_DEVICE_ERROR The variable could not be retrieved because of a device error.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-PeiGetNextVariableName (
>- IN CONST EFI_PEI_READ_ONLY_VARIABLE2_PPI *This,
>- IN OUT UINTN *VariableNameSize,
>- IN OUT CHAR16 *VariableName,
>- IN OUT EFI_GUID *VariableGuid
>- );
>-
>-#endif
>diff --git a/SecurityPkg/VariableAuthenticated/Pei/VariablePei.inf b/SecurityPkg/VariableAuthenticated/Pei/VariablePei.inf
>deleted file mode 100644
>index fa0b5e9..0000000
>--- a/SecurityPkg/VariableAuthenticated/Pei/VariablePei.inf
>+++ /dev/null
>@@ -1,73 +0,0 @@
>-## @file
>-# Implements ReadOnly Variable Services required by PEIM and installs PEI ReadOnly Varaiable2 PPI
>-# This module implements ReadOnly Variable Services required by PEIM and installs PEI ReadOnly Varaiable2 PPI.
>-#
>-# Copyright (c) 2009 - 2014, 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
>-# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
>-# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
>-#
>-##
>-
>-[Defines]
>- INF_VERSION = 0x00010005
>- BASE_NAME = PeiVariableAuth
>- MODULE_UNI_FILE = PeiVariableAuth.uni
>- FILE_GUID = B1F7AF2F-2807-478c-A893-2BF4DDD1F62B
>- MODULE_TYPE = PEIM
>- VERSION_STRING = 1.0
>- ENTRY_POINT = PeimInitializeVariableServices
>-
>-#
>-# The following information is for reference only and not required by the build tools.
>-#
>-# VALID_ARCHITECTURES = IA32 X64 IPF EBC
>-#
>-
>-[Sources]
>- Variable.c
>- Variable.h
>-
>-[Packages]
>- MdePkg/MdePkg.dec
>- MdeModulePkg/MdeModulePkg.dec
>- SecurityPkg/SecurityPkg.dec
>-
>-[LibraryClasses]
>- BaseMemoryLib
>- PcdLib
>- HobLib
>- PeimEntryPoint
>- DebugLib
>- PeiServicesTablePointerLib
>- PeiServicesLib
>-
>-[Guids]
>- ## CONSUMES ## GUID # Variable store header
>- ## SOMETIMES_CONSUMES ## HOB
>- gEfiAuthenticatedVariableGuid
>- ## SOMETIMES_PRODUCES ## HOB
>- ## SOMETIMES_CONSUMES ## HOB
>- gEfiVariableIndexTableGuid
>- gEfiSystemNvDataFvGuid ## SOMETIMES_CONSUMES ## GUID
>- gEdkiiFaultTolerantWriteGuid ## SOMETIMES_CONSUMES ## HOB
>-
>-[Ppis]
>- gEfiPeiReadOnlyVariable2PpiGuid ## PRODUCES
>-
>-[Pcd]
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase ## SOMETIMES_CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase64 ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableSize ## CONSUMES
>-
>-[Depex]
>- gEdkiiFaultTolerantWriteGuid
>-
>-# [BootMode]
>-# RECOVERY_FULL ## SOMETIMES_CONSUMES
>-
>-[UserExtensions.TianoCore."ExtraFiles"]
>- PeiVariableExtra.uni
>\ No newline at end of file
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.c
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.c
>deleted file mode 100644
>index 9599c8a..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.c
>+++ /dev/null
>@@ -1,2532 +0,0 @@
>-/** @file
>- Implement authentication services for the authenticated variable
>- service in UEFI2.2.
>-
>- Caution: This module requires additional review when modified.
>- This driver will have external input - variable data. It may be input in SMM mode.
>- This external input must be validated carefully to avoid security issue like
>- buffer overflow, integer overflow.
>- Variable attribute should also be checked to avoid authentication bypass.
>- The whole SMM authentication variable design relies on the integrity of flash part and SMM.
>- which is assumed to be protected by platform. All variable code and metadata in flash/SMM Memory
>- may not be modified without authorization. If platform fails to protect these resources,
>- the authentication service provided in this driver will be broken, and the behavior is undefined.
>-
>- ProcessVarWithPk(), ProcessVarWithKek() and ProcessVariable() are the function to do
>- variable authentication.
>-
>- VerifyTimeBasedPayload() and VerifyCounterBasedPayload() are sub function to do verification.
>- They will do basic validation for authentication data structure, then call crypto library
>- to verify the signature.
>-
>-Copyright (c) 2009 - 2015, 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
>-
>-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 "Variable.h"
>-#include "AuthService.h"
>-
>-///
>-/// Global database array for scratch
>-///
>-UINT8 *mPubKeyStore;
>-UINT32 mPubKeyNumber;
>-UINT32 mMaxKeyNumber;
>-UINT32 mMaxKeyDbSize;
>-UINT8 *mCertDbStore;
>-UINT32 mMaxCertDbSize;
>-UINT32 mPlatformMode;
>-UINT8 mVendorKeyState;
>-
>-EFI_GUID mSignatureSupport[] = {EFI_CERT_SHA1_GUID, EFI_CERT_SHA256_GUID, EFI_CERT_RSA2048_GUID,
>EFI_CERT_X509_GUID};
>-//
>-// Public Exponent of RSA Key.
>-//
>-CONST UINT8 mRsaE[] = { 0x01, 0x00, 0x01 };
>-//
>-// Hash context pointer
>-//
>-VOID *mHashCtx = NULL;
>-
>-//
>-// Requirement for different signature type which have been defined in UEFI spec.
>-// These data are used to peform SignatureList format check while setting PK/KEK variable.
>-//
>-EFI_SIGNATURE_ITEM mSupportSigItem[] = {
>-//{SigType, SigHeaderSize, SigDataSize }
>- {EFI_CERT_SHA256_GUID, 0, 32 },
>- {EFI_CERT_RSA2048_GUID, 0, 256 },
>- {EFI_CERT_RSA2048_SHA256_GUID, 0, 256 },
>- {EFI_CERT_SHA1_GUID, 0, 20 },
>- {EFI_CERT_RSA2048_SHA1_GUID, 0, 256 },
>- {EFI_CERT_X509_GUID, 0, ((UINT32) ~0)},
>- {EFI_CERT_SHA224_GUID, 0, 28 },
>- {EFI_CERT_SHA384_GUID, 0, 48 },
>- {EFI_CERT_SHA512_GUID, 0, 64 },
>- {EFI_CERT_X509_SHA256_GUID, 0, 48 },
>- {EFI_CERT_X509_SHA384_GUID, 0, 64 },
>- {EFI_CERT_X509_SHA512_GUID, 0, 80 }
>-};
>-
>-/**
>- Determine whether this operation needs a physical present user.
>-
>- @param[in] VariableName Name of the Variable.
>- @param[in] VendorGuid GUID of the Variable.
>-
>- @retval TRUE This variable is protected, only a physical present user could set this variable.
>- @retval FALSE This variable is not protected.
>-
>-**/
>-BOOLEAN
>-NeedPhysicallyPresent(
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- if ((CompareGuid (VendorGuid, &gEfiSecureBootEnableDisableGuid) && (StrCmp (VariableName,
>EFI_SECURE_BOOT_ENABLE_NAME) == 0))
>- || (CompareGuid (VendorGuid, &gEfiCustomModeEnableGuid) && (StrCmp (VariableName, EFI_CUSTOM_MODE_NAME) == 0))) {
>- return TRUE;
>- }
>-
>- return FALSE;
>-}
>-
>-/**
>- Determine whether the platform is operating in Custom Secure Boot mode.
>-
>- @retval TRUE The platform is operating in Custom mode.
>- @retval FALSE The platform is operating in Standard mode.
>-
>-**/
>-BOOLEAN
>-InCustomMode (
>- VOID
>- )
>-{
>- VARIABLE_POINTER_TRACK Variable;
>-
>- FindVariable (EFI_CUSTOM_MODE_NAME, &gEfiCustomModeEnableGuid, &Variable, &mVariableModuleGlobal->VariableGlobal,
>FALSE);
>- if (Variable.CurrPtr != NULL && *(GetVariableDataPtr (Variable.CurrPtr)) == CUSTOM_SECURE_BOOT_MODE) {
>- return TRUE;
>- }
>-
>- return FALSE;
>-}
>-
>-/**
>- Initializes for authenticated varibale service.
>-
>- @param[in] MaxAuthVariableSize Reflect the overhead associated with the saving
>- of a single EFI authenticated variable with the exception
>- of the overhead associated with the length
>- of the string name of the EFI variable.
>-
>- @retval EFI_SUCCESS Function successfully executed.
>- @retval EFI_OUT_OF_RESOURCES Fail to allocate enough memory resources.
>-
>-**/
>-EFI_STATUS
>-AutenticatedVariableServiceInitialize (
>- IN UINTN MaxAuthVariableSize
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK Variable;
>- VARIABLE_POINTER_TRACK PkVariable;
>- UINT8 VarValue;
>- UINT32 VarAttr;
>- UINT8 *Data;
>- UINTN DataSize;
>- UINTN CtxSize;
>- UINT8 SecureBootMode;
>- UINT8 SecureBootEnable;
>- UINT8 CustomMode;
>- UINT32 ListSize;
>-
>- //
>- // Initialize hash context.
>- //
>- CtxSize = Sha256GetContextSize ();
>- mHashCtx = AllocateRuntimePool (CtxSize);
>- if (mHashCtx == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- //
>- // Reserve runtime buffer for public key database. The size excludes variable header and name size.
>- //
>- mMaxKeyDbSize = (UINT32) (MaxAuthVariableSize - sizeof (AUTHVAR_KEYDB_NAME));
>- mMaxKeyNumber = mMaxKeyDbSize / EFI_CERT_TYPE_RSA2048_SIZE;
>- mPubKeyStore = AllocateRuntimePool (mMaxKeyDbSize);
>- if (mPubKeyStore == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- //
>- // Reserve runtime buffer for certificate database. The size excludes variable header and name size.
>- //
>- mMaxCertDbSize = (UINT32) (MaxAuthVariableSize - sizeof (EFI_CERT_DB_NAME));
>- mCertDbStore = AllocateRuntimePool (mMaxCertDbSize);
>- if (mCertDbStore == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- //
>- // Check "AuthVarKeyDatabase" variable's existence.
>- // If it doesn't exist, create a new one with initial value of 0 and EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS set.
>- //
>- Status = FindVariable (
>- AUTHVAR_KEYDB_NAME,
>- &gEfiAuthenticatedVariableGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>-
>- if (Variable.CurrPtr == NULL) {
>- VarAttr = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS |
>EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS;
>- VarValue = 0;
>- mPubKeyNumber = 0;
>- Status = UpdateVariable (
>- AUTHVAR_KEYDB_NAME,
>- &gEfiAuthenticatedVariableGuid,
>- &VarValue,
>- sizeof(UINT8),
>- VarAttr,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- } else {
>- //
>- // Load database in global variable for cache.
>- //
>- DataSize = DataSizeOfVariable (Variable.CurrPtr);
>- Data = GetVariableDataPtr (Variable.CurrPtr);
>- ASSERT ((DataSize != 0) && (Data != NULL));
>- //
>- // "AuthVarKeyDatabase" is an internal variable. Its DataSize is always ensured not to exceed mPubKeyStore buffer size(See
>definition before)
>- // Therefore, there is no memory overflow in underlying CopyMem.
>- //
>- CopyMem (mPubKeyStore, (UINT8 *) Data, DataSize);
>- mPubKeyNumber = (UINT32) (DataSize / EFI_CERT_TYPE_RSA2048_SIZE);
>- }
>-
>- FindVariable (EFI_PLATFORM_KEY_NAME, &gEfiGlobalVariableGuid, &PkVariable, &mVariableModuleGlobal->VariableGlobal,
>FALSE);
>- if (PkVariable.CurrPtr == NULL) {
>- DEBUG ((EFI_D_INFO, "Variable %s does not exist.\n", EFI_PLATFORM_KEY_NAME));
>- } else {
>- DEBUG ((EFI_D_INFO, "Variable %s exists.\n", EFI_PLATFORM_KEY_NAME));
>- }
>-
>- //
>- // Create "SetupMode" variable with BS+RT attribute set.
>- //
>- FindVariable (EFI_SETUP_MODE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal->VariableGlobal, FALSE);
>- if (PkVariable.CurrPtr == NULL) {
>- mPlatformMode = SETUP_MODE;
>- } else {
>- mPlatformMode = USER_MODE;
>- }
>- Status = UpdateVariable (
>- EFI_SETUP_MODE_NAME,
>- &gEfiGlobalVariableGuid,
>- &mPlatformMode,
>- sizeof(UINT8),
>- EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- //
>- // Create "SignatureSupport" variable with BS+RT attribute set.
>- //
>- FindVariable (EFI_SIGNATURE_SUPPORT_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal->VariableGlobal,
>FALSE);
>- Status = UpdateVariable (
>- EFI_SIGNATURE_SUPPORT_NAME,
>- &gEfiGlobalVariableGuid,
>- mSignatureSupport,
>- sizeof(mSignatureSupport),
>- EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- //
>- // If "SecureBootEnable" variable exists, then update "SecureBoot" variable.
>- // If "SecureBootEnable" variable is SECURE_BOOT_ENABLE and in USER_MODE, Set "SecureBoot" variable to
>SECURE_BOOT_MODE_ENABLE.
>- // If "SecureBootEnable" variable is SECURE_BOOT_DISABLE, Set "SecureBoot" variable to SECURE_BOOT_MODE_DISABLE.
>- //
>- SecureBootEnable = SECURE_BOOT_DISABLE;
>- FindVariable (EFI_SECURE_BOOT_ENABLE_NAME, &gEfiSecureBootEnableDisableGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>- if (Variable.CurrPtr != NULL) {
>- if (mPlatformMode == SETUP_MODE){
>- //
>- // PK is cleared in runtime. "SecureBootMode" is not updated before reboot
>- // Delete "SecureBootMode" in SetupMode
>- //
>- Status = UpdateVariable (
>- EFI_SECURE_BOOT_ENABLE_NAME,
>- &gEfiSecureBootEnableDisableGuid,
>- &SecureBootEnable,
>- 0,
>- EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- } else {
>- SecureBootEnable = *(GetVariableDataPtr (Variable.CurrPtr));
>- }
>- } else if (mPlatformMode == USER_MODE) {
>- //
>- // "SecureBootEnable" not exist, initialize it in USER_MODE.
>- //
>- SecureBootEnable = SECURE_BOOT_ENABLE;
>- Status = UpdateVariable (
>- EFI_SECURE_BOOT_ENABLE_NAME,
>- &gEfiSecureBootEnableDisableGuid,
>- &SecureBootEnable,
>- sizeof (UINT8),
>- EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- }
>-
>- //
>- // Create "SecureBoot" variable with BS+RT attribute set.
>- //
>- if (SecureBootEnable == SECURE_BOOT_ENABLE && mPlatformMode == USER_MODE) {
>- SecureBootMode = SECURE_BOOT_MODE_ENABLE;
>- } else {
>- SecureBootMode = SECURE_BOOT_MODE_DISABLE;
>- }
>- FindVariable (EFI_SECURE_BOOT_MODE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal->VariableGlobal,
>FALSE);
>- Status = UpdateVariable (
>- EFI_SECURE_BOOT_MODE_NAME,
>- &gEfiGlobalVariableGuid,
>- &SecureBootMode,
>- sizeof (UINT8),
>- EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- DEBUG ((EFI_D_INFO, "Variable %s is %x\n", EFI_SETUP_MODE_NAME, mPlatformMode));
>- DEBUG ((EFI_D_INFO, "Variable %s is %x\n", EFI_SECURE_BOOT_MODE_NAME, SecureBootMode));
>- DEBUG ((EFI_D_INFO, "Variable %s is %x\n", EFI_SECURE_BOOT_ENABLE_NAME, SecureBootEnable));
>-
>- //
>- // Initialize "CustomMode" in STANDARD_SECURE_BOOT_MODE state.
>- //
>- FindVariable (EFI_CUSTOM_MODE_NAME, &gEfiCustomModeEnableGuid, &Variable, &mVariableModuleGlobal->VariableGlobal,
>FALSE);
>- CustomMode = STANDARD_SECURE_BOOT_MODE;
>- Status = UpdateVariable (
>- EFI_CUSTOM_MODE_NAME,
>- &gEfiCustomModeEnableGuid,
>- &CustomMode,
>- sizeof (UINT8),
>- EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- DEBUG ((EFI_D_INFO, "Variable %s is %x\n", EFI_CUSTOM_MODE_NAME, CustomMode));
>-
>- //
>- // Check "certdb" variable's existence.
>- // If it doesn't exist, then create a new one with
>- // EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS set.
>- //
>- Status = FindVariable (
>- EFI_CERT_DB_NAME,
>- &gEfiCertDbGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>-
>- if (Variable.CurrPtr == NULL) {
>- VarAttr = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS;
>- ListSize = sizeof (UINT32);
>- Status = UpdateVariable (
>- EFI_CERT_DB_NAME,
>- &gEfiCertDbGuid,
>- &ListSize,
>- sizeof (UINT32),
>- VarAttr,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- }
>-
>- //
>- // Check "VendorKeysNv" variable's existence and create "VendorKeys" variable accordingly.
>- //
>- FindVariable (EFI_VENDOR_KEYS_NV_VARIABLE_NAME, &gEfiVendorKeysNvGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>- if (Variable.CurrPtr != NULL) {
>- mVendorKeyState = *(GetVariableDataPtr (Variable.CurrPtr));
>- } else {
>- //
>- // "VendorKeysNv" not exist, initialize it in VENDOR_KEYS_VALID state.
>- //
>- mVendorKeyState = VENDOR_KEYS_VALID;
>- Status = UpdateVariable (
>- EFI_VENDOR_KEYS_NV_VARIABLE_NAME,
>- &gEfiVendorKeysNvGuid,
>- &mVendorKeyState,
>- sizeof (UINT8),
>- EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- }
>-
>- //
>- // Create "VendorKeys" variable with BS+RT attribute set.
>- //
>- FindVariable (EFI_VENDOR_KEYS_VARIABLE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>- Status = UpdateVariable (
>- EFI_VENDOR_KEYS_VARIABLE_NAME,
>- &gEfiGlobalVariableGuid,
>- &mVendorKeyState,
>- sizeof (UINT8),
>- EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- DEBUG ((EFI_D_INFO, "Variable %s is %x\n", EFI_VENDOR_KEYS_VARIABLE_NAME, mVendorKeyState));
>-
>- return Status;
>-}
>-
>-/**
>- Add public key in store and return its index.
>-
>- @param[in] PubKey Input pointer to Public Key data
>- @param[in] VariableDataEntry The variable data entry
>-
>- @return Index of new added item
>-
>-**/
>-UINT32
>-AddPubKeyInStore (
>- IN UINT8 *PubKey,
>- IN VARIABLE_ENTRY_CONSISTENCY *VariableDataEntry
>- )
>-{
>- EFI_STATUS Status;
>- BOOLEAN IsFound;
>- UINT32 Index;
>- VARIABLE_POINTER_TRACK Variable;
>- UINT8 *Ptr;
>- UINT8 *Data;
>- UINTN DataSize;
>- VARIABLE_ENTRY_CONSISTENCY PublicKeyEntry;
>- UINT32 Attributes;
>-
>- if (PubKey == NULL) {
>- return 0;
>- }
>-
>- Status = FindVariable (
>- AUTHVAR_KEYDB_NAME,
>- &gEfiAuthenticatedVariableGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- DEBUG ((EFI_D_ERROR, "Get public key database variable failure, Status = %r\n", Status));
>- return 0;
>- }
>-
>- //
>- // Check whether the public key entry does exist.
>- //
>- IsFound = FALSE;
>- for (Ptr = mPubKeyStore, Index = 1; Index <= mPubKeyNumber; Index++) {
>- if (CompareMem (Ptr, PubKey, EFI_CERT_TYPE_RSA2048_SIZE) == 0) {
>- IsFound = TRUE;
>- break;
>- }
>- Ptr += EFI_CERT_TYPE_RSA2048_SIZE;
>- }
>-
>- if (!IsFound) {
>- //
>- // Add public key in database.
>- //
>- if (mPubKeyNumber == mMaxKeyNumber) {
>- //
>- // Public key dadatase is full, try to reclaim invalid key.
>- //
>- if (AtRuntime ()) {
>- //
>- // NV storage can't reclaim at runtime.
>- //
>- return 0;
>- }
>-
>- Status = Reclaim (
>- mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase,
>- &mVariableModuleGlobal->NonVolatileLastVariableOffset,
>- FALSE,
>- NULL,
>- NULL,
>- 0,
>- TRUE
>- );
>- if (EFI_ERROR (Status)) {
>- return 0;
>- }
>-
>- Status = FindVariable (
>- AUTHVAR_KEYDB_NAME,
>- &gEfiAuthenticatedVariableGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- DEBUG ((EFI_D_ERROR, "Get public key database variable failure, Status = %r\n", Status));
>- return 0;
>- }
>-
>- DataSize = DataSizeOfVariable (Variable.CurrPtr);
>- Data = GetVariableDataPtr (Variable.CurrPtr);
>- ASSERT ((DataSize != 0) && (Data != NULL));
>- //
>- // "AuthVarKeyDatabase" is an internal used variable. Its DataSize is always ensured not to exceed mPubKeyStore buffer size(See
>definition before)
>- // Therefore, there is no memory overflow in underlying CopyMem.
>- //
>- CopyMem (mPubKeyStore, (UINT8 *) Data, DataSize);
>- mPubKeyNumber = (UINT32) (DataSize / EFI_CERT_TYPE_RSA2048_SIZE);
>-
>- if (mPubKeyNumber == mMaxKeyNumber) {
>- return 0;
>- }
>- }
>-
>- //
>- // Check the variable space for both public key and variable data.
>- //
>- PublicKeyEntry.VariableSize = (mPubKeyNumber + 1) * EFI_CERT_TYPE_RSA2048_SIZE;
>- PublicKeyEntry.Guid = &gEfiAuthenticatedVariableGuid;
>- PublicKeyEntry.Name = AUTHVAR_KEYDB_NAME;
>- Attributes = VARIABLE_ATTRIBUTE_NV_BS_RT | EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS;
>-
>- if (!CheckRemainingSpaceForConsistency (Attributes, &PublicKeyEntry, VariableDataEntry, NULL)) {
>- //
>- // No enough variable space.
>- //
>- return 0;
>- }
>-
>- CopyMem (mPubKeyStore + mPubKeyNumber * EFI_CERT_TYPE_RSA2048_SIZE, PubKey, EFI_CERT_TYPE_RSA2048_SIZE);
>- Index = ++mPubKeyNumber;
>- //
>- // Update public key database variable.
>- //
>- Status = UpdateVariable (
>- AUTHVAR_KEYDB_NAME,
>- &gEfiAuthenticatedVariableGuid,
>- mPubKeyStore,
>- mPubKeyNumber * EFI_CERT_TYPE_RSA2048_SIZE,
>- Attributes,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- DEBUG ((EFI_D_ERROR, "Update public key database variable failure, Status = %r\n", Status));
>- return 0;
>- }
>- }
>-
>- return Index;
>-}
>-
>-/**
>- Verify data payload with AuthInfo in EFI_CERT_TYPE_RSA2048_SHA256_GUID type.
>- Follow the steps in UEFI2.2.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>-
>- @param[in] Data Pointer to data with AuthInfo.
>- @param[in] DataSize Size of Data.
>- @param[in] PubKey Public key used for verification.
>-
>- @retval EFI_INVALID_PARAMETER Invalid parameter.
>- @retval EFI_SECURITY_VIOLATION If authentication failed.
>- @retval EFI_SUCCESS Authentication successful.
>-
>-**/
>-EFI_STATUS
>-VerifyCounterBasedPayload (
>- IN UINT8 *Data,
>- IN UINTN DataSize,
>- IN UINT8 *PubKey
>- )
>-{
>- BOOLEAN Status;
>- EFI_VARIABLE_AUTHENTICATION *CertData;
>- EFI_CERT_BLOCK_RSA_2048_SHA256 *CertBlock;
>- UINT8 Digest[SHA256_DIGEST_SIZE];
>- VOID *Rsa;
>- UINTN PayloadSize;
>-
>- PayloadSize = DataSize - AUTHINFO_SIZE;
>- Rsa = NULL;
>- CertData = NULL;
>- CertBlock = NULL;
>-
>- if (Data == NULL || PubKey == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- CertData = (EFI_VARIABLE_AUTHENTICATION *) Data;
>- CertBlock = (EFI_CERT_BLOCK_RSA_2048_SHA256 *) (CertData->AuthInfo.CertData);
>-
>- //
>- // wCertificateType should be WIN_CERT_TYPE_EFI_GUID.
>- // Cert type should be EFI_CERT_TYPE_RSA2048_SHA256_GUID.
>- //
>- if ((CertData->AuthInfo.Hdr.wCertificateType != WIN_CERT_TYPE_EFI_GUID) ||
>- !CompareGuid (&CertData->AuthInfo.CertType, &gEfiCertTypeRsa2048Sha256Guid)
>- ) {
>- //
>- // Invalid AuthInfo type, return EFI_SECURITY_VIOLATION.
>- //
>- return EFI_SECURITY_VIOLATION;
>- }
>- //
>- // Hash data payload with SHA256.
>- //
>- ZeroMem (Digest, SHA256_DIGEST_SIZE);
>- Status = Sha256Init (mHashCtx);
>- if (!Status) {
>- goto Done;
>- }
>- Status = Sha256Update (mHashCtx, Data + AUTHINFO_SIZE, PayloadSize);
>- if (!Status) {
>- goto Done;
>- }
>- //
>- // Hash Size.
>- //
>- Status = Sha256Update (mHashCtx, &PayloadSize, sizeof (UINTN));
>- if (!Status) {
>- goto Done;
>- }
>- //
>- // Hash Monotonic Count.
>- //
>- Status = Sha256Update (mHashCtx, &CertData->MonotonicCount, sizeof (UINT64));
>- if (!Status) {
>- goto Done;
>- }
>- Status = Sha256Final (mHashCtx, Digest);
>- if (!Status) {
>- goto Done;
>- }
>- //
>- // Generate & Initialize RSA Context.
>- //
>- Rsa = RsaNew ();
>- ASSERT (Rsa != NULL);
>- //
>- // Set RSA Key Components.
>- // NOTE: Only N and E are needed to be set as RSA public key for signature verification.
>- //
>- Status = RsaSetKey (Rsa, RsaKeyN, PubKey, EFI_CERT_TYPE_RSA2048_SIZE);
>- if (!Status) {
>- goto Done;
>- }
>- Status = RsaSetKey (Rsa, RsaKeyE, mRsaE, sizeof (mRsaE));
>- if (!Status) {
>- goto Done;
>- }
>- //
>- // Verify the signature.
>- //
>- Status = RsaPkcs1Verify (
>- Rsa,
>- Digest,
>- SHA256_DIGEST_SIZE,
>- CertBlock->Signature,
>- EFI_CERT_TYPE_RSA2048_SHA256_SIZE
>- );
>-
>-Done:
>- if (Rsa != NULL) {
>- RsaFree (Rsa);
>- }
>- if (Status) {
>- return EFI_SUCCESS;
>- } else {
>- return EFI_SECURITY_VIOLATION;
>- }
>-}
>-
>-/**
>- Update platform mode.
>-
>- @param[in] Mode SETUP_MODE or USER_MODE.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Update platform mode successfully.
>-
>-**/
>-EFI_STATUS
>-UpdatePlatformMode (
>- IN UINT32 Mode
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK Variable;
>- UINT8 SecureBootMode;
>- UINT8 SecureBootEnable;
>- UINTN VariableDataSize;
>-
>- Status = FindVariable (
>- EFI_SETUP_MODE_NAME,
>- &gEfiGlobalVariableGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- //
>- // Update the value of SetupMode variable by a simple mem copy, this could avoid possible
>- // variable storage reclaim at runtime.
>- //
>- mPlatformMode = (UINT8) Mode;
>- CopyMem (GetVariableDataPtr (Variable.CurrPtr), &mPlatformMode, sizeof(UINT8));
>-
>- if (AtRuntime ()) {
>- //
>- // SecureBoot Variable indicates whether the platform firmware is operating
>- // in Secure boot mode (1) or not (0), so we should not change SecureBoot
>- // Variable in runtime.
>- //
>- return Status;
>- }
>-
>- //
>- // Check "SecureBoot" variable's existence.
>- // If it doesn't exist, firmware has no capability to perform driver signing verification,
>- // then set "SecureBoot" to 0.
>- //
>- Status = FindVariable (
>- EFI_SECURE_BOOT_MODE_NAME,
>- &gEfiGlobalVariableGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- //
>- // If "SecureBoot" variable exists, then check "SetupMode" variable update.
>- // If "SetupMode" variable is USER_MODE, "SecureBoot" variable is set to 1.
>- // If "SetupMode" variable is SETUP_MODE, "SecureBoot" variable is set to 0.
>- //
>- if (Variable.CurrPtr == NULL) {
>- SecureBootMode = SECURE_BOOT_MODE_DISABLE;
>- } else {
>- if (mPlatformMode == USER_MODE) {
>- SecureBootMode = SECURE_BOOT_MODE_ENABLE;
>- } else if (mPlatformMode == SETUP_MODE) {
>- SecureBootMode = SECURE_BOOT_MODE_DISABLE;
>- } else {
>- return EFI_NOT_FOUND;
>- }
>- }
>-
>- Status = UpdateVariable (
>- EFI_SECURE_BOOT_MODE_NAME,
>- &gEfiGlobalVariableGuid,
>- &SecureBootMode,
>- sizeof(UINT8),
>- EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- //
>- // Check "SecureBootEnable" variable's existence. It can enable/disable secure boot feature.
>- //
>- Status = FindVariable (
>- EFI_SECURE_BOOT_ENABLE_NAME,
>- &gEfiSecureBootEnableDisableGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>-
>- if (SecureBootMode == SECURE_BOOT_MODE_ENABLE) {
>- //
>- // Create the "SecureBootEnable" variable as secure boot is enabled.
>- //
>- SecureBootEnable = SECURE_BOOT_ENABLE;
>- VariableDataSize = sizeof (SecureBootEnable);
>- } else {
>- //
>- // Delete the "SecureBootEnable" variable if this variable exist as "SecureBoot"
>- // variable is not in secure boot state.
>- //
>- if (Variable.CurrPtr == NULL || EFI_ERROR (Status)) {
>- return EFI_SUCCESS;
>- }
>- SecureBootEnable = SECURE_BOOT_DISABLE;
>- VariableDataSize = 0;
>- }
>-
>- Status = UpdateVariable (
>- EFI_SECURE_BOOT_ENABLE_NAME,
>- &gEfiSecureBootEnableDisableGuid,
>- &SecureBootEnable,
>- VariableDataSize,
>- EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- return Status;
>-}
>-
>-/**
>- Check input data form to make sure it is a valid EFI_SIGNATURE_LIST for PK/KEK/db/dbx/dbt variable.
>-
>- @param[in] VariableName Name of Variable to be check.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Point to the variable data to be checked.
>- @param[in] DataSize Size of Data.
>-
>- @return EFI_INVALID_PARAMETER Invalid signature list format.
>- @return EFI_SUCCESS Passed signature list format check successfully.
>-
>-**/
>-EFI_STATUS
>-CheckSignatureListFormat(
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize
>- )
>-{
>- EFI_SIGNATURE_LIST *SigList;
>- UINTN SigDataSize;
>- UINT32 Index;
>- UINT32 SigCount;
>- BOOLEAN IsPk;
>- VOID *RsaContext;
>- EFI_SIGNATURE_DATA *CertData;
>- UINTN CertLen;
>-
>- if (DataSize == 0) {
>- return EFI_SUCCESS;
>- }
>-
>- ASSERT (VariableName != NULL && VendorGuid != NULL && Data != NULL);
>-
>- if (CompareGuid (VendorGuid, &gEfiGlobalVariableGuid) && (StrCmp (VariableName, EFI_PLATFORM_KEY_NAME) == 0)){
>- IsPk = TRUE;
>- } else if ((CompareGuid (VendorGuid, &gEfiGlobalVariableGuid) && (StrCmp (VariableName, EFI_KEY_EXCHANGE_KEY_NAME) ==
>0)) ||
>- (CompareGuid (VendorGuid, &gEfiImageSecurityDatabaseGuid) &&
>- ((StrCmp (VariableName, EFI_IMAGE_SECURITY_DATABASE) == 0) || (StrCmp (VariableName,
>EFI_IMAGE_SECURITY_DATABASE1) == 0) ||
>- (StrCmp (VariableName, EFI_IMAGE_SECURITY_DATABASE2) == 0)))) {
>- IsPk = FALSE;
>- } else {
>- return EFI_SUCCESS;
>- }
>-
>- SigCount = 0;
>- SigList = (EFI_SIGNATURE_LIST *) Data;
>- SigDataSize = DataSize;
>- RsaContext = NULL;
>-
>- //
>- // Walk throuth the input signature list and check the data format.
>- // If any signature is incorrectly formed, the whole check will fail.
>- //
>- while ((SigDataSize > 0) && (SigDataSize >= SigList->SignatureListSize)) {
>- for (Index = 0; Index < (sizeof (mSupportSigItem) / sizeof (EFI_SIGNATURE_ITEM)); Index++ ) {
>- if (CompareGuid (&SigList->SignatureType, &mSupportSigItem[Index].SigType)) {
>- //
>- // The value of SignatureSize should always be 16 (size of SignatureOwner
>- // component) add the data length according to signature type.
>- //
>- if (mSupportSigItem[Index].SigDataSize != ((UINT32) ~0) &&
>- (SigList->SignatureSize - sizeof (EFI_GUID)) != mSupportSigItem[Index].SigDataSize) {
>- return EFI_INVALID_PARAMETER;
>- }
>- if (mSupportSigItem[Index].SigHeaderSize != ((UINTN) ~0) &&
>- SigList->SignatureHeaderSize != mSupportSigItem[Index].SigHeaderSize) {
>- return EFI_INVALID_PARAMETER;
>- }
>- break;
>- }
>- }
>-
>- if (Index == (sizeof (mSupportSigItem) / sizeof (EFI_SIGNATURE_ITEM))) {
>- //
>- // Undefined signature type.
>- //
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (CompareGuid (&SigList->SignatureType, &gEfiCertX509Guid)) {
>- //
>- // Try to retrieve the RSA public key from the X.509 certificate.
>- // If this operation fails, it's not a valid certificate.
>- //
>- RsaContext = RsaNew ();
>- if (RsaContext == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>- CertData = (EFI_SIGNATURE_DATA *) ((UINT8 *) SigList + sizeof (EFI_SIGNATURE_LIST) + SigList->SignatureHeaderSize);
>- CertLen = SigList->SignatureSize - sizeof (EFI_GUID);
>- if (!RsaGetPublicKeyFromX509 (CertData->SignatureData, CertLen, &RsaContext)) {
>- RsaFree (RsaContext);
>- return EFI_INVALID_PARAMETER;
>- }
>- RsaFree (RsaContext);
>- }
>-
>- if ((SigList->SignatureListSize - sizeof (EFI_SIGNATURE_LIST) - SigList->SignatureHeaderSize) % SigList->SignatureSize != 0) {
>- return EFI_INVALID_PARAMETER;
>- }
>- SigCount += (SigList->SignatureListSize - sizeof (EFI_SIGNATURE_LIST) - SigList->SignatureHeaderSize) / SigList->SignatureSize;
>-
>- SigDataSize -= SigList->SignatureListSize;
>- SigList = (EFI_SIGNATURE_LIST *) ((UINT8 *) SigList + SigList->SignatureListSize);
>- }
>-
>- if (((UINTN) SigList - (UINTN) Data) != DataSize) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (IsPk && SigCount > 1) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Update "VendorKeys" variable to record the out of band secure boot key modification.
>-
>- @return EFI_SUCCESS Variable is updated successfully.
>- @return Others Failed to update variable.
>-
>-**/
>-EFI_STATUS
>-VendorKeyIsModified (
>- VOID
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK Variable;
>-
>- if (mVendorKeyState == VENDOR_KEYS_MODIFIED) {
>- return EFI_SUCCESS;
>- }
>- mVendorKeyState = VENDOR_KEYS_MODIFIED;
>-
>- FindVariable (EFI_VENDOR_KEYS_NV_VARIABLE_NAME, &gEfiVendorKeysNvGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>- Status = UpdateVariable (
>- EFI_VENDOR_KEYS_NV_VARIABLE_NAME,
>- &gEfiVendorKeysNvGuid,
>- &mVendorKeyState,
>- sizeof (UINT8),
>- EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- FindVariable (EFI_VENDOR_KEYS_VARIABLE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>- return UpdateVariable (
>- EFI_VENDOR_KEYS_VARIABLE_NAME,
>- &gEfiGlobalVariableGuid,
>- &mVendorKeyState,
>- sizeof (UINT8),
>- EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>-}
>-
>-/**
>- Process variable with platform key for verification.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable
>- @param[in] IsPk Indicate whether it is to process pk.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SECURITY_VIOLATION The variable does NOT pass the validation.
>- check carried out by the firmware.
>- @return EFI_SUCCESS Variable passed validation successfully.
>-
>-**/
>-EFI_STATUS
>-ProcessVarWithPk (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes OPTIONAL,
>- IN BOOLEAN IsPk
>- )
>-{
>- EFI_STATUS Status;
>- BOOLEAN Del;
>- UINT8 *Payload;
>- UINTN PayloadSize;
>-
>- if ((Attributes & EFI_VARIABLE_NON_VOLATILE) == 0 ||
>- (Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) == 0) {
>- //
>- // PK, KEK and db/dbx/dbt should set EFI_VARIABLE_NON_VOLATILE attribute and should be a time-based
>- // authenticated variable.
>- //
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- Del = FALSE;
>- if ((InCustomMode() && UserPhysicalPresent()) || (mPlatformMode == SETUP_MODE && !IsPk)) {
>- Payload = (UINT8 *) Data + AUTHINFO2_SIZE (Data);
>- PayloadSize = DataSize - AUTHINFO2_SIZE (Data);
>- if (PayloadSize == 0) {
>- Del = TRUE;
>- }
>-
>- Status = CheckSignatureListFormat(VariableName, VendorGuid, Payload, PayloadSize);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- Status = UpdateVariable (
>- VariableName,
>- VendorGuid,
>- Payload,
>- PayloadSize,
>- Attributes,
>- 0,
>- 0,
>- Variable,
>- &((EFI_VARIABLE_AUTHENTICATION_2 *) Data)->TimeStamp
>- );
>- if (EFI_ERROR(Status)) {
>- return Status;
>- }
>-
>- if ((mPlatformMode != SETUP_MODE) || IsPk) {
>- Status = VendorKeyIsModified ();
>- }
>- } else if (mPlatformMode == USER_MODE) {
>- //
>- // Verify against X509 Cert in PK database.
>- //
>- Status = VerifyTimeBasedPayload (
>- VariableName,
>- VendorGuid,
>- Data,
>- DataSize,
>- Variable,
>- Attributes,
>- AuthVarTypePk,
>- &Del
>- );
>- } else {
>- //
>- // Verify against the certificate in data payload.
>- //
>- Status = VerifyTimeBasedPayload (
>- VariableName,
>- VendorGuid,
>- Data,
>- DataSize,
>- Variable,
>- Attributes,
>- AuthVarTypePayload,
>- &Del
>- );
>- }
>-
>- if (!EFI_ERROR(Status) && IsPk) {
>- if (mPlatformMode == SETUP_MODE && !Del) {
>- //
>- // If enroll PK in setup mode, need change to user mode.
>- //
>- Status = UpdatePlatformMode (USER_MODE);
>- } else if (mPlatformMode == USER_MODE && Del){
>- //
>- // If delete PK in user mode, need change to setup mode.
>- //
>- Status = UpdatePlatformMode (SETUP_MODE);
>- }
>- }
>-
>- return Status;
>-}
>-
>-/**
>- Process variable with key exchange key for verification.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SECURITY_VIOLATION The variable does NOT pass the validation
>- check carried out by the firmware.
>- @return EFI_SUCCESS Variable pass validation successfully.
>-
>-**/
>-EFI_STATUS
>-ProcessVarWithKek (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes OPTIONAL
>- )
>-{
>- EFI_STATUS Status;
>- UINT8 *Payload;
>- UINTN PayloadSize;
>-
>- if ((Attributes & EFI_VARIABLE_NON_VOLATILE) == 0 ||
>- (Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) == 0) {
>- //
>- // DB, DBX and DBT should set EFI_VARIABLE_NON_VOLATILE attribute and should be a time-based
>- // authenticated variable.
>- //
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- Status = EFI_SUCCESS;
>- if (mPlatformMode == USER_MODE && !(InCustomMode() && UserPhysicalPresent())) {
>- //
>- // Time-based, verify against X509 Cert KEK.
>- //
>- return VerifyTimeBasedPayload (
>- VariableName,
>- VendorGuid,
>- Data,
>- DataSize,
>- Variable,
>- Attributes,
>- AuthVarTypeKek,
>- NULL
>- );
>- } else {
>- //
>- // If in setup mode or custom secure boot mode, no authentication needed.
>- //
>- Payload = (UINT8 *) Data + AUTHINFO2_SIZE (Data);
>- PayloadSize = DataSize - AUTHINFO2_SIZE (Data);
>-
>- Status = CheckSignatureListFormat(VariableName, VendorGuid, Payload, PayloadSize);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- Status = UpdateVariable (
>- VariableName,
>- VendorGuid,
>- Payload,
>- PayloadSize,
>- Attributes,
>- 0,
>- 0,
>- Variable,
>- &((EFI_VARIABLE_AUTHENTICATION_2 *) Data)->TimeStamp
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- if (mPlatformMode != SETUP_MODE) {
>- Status = VendorKeyIsModified ();
>- }
>- }
>-
>- return Status;
>-}
>-
>-/**
>- Check if it is to delete auth variable.
>-
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>-
>- @retval TRUE It is to delete auth variable.
>- @retval FALSE It is not to delete auth variable.
>-
>-**/
>-BOOLEAN
>-IsDeleteAuthVariable (
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes
>- )
>-{
>- BOOLEAN Del;
>- UINTN PayloadSize;
>-
>- Del = FALSE;
>-
>- //
>- // To delete a variable created with the EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS
>- // or the EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS attribute,
>- // SetVariable must be used with attributes matching the existing variable
>- // and the DataSize set to the size of the AuthInfo descriptor.
>- //
>- if ((Variable->CurrPtr != NULL) &&
>- (Attributes == Variable->CurrPtr->Attributes) &&
>- ((Attributes & (EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS)) != 0)) {
>- if ((Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) != 0) {
>- PayloadSize = DataSize - AUTHINFO2_SIZE (Data);
>- if (PayloadSize == 0) {
>- Del = TRUE;
>- }
>- } else {
>- PayloadSize = DataSize - AUTHINFO_SIZE;
>- if (PayloadSize == 0) {
>- Del = TRUE;
>- }
>- }
>- }
>-
>- return Del;
>-}
>-
>-/**
>- Process variable with
>EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS/EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS set
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>-
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_WRITE_PROTECTED Variable is write-protected and needs authentication with
>- EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS set.
>- @return EFI_OUT_OF_RESOURCES The Database to save the public key is full.
>- @return EFI_SECURITY_VIOLATION The variable is with EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS
>- set, but the AuthInfo does NOT pass the validation
>- check carried out by the firmware.
>- @return EFI_SUCCESS Variable is not write-protected or pass validation successfully.
>-
>-**/
>-EFI_STATUS
>-ProcessVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes
>- )
>-{
>- EFI_STATUS Status;
>- BOOLEAN IsDeletion;
>- BOOLEAN IsFirstTime;
>- UINT8 *PubKey;
>- EFI_VARIABLE_AUTHENTICATION *CertData;
>- EFI_CERT_BLOCK_RSA_2048_SHA256 *CertBlock;
>- UINT32 KeyIndex;
>- UINT64 MonotonicCount;
>- VARIABLE_ENTRY_CONSISTENCY VariableDataEntry;
>-
>- KeyIndex = 0;
>- CertData = NULL;
>- CertBlock = NULL;
>- PubKey = NULL;
>- IsDeletion = FALSE;
>- Status = EFI_SUCCESS;
>-
>- if (IsDeleteAuthVariable (Data, DataSize, Variable, Attributes) && UserPhysicalPresent()) {
>- //
>- // Allow the delete operation of common authenticated variable at user physical presence.
>- //
>- if ((Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) != 0) {
>- Status = DeleteCertsFromDb (VariableName, VendorGuid);
>- }
>- if (!EFI_ERROR (Status)) {
>- Status = UpdateVariable (
>- VariableName,
>- VendorGuid,
>- NULL,
>- 0,
>- 0,
>- 0,
>- 0,
>- Variable,
>- NULL
>- );
>- }
>- return Status;
>- }
>-
>- if (NeedPhysicallyPresent (VariableName, VendorGuid) && !UserPhysicalPresent()) {
>- //
>- // This variable is protected, only physical present user could modify its value.
>- //
>- return EFI_SECURITY_VIOLATION;
>- }
>-
>- //
>- // A time-based authenticated variable and a count-based authenticated variable
>- // can't be updated by each other.
>- //
>- if (Variable->CurrPtr != NULL) {
>- if (((Attributes & EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) != 0) &&
>- ((Variable->CurrPtr->Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) != 0)) {
>- return EFI_SECURITY_VIOLATION;
>- }
>-
>- if (((Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) != 0) &&
>- ((Variable->CurrPtr->Attributes & EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) != 0)) {
>- return EFI_SECURITY_VIOLATION;
>- }
>- }
>-
>- //
>- // Process Time-based Authenticated variable.
>- //
>- if ((Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) != 0) {
>- return VerifyTimeBasedPayload (
>- VariableName,
>- VendorGuid,
>- Data,
>- DataSize,
>- Variable,
>- Attributes,
>- AuthVarTypePriv,
>- NULL
>- );
>- }
>-
>- //
>- // Determine if first time SetVariable with the EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS.
>- //
>- if ((Attributes & EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) != 0) {
>- //
>- // Determine current operation type.
>- //
>- if (DataSize == AUTHINFO_SIZE) {
>- IsDeletion = TRUE;
>- }
>- //
>- // Determine whether this is the first time with EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS set.
>- //
>- if (Variable->CurrPtr == NULL) {
>- IsFirstTime = TRUE;
>- } else if ((Variable->CurrPtr->Attributes & EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) == 0) {
>- IsFirstTime = TRUE;
>- } else {
>- KeyIndex = Variable->CurrPtr->PubKeyIndex;
>- IsFirstTime = FALSE;
>- }
>- } else if ((Variable->CurrPtr != NULL) &&
>- ((Variable->CurrPtr->Attributes & (EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS)) != 0)
>- ) {
>- //
>- // If the variable is already write-protected, it always needs authentication before update.
>- //
>- return EFI_WRITE_PROTECTED;
>- } else {
>- //
>- // If without EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS, set and attributes collision.
>- // That means it is not authenticated variable, just update variable as usual.
>- //
>- Status = UpdateVariable (VariableName, VendorGuid, Data, DataSize, Attributes, 0, 0, Variable, NULL);
>- return Status;
>- }
>-
>- //
>- // Get PubKey and check Monotonic Count value corresponding to the variable.
>- //
>- CertData = (EFI_VARIABLE_AUTHENTICATION *) Data;
>- CertBlock = (EFI_CERT_BLOCK_RSA_2048_SHA256 *) (CertData->AuthInfo.CertData);
>- PubKey = CertBlock->PublicKey;
>-
>- //
>- // Update Monotonic Count value.
>- //
>- MonotonicCount = CertData->MonotonicCount;
>-
>- if (!IsFirstTime) {
>- //
>- // 2 cases need to check here
>- // 1. Internal PubKey variable. PubKeyIndex is always 0
>- // 2. Other counter-based AuthVariable. Check input PubKey.
>- //
>- if (KeyIndex == 0 || CompareMem (PubKey, mPubKeyStore + (KeyIndex - 1) * EFI_CERT_TYPE_RSA2048_SIZE,
>EFI_CERT_TYPE_RSA2048_SIZE) != 0) {
>- return EFI_SECURITY_VIOLATION;
>- }
>- //
>- // Compare the current monotonic count and ensure that it is greater than the last SetVariable
>- // operation with the EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS attribute set.
>- //
>- if (CertData->MonotonicCount <= Variable->CurrPtr->MonotonicCount) {
>- //
>- // Monotonic count check fail, suspicious replay attack, return EFI_SECURITY_VIOLATION.
>- //
>- return EFI_SECURITY_VIOLATION;
>- }
>- }
>- //
>- // Verify the certificate in Data payload.
>- //
>- Status = VerifyCounterBasedPayload (Data, DataSize, PubKey);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- //
>- // Now, the signature has been verified!
>- //
>- if (IsFirstTime && !IsDeletion) {
>- VariableDataEntry.VariableSize = DataSize - AUTHINFO_SIZE;
>- VariableDataEntry.Guid = VendorGuid;
>- VariableDataEntry.Name = VariableName;
>-
>- //
>- // Update public key database variable if need.
>- //
>- KeyIndex = AddPubKeyInStore (PubKey, &VariableDataEntry);
>- if (KeyIndex == 0) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>- }
>-
>- //
>- // Verification pass.
>- //
>- return UpdateVariable (VariableName, VendorGuid, (UINT8*)Data + AUTHINFO_SIZE, DataSize - AUTHINFO_SIZE, Attributes,
>KeyIndex, MonotonicCount, Variable, NULL);
>-}
>-
>-/**
>- Merge two buffers which formatted as EFI_SIGNATURE_LIST. Only the new EFI_SIGNATURE_DATA
>- will be appended to the original EFI_SIGNATURE_LIST, duplicate EFI_SIGNATURE_DATA
>- will be ignored.
>-
>- @param[in, out] Data Pointer to original EFI_SIGNATURE_LIST.
>- @param[in] DataSize Size of Data buffer.
>- @param[in] FreeBufSize Size of free data buffer
>- @param[in] NewData Pointer to new EFI_SIGNATURE_LIST to be appended.
>- @param[in] NewDataSize Size of NewData buffer.
>- @param[out] MergedBufSize Size of the merged buffer
>-
>- @return EFI_BUFFER_TOO_SMALL if input Data buffer overflowed
>-
>-**/
>-EFI_STATUS
>-AppendSignatureList (
>- IN OUT VOID *Data,
>- IN UINTN DataSize,
>- IN UINTN FreeBufSize,
>- IN VOID *NewData,
>- IN UINTN NewDataSize,
>- OUT UINTN *MergedBufSize
>- )
>-{
>- EFI_SIGNATURE_LIST *CertList;
>- EFI_SIGNATURE_DATA *Cert;
>- UINTN CertCount;
>- EFI_SIGNATURE_LIST *NewCertList;
>- EFI_SIGNATURE_DATA *NewCert;
>- UINTN NewCertCount;
>- UINTN Index;
>- UINTN Index2;
>- UINTN Size;
>- UINT8 *Tail;
>- UINTN CopiedCount;
>- UINTN SignatureListSize;
>- BOOLEAN IsNewCert;
>-
>- Tail = (UINT8 *) Data + DataSize;
>-
>- NewCertList = (EFI_SIGNATURE_LIST *) NewData;
>- while ((NewDataSize > 0) && (NewDataSize >= NewCertList->SignatureListSize)) {
>- NewCert = (EFI_SIGNATURE_DATA *) ((UINT8 *) NewCertList + sizeof (EFI_SIGNATURE_LIST) + NewCertList-
>>SignatureHeaderSize);
>- NewCertCount = (NewCertList->SignatureListSize - sizeof (EFI_SIGNATURE_LIST) - NewCertList->SignatureHeaderSize) /
>NewCertList->SignatureSize;
>-
>- CopiedCount = 0;
>- for (Index = 0; Index < NewCertCount; Index++) {
>- IsNewCert = TRUE;
>-
>- Size = DataSize;
>- CertList = (EFI_SIGNATURE_LIST *) Data;
>- while ((Size > 0) && (Size >= CertList->SignatureListSize)) {
>- if (CompareGuid (&CertList->SignatureType, &NewCertList->SignatureType) &&
>- (CertList->SignatureSize == NewCertList->SignatureSize)) {
>- Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) CertList + sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
>- CertCount = (CertList->SignatureListSize - sizeof (EFI_SIGNATURE_LIST) - CertList->SignatureHeaderSize) / CertList-
>>SignatureSize;
>- for (Index2 = 0; Index2 < CertCount; Index2++) {
>- //
>- // Iterate each Signature Data in this Signature List.
>- //
>- if (CompareMem (NewCert, Cert, CertList->SignatureSize) == 0) {
>- IsNewCert = FALSE;
>- break;
>- }
>- Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) Cert + CertList->SignatureSize);
>- }
>- }
>-
>- if (!IsNewCert) {
>- break;
>- }
>- Size -= CertList->SignatureListSize;
>- CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList + CertList->SignatureListSize);
>- }
>-
>- if (IsNewCert) {
>- //
>- // New EFI_SIGNATURE_DATA, append it.
>- //
>- if (CopiedCount == 0) {
>- if (FreeBufSize < sizeof (EFI_SIGNATURE_LIST) + NewCertList->SignatureHeaderSize) {
>- return EFI_BUFFER_TOO_SMALL;
>- }
>-
>- //
>- // Copy EFI_SIGNATURE_LIST header for only once.
>- //
>-
>- CopyMem (Tail, NewCertList, sizeof (EFI_SIGNATURE_LIST) + NewCertList->SignatureHeaderSize);
>- Tail = Tail + sizeof (EFI_SIGNATURE_LIST) + NewCertList->SignatureHeaderSize;
>- FreeBufSize -= sizeof (EFI_SIGNATURE_LIST) + NewCertList->SignatureHeaderSize;
>- }
>-
>- if (FreeBufSize < NewCertList->SignatureSize) {
>- return EFI_BUFFER_TOO_SMALL;
>- }
>- CopyMem (Tail, NewCert, NewCertList->SignatureSize);
>- Tail += NewCertList->SignatureSize;
>- FreeBufSize -= NewCertList->SignatureSize;
>- CopiedCount++;
>- }
>-
>- NewCert = (EFI_SIGNATURE_DATA *) ((UINT8 *) NewCert + NewCertList->SignatureSize);
>- }
>-
>- //
>- // Update SignatureListSize in newly appended EFI_SIGNATURE_LIST.
>- //
>- if (CopiedCount != 0) {
>- SignatureListSize = sizeof (EFI_SIGNATURE_LIST) + NewCertList->SignatureHeaderSize + (CopiedCount * NewCertList-
>>SignatureSize);
>- CertList = (EFI_SIGNATURE_LIST *) (Tail - SignatureListSize);
>- CertList->SignatureListSize = (UINT32) SignatureListSize;
>- }
>-
>- NewDataSize -= NewCertList->SignatureListSize;
>- NewCertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) NewCertList + NewCertList->SignatureListSize);
>- }
>-
>- *MergedBufSize = (Tail - (UINT8 *) Data);
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Compare two EFI_TIME data.
>-
>-
>- @param FirstTime A pointer to the first EFI_TIME data.
>- @param SecondTime A pointer to the second EFI_TIME data.
>-
>- @retval TRUE The FirstTime is not later than the SecondTime.
>- @retval FALSE The FirstTime is later than the SecondTime.
>-
>-**/
>-BOOLEAN
>-CompareTimeStamp (
>- IN EFI_TIME *FirstTime,
>- IN EFI_TIME *SecondTime
>- )
>-{
>- if (FirstTime->Year != SecondTime->Year) {
>- return (BOOLEAN) (FirstTime->Year < SecondTime->Year);
>- } else if (FirstTime->Month != SecondTime->Month) {
>- return (BOOLEAN) (FirstTime->Month < SecondTime->Month);
>- } else if (FirstTime->Day != SecondTime->Day) {
>- return (BOOLEAN) (FirstTime->Day < SecondTime->Day);
>- } else if (FirstTime->Hour != SecondTime->Hour) {
>- return (BOOLEAN) (FirstTime->Hour < SecondTime->Hour);
>- } else if (FirstTime->Minute != SecondTime->Minute) {
>- return (BOOLEAN) (FirstTime->Minute < SecondTime->Minute);
>- }
>-
>- return (BOOLEAN) (FirstTime->Second <= SecondTime->Second);
>-}
>-
>-/**
>- Find matching signer's certificates for common authenticated variable
>- by corresponding VariableName and VendorGuid from "certdb".
>-
>- The data format of "certdb":
>- //
>- // UINT32 CertDbListSize;
>- // /// AUTH_CERT_DB_DATA Certs1[];
>- // /// AUTH_CERT_DB_DATA Certs2[];
>- // /// ...
>- // /// AUTH_CERT_DB_DATA Certsn[];
>- //
>-
>- @param[in] VariableName Name of authenticated Variable.
>- @param[in] VendorGuid Vendor GUID of authenticated Variable.
>- @param[in] Data Pointer to variable "certdb".
>- @param[in] DataSize Size of variable "certdb".
>- @param[out] CertOffset Offset of matching CertData, from starting of Data.
>- @param[out] CertDataSize Length of CertData in bytes.
>- @param[out] CertNodeOffset Offset of matching AUTH_CERT_DB_DATA , from
>- starting of Data.
>- @param[out] CertNodeSize Length of AUTH_CERT_DB_DATA in bytes.
>-
>- @retval EFI_INVALID_PARAMETER Any input parameter is invalid.
>- @retval EFI_NOT_FOUND Fail to find matching certs.
>- @retval EFI_SUCCESS Find matching certs and output parameters.
>-
>-**/
>-EFI_STATUS
>-FindCertsFromDb (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT8 *Data,
>- IN UINTN DataSize,
>- OUT UINT32 *CertOffset, OPTIONAL
>- OUT UINT32 *CertDataSize, OPTIONAL
>- OUT UINT32 *CertNodeOffset,OPTIONAL
>- OUT UINT32 *CertNodeSize OPTIONAL
>- )
>-{
>- UINT32 Offset;
>- AUTH_CERT_DB_DATA *Ptr;
>- UINT32 CertSize;
>- UINT32 NameSize;
>- UINT32 NodeSize;
>- UINT32 CertDbListSize;
>-
>- if ((VariableName == NULL) || (VendorGuid == NULL) || (Data == NULL)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // Check whether DataSize matches recorded CertDbListSize.
>- //
>- if (DataSize < sizeof (UINT32)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- CertDbListSize = ReadUnaligned32 ((UINT32 *) Data);
>-
>- if (CertDbListSize != (UINT32) DataSize) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- Offset = sizeof (UINT32);
>-
>- //
>- // Get corresponding certificates by VendorGuid and VariableName.
>- //
>- while (Offset < (UINT32) DataSize) {
>- Ptr = (AUTH_CERT_DB_DATA *) (Data + Offset);
>- //
>- // Check whether VendorGuid matches.
>- //
>- if (CompareGuid (&Ptr->VendorGuid, VendorGuid)) {
>- NodeSize = ReadUnaligned32 (&Ptr->CertNodeSize);
>- NameSize = ReadUnaligned32 (&Ptr->NameSize);
>- CertSize = ReadUnaligned32 (&Ptr->CertDataSize);
>-
>- if (NodeSize != sizeof (EFI_GUID) + sizeof (UINT32) * 3 + CertSize +
>- sizeof (CHAR16) * NameSize) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- Offset = Offset + sizeof (EFI_GUID) + sizeof (UINT32) * 3;
>- //
>- // Check whether VariableName matches.
>- //
>- if ((NameSize == StrLen (VariableName)) &&
>- (CompareMem (Data + Offset, VariableName, NameSize * sizeof (CHAR16)) == 0)) {
>- Offset = Offset + NameSize * sizeof (CHAR16);
>-
>- if (CertOffset != NULL) {
>- *CertOffset = Offset;
>- }
>-
>- if (CertDataSize != NULL) {
>- *CertDataSize = CertSize;
>- }
>-
>- if (CertNodeOffset != NULL) {
>- *CertNodeOffset = (UINT32) ((UINT8 *) Ptr - Data);
>- }
>-
>- if (CertNodeSize != NULL) {
>- *CertNodeSize = NodeSize;
>- }
>-
>- return EFI_SUCCESS;
>- } else {
>- Offset = Offset + NameSize * sizeof (CHAR16) + CertSize;
>- }
>- } else {
>- NodeSize = ReadUnaligned32 (&Ptr->CertNodeSize);
>- Offset = Offset + NodeSize;
>- }
>- }
>-
>- return EFI_NOT_FOUND;
>-}
>-
>-/**
>- Retrieve signer's certificates for common authenticated variable
>- by corresponding VariableName and VendorGuid from "certdb".
>-
>- @param[in] VariableName Name of authenticated Variable.
>- @param[in] VendorGuid Vendor GUID of authenticated Variable.
>- @param[out] CertData Pointer to signer's certificates.
>- @param[out] CertDataSize Length of CertData in bytes.
>-
>- @retval EFI_INVALID_PARAMETER Any input parameter is invalid.
>- @retval EFI_NOT_FOUND Fail to find "certdb" or matching certs.
>- @retval EFI_SUCCESS Get signer's certificates successfully.
>-
>-**/
>-EFI_STATUS
>-GetCertsFromDb (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- OUT UINT8 **CertData,
>- OUT UINT32 *CertDataSize
>- )
>-{
>- VARIABLE_POINTER_TRACK CertDbVariable;
>- EFI_STATUS Status;
>- UINT8 *Data;
>- UINTN DataSize;
>- UINT32 CertOffset;
>-
>- if ((VariableName == NULL) || (VendorGuid == NULL) || (CertData == NULL) || (CertDataSize == NULL)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // Get variable "certdb".
>- //
>- Status = FindVariable (
>- EFI_CERT_DB_NAME,
>- &gEfiCertDbGuid,
>- &CertDbVariable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- DataSize = DataSizeOfVariable (CertDbVariable.CurrPtr);
>- Data = GetVariableDataPtr (CertDbVariable.CurrPtr);
>- if ((DataSize == 0) || (Data == NULL)) {
>- ASSERT (FALSE);
>- return EFI_NOT_FOUND;
>- }
>-
>- Status = FindCertsFromDb (
>- VariableName,
>- VendorGuid,
>- Data,
>- DataSize,
>- &CertOffset,
>- CertDataSize,
>- NULL,
>- NULL
>- );
>-
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- *CertData = Data + CertOffset;
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Delete matching signer's certificates when deleting common authenticated
>- variable by corresponding VariableName and VendorGuid from "certdb".
>-
>- @param[in] VariableName Name of authenticated Variable.
>- @param[in] VendorGuid Vendor GUID of authenticated Variable.
>-
>- @retval EFI_INVALID_PARAMETER Any input parameter is invalid.
>- @retval EFI_NOT_FOUND Fail to find "certdb" or matching certs.
>- @retval EFI_OUT_OF_RESOURCES The operation is failed due to lack of resources.
>- @retval EFI_SUCCESS The operation is completed successfully.
>-
>-**/
>-EFI_STATUS
>-DeleteCertsFromDb (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- VARIABLE_POINTER_TRACK CertDbVariable;
>- EFI_STATUS Status;
>- UINT8 *Data;
>- UINTN DataSize;
>- UINT32 VarAttr;
>- UINT32 CertNodeOffset;
>- UINT32 CertNodeSize;
>- UINT8 *NewCertDb;
>- UINT32 NewCertDbSize;
>-
>- if ((VariableName == NULL) || (VendorGuid == NULL)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // Get variable "certdb".
>- //
>- Status = FindVariable (
>- EFI_CERT_DB_NAME,
>- &gEfiCertDbGuid,
>- &CertDbVariable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- DataSize = DataSizeOfVariable (CertDbVariable.CurrPtr);
>- Data = GetVariableDataPtr (CertDbVariable.CurrPtr);
>- if ((DataSize == 0) || (Data == NULL)) {
>- ASSERT (FALSE);
>- return EFI_NOT_FOUND;
>- }
>-
>- if (DataSize == sizeof (UINT32)) {
>- //
>- // There is no certs in certdb.
>- //
>- return EFI_SUCCESS;
>- }
>-
>- //
>- // Get corresponding cert node from certdb.
>- //
>- Status = FindCertsFromDb (
>- VariableName,
>- VendorGuid,
>- Data,
>- DataSize,
>- NULL,
>- NULL,
>- &CertNodeOffset,
>- &CertNodeSize
>- );
>-
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- if (DataSize < (CertNodeOffset + CertNodeSize)) {
>- return EFI_NOT_FOUND;
>- }
>-
>- //
>- // Construct new data content of variable "certdb".
>- //
>- NewCertDbSize = (UINT32) DataSize - CertNodeSize;
>- NewCertDb = (UINT8*) mCertDbStore;
>-
>- //
>- // Copy the DB entries before deleting node.
>- //
>- CopyMem (NewCertDb, Data, CertNodeOffset);
>- //
>- // Update CertDbListSize.
>- //
>- CopyMem (NewCertDb, &NewCertDbSize, sizeof (UINT32));
>- //
>- // Copy the DB entries after deleting node.
>- //
>- if (DataSize > (CertNodeOffset + CertNodeSize)) {
>- CopyMem (
>- NewCertDb + CertNodeOffset,
>- Data + CertNodeOffset + CertNodeSize,
>- DataSize - CertNodeOffset - CertNodeSize
>- );
>- }
>-
>- //
>- // Set "certdb".
>- //
>- VarAttr = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS;
>- Status = UpdateVariable (
>- EFI_CERT_DB_NAME,
>- &gEfiCertDbGuid,
>- NewCertDb,
>- NewCertDbSize,
>- VarAttr,
>- 0,
>- 0,
>- &CertDbVariable,
>- NULL
>- );
>-
>- return Status;
>-}
>-
>-/**
>- Insert signer's certificates for common authenticated variable with VariableName
>- and VendorGuid in AUTH_CERT_DB_DATA to "certdb".
>-
>- @param[in] VariableName Name of authenticated Variable.
>- @param[in] VendorGuid Vendor GUID of authenticated Variable.
>- @param[in] CertData Pointer to signer's certificates.
>- @param[in] CertDataSize Length of CertData in bytes.
>-
>- @retval EFI_INVALID_PARAMETER Any input parameter is invalid.
>- @retval EFI_ACCESS_DENIED An AUTH_CERT_DB_DATA entry with same VariableName
>- and VendorGuid already exists.
>- @retval EFI_OUT_OF_RESOURCES The operation is failed due to lack of resources.
>- @retval EFI_SUCCESS Insert an AUTH_CERT_DB_DATA entry to "certdb"
>-
>-**/
>-EFI_STATUS
>-InsertCertsToDb (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT8 *CertData,
>- IN UINTN CertDataSize
>- )
>-{
>- VARIABLE_POINTER_TRACK CertDbVariable;
>- EFI_STATUS Status;
>- UINT8 *Data;
>- UINTN DataSize;
>- UINT32 VarAttr;
>- UINT8 *NewCertDb;
>- UINT32 NewCertDbSize;
>- UINT32 CertNodeSize;
>- UINT32 NameSize;
>- AUTH_CERT_DB_DATA *Ptr;
>-
>- if ((VariableName == NULL) || (VendorGuid == NULL) || (CertData == NULL)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // Get variable "certdb".
>- //
>- Status = FindVariable (
>- EFI_CERT_DB_NAME,
>- &gEfiCertDbGuid,
>- &CertDbVariable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- DataSize = DataSizeOfVariable (CertDbVariable.CurrPtr);
>- Data = GetVariableDataPtr (CertDbVariable.CurrPtr);
>- if ((DataSize == 0) || (Data == NULL)) {
>- ASSERT (FALSE);
>- return EFI_NOT_FOUND;
>- }
>-
>- //
>- // Find whether matching cert node already exists in "certdb".
>- // If yes return error.
>- //
>- Status = FindCertsFromDb (
>- VariableName,
>- VendorGuid,
>- Data,
>- DataSize,
>- NULL,
>- NULL,
>- NULL,
>- NULL
>- );
>-
>- if (!EFI_ERROR (Status)) {
>- ASSERT (FALSE);
>- return EFI_ACCESS_DENIED;
>- }
>-
>- //
>- // Construct new data content of variable "certdb".
>- //
>- NameSize = (UINT32) StrLen (VariableName);
>- CertNodeSize = sizeof (AUTH_CERT_DB_DATA) + (UINT32) CertDataSize + NameSize * sizeof (CHAR16);
>- NewCertDbSize = (UINT32) DataSize + CertNodeSize;
>- if (NewCertDbSize > mMaxCertDbSize) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>- NewCertDb = (UINT8*) mCertDbStore;
>-
>- //
>- // Copy the DB entries before deleting node.
>- //
>- CopyMem (NewCertDb, Data, DataSize);
>- //
>- // Update CertDbListSize.
>- //
>- CopyMem (NewCertDb, &NewCertDbSize, sizeof (UINT32));
>- //
>- // Construct new cert node.
>- //
>- Ptr = (AUTH_CERT_DB_DATA *) (NewCertDb + DataSize);
>- CopyGuid (&Ptr->VendorGuid, VendorGuid);
>- CopyMem (&Ptr->CertNodeSize, &CertNodeSize, sizeof (UINT32));
>- CopyMem (&Ptr->NameSize, &NameSize, sizeof (UINT32));
>- CopyMem (&Ptr->CertDataSize, &CertDataSize, sizeof (UINT32));
>-
>- CopyMem (
>- (UINT8 *) Ptr + sizeof (AUTH_CERT_DB_DATA),
>- VariableName,
>- NameSize * sizeof (CHAR16)
>- );
>-
>- CopyMem (
>- (UINT8 *) Ptr + sizeof (AUTH_CERT_DB_DATA) + NameSize * sizeof (CHAR16),
>- CertData,
>- CertDataSize
>- );
>-
>- //
>- // Set "certdb".
>- //
>- VarAttr = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS;
>- Status = UpdateVariable (
>- EFI_CERT_DB_NAME,
>- &gEfiCertDbGuid,
>- NewCertDb,
>- NewCertDbSize,
>- VarAttr,
>- 0,
>- 0,
>- &CertDbVariable,
>- NULL
>- );
>-
>- return Status;
>-}
>-
>-/**
>- Process variable with EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS set
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>- @param[in] AuthVarType Verify against PK, KEK database, private database or certificate in data payload.
>- @param[out] VarDel Delete the variable or not.
>-
>- @retval EFI_INVALID_PARAMETER Invalid parameter.
>- @retval EFI_SECURITY_VIOLATION The variable does NOT pass the validation
>- check carried out by the firmware.
>- @retval EFI_OUT_OF_RESOURCES Failed to process variable due to lack
>- of resources.
>- @retval EFI_SUCCESS Variable pass validation successfully.
>-
>-**/
>-EFI_STATUS
>-VerifyTimeBasedPayload (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes,
>- IN AUTHVAR_TYPE AuthVarType,
>- OUT BOOLEAN *VarDel
>- )
>-{
>- UINT8 *RootCert;
>- UINT8 *SigData;
>- UINT8 *PayloadPtr;
>- UINTN RootCertSize;
>- UINTN Index;
>- UINTN CertCount;
>- UINTN PayloadSize;
>- UINT32 Attr;
>- UINT32 SigDataSize;
>- UINT32 KekDataSize;
>- BOOLEAN VerifyStatus;
>- EFI_STATUS Status;
>- EFI_SIGNATURE_LIST *CertList;
>- EFI_SIGNATURE_DATA *Cert;
>- VARIABLE_POINTER_TRACK KekVariable;
>- EFI_VARIABLE_AUTHENTICATION_2 *CertData;
>- UINT8 *NewData;
>- UINTN NewDataSize;
>- VARIABLE_POINTER_TRACK PkVariable;
>- UINT8 *Buffer;
>- UINTN Length;
>- UINT8 *SignerCerts;
>- UINTN CertStackSize;
>- UINT8 *CertsInCertDb;
>- UINT32 CertsSizeinDb;
>-
>- VerifyStatus = FALSE;
>- CertData = NULL;
>- NewData = NULL;
>- Attr = Attributes;
>- SignerCerts = NULL;
>- RootCert = NULL;
>- CertsInCertDb = NULL;
>-
>- //
>- // When the attribute EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS is
>- // set, then the Data buffer shall begin with an instance of a complete (and serialized)
>- // EFI_VARIABLE_AUTHENTICATION_2 descriptor. The descriptor shall be followed by the new
>- // variable value and DataSize shall reflect the combined size of the descriptor and the new
>- // variable value. The authentication descriptor is not part of the variable data and is not
>- // returned by subsequent calls to GetVariable().
>- //
>- CertData = (EFI_VARIABLE_AUTHENTICATION_2 *) Data;
>-
>- //
>- // Verify that Pad1, Nanosecond, TimeZone, Daylight and Pad2 components of the
>- // TimeStamp value are set to zero.
>- //
>- if ((CertData->TimeStamp.Pad1 != 0) ||
>- (CertData->TimeStamp.Nanosecond != 0) ||
>- (CertData->TimeStamp.TimeZone != 0) ||
>- (CertData->TimeStamp.Daylight != 0) ||
>- (CertData->TimeStamp.Pad2 != 0)) {
>- return EFI_SECURITY_VIOLATION;
>- }
>-
>- if ((Variable->CurrPtr != NULL) && ((Attributes & EFI_VARIABLE_APPEND_WRITE) == 0)) {
>- if (CompareTimeStamp (&CertData->TimeStamp, &Variable->CurrPtr->TimeStamp)) {
>- //
>- // TimeStamp check fail, suspicious replay attack, return EFI_SECURITY_VIOLATION.
>- //
>- return EFI_SECURITY_VIOLATION;
>- }
>- }
>-
>- //
>- // wCertificateType should be WIN_CERT_TYPE_EFI_GUID.
>- // Cert type should be EFI_CERT_TYPE_PKCS7_GUID.
>- //
>- if ((CertData->AuthInfo.Hdr.wCertificateType != WIN_CERT_TYPE_EFI_GUID) ||
>- !CompareGuid (&CertData->AuthInfo.CertType, &gEfiCertPkcs7Guid)) {
>- //
>- // Invalid AuthInfo type, return EFI_SECURITY_VIOLATION.
>- //
>- return EFI_SECURITY_VIOLATION;
>- }
>-
>- //
>- // Find out Pkcs7 SignedData which follows the EFI_VARIABLE_AUTHENTICATION_2 descriptor.
>- // AuthInfo.Hdr.dwLength is the length of the entire certificate, including the length of the header.
>- //
>- SigData = CertData->AuthInfo.CertData;
>- SigDataSize = CertData->AuthInfo.Hdr.dwLength - (UINT32) (OFFSET_OF (WIN_CERTIFICATE_UEFI_GUID, CertData));
>-
>- //
>- // Find out the new data payload which follows Pkcs7 SignedData directly.
>- //
>- PayloadPtr = SigData + SigDataSize;
>- PayloadSize = DataSize - OFFSET_OF_AUTHINFO2_CERT_DATA - (UINTN) SigDataSize;
>-
>- //
>- // Construct a serialization buffer of the values of the VariableName, VendorGuid and Attributes
>- // parameters of the SetVariable() call and the TimeStamp component of the
>- // EFI_VARIABLE_AUTHENTICATION_2 descriptor followed by the variable's new value
>- // i.e. (VariableName, VendorGuid, Attributes, TimeStamp, Data)
>- //
>- NewDataSize = PayloadSize + sizeof (EFI_TIME) + sizeof (UINT32) +
>- sizeof (EFI_GUID) + StrSize (VariableName) - sizeof (CHAR16);
>- //
>- // Here is to reuse scratch data area(at the end of volatile variable store)
>- // to reduce SMRAM consumption for SMM variable driver.
>- // The scratch buffer is enough to hold the serialized data and safe to use,
>- // because it will be used at here to do verification only first
>- // and then used in UpdateVariable() for a time based auth variable set.
>- //
>- NewData = (UINT8 *) GetEndPointer ((VARIABLE_STORE_HEADER *) ((UINTN) mVariableModuleGlobal-
>>VariableGlobal.VolatileVariableBase));
>-
>- Buffer = NewData;
>- Length = StrLen (VariableName) * sizeof (CHAR16);
>- CopyMem (Buffer, VariableName, Length);
>- Buffer += Length;
>-
>- Length = sizeof (EFI_GUID);
>- CopyMem (Buffer, VendorGuid, Length);
>- Buffer += Length;
>-
>- Length = sizeof (UINT32);
>- CopyMem (Buffer, &Attr, Length);
>- Buffer += Length;
>-
>- Length = sizeof (EFI_TIME);
>- CopyMem (Buffer, &CertData->TimeStamp, Length);
>- Buffer += Length;
>-
>- CopyMem (Buffer, PayloadPtr, PayloadSize);
>-
>- if (AuthVarType == AuthVarTypePk) {
>- //
>- // Verify that the signature has been made with the current Platform Key (no chaining for PK).
>- // First, get signer's certificates from SignedData.
>- //
>- VerifyStatus = Pkcs7GetSigners (
>- SigData,
>- SigDataSize,
>- &SignerCerts,
>- &CertStackSize,
>- &RootCert,
>- &RootCertSize
>- );
>- if (!VerifyStatus) {
>- goto Exit;
>- }
>-
>- //
>- // Second, get the current platform key from variable. Check whether it's identical with signer's certificates
>- // in SignedData. If not, return error immediately.
>- //
>- Status = FindVariable (
>- EFI_PLATFORM_KEY_NAME,
>- &gEfiGlobalVariableGuid,
>- &PkVariable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- VerifyStatus = FALSE;
>- goto Exit;
>- }
>- CertList = (EFI_SIGNATURE_LIST *) GetVariableDataPtr (PkVariable.CurrPtr);
>- Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) CertList + sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
>- if ((RootCertSize != (CertList->SignatureSize - (sizeof (EFI_SIGNATURE_DATA) - 1))) ||
>- (CompareMem (Cert->SignatureData, RootCert, RootCertSize) != 0)) {
>- VerifyStatus = FALSE;
>- goto Exit;
>- }
>-
>- //
>- // Verify Pkcs7 SignedData via Pkcs7Verify library.
>- //
>- VerifyStatus = Pkcs7Verify (
>- SigData,
>- SigDataSize,
>- RootCert,
>- RootCertSize,
>- NewData,
>- NewDataSize
>- );
>-
>- } else if (AuthVarType == AuthVarTypeKek) {
>-
>- //
>- // Get KEK database from variable.
>- //
>- Status = FindVariable (
>- EFI_KEY_EXCHANGE_KEY_NAME,
>- &gEfiGlobalVariableGuid,
>- &KekVariable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- //
>- // Ready to verify Pkcs7 SignedData. Go through KEK Signature Database to find out X.509 CertList.
>- //
>- KekDataSize = KekVariable.CurrPtr->DataSize;
>- CertList = (EFI_SIGNATURE_LIST *) GetVariableDataPtr (KekVariable.CurrPtr);
>- while ((KekDataSize > 0) && (KekDataSize >= CertList->SignatureListSize)) {
>- if (CompareGuid (&CertList->SignatureType, &gEfiCertX509Guid)) {
>- Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) CertList + sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
>- CertCount = (CertList->SignatureListSize - sizeof (EFI_SIGNATURE_LIST) - CertList->SignatureHeaderSize) / CertList-
>>SignatureSize;
>- for (Index = 0; Index < CertCount; Index++) {
>- //
>- // Iterate each Signature Data Node within this CertList for a verify
>- //
>- RootCert = Cert->SignatureData;
>- RootCertSize = CertList->SignatureSize - (sizeof (EFI_SIGNATURE_DATA) - 1);
>-
>- //
>- // Verify Pkcs7 SignedData via Pkcs7Verify library.
>- //
>- VerifyStatus = Pkcs7Verify (
>- SigData,
>- SigDataSize,
>- RootCert,
>- RootCertSize,
>- NewData,
>- NewDataSize
>- );
>- if (VerifyStatus) {
>- goto Exit;
>- }
>- Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) Cert + CertList->SignatureSize);
>- }
>- }
>- KekDataSize -= CertList->SignatureListSize;
>- CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList + CertList->SignatureListSize);
>- }
>- } else if (AuthVarType == AuthVarTypePriv) {
>-
>- //
>- // Process common authenticated variable except PK/KEK/DB/DBX/DBT.
>- // Get signer's certificates from SignedData.
>- //
>- VerifyStatus = Pkcs7GetSigners (
>- SigData,
>- SigDataSize,
>- &SignerCerts,
>- &CertStackSize,
>- &RootCert,
>- &RootCertSize
>- );
>- if (!VerifyStatus) {
>- goto Exit;
>- }
>-
>- //
>- // Get previously stored signer's certificates from certdb for existing
>- // variable. Check whether they are identical with signer's certificates
>- // in SignedData. If not, return error immediately.
>- //
>- if ((Variable->CurrPtr != NULL)) {
>- VerifyStatus = FALSE;
>-
>- Status = GetCertsFromDb (VariableName, VendorGuid, &CertsInCertDb, &CertsSizeinDb);
>- if (EFI_ERROR (Status)) {
>- goto Exit;
>- }
>-
>- if ((CertStackSize != CertsSizeinDb) ||
>- (CompareMem (SignerCerts, CertsInCertDb, CertsSizeinDb) != 0)) {
>- goto Exit;
>- }
>- }
>-
>- VerifyStatus = Pkcs7Verify (
>- SigData,
>- SigDataSize,
>- RootCert,
>- RootCertSize,
>- NewData,
>- NewDataSize
>- );
>- if (!VerifyStatus) {
>- goto Exit;
>- }
>-
>- //
>- // Delete signer's certificates when delete the common authenticated variable.
>- //
>- if ((PayloadSize == 0) && (Variable->CurrPtr != NULL) && ((Attributes & EFI_VARIABLE_APPEND_WRITE) == 0)) {
>- Status = DeleteCertsFromDb (VariableName, VendorGuid);
>- if (EFI_ERROR (Status)) {
>- VerifyStatus = FALSE;
>- goto Exit;
>- }
>- } else if (Variable->CurrPtr == NULL && PayloadSize != 0) {
>- //
>- // Insert signer's certificates when adding a new common authenticated variable.
>- //
>- Status = InsertCertsToDb (VariableName, VendorGuid, SignerCerts, CertStackSize);
>- if (EFI_ERROR (Status)) {
>- VerifyStatus = FALSE;
>- goto Exit;
>- }
>- }
>- } else if (AuthVarType == AuthVarTypePayload) {
>- CertList = (EFI_SIGNATURE_LIST *) PayloadPtr;
>- Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) CertList + sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
>- RootCert = Cert->SignatureData;
>- RootCertSize = CertList->SignatureSize - (sizeof (EFI_SIGNATURE_DATA) - 1);
>-
>- // Verify Pkcs7 SignedData via Pkcs7Verify library.
>- //
>- VerifyStatus = Pkcs7Verify (
>- SigData,
>- SigDataSize,
>- RootCert,
>- RootCertSize,
>- NewData,
>- NewDataSize
>- );
>- } else {
>- return EFI_SECURITY_VIOLATION;
>- }
>-
>-Exit:
>-
>- if (AuthVarType == AuthVarTypePk || AuthVarType == AuthVarTypePriv) {
>- Pkcs7FreeSigners (RootCert);
>- Pkcs7FreeSigners (SignerCerts);
>- }
>-
>- if (!VerifyStatus) {
>- return EFI_SECURITY_VIOLATION;
>- }
>-
>- Status = CheckSignatureListFormat(VariableName, VendorGuid, PayloadPtr, PayloadSize);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- if ((PayloadSize == 0) && (VarDel != NULL)) {
>- *VarDel = TRUE;
>- }
>-
>- //
>- // Final step: Update/Append Variable if it pass Pkcs7Verify
>- //
>- return UpdateVariable (
>- VariableName,
>- VendorGuid,
>- PayloadPtr,
>- PayloadSize,
>- Attributes,
>- 0,
>- 0,
>- Variable,
>- &CertData->TimeStamp
>- );
>-}
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.h
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.h
>deleted file mode 100644
>index 56def50..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/AuthService.h
>+++ /dev/null
>@@ -1,360 +0,0 @@
>-/** @file
>- The internal header file includes the common header files, defines
>- internal structure and functions used by AuthService module.
>-
>- Caution: This module requires additional review when modified.
>- This driver will have external input - variable data. It may be input in SMM mode.
>- This external input must be validated carefully to avoid security issue like
>- buffer overflow, integer overflow.
>- Variable attribute should also be checked to avoid authentication bypass.
>- The whole SMM authentication variable design relies on the integrity of flash part and SMM.
>- which is assumed to be protected by platform. All variable code and metadata in flash/SMM Memory
>- may not be modified without authorization. If platform fails to protect these resources,
>- the authentication service provided in this driver will be broken, and the behavior is undefined.
>-
>-Copyright (c) 2009 - 2015, 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
>-
>-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 _AUTHSERVICE_H_
>-#define _AUTHSERVICE_H_
>-
>-#define EFI_CERT_TYPE_RSA2048_SHA256_SIZE 256
>-#define EFI_CERT_TYPE_RSA2048_SIZE 256
>-
>-///
>-/// Size of AuthInfo prior to the data payload.
>-///
>-#define AUTHINFO_SIZE ((OFFSET_OF (EFI_VARIABLE_AUTHENTICATION, AuthInfo)) + \
>- (OFFSET_OF (WIN_CERTIFICATE_UEFI_GUID, CertData)) + \
>- sizeof (EFI_CERT_BLOCK_RSA_2048_SHA256))
>-
>-#define AUTHINFO2_SIZE(VarAuth2) ((OFFSET_OF (EFI_VARIABLE_AUTHENTICATION_2, AuthInfo)) + \
>- (UINTN) ((EFI_VARIABLE_AUTHENTICATION_2 *) (VarAuth2))->AuthInfo.Hdr.dwLength)
>-
>-#define OFFSET_OF_AUTHINFO2_CERT_DATA ((OFFSET_OF (EFI_VARIABLE_AUTHENTICATION_2, AuthInfo)) + \
>- (OFFSET_OF (WIN_CERTIFICATE_UEFI_GUID, CertData)))
>-
>-///
>-/// "AuthVarKeyDatabase" variable for the Public Key store.
>-///
>-#define AUTHVAR_KEYDB_NAME L"AuthVarKeyDatabase"
>-
>-///
>-/// "certdb" variable stores the signer's certificates for non PK/KEK/DB/DBX
>-/// variables with EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS set.
>-///
>-///
>-#define EFI_CERT_DB_NAME L"certdb"
>-
>-///
>-/// Struct to record signature requirement defined by UEFI spec.
>-/// For SigHeaderSize and SigDataSize, ((UINT32) ~0) means NO exact length requirement for this field.
>-///
>-typedef struct {
>- EFI_GUID SigType;
>- // Expected SignatureHeader size in Bytes.
>- UINT32 SigHeaderSize;
>- // Expected SignatureData size in Bytes.
>- UINT32 SigDataSize;
>-} EFI_SIGNATURE_ITEM;
>-
>-typedef enum {
>- AuthVarTypePk,
>- AuthVarTypeKek,
>- AuthVarTypePriv,
>- AuthVarTypePayload
>-} AUTHVAR_TYPE;
>-
>-#pragma pack(1)
>-typedef struct {
>- EFI_GUID VendorGuid;
>- UINT32 CertNodeSize;
>- UINT32 NameSize;
>- UINT32 CertDataSize;
>- /// CHAR16 VariableName[NameSize];
>- /// UINT8 CertData[CertDataSize];
>-} AUTH_CERT_DB_DATA;
>-#pragma pack()
>-
>-/**
>- Process variable with
>EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS/EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS set.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>-
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter
>- @return EFI_WRITE_PROTECTED Variable is write-protected and needs authentication with
>- EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS set.
>- @return EFI_SECURITY_VIOLATION The variable is with EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS
>- set, but the AuthInfo does NOT pass the validation
>- check carried out by the firmware.
>- @return EFI_SUCCESS Variable is not write-protected, or passed validation successfully.
>-
>-**/
>-EFI_STATUS
>-ProcessVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes
>- );
>-
>-/**
>- Update platform mode.
>-
>- @param[in] Mode SETUP_MODE or USER_MODE.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Update platform mode successfully.
>-
>-**/
>-EFI_STATUS
>-UpdatePlatformMode (
>- IN UINT32 Mode
>- );
>-
>-/**
>- Initializes for authenticated varibale service.
>-
>- @param[in] MaxAuthVariableSize Reflect the overhead associated with the saving
>- of a single EFI authenticated variable with the exception
>- of the overhead associated with the length
>- of the string name of the EFI variable.
>-
>- @retval EFI_SUCCESS Function successfully executed.
>- @retval EFI_OUT_OF_RESOURCES Fail to allocate enough memory resources.
>-
>-**/
>-EFI_STATUS
>-AutenticatedVariableServiceInitialize (
>- IN UINTN MaxAuthVariableSize
>- );
>-
>-/**
>- Initializes for cryptlib service before use, include register algrithm and allocate scratch.
>-
>-**/
>-VOID
>-CryptLibraryInitialize (
>- VOID
>- );
>-
>-/**
>- Check input data form to make sure it is a valid EFI_SIGNATURE_LIST for PK/KEK variable.
>-
>- @param[in] VariableName Name of Variable to be check.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Point to the variable data to be checked.
>- @param[in] DataSize Size of Data.
>-
>- @return EFI_INVALID_PARAMETER Invalid signature list format.
>- @return EFI_SUCCESS Passed signature list format check successfully.
>-
>-**/
>-EFI_STATUS
>-CheckSignatureListFormat(
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize
>- );
>-
>-/**
>- Process variable with platform key for verification.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>- @param[in] IsPk Indicate whether it is to process pk.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter
>- @return EFI_SECURITY_VIOLATION The variable does NOT pass the validation
>- check carried out by the firmware.
>- @return EFI_SUCCESS Variable passed validation successfully.
>-
>-**/
>-EFI_STATUS
>-ProcessVarWithPk (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes OPTIONAL,
>- IN BOOLEAN IsPk
>- );
>-
>-/**
>- Process variable with key exchange key for verification.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Variable The variable information that is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SECURITY_VIOLATION The variable does NOT pass the validation
>- check carried out by the firmware.
>- @return EFI_SUCCESS Variable passed validation successfully.
>-
>-**/
>-EFI_STATUS
>-ProcessVarWithKek (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes OPTIONAL
>- );
>-
>-/**
>- Merge two buffers which formatted as EFI_SIGNATURE_LIST. Only the new EFI_SIGNATURE_DATA
>- will be appended to the original EFI_SIGNATURE_LIST, duplicate EFI_SIGNATURE_DATA
>- will be ignored.
>-
>- @param[in, out] Data Pointer to original EFI_SIGNATURE_LIST.
>- @param[in] DataSize Size of Data buffer.
>- @param[in] FreeBufSize Size of free data buffer
>- @param[in] NewData Pointer to new EFI_SIGNATURE_LIST to be appended.
>- @param[in] NewDataSize Size of NewData buffer.
>- @param[out] MergedBufSize Size of the merged buffer
>-
>- @return EFI_BUFFER_TOO_SMALL if input Data buffer overflowed
>-
>-**/
>-EFI_STATUS
>-AppendSignatureList (
>- IN OUT VOID *Data,
>- IN UINTN DataSize,
>- IN UINTN FreeBufSize,
>- IN VOID *NewData,
>- IN UINTN NewDataSize,
>- OUT UINTN *MergedBufSize
>- );
>-
>-/**
>- Compare two EFI_TIME data.
>-
>-
>- @param FirstTime A pointer to the first EFI_TIME data.
>- @param SecondTime A pointer to the second EFI_TIME data.
>-
>- @retval TRUE The FirstTime is not later than the SecondTime.
>- @retval FALSE The FirstTime is later than the SecondTime.
>-
>-**/
>-BOOLEAN
>-CompareTimeStamp (
>- IN EFI_TIME *FirstTime,
>- IN EFI_TIME *SecondTime
>- );
>-
>-/**
>- Delete matching signer's certificates when deleting common authenticated
>- variable by corresponding VariableName and VendorGuid from "certdb".
>-
>- @param[in] VariableName Name of authenticated Variable.
>- @param[in] VendorGuid Vendor GUID of authenticated Variable.
>-
>- @retval EFI_INVALID_PARAMETER Any input parameter is invalid.
>- @retval EFI_NOT_FOUND Fail to find "certdb" or matching certs.
>- @retval EFI_OUT_OF_RESOURCES The operation is failed due to lack of resources.
>- @retval EFI_SUCCESS The operation is completed successfully.
>-
>-**/
>-EFI_STATUS
>-DeleteCertsFromDb (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- );
>-
>-/**
>- Process variable with EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS set
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Data Data pointer.
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Variable The variable information which is used to keep track of variable usage.
>- @param[in] Attributes Attribute value of the variable.
>- @param[in] AuthVarType Verify against PK or KEK database or private database.
>- @param[out] VarDel Delete the variable or not.
>-
>- @retval EFI_INVALID_PARAMETER Invalid parameter.
>- @retval EFI_SECURITY_VIOLATION The variable does NOT pass the validation
>- check carried out by the firmware.
>- @retval EFI_OUT_OF_RESOURCES Failed to process variable due to lack
>- of resources.
>- @retval EFI_SUCCESS Variable pass validation successfully.
>-
>-**/
>-EFI_STATUS
>-VerifyTimeBasedPayload (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN VARIABLE_POINTER_TRACK *Variable,
>- IN UINT32 Attributes,
>- IN AUTHVAR_TYPE AuthVarType,
>- OUT BOOLEAN *VarDel
>- );
>-
>-extern UINT8 *mPubKeyStore;
>-extern UINT8 *mCertDbStore;
>-extern UINT32 mPubKeyNumber;
>-extern VOID *mHashCtx;
>-
>-#endif
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Measurement.c
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/Measurement.c
>deleted file mode 100644
>index 1b625e7..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Measurement.c
>+++ /dev/null
>@@ -1,255 +0,0 @@
>-/** @file
>- Measure TrEE required variable.
>-
>-Copyright (c) 2013 - 2014, 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
>-
>-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 <PiDxe.h>
>-#include <Guid/ImageAuthentication.h>
>-#include <IndustryStandard/UefiTcgPlatform.h>
>-#include <Protocol/TrEEProtocol.h>
>-
>-#include <Library/UefiBootServicesTableLib.h>
>-#include <Library/UefiRuntimeServicesTableLib.h>
>-#include <Library/MemoryAllocationLib.h>
>-#include <Library/BaseMemoryLib.h>
>-#include <Library/DebugLib.h>
>-#include <Library/BaseLib.h>
>-#include <Library/TpmMeasurementLib.h>
>-
>-typedef struct {
>- CHAR16 *VariableName;
>- EFI_GUID *VendorGuid;
>-} VARIABLE_TYPE;
>-
>-VARIABLE_TYPE mVariableType[] = {
>- {EFI_SECURE_BOOT_MODE_NAME, &gEfiGlobalVariableGuid},
>- {EFI_PLATFORM_KEY_NAME, &gEfiGlobalVariableGuid},
>- {EFI_KEY_EXCHANGE_KEY_NAME, &gEfiGlobalVariableGuid},
>- {EFI_IMAGE_SECURITY_DATABASE, &gEfiImageSecurityDatabaseGuid},
>- {EFI_IMAGE_SECURITY_DATABASE1, &gEfiImageSecurityDatabaseGuid},
>-};
>-
>-/**
>- This function will return if this variable is SecureBootPolicy Variable.
>-
>- @param[in] VariableName A Null-terminated string that is the name of the vendor's variable.
>- @param[in] VendorGuid A unique identifier for the vendor.
>-
>- @retval TRUE This is SecureBootPolicy Variable
>- @retval FALSE This is not SecureBootPolicy Variable
>-**/
>-BOOLEAN
>-IsSecureBootPolicyVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- UINTN Index;
>-
>- for (Index = 0; Index < sizeof(mVariableType)/sizeof(mVariableType[0]); Index++) {
>- if ((StrCmp (VariableName, mVariableType[Index].VariableName) == 0) &&
>- (CompareGuid (VendorGuid, mVariableType[Index].VendorGuid))) {
>- return TRUE;
>- }
>- }
>- return FALSE;
>-}
>-
>-/**
>- Measure and log an EFI variable, and extend the measurement result into a specific PCR.
>-
>- @param[in] VarName A Null-terminated string that is the name of the vendor's variable.
>- @param[in] VendorGuid A unique identifier for the vendor.
>- @param[in] VarData The content of the variable data.
>- @param[in] VarSize The size of the variable data.
>-
>- @retval EFI_SUCCESS Operation completed successfully.
>- @retval EFI_OUT_OF_RESOURCES Out of memory.
>- @retval EFI_DEVICE_ERROR The operation was unsuccessful.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-MeasureVariable (
>- IN CHAR16 *VarName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *VarData,
>- IN UINTN VarSize
>- )
>-{
>- EFI_STATUS Status;
>- UINTN VarNameLength;
>- EFI_VARIABLE_DATA_TREE *VarLog;
>- UINT32 VarLogSize;
>-
>- ASSERT ((VarSize == 0 && VarData == NULL) || (VarSize != 0 && VarData != NULL));
>-
>- VarNameLength = StrLen (VarName);
>- VarLogSize = (UINT32)(sizeof (*VarLog) + VarNameLength * sizeof (*VarName) + VarSize
>- - sizeof (VarLog->UnicodeName) - sizeof (VarLog->VariableData));
>-
>- VarLog = (EFI_VARIABLE_DATA_TREE *) AllocateZeroPool (VarLogSize);
>- if (VarLog == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- CopyMem (&VarLog->VariableName, VendorGuid, sizeof(VarLog->VariableName));
>- VarLog->UnicodeNameLength = VarNameLength;
>- VarLog->VariableDataLength = VarSize;
>- CopyMem (
>- VarLog->UnicodeName,
>- VarName,
>- VarNameLength * sizeof (*VarName)
>- );
>- if (VarSize != 0) {
>- CopyMem (
>- (CHAR16 *)VarLog->UnicodeName + VarNameLength,
>- VarData,
>- VarSize
>- );
>- }
>-
>- DEBUG ((EFI_D_INFO, "AuthVariableDxe: MeasureVariable (Pcr - %x, EventType - %x, ", (UINTN)7,
>(UINTN)EV_EFI_VARIABLE_AUTHORITY));
>- DEBUG ((EFI_D_INFO, "VariableName - %s, VendorGuid - %g)\n", VarName, VendorGuid));
>-
>- Status = TpmMeasureAndLogData (
>- 7,
>- EV_EFI_VARIABLE_DRIVER_CONFIG,
>- VarLog,
>- VarLogSize,
>- VarLog,
>- VarLogSize
>- );
>- FreePool (VarLog);
>- return Status;
>-}
>-
>-/**
>- Returns the status whether get the variable success. The function retrieves
>- variable through the UEFI Runtime Service GetVariable(). The
>- returned buffer is allocated using AllocatePool(). The caller is responsible
>- for freeing this buffer with FreePool().
>-
>- This API is only invoked in boot time. It may NOT be invoked at runtime.
>-
>- @param[in] Name The pointer to a Null-terminated Unicode string.
>- @param[in] Guid The pointer to an EFI_GUID structure
>- @param[out] Value The buffer point saved the variable info.
>- @param[out] Size The buffer size of the variable.
>-
>- @return EFI_OUT_OF_RESOURCES Allocate buffer failed.
>- @return EFI_SUCCESS Find the specified variable.
>- @return Others Errors Return errors from call to gRT->GetVariable.
>-
>-**/
>-EFI_STATUS
>-InternalGetVariable (
>- IN CONST CHAR16 *Name,
>- IN CONST EFI_GUID *Guid,
>- OUT VOID **Value,
>- OUT UINTN *Size
>- )
>-{
>- EFI_STATUS Status;
>- UINTN BufferSize;
>-
>- //
>- // Try to get the variable size.
>- //
>- BufferSize = 0;
>- *Value = NULL;
>- if (Size != NULL) {
>- *Size = 0;
>- }
>-
>- Status = gRT->GetVariable ((CHAR16 *) Name, (EFI_GUID *) Guid, NULL, &BufferSize, *Value);
>- if (Status != EFI_BUFFER_TOO_SMALL) {
>- return Status;
>- }
>-
>- //
>- // Allocate buffer to get the variable.
>- //
>- *Value = AllocatePool (BufferSize);
>- ASSERT (*Value != NULL);
>- if (*Value == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- //
>- // Get the variable data.
>- //
>- Status = gRT->GetVariable ((CHAR16 *) Name, (EFI_GUID *) Guid, NULL, &BufferSize, *Value);
>- if (EFI_ERROR (Status)) {
>- FreePool(*Value);
>- *Value = NULL;
>- }
>-
>- if (Size != NULL) {
>- *Size = BufferSize;
>- }
>-
>- return Status;
>-}
>-
>-/**
>- SecureBoot Hook for SetVariable.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>-
>-**/
>-VOID
>-EFIAPI
>-SecureBootHook (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- EFI_STATUS Status;
>- UINTN VariableDataSize;
>- VOID *VariableData;
>-
>- if (!IsSecureBootPolicyVariable (VariableName, VendorGuid)) {
>- return ;
>- }
>-
>- //
>- // We should NOT use Data and DataSize here,because it may include signature,
>- // or is just partial with append attributes, or is deleted.
>- // We should GetVariable again, to get full variable content.
>- //
>- Status = InternalGetVariable (
>- VariableName,
>- VendorGuid,
>- &VariableData,
>- &VariableDataSize
>- );
>- if (EFI_ERROR (Status)) {
>- VariableData = NULL;
>- VariableDataSize = 0;
>- }
>-
>- Status = MeasureVariable (
>- VariableName,
>- VendorGuid,
>- VariableData,
>- VariableDataSize
>- );
>- DEBUG ((EFI_D_INFO, "MeasureBootPolicyVariable - %r\n", Status));
>-
>- if (VariableData != NULL) {
>- FreePool (VariableData);
>- }
>-
>- return ;
>-}
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Reclaim.c b/SecurityPkg/VariableAuthenticated/RuntimeDxe/Reclaim.c
>deleted file mode 100644
>index d79cd36..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Reclaim.c
>+++ /dev/null
>@@ -1,161 +0,0 @@
>-/** @file
>- Handles non-volatile variable store garbage collection, using FTW
>- (Fault Tolerant Write) protocol.
>-
>-Copyright (c) 2009 - 2014, 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
>-
>-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 "Variable.h"
>-
>-/**
>- Gets LBA of block and offset by given address.
>-
>- This function gets the Logical Block Address (LBA) of a firmware
>- volume block containing the given address, and the offset of the
>- address on the block.
>-
>- @param Address Address which should be contained
>- by returned FVB handle.
>- @param Lba Pointer to LBA for output.
>- @param Offset Pointer to offset for output.
>-
>- @retval EFI_SUCCESS LBA and offset successfully returned.
>- @retval EFI_NOT_FOUND Fail to find FVB handle by address.
>- @retval EFI_ABORTED Fail to find valid LBA and offset.
>-
>-**/
>-EFI_STATUS
>-GetLbaAndOffsetByAddress (
>- IN EFI_PHYSICAL_ADDRESS Address,
>- OUT EFI_LBA *Lba,
>- OUT UINTN *Offset
>- )
>-{
>- EFI_STATUS Status;
>- EFI_PHYSICAL_ADDRESS FvbBaseAddress;
>- EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL *Fvb;
>- EFI_FIRMWARE_VOLUME_HEADER *FwVolHeader;
>- EFI_FV_BLOCK_MAP_ENTRY *FvbMapEntry;
>- UINT32 LbaIndex;
>-
>- *Lba = (EFI_LBA) (-1);
>- *Offset = 0;
>- Fvb = NULL;
>-
>- //
>- // Get the proper FVB protocol.
>- //
>- Status = GetFvbInfoByAddress (Address, NULL, &Fvb);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- //
>- // Get the Base Address of FV.
>- //
>- Status = Fvb->GetPhysicalAddress (Fvb, &FvbBaseAddress);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- FwVolHeader = (EFI_FIRMWARE_VOLUME_HEADER *) ((UINTN) FvbBaseAddress);
>-
>- //
>- // Get the (LBA, Offset) of Address.
>- //
>- if ((FwVolHeader->FvLength) > (FwVolHeader->HeaderLength)) {
>- //
>- // BUGBUG: Assume one FV has one type of BlockLength.
>- //
>- FvbMapEntry = &FwVolHeader->BlockMap[0];
>- for (LbaIndex = 1; LbaIndex <= FvbMapEntry->NumBlocks; LbaIndex += 1) {
>- if (Address < (FvbBaseAddress + FvbMapEntry->Length * LbaIndex)) {
>- //
>- // Found the (Lba, Offset).
>- //
>- *Lba = LbaIndex - 1;
>- *Offset = (UINTN) (Address - (FvbBaseAddress + FvbMapEntry->Length * (LbaIndex - 1)));
>- return EFI_SUCCESS;
>- }
>- }
>- }
>-
>- return EFI_ABORTED;
>-}
>-
>-/**
>- Writes a buffer to variable storage space, in the working block.
>-
>- This function writes a buffer to variable storage space into a firmware
>- volume block device. The destination is specified by parameter
>- VariableBase. Fault Tolerant Write protocol is used for writing.
>-
>- @param VariableBase Base address of variable to write
>- @param VariableBuffer Point to the variable data buffer.
>-
>- @retval EFI_SUCCESS The function completed successfully.
>- @retval EFI_NOT_FOUND Fail to locate Fault Tolerant Write protocol.
>- @retval EFI_ABORTED The function could not complete successfully.
>-
>-**/
>-EFI_STATUS
>-FtwVariableSpace (
>- IN EFI_PHYSICAL_ADDRESS VariableBase,
>- IN VARIABLE_STORE_HEADER *VariableBuffer
>- )
>-{
>- EFI_STATUS Status;
>- EFI_HANDLE FvbHandle;
>- EFI_LBA VarLba;
>- UINTN VarOffset;
>- UINTN FtwBufferSize;
>- EFI_FAULT_TOLERANT_WRITE_PROTOCOL *FtwProtocol;
>-
>- //
>- // Locate fault tolerant write protocol.
>- //
>- Status = GetFtwProtocol((VOID **) &FtwProtocol);
>- if (EFI_ERROR (Status)) {
>- return EFI_NOT_FOUND;
>- }
>- //
>- // Locate Fvb handle by address.
>- //
>- Status = GetFvbInfoByAddress (VariableBase, &FvbHandle, NULL);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- //
>- // Get LBA and Offset by address.
>- //
>- Status = GetLbaAndOffsetByAddress (VariableBase, &VarLba, &VarOffset);
>- if (EFI_ERROR (Status)) {
>- return EFI_ABORTED;
>- }
>-
>- FtwBufferSize = ((VARIABLE_STORE_HEADER *) ((UINTN) VariableBase))->Size;
>- ASSERT (FtwBufferSize == VariableBuffer->Size);
>-
>- //
>- // FTW write record.
>- //
>- Status = FtwProtocol->Write (
>- FtwProtocol,
>- VarLba, // LBA
>- VarOffset, // Offset
>- FtwBufferSize, // NumBytes
>- NULL, // PrivateData NULL
>- FvbHandle, // Fvb Handle
>- (VOID *) VariableBuffer // write buffer
>- );
>-
>- return Status;
>-}
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VarCheck.c
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VarCheck.c
>deleted file mode 100644
>index 740632f..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VarCheck.c
>+++ /dev/null
>@@ -1,1264 +0,0 @@
>-/** @file
>- Implementation functions and structures for var check protocol.
>-
>-Copyright (c) 2015, 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
>-
>-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 "Variable.h"
>-#include "AuthService.h"
>-#include <Library/DevicePathLib.h>
>-
>-extern LIST_ENTRY mLockedVariableList;
>-extern BOOLEAN mEndOfDxe;
>-extern BOOLEAN mEnableLocking;
>-
>-#define VAR_CHECK_HANDLER_TABLE_SIZE 0x8
>-
>-UINT32 mNumberOfHandler = 0;
>-UINT32 mMaxNumberOfHandler = 0;
>-VAR_CHECK_SET_VARIABLE_CHECK_HANDLER *mHandlerTable = NULL;
>-
>-typedef struct {
>- LIST_ENTRY Link;
>- EFI_GUID Guid;
>- VAR_CHECK_VARIABLE_PROPERTY VariableProperty;
>- //CHAR16 *Name;
>-} VAR_CHECK_VARIABLE_ENTRY;
>-
>-LIST_ENTRY mVarCheckVariableList = INITIALIZE_LIST_HEAD_VARIABLE (mVarCheckVariableList);
>-
>-typedef
>-EFI_STATUS
>-(EFIAPI *INTERNAL_VAR_CHECK_FUNCTION) (
>- IN VAR_CHECK_VARIABLE_PROPERTY *Propery,
>- IN UINTN DataSize,
>- IN VOID *Data
>- );
>-
>-typedef struct {
>- CHAR16 *Name;
>- VAR_CHECK_VARIABLE_PROPERTY VariableProperty;
>- INTERNAL_VAR_CHECK_FUNCTION CheckFunction;
>-} UEFI_DEFINED_VARIABLE_ENTRY;
>-
>-/**
>- Internal check for load option.
>-
>- @param[in] VariablePropery Pointer to variable property.
>- @param[in] DataSize Data size.
>- @param[in] Data Pointer to data buffer.
>-
>- @retval EFI_SUCCESS The SetVariable check result was success.
>- @retval EFI_INVALID_PARAMETER The data buffer is not a valid load option.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckLoadOption (
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariablePropery,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- UINT16 FilePathListLength;
>- CHAR16 *Description;
>- EFI_DEVICE_PATH_PROTOCOL *FilePathList;
>-
>- FilePathListLength = *((UINT16 *) ((UINTN) Data + sizeof (UINT32)));
>-
>- //
>- // Check Description
>- //
>- Description = (CHAR16 *) ((UINTN) Data + sizeof (UINT32) + sizeof (UINT16));
>- while (Description < (CHAR16 *) ((UINTN) Data + DataSize)) {
>- if (*Description == L'\0') {
>- break;
>- }
>- Description++;
>- }
>- if ((UINTN) Description >= ((UINTN) Data + DataSize)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- Description++;
>-
>- //
>- // Check FilePathList
>- //
>- FilePathList = (EFI_DEVICE_PATH_PROTOCOL *) Description;
>- if ((UINTN) FilePathList > (MAX_ADDRESS - FilePathListLength)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- if (((UINTN) FilePathList + FilePathListLength) > ((UINTN) Data + DataSize)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- if (FilePathListLength < sizeof (EFI_DEVICE_PATH_PROTOCOL)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- if (!IsDevicePathValid (FilePathList, FilePathListLength)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Internal check for key option.
>-
>- @param[in] VariablePropery Pointer to variable property.
>- @param[in] DataSize Data size.
>- @param[in] Data Pointer to data buffer.
>-
>- @retval EFI_SUCCESS The SetVariable check result was success.
>- @retval EFI_INVALID_PARAMETER The data buffer is not a valid key option.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckKeyOption (
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariablePropery,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- if (((DataSize - sizeof (EFI_KEY_OPTION)) % sizeof (EFI_INPUT_KEY)) != 0) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Internal check for device path.
>-
>- @param[in] VariablePropery Pointer to variable property.
>- @param[in] DataSize Data size.
>- @param[in] Data Pointer to data buffer.
>-
>- @retval EFI_SUCCESS The SetVariable check result was success.
>- @retval EFI_INVALID_PARAMETER The data buffer is not a valid device path.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckDevicePath (
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariablePropery,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- if (!IsDevicePathValid ((EFI_DEVICE_PATH_PROTOCOL *) Data, DataSize)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Internal check for ASCII string.
>-
>- @param[in] VariablePropery Pointer to variable property.
>- @param[in] DataSize Data size.
>- @param[in] Data Pointer to data buffer.
>-
>- @retval EFI_SUCCESS The SetVariable check result was success.
>- @retval EFI_INVALID_PARAMETER The data buffer is not a Null-terminated ASCII string.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckAsciiString (
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariablePropery,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- CHAR8 *String;
>- UINTN Index;
>-
>- String = (CHAR8 *) Data;
>- if (String[DataSize - 1] == '\0') {
>- return EFI_SUCCESS;
>- } else {
>- for (Index = 1; Index < DataSize && (String[DataSize - 1 - Index] != '\0'); Index++);
>- if (Index == DataSize) {
>- return EFI_INVALID_PARAMETER;
>- }
>- }
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Internal check for size array.
>-
>- @param[in] VariablePropery Pointer to variable property.
>- @param[in] DataSize Data size.
>- @param[in] Data Pointer to data buffer.
>-
>- @retval EFI_SUCCESS The SetVariable check result was success.
>- @retval EFI_INVALID_PARAMETER The DataSize is not size array.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckSizeArray (
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariablePropery,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- if ((DataSize % VariablePropery->MinSize) != 0) {
>- return EFI_INVALID_PARAMETER;
>- }
>- return EFI_SUCCESS;
>-}
>-
>-//
>-// To prevent name collisions with possible future globally defined variables,
>-// other internal firmware data variables that are not defined here must be
>-// saved with a unique VendorGuid other than EFI_GLOBAL_VARIABLE or
>-// any other GUID defined by the UEFI Specification. Implementations must
>-// only permit the creation of variables with a UEFI Specification-defined
>-// VendorGuid when these variables are documented in the UEFI Specification.
>-//
>-UEFI_DEFINED_VARIABLE_ENTRY mGlobalVariableList[] = {
>- {
>- EFI_LANG_CODES_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- InternalVarCheckAsciiString
>- },
>- {
>- EFI_LANG_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- InternalVarCheckAsciiString
>- },
>- {
>- EFI_TIME_OUT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT16),
>- sizeof (UINT16)
>- },
>- NULL
>- },
>- {
>- EFI_PLATFORM_LANG_CODES_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- InternalVarCheckAsciiString
>- },
>- {
>- EFI_PLATFORM_LANG_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- InternalVarCheckAsciiString
>- },
>- {
>- EFI_CON_IN_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (EFI_DEVICE_PATH_PROTOCOL),
>- MAX_UINTN
>- },
>- InternalVarCheckDevicePath
>- },
>- {
>- EFI_CON_OUT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (EFI_DEVICE_PATH_PROTOCOL),
>- MAX_UINTN
>- },
>- InternalVarCheckDevicePath
>- },
>- {
>- EFI_ERR_OUT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (EFI_DEVICE_PATH_PROTOCOL),
>- MAX_UINTN
>- },
>- InternalVarCheckDevicePath
>- },
>- {
>- EFI_CON_IN_DEV_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (EFI_DEVICE_PATH_PROTOCOL),
>- MAX_UINTN
>- },
>- InternalVarCheckDevicePath
>- },
>- {
>- EFI_CON_OUT_DEV_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (EFI_DEVICE_PATH_PROTOCOL),
>- MAX_UINTN
>- },
>- InternalVarCheckDevicePath
>- },
>- {
>- EFI_ERR_OUT_DEV_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (EFI_DEVICE_PATH_PROTOCOL),
>- MAX_UINTN
>- },
>- InternalVarCheckDevicePath
>- },
>- {
>- EFI_BOOT_ORDER_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT16),
>- MAX_UINTN
>- },
>- InternalVarCheckSizeArray
>- },
>- {
>- EFI_BOOT_NEXT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT16),
>- sizeof (UINT16)
>- },
>- NULL
>- },
>- {
>- EFI_BOOT_CURRENT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (UINT16),
>- sizeof (UINT16)
>- },
>- NULL
>- },
>- {
>- EFI_BOOT_OPTION_SUPPORT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (UINT32),
>- sizeof (UINT32)
>- },
>- NULL
>- },
>- {
>- EFI_DRIVER_ORDER_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT16),
>- MAX_UINTN
>- },
>- InternalVarCheckSizeArray
>- },
>- {
>- EFI_SYS_PREP_ORDER_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT16),
>- MAX_UINTN
>- },
>- InternalVarCheckSizeArray
>- },
>- {
>- EFI_HW_ERR_REC_SUPPORT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT16),
>- sizeof (UINT16)
>- },
>- NULL
>- },
>- {
>- EFI_SETUP_MODE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (UINT8),
>- sizeof (UINT8)
>- },
>- NULL
>- },
>- {
>- EFI_KEY_EXCHANGE_KEY_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_PLATFORM_KEY_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_SIGNATURE_SUPPORT_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (EFI_GUID),
>- MAX_UINTN
>- },
>- InternalVarCheckSizeArray
>- },
>- {
>- EFI_SECURE_BOOT_MODE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (UINT8),
>- sizeof (UINT8)
>- },
>- NULL
>- },
>- {
>- EFI_KEK_DEFAULT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_PK_DEFAULT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_DB_DEFAULT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_DBX_DEFAULT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_DBT_DEFAULT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_OS_INDICATIONS_SUPPORT_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (UINT64),
>- sizeof (UINT64)
>- },
>- NULL
>- },
>- {
>- EFI_OS_INDICATIONS_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT64),
>- sizeof (UINT64)
>- },
>- NULL
>- },
>- {
>- EFI_VENDOR_KEYS_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_BS_RT,
>- sizeof (UINT8),
>- sizeof (UINT8)
>- },
>- NULL
>- },
>-};
>-UEFI_DEFINED_VARIABLE_ENTRY mGlobalVariableList2[] = {
>- {
>- L"Boot####",
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT32) + sizeof (UINT16),
>- MAX_UINTN
>- },
>- InternalVarCheckLoadOption
>- },
>- {
>- L"Driver####",
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT32) + sizeof (UINT16),
>- MAX_UINTN
>- },
>- InternalVarCheckLoadOption
>- },
>- {
>- L"SysPrep####",
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (UINT32) + sizeof (UINT16),
>- MAX_UINTN
>- },
>- InternalVarCheckLoadOption
>- },
>- {
>- L"Key####",
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (EFI_KEY_OPTION),
>- sizeof (EFI_KEY_OPTION) + 3 * sizeof (EFI_INPUT_KEY)
>- },
>- InternalVarCheckKeyOption
>- },
>-};
>-
>-//
>-// EFI_IMAGE_SECURITY_DATABASE_GUID
>-//
>-UEFI_DEFINED_VARIABLE_ENTRY mImageSecurityVariableList[] = {
>- {
>- EFI_IMAGE_SECURITY_DATABASE,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_IMAGE_SECURITY_DATABASE1,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>- {
>- EFI_IMAGE_SECURITY_DATABASE2,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AT,
>- 1,
>- MAX_UINTN
>- },
>- NULL
>- },
>-};
>-
>-typedef struct {
>- EFI_GUID *Guid;
>- CHAR16 *Name;
>- VAR_CHECK_VARIABLE_PROPERTY VariableProperty;
>- INTERNAL_VAR_CHECK_FUNCTION CheckFunction;
>-} VARIABLE_DRIVER_VARIABLE_ENTRY;
>-
>-VARIABLE_DRIVER_VARIABLE_ENTRY mVariableDriverVariableList[] = {
>- {
>- &gEfiSecureBootEnableDisableGuid,
>- EFI_SECURE_BOOT_ENABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS,
>- sizeof (UINT8),
>- sizeof (UINT8)
>- }
>- },
>- {
>- &gEfiCustomModeEnableGuid,
>- EFI_CUSTOM_MODE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- 0,
>- VARIABLE_ATTRIBUTE_NV_BS,
>- sizeof (UINT8),
>- sizeof (UINT8)
>- }
>- },
>- {
>- &gEfiVendorKeysNvGuid,
>- EFI_VENDOR_KEYS_NV_VARIABLE_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AT,
>- sizeof (UINT8),
>- sizeof (UINT8)
>- }
>- },
>- {
>- &gEfiAuthenticatedVariableGuid,
>- AUTHVAR_KEYDB_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AW,
>- sizeof (UINT8),
>- MAX_UINTN
>- }
>- },
>- {
>- &gEfiCertDbGuid,
>- EFI_CERT_DB_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_NV_BS_RT_AT,
>- sizeof (UINT32),
>- MAX_UINTN
>- }
>- },
>- {
>- &gEdkiiVarErrorFlagGuid,
>- VAR_ERROR_FLAG_NAME,
>- {
>- VAR_CHECK_VARIABLE_PROPERTY_REVISION,
>- VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY,
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- sizeof (VAR_ERROR_FLAG),
>- sizeof (VAR_ERROR_FLAG)
>- }
>- },
>-};
>-
>-/**
>- Get UEFI defined global variable or image security database variable property.
>- The code will check if variable guid is global variable or image security database guid first.
>- If yes, further check if variable name is in mGlobalVariableList, mGlobalVariableList2 or mImageSecurityVariableList.
>-
>- @param[in] VariableName Pointer to variable name.
>- @param[in] VendorGuid Variable Vendor Guid.
>- @param[in] WildcardMatch Try wildcard match or not.
>- @param[out] VariableProperty Pointer to variable property.
>- @param[out] VarCheckFunction Pointer to check function.
>-
>- @retval EFI_SUCCESS Variable is not global variable or image security database variable.
>- @retval EFI_INVALID_PARAMETER Variable is global variable or image security database variable, but variable name is not in the lists.
>-
>-**/
>-EFI_STATUS
>-GetUefiDefinedVariableProperty (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN BOOLEAN WildcardMatch,
>- OUT VAR_CHECK_VARIABLE_PROPERTY **VariableProperty,
>- OUT INTERNAL_VAR_CHECK_FUNCTION *VarCheckFunction OPTIONAL
>- )
>-{
>- UINTN Index;
>- UINTN NameLength;
>-
>- if (CompareGuid (VendorGuid, &gEfiGlobalVariableGuid)) {
>- //
>- // Try list 1, exactly match.
>- //
>- for (Index = 0; Index < sizeof (mGlobalVariableList)/sizeof (mGlobalVariableList[0]); Index++) {
>- if (StrCmp (mGlobalVariableList[Index].Name, VariableName) == 0) {
>- if (VarCheckFunction != NULL) {
>- *VarCheckFunction = mGlobalVariableList[Index].CheckFunction;
>- }
>- *VariableProperty = &mGlobalVariableList[Index].VariableProperty;
>- return EFI_SUCCESS;
>- }
>- }
>-
>- //
>- // Try list 2.
>- //
>- NameLength = StrLen (VariableName) - 4;
>- for (Index = 0; Index < sizeof (mGlobalVariableList2)/sizeof (mGlobalVariableList2[0]); Index++) {
>- if (WildcardMatch) {
>- if ((StrLen (VariableName) == StrLen (mGlobalVariableList2[Index].Name)) &&
>- (StrnCmp (mGlobalVariableList2[Index].Name, VariableName, NameLength) == 0) &&
>- IsHexaDecimalDigitCharacter (VariableName[NameLength]) &&
>- IsHexaDecimalDigitCharacter (VariableName[NameLength + 1]) &&
>- IsHexaDecimalDigitCharacter (VariableName[NameLength + 2]) &&
>- IsHexaDecimalDigitCharacter (VariableName[NameLength + 3])) {
>- if (VarCheckFunction != NULL) {
>- *VarCheckFunction = mGlobalVariableList2[Index].CheckFunction;
>- }
>- *VariableProperty = &mGlobalVariableList2[Index].VariableProperty;
>- return EFI_SUCCESS;
>- }
>- }
>- if (StrCmp (mGlobalVariableList2[Index].Name, VariableName) == 0) {
>- if (VarCheckFunction != NULL) {
>- *VarCheckFunction = mGlobalVariableList2[Index].CheckFunction;
>- }
>- *VariableProperty = &mGlobalVariableList2[Index].VariableProperty;
>- return EFI_SUCCESS;
>- }
>- }
>-
>- //
>- // The variable name is not in the lists.
>- //
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (CompareGuid (VendorGuid, &gEfiImageSecurityDatabaseGuid)){
>- for (Index = 0; Index < sizeof (mImageSecurityVariableList)/sizeof (mImageSecurityVariableList[0]); Index++) {
>- if (StrCmp (mImageSecurityVariableList[Index].Name, VariableName) == 0) {
>- if (VarCheckFunction != NULL) {
>- *VarCheckFunction = mImageSecurityVariableList[Index].CheckFunction;
>- }
>- *VariableProperty = &mImageSecurityVariableList[Index].VariableProperty;
>- return EFI_SUCCESS;
>- }
>- }
>-
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // It is not global variable or image security database variable.
>- //
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Get variable property for variables managed by Varaible driver.
>-
>- @param[in] VariableName Pointer to variable name.
>- @param[in] VendorGuid Variable Vendor Guid.
>-
>- @return Pointer to variable property.
>-
>-**/
>-VAR_CHECK_VARIABLE_PROPERTY *
>-GetVariableDriverVariableProperty (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- UINTN Index;
>-
>- for (Index = 0; Index < sizeof (mVariableDriverVariableList)/sizeof (mVariableDriverVariableList[0]); Index++) {
>- if ((CompareGuid (mVariableDriverVariableList[Index].Guid, VendorGuid)) && (StrCmp (mVariableDriverVariableList[Index].Name,
>VariableName) == 0)) {
>- return &mVariableDriverVariableList[Index].VariableProperty;
>- }
>- }
>-
>- return NULL;
>-}
>-
>-/**
>- Internal SetVariable check.
>-
>- @param[in] VariableName Name of Variable to set.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Attributes Attribute value of the variable.
>- @param[in] DataSize Size of Data to set.
>- @param[in] Data Data pointer.
>-
>- @retval EFI_SUCCESS The SetVariable check result was success.
>- @retval EFI_INVALID_PARAMETER An invalid combination of attribute bits, name, and GUID was supplied,
>- or the DataSize exceeds the minimum or maximum allowed,
>- or the Data value is not following UEFI spec for UEFI defined variables.
>- @retval EFI_WRITE_PROTECTED The variable in question is read-only.
>- @retval Others The return status from check handler.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckSetVariableCheck (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT32 Attributes,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- EFI_STATUS Status;
>- UINTN Index;
>- LIST_ENTRY *Link;
>- VAR_CHECK_VARIABLE_ENTRY *Entry;
>- CHAR16 *Name;
>- VAR_CHECK_VARIABLE_PROPERTY *Property;
>- INTERNAL_VAR_CHECK_FUNCTION VarCheckFunction;
>-
>- if (!mEndOfDxe) {
>- //
>- // Only do check after End Of Dxe.
>- //
>- return EFI_SUCCESS;
>- }
>-
>- Property = NULL;
>- VarCheckFunction = NULL;
>-
>- for ( Link = GetFirstNode (&mVarCheckVariableList)
>- ; !IsNull (&mVarCheckVariableList, Link)
>- ; Link = GetNextNode (&mVarCheckVariableList, Link)
>- ) {
>- Entry = BASE_CR (Link, VAR_CHECK_VARIABLE_ENTRY, Link);
>- Name = (CHAR16 *) ((UINTN) Entry + sizeof (*Entry));
>- if (CompareGuid (&Entry->Guid, VendorGuid) && (StrCmp (Name, VariableName) == 0)) {
>- Property = &Entry->VariableProperty;
>- break;
>- }
>- }
>- if (Property == NULL) {
>- Property = GetVariableDriverVariableProperty (VariableName, VendorGuid);
>- }
>- if (Property == NULL) {
>- Status = GetUefiDefinedVariableProperty (VariableName, VendorGuid, TRUE, &Property, &VarCheckFunction);
>- if (EFI_ERROR (Status)) {
>- DEBUG ((EFI_D_INFO, "[Variable]: Var Check UEFI defined variable fail %r - %g:%s\n", Status, VendorGuid, VariableName));
>- return Status;
>- }
>- }
>- if (Property != NULL) {
>- if (mEnableLocking && ((Property->Property & VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY) != 0)) {
>- DEBUG ((EFI_D_INFO, "[Variable]: Var Check ReadOnly variable fail %r - %g:%s\n", EFI_WRITE_PROTECTED, VendorGuid,
>VariableName));
>- return EFI_WRITE_PROTECTED;
>- }
>- if (!((((Attributes & EFI_VARIABLE_APPEND_WRITE) == 0) && (DataSize == 0)) || (Attributes == 0))) {
>- //
>- // Not to delete variable.
>- //
>- if ((Attributes & (~EFI_VARIABLE_APPEND_WRITE)) != Property->Attributes) {
>- DEBUG ((EFI_D_INFO, "[Variable]: Var Check Attributes(0x%08x to 0x%08x) fail %r - %g:%s\n", Property->Attributes, Attributes,
>EFI_INVALID_PARAMETER, VendorGuid, VariableName));
>- return EFI_INVALID_PARAMETER;
>- }
>- if (DataSize != 0) {
>- if ((DataSize < Property->MinSize) || (DataSize > Property->MaxSize)) {
>- DEBUG ((EFI_D_INFO, "[Variable]: Var Check DataSize fail(0x%x not in 0x%x - 0x%x) %r - %g:%s\n", DataSize, Property->MinSize,
>Property->MaxSize, EFI_INVALID_PARAMETER, VendorGuid, VariableName));
>- return EFI_INVALID_PARAMETER;
>- }
>- if (VarCheckFunction != NULL) {
>- Status = VarCheckFunction (
>- Property,
>- DataSize,
>- Data
>- );
>- if (EFI_ERROR (Status)) {
>- DEBUG ((EFI_D_INFO, "[Variable]: Internal Var Check function fail %r - %g:%s\n", Status, VendorGuid, VariableName));
>- return Status;
>- }
>- }
>- }
>- }
>- }
>-
>- for (Index = 0; Index < mNumberOfHandler; Index ++) {
>- Status = mHandlerTable[Index] (
>- VariableName,
>- VendorGuid,
>- Attributes,
>- DataSize,
>- Data
>- );
>- if (EFI_ERROR (Status)) {
>- DEBUG ((EFI_D_INFO, "[Variable]: Var Check handler fail %r - %g:%s\n", Status, VendorGuid, VariableName));
>- return Status;
>- }
>- }
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Reallocates more global memory to store the registered handler list.
>-
>- @retval RETURN_SUCCESS Reallocate memory successfully.
>- @retval RETURN_OUT_OF_RESOURCES No enough memory to allocate.
>-
>-**/
>-RETURN_STATUS
>-EFIAPI
>-ReallocateHandlerTable (
>- VOID
>- )
>-{
>- VAR_CHECK_SET_VARIABLE_CHECK_HANDLER *HandlerTable;
>-
>- //
>- // Reallocate memory for check handler table.
>- //
>- HandlerTable = ReallocateRuntimePool (
>- mMaxNumberOfHandler * sizeof (VAR_CHECK_SET_VARIABLE_CHECK_HANDLER),
>- (mMaxNumberOfHandler + VAR_CHECK_HANDLER_TABLE_SIZE) * sizeof (VAR_CHECK_SET_VARIABLE_CHECK_HANDLER),
>- mHandlerTable
>- );
>-
>- //
>- // No enough resource to allocate.
>- //
>- if (HandlerTable == NULL) {
>- return RETURN_OUT_OF_RESOURCES;
>- }
>-
>- mHandlerTable = HandlerTable;
>- //
>- // Increase max handler number.
>- //
>- mMaxNumberOfHandler = mMaxNumberOfHandler + VAR_CHECK_HANDLER_TABLE_SIZE;
>- return RETURN_SUCCESS;
>-}
>-
>-/**
>- Register SetVariable check handler.
>-
>- @param[in] Handler Pointer to check handler.
>-
>- @retval EFI_SUCCESS The SetVariable check handler was registered successfully.
>- @retval EFI_INVALID_PARAMETER Handler is NULL.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource for the SetVariable check handler register request.
>- @retval EFI_UNSUPPORTED This interface is not implemented.
>- For example, it is unsupported in VarCheck protocol if both VarCheck and SmmVarCheck protocols are present.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckRegisterSetVariableCheckHandler (
>- IN VAR_CHECK_SET_VARIABLE_CHECK_HANDLER Handler
>- )
>-{
>- EFI_STATUS Status;
>-
>- if (Handler == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (mEndOfDxe) {
>- return EFI_ACCESS_DENIED;
>- }
>-
>- DEBUG ((EFI_D_INFO, "RegisterSetVariableCheckHandler - 0x%x\n", Handler));
>-
>- //
>- // Check whether the handler list is enough to store new handler.
>- //
>- if (mNumberOfHandler == mMaxNumberOfHandler) {
>- //
>- // Allocate more resources for new handler.
>- //
>- Status = ReallocateHandlerTable();
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- }
>-
>- //
>- // Register new handler into the handler list.
>- //
>- mHandlerTable[mNumberOfHandler] = Handler;
>- mNumberOfHandler ++;
>-
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Variable property get function.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[in] WildcardMatch Try wildcard match or not.
>-
>- @return Pointer to the property of variable specified by the Name and Guid.
>-
>-**/
>-VAR_CHECK_VARIABLE_PROPERTY *
>-VariablePropertyGetFunction (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- IN BOOLEAN WildcardMatch
>- )
>-{
>- LIST_ENTRY *Link;
>- VAR_CHECK_VARIABLE_ENTRY *Entry;
>- CHAR16 *VariableName;
>- VAR_CHECK_VARIABLE_PROPERTY *Property;
>-
>- for ( Link = GetFirstNode (&mVarCheckVariableList)
>- ; !IsNull (&mVarCheckVariableList, Link)
>- ; Link = GetNextNode (&mVarCheckVariableList, Link)
>- ) {
>- Entry = BASE_CR (Link, VAR_CHECK_VARIABLE_ENTRY, Link);
>- VariableName = (CHAR16 *) ((UINTN) Entry + sizeof (*Entry));
>- if (CompareGuid (&Entry->Guid, Guid) && (StrCmp (VariableName, Name) == 0)) {
>- return &Entry->VariableProperty;
>- }
>- }
>-
>- Property = GetVariableDriverVariableProperty (Name, Guid);
>- if (Property == NULL) {
>- GetUefiDefinedVariableProperty (Name, Guid, WildcardMatch, &Property, NULL);
>- }
>-
>- return Property;
>-}
>-
>-/**
>- Variable property set.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[in] VariableProperty Pointer to the input variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was set successfully.
>- @retval EFI_INVALID_PARAMETER Name, Guid or VariableProperty is NULL, or Name is an empty string,
>- or the fields of VariableProperty are not valid.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource for the variable property set request.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckVariablePropertySet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- )
>-{
>- EFI_STATUS Status;
>- VAR_CHECK_VARIABLE_ENTRY *Entry;
>- CHAR16 *VariableName;
>- VAR_CHECK_VARIABLE_PROPERTY *Property;
>-
>- if (Name == NULL || Name[0] == 0 || Guid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (VariableProperty == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (VariableProperty->Revision != VAR_CHECK_VARIABLE_PROPERTY_REVISION) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (mEndOfDxe) {
>- return EFI_ACCESS_DENIED;
>- }
>-
>- Status = EFI_SUCCESS;
>-
>- AcquireLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- Property = VariablePropertyGetFunction (Name, Guid, FALSE);
>- if (Property != NULL) {
>- CopyMem (Property, VariableProperty, sizeof (*VariableProperty));
>- } else {
>- Entry = AllocateRuntimeZeroPool (sizeof (*Entry) + StrSize (Name));
>- if (Entry == NULL) {
>- Status = EFI_OUT_OF_RESOURCES;
>- goto Done;
>- }
>- VariableName = (CHAR16 *) ((UINTN) Entry + sizeof (*Entry));
>- StrnCpy (VariableName, Name, StrLen (Name));
>- CopyGuid (&Entry->Guid, Guid);
>- CopyMem (&Entry->VariableProperty, VariableProperty, sizeof (*VariableProperty));
>- InsertTailList (&mVarCheckVariableList, &Entry->Link);
>- }
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- return Status;
>-}
>-
>-/**
>- Internal variable property get.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[out] VariableProperty Pointer to the output variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was got successfully.
>- @retval EFI_NOT_FOUND The property of variable specified by the Name and Guid was not found.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckVariablePropertyGet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- OUT VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- )
>-{
>- LIST_ENTRY *Link;
>- VARIABLE_ENTRY *Entry;
>- CHAR16 *VariableName;
>- BOOLEAN Found;
>- VAR_CHECK_VARIABLE_PROPERTY *Property;
>-
>- Found = FALSE;
>-
>- Property = VariablePropertyGetFunction (Name, Guid, TRUE);
>- if (Property != NULL) {
>- CopyMem (VariableProperty, Property, sizeof (*VariableProperty));
>- Found = TRUE;
>- }
>-
>- for ( Link = GetFirstNode (&mLockedVariableList)
>- ; !IsNull (&mLockedVariableList, Link)
>- ; Link = GetNextNode (&mLockedVariableList, Link)
>- ) {
>- Entry = BASE_CR (Link, VARIABLE_ENTRY, Link);
>- VariableName = (CHAR16 *) ((UINTN) Entry + sizeof (*Entry));
>- if (CompareGuid (&Entry->Guid, Guid) && (StrCmp (VariableName, Name) == 0)) {
>- VariableProperty->Property |= VAR_CHECK_VARIABLE_PROPERTY_READ_ONLY;
>- if (!Found) {
>- VariableProperty->Revision = VAR_CHECK_VARIABLE_PROPERTY_REVISION;
>- Found = TRUE;
>- }
>- }
>- }
>-
>- return (Found ? EFI_SUCCESS : EFI_NOT_FOUND);
>-}
>-
>-/**
>- Variable property get.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[out] VariableProperty Pointer to the output variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was got successfully.
>- @retval EFI_INVALID_PARAMETER Name, Guid or VariableProperty is NULL, or Name is an empty string.
>- @retval EFI_NOT_FOUND The property of variable specified by the Name and Guid was not found.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckVariablePropertyGet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- OUT VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- )
>-{
>- EFI_STATUS Status;
>-
>- if (Name == NULL || Name[0] == 0 || Guid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (VariableProperty == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- Status = InternalVarCheckVariablePropertyGet (Name, Guid, VariableProperty);
>-
>- ReleaseLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- return Status;
>-}
>-
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.c b/SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.c
>deleted file mode 100644
>index 15d0531..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.c
>+++ /dev/null
>@@ -1,4170 +0,0 @@
>-/** @file
>- The common variable operation routines shared by DXE_RUNTIME variable
>- module and DXE_SMM variable module.
>-
>- Caution: This module requires additional review when modified.
>- This driver will have external input - variable data. They may be input in SMM mode.
>- This external input must be validated carefully to avoid security issue like
>- buffer overflow, integer overflow.
>-
>- VariableServiceGetNextVariableName () and VariableServiceQueryVariableInfo() are external API.
>- They need check input parameter.
>-
>- VariableServiceGetVariable() and VariableServiceSetVariable() are external API
>- to receive datasize and data buffer. The size should be checked carefully.
>-
>- VariableServiceSetVariable() should also check authenticate data to avoid buffer overflow,
>- integer overflow. It should also check attribute to avoid authentication bypass.
>-
>-Copyright (c) 2009 - 2015, 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
>-
>-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 "Variable.h"
>-#include "AuthService.h"
>-
>-VARIABLE_MODULE_GLOBAL *mVariableModuleGlobal;
>-
>-///
>-/// Define a memory cache that improves the search performance for a variable.
>-///
>-VARIABLE_STORE_HEADER *mNvVariableCache = NULL;
>-
>-///
>-/// The memory entry used for variable statistics data.
>-///
>-VARIABLE_INFO_ENTRY *gVariableInfo = NULL;
>-
>-///
>-/// The list to store the variables which cannot be set after the EFI_END_OF_DXE_EVENT_GROUP_GUID
>-/// or EVT_GROUP_READY_TO_BOOT event.
>-///
>-LIST_ENTRY mLockedVariableList = INITIALIZE_LIST_HEAD_VARIABLE (mLockedVariableList);
>-
>-///
>-/// The flag to indicate whether the platform has left the DXE phase of execution.
>-///
>-BOOLEAN mEndOfDxe = FALSE;
>-
>-///
>-/// The flag to indicate whether the variable storage locking is enabled.
>-///
>-BOOLEAN mEnableLocking = TRUE;
>-
>-//
>-// It will record the current boot error flag before EndOfDxe.
>-//
>-VAR_ERROR_FLAG mCurrentBootVarErrFlag = VAR_ERROR_FLAG_NO_ERROR;
>-
>-/**
>-
>- SecureBoot Hook for auth variable update.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>-**/
>-VOID
>-EFIAPI
>-SecureBootHook (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- );
>-
>-/**
>- Routine used to track statistical information about variable usage.
>- The data is stored in the EFI system table so it can be accessed later.
>- VariableInfo.efi can dump out the table. Only Boot Services variable
>- accesses are tracked by this code. The PcdVariableCollectStatistics
>- build flag controls if this feature is enabled.
>-
>- A read that hits in the cache will have Read and Cache true for
>- the transaction. Data is allocated by this routine, but never
>- freed.
>-
>- @param[in] VariableName Name of the Variable to track.
>- @param[in] VendorGuid Guid of the Variable to track.
>- @param[in] Volatile TRUE if volatile FALSE if non-volatile.
>- @param[in] Read TRUE if GetVariable() was called.
>- @param[in] Write TRUE if SetVariable() was called.
>- @param[in] Delete TRUE if deleted via SetVariable().
>- @param[in] Cache TRUE for a cache hit.
>-
>-**/
>-VOID
>-UpdateVariableInfo (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN BOOLEAN Volatile,
>- IN BOOLEAN Read,
>- IN BOOLEAN Write,
>- IN BOOLEAN Delete,
>- IN BOOLEAN Cache
>- )
>-{
>- VARIABLE_INFO_ENTRY *Entry;
>-
>- if (FeaturePcdGet (PcdVariableCollectStatistics)) {
>-
>- if (AtRuntime ()) {
>- // Don't collect statistics at runtime.
>- return;
>- }
>-
>- if (gVariableInfo == NULL) {
>- //
>- // On the first call allocate a entry and place a pointer to it in
>- // the EFI System Table.
>- //
>- gVariableInfo = AllocateZeroPool (sizeof (VARIABLE_INFO_ENTRY));
>- ASSERT (gVariableInfo != NULL);
>-
>- CopyGuid (&gVariableInfo->VendorGuid, VendorGuid);
>- gVariableInfo->Name = AllocatePool (StrSize (VariableName));
>- ASSERT (gVariableInfo->Name != NULL);
>- StrCpy (gVariableInfo->Name, VariableName);
>- gVariableInfo->Volatile = Volatile;
>- }
>-
>-
>- for (Entry = gVariableInfo; Entry != NULL; Entry = Entry->Next) {
>- if (CompareGuid (VendorGuid, &Entry->VendorGuid)) {
>- if (StrCmp (VariableName, Entry->Name) == 0) {
>- if (Read) {
>- Entry->ReadCount++;
>- }
>- if (Write) {
>- Entry->WriteCount++;
>- }
>- if (Delete) {
>- Entry->DeleteCount++;
>- }
>- if (Cache) {
>- Entry->CacheCount++;
>- }
>-
>- return;
>- }
>- }
>-
>- if (Entry->Next == NULL) {
>- //
>- // If the entry is not in the table add it.
>- // Next iteration of the loop will fill in the data.
>- //
>- Entry->Next = AllocateZeroPool (sizeof (VARIABLE_INFO_ENTRY));
>- ASSERT (Entry->Next != NULL);
>-
>- CopyGuid (&Entry->Next->VendorGuid, VendorGuid);
>- Entry->Next->Name = AllocatePool (StrSize (VariableName));
>- ASSERT (Entry->Next->Name != NULL);
>- StrCpy (Entry->Next->Name, VariableName);
>- Entry->Next->Volatile = Volatile;
>- }
>-
>- }
>- }
>-}
>-
>-
>-/**
>-
>- This code checks if variable header is valid or not.
>-
>- @param Variable Pointer to the Variable Header.
>- @param VariableStoreEnd Pointer to the Variable Store End.
>-
>- @retval TRUE Variable header is valid.
>- @retval FALSE Variable header is not valid.
>-
>-**/
>-BOOLEAN
>-IsValidVariableHeader (
>- IN VARIABLE_HEADER *Variable,
>- IN VARIABLE_HEADER *VariableStoreEnd
>- )
>-{
>- if ((Variable == NULL) || (Variable >= VariableStoreEnd) || (Variable->StartId != VARIABLE_DATA)) {
>- //
>- // Variable is NULL or has reached the end of variable store,
>- // or the StartId is not correct.
>- //
>- return FALSE;
>- }
>-
>- return TRUE;
>-}
>-
>-
>-/**
>-
>- This function writes data to the FWH at the correct LBA even if the LBAs
>- are fragmented.
>-
>- @param Global Pointer to VARAIBLE_GLOBAL structure.
>- @param Volatile Point out the Variable is Volatile or Non-Volatile.
>- @param SetByIndex TRUE if target pointer is given as index.
>- FALSE if target pointer is absolute.
>- @param Fvb Pointer to the writable FVB protocol.
>- @param DataPtrIndex Pointer to the Data from the end of VARIABLE_STORE_HEADER
>- structure.
>- @param DataSize Size of data to be written.
>- @param Buffer Pointer to the buffer from which data is written.
>-
>- @retval EFI_INVALID_PARAMETER Parameters not valid.
>- @retval EFI_SUCCESS Variable store successfully updated.
>-
>-**/
>-EFI_STATUS
>-UpdateVariableStore (
>- IN VARIABLE_GLOBAL *Global,
>- IN BOOLEAN Volatile,
>- IN BOOLEAN SetByIndex,
>- IN EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL *Fvb,
>- IN UINTN DataPtrIndex,
>- IN UINT32 DataSize,
>- IN UINT8 *Buffer
>- )
>-{
>- EFI_FV_BLOCK_MAP_ENTRY *PtrBlockMapEntry;
>- UINTN BlockIndex2;
>- UINTN LinearOffset;
>- UINTN CurrWriteSize;
>- UINTN CurrWritePtr;
>- UINT8 *CurrBuffer;
>- EFI_LBA LbaNumber;
>- UINTN Size;
>- EFI_FIRMWARE_VOLUME_HEADER *FwVolHeader;
>- VARIABLE_STORE_HEADER *VolatileBase;
>- EFI_PHYSICAL_ADDRESS FvVolHdr;
>- EFI_PHYSICAL_ADDRESS DataPtr;
>- EFI_STATUS Status;
>-
>- FwVolHeader = NULL;
>- DataPtr = DataPtrIndex;
>-
>- //
>- // Check if the Data is Volatile.
>- //
>- if (!Volatile) {
>- if (Fvb == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>- Status = Fvb->GetPhysicalAddress(Fvb, &FvVolHdr);
>- ASSERT_EFI_ERROR (Status);
>-
>- FwVolHeader = (EFI_FIRMWARE_VOLUME_HEADER *) ((UINTN) FvVolHdr);
>- //
>- // Data Pointer should point to the actual Address where data is to be
>- // written.
>- //
>- if (SetByIndex) {
>- DataPtr += mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase;
>- }
>-
>- if ((DataPtr + DataSize) >= ((EFI_PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) FwVolHeader + FwVolHeader->FvLength))) {
>- return EFI_INVALID_PARAMETER;
>- }
>- } else {
>- //
>- // Data Pointer should point to the actual Address where data is to be
>- // written.
>- //
>- VolatileBase = (VARIABLE_STORE_HEADER *) ((UINTN) mVariableModuleGlobal->VariableGlobal.VolatileVariableBase);
>- if (SetByIndex) {
>- DataPtr += mVariableModuleGlobal->VariableGlobal.VolatileVariableBase;
>- }
>-
>- if ((DataPtr + DataSize) >= ((UINTN) ((UINT8 *) VolatileBase + VolatileBase->Size))) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // If Volatile Variable just do a simple mem copy.
>- //
>- CopyMem ((UINT8 *)(UINTN)DataPtr, Buffer, DataSize);
>- return EFI_SUCCESS;
>- }
>-
>- //
>- // If we are here we are dealing with Non-Volatile Variables.
>- //
>- LinearOffset = (UINTN) FwVolHeader;
>- CurrWritePtr = (UINTN) DataPtr;
>- CurrWriteSize = DataSize;
>- CurrBuffer = Buffer;
>- LbaNumber = 0;
>-
>- if (CurrWritePtr < LinearOffset) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- for (PtrBlockMapEntry = FwVolHeader->BlockMap; PtrBlockMapEntry->NumBlocks != 0; PtrBlockMapEntry++) {
>- for (BlockIndex2 = 0; BlockIndex2 < PtrBlockMapEntry->NumBlocks; BlockIndex2++) {
>- //
>- // Check to see if the Variable Writes are spanning through multiple
>- // blocks.
>- //
>- if ((CurrWritePtr >= LinearOffset) && (CurrWritePtr < LinearOffset + PtrBlockMapEntry->Length)) {
>- if ((CurrWritePtr + CurrWriteSize) <= (LinearOffset + PtrBlockMapEntry->Length)) {
>- Status = Fvb->Write (
>- Fvb,
>- LbaNumber,
>- (UINTN) (CurrWritePtr - LinearOffset),
>- &CurrWriteSize,
>- CurrBuffer
>- );
>- return Status;
>- } else {
>- Size = (UINT32) (LinearOffset + PtrBlockMapEntry->Length - CurrWritePtr);
>- Status = Fvb->Write (
>- Fvb,
>- LbaNumber,
>- (UINTN) (CurrWritePtr - LinearOffset),
>- &Size,
>- CurrBuffer
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- CurrWritePtr = LinearOffset + PtrBlockMapEntry->Length;
>- CurrBuffer = CurrBuffer + Size;
>- CurrWriteSize = CurrWriteSize - Size;
>- }
>- }
>-
>- LinearOffset += PtrBlockMapEntry->Length;
>- LbaNumber++;
>- }
>- }
>-
>- return EFI_SUCCESS;
>-}
>-
>-
>-/**
>-
>- This code gets the current status of Variable Store.
>-
>- @param VarStoreHeader Pointer to the Variable Store Header.
>-
>- @retval EfiRaw Variable store status is raw.
>- @retval EfiValid Variable store status is valid.
>- @retval EfiInvalid Variable store status is invalid.
>-
>-**/
>-VARIABLE_STORE_STATUS
>-GetVariableStoreStatus (
>- IN VARIABLE_STORE_HEADER *VarStoreHeader
>- )
>-{
>- if (CompareGuid (&VarStoreHeader->Signature, &gEfiAuthenticatedVariableGuid) &&
>- VarStoreHeader->Format == VARIABLE_STORE_FORMATTED &&
>- VarStoreHeader->State == VARIABLE_STORE_HEALTHY
>- ) {
>-
>- return EfiValid;
>- } else if (((UINT32 *)(&VarStoreHeader->Signature))[0] == 0xffffffff &&
>- ((UINT32 *)(&VarStoreHeader->Signature))[1] == 0xffffffff &&
>- ((UINT32 *)(&VarStoreHeader->Signature))[2] == 0xffffffff &&
>- ((UINT32 *)(&VarStoreHeader->Signature))[3] == 0xffffffff &&
>- VarStoreHeader->Size == 0xffffffff &&
>- VarStoreHeader->Format == 0xff &&
>- VarStoreHeader->State == 0xff
>- ) {
>-
>- return EfiRaw;
>- } else {
>- return EfiInvalid;
>- }
>-}
>-
>-
>-/**
>-
>- This code gets the size of name of variable.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return UINTN Size of variable in bytes.
>-
>-**/
>-UINTN
>-NameSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- if (Variable->State == (UINT8) (-1) ||
>- Variable->DataSize == (UINT32) (-1) ||
>- Variable->NameSize == (UINT32) (-1) ||
>- Variable->Attributes == (UINT32) (-1)) {
>- return 0;
>- }
>- return (UINTN) Variable->NameSize;
>-}
>-
>-/**
>-
>- This code gets the size of variable data.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Size of variable in bytes.
>-
>-**/
>-UINTN
>-DataSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- if (Variable->State == (UINT8) (-1) ||
>- Variable->DataSize == (UINT32) (-1) ||
>- Variable->NameSize == (UINT32) (-1) ||
>- Variable->Attributes == (UINT32) (-1)) {
>- return 0;
>- }
>- return (UINTN) Variable->DataSize;
>-}
>-
>-/**
>-
>- This code gets the pointer to the variable name.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Pointer to Variable Name which is Unicode encoding.
>-
>-**/
>-CHAR16 *
>-GetVariableNamePtr (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>-
>- return (CHAR16 *) (Variable + 1);
>-}
>-
>-/**
>-
>- This code gets the pointer to the variable data.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Pointer to Variable Data.
>-
>-**/
>-UINT8 *
>-GetVariableDataPtr (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- UINTN Value;
>-
>- //
>- // Be careful about pad size for alignment.
>- //
>- Value = (UINTN) GetVariableNamePtr (Variable);
>- Value += NameSizeOfVariable (Variable);
>- Value += GET_PAD_SIZE (NameSizeOfVariable (Variable));
>-
>- return (UINT8 *) Value;
>-}
>-
>-
>-/**
>-
>- This code gets the pointer to the next variable header.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Pointer to next variable header.
>-
>-**/
>-VARIABLE_HEADER *
>-GetNextVariablePtr (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- UINTN Value;
>-
>- Value = (UINTN) GetVariableDataPtr (Variable);
>- Value += DataSizeOfVariable (Variable);
>- Value += GET_PAD_SIZE (DataSizeOfVariable (Variable));
>-
>- //
>- // Be careful about pad size for alignment.
>- //
>- return (VARIABLE_HEADER *) HEADER_ALIGN (Value);
>-}
>-
>-/**
>-
>- Gets the pointer to the first variable header in given variable store area.
>-
>- @param VarStoreHeader Pointer to the Variable Store Header.
>-
>- @return Pointer to the first variable header.
>-
>-**/
>-VARIABLE_HEADER *
>-GetStartPointer (
>- IN VARIABLE_STORE_HEADER *VarStoreHeader
>- )
>-{
>- //
>- // The end of variable store.
>- //
>- return (VARIABLE_HEADER *) HEADER_ALIGN (VarStoreHeader + 1);
>-}
>-
>-/**
>-
>- Gets the pointer to the end of the variable storage area.
>-
>- This function gets pointer to the end of the variable storage
>- area, according to the input variable store header.
>-
>- @param VarStoreHeader Pointer to the Variable Store Header.
>-
>- @return Pointer to the end of the variable storage area.
>-
>-**/
>-VARIABLE_HEADER *
>-GetEndPointer (
>- IN VARIABLE_STORE_HEADER *VarStoreHeader
>- )
>-{
>- //
>- // The end of variable store
>- //
>- return (VARIABLE_HEADER *) HEADER_ALIGN ((UINTN) VarStoreHeader + VarStoreHeader->Size);
>-}
>-
>-/**
>- Record variable error flag.
>-
>- @param[in] Flag Variable error flag to record.
>- @param[in] VariableName Name of variable.
>- @param[in] VendorGuid Guid of variable.
>- @param[in] Attributes Attributes of the variable.
>- @param[in] VariableSize Size of the variable.
>-
>-**/
>-VOID
>-RecordVarErrorFlag (
>- IN VAR_ERROR_FLAG Flag,
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT32 Attributes,
>- IN UINTN VariableSize
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK Variable;
>- VAR_ERROR_FLAG *VarErrFlag;
>- VAR_ERROR_FLAG TempFlag;
>-
>- DEBUG_CODE (
>- DEBUG ((EFI_D_ERROR, "RecordVarErrorFlag (0x%02x) %s:%g - 0x%08x - 0x%x\n", Flag, VariableName, VendorGuid, Attributes,
>VariableSize));
>- if (Flag == VAR_ERROR_FLAG_SYSTEM_ERROR) {
>- if (AtRuntime ()) {
>- DEBUG ((EFI_D_ERROR, "CommonRuntimeVariableSpace = 0x%x - CommonVariableTotalSize = 0x%x\n",
>mVariableModuleGlobal->CommonRuntimeVariableSpace, mVariableModuleGlobal->CommonVariableTotalSize));
>- } else {
>- DEBUG ((EFI_D_ERROR, "CommonVariableSpace = 0x%x - CommonVariableTotalSize = 0x%x\n", mVariableModuleGlobal-
>>CommonVariableSpace, mVariableModuleGlobal->CommonVariableTotalSize));
>- }
>- } else {
>- DEBUG ((EFI_D_ERROR, "CommonMaxUserVariableSpace = 0x%x - CommonUserVariableTotalSize = 0x%x\n",
>mVariableModuleGlobal->CommonMaxUserVariableSpace, mVariableModuleGlobal->CommonUserVariableTotalSize));
>- }
>- );
>-
>- if (!mEndOfDxe) {
>- //
>- // Before EndOfDxe, just record the current boot variable error flag to local variable,
>- // and leave the variable error flag in NV flash as the last boot variable error flag.
>- // After EndOfDxe in InitializeVarErrorFlag (), the variable error flag in NV flash
>- // will be initialized to this local current boot variable error flag.
>- //
>- mCurrentBootVarErrFlag &= Flag;
>- return;
>- }
>-
>- //
>- // Record error flag (it should have be initialized).
>- //
>- Status = FindVariable (
>- VAR_ERROR_FLAG_NAME,
>- &gEdkiiVarErrorFlagGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (!EFI_ERROR (Status)) {
>- VarErrFlag = (VAR_ERROR_FLAG *) GetVariableDataPtr (Variable.CurrPtr);
>- TempFlag = *VarErrFlag;
>- TempFlag &= Flag;
>- if (TempFlag == *VarErrFlag) {
>- return;
>- }
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE,
>- FALSE,
>- mVariableModuleGlobal->FvbInstance,
>- (UINTN) VarErrFlag - (UINTN) mNvVariableCache + (UINTN) mVariableModuleGlobal-
>>VariableGlobal.NonVolatileVariableBase,
>- sizeof (TempFlag),
>- &TempFlag
>- );
>- if (!EFI_ERROR (Status)) {
>- //
>- // Update the data in NV cache.
>- //
>- *VarErrFlag = Flag;
>- }
>- }
>-}
>-
>-/**
>- Initialize variable error flag.
>-
>- Before EndOfDxe, the variable indicates the last boot variable error flag,
>- then it means the last boot variable error flag must be got before EndOfDxe.
>- After EndOfDxe, the variable indicates the current boot variable error flag,
>- then it means the current boot variable error flag must be got after EndOfDxe.
>-
>-**/
>-VOID
>-InitializeVarErrorFlag (
>- VOID
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK Variable;
>- VAR_ERROR_FLAG Flag;
>- VAR_ERROR_FLAG VarErrFlag;
>-
>- if (!mEndOfDxe) {
>- return;
>- }
>-
>- Flag = mCurrentBootVarErrFlag;
>- DEBUG ((EFI_D_INFO, "Initialize variable error flag (%02x)\n", Flag));
>-
>- Status = FindVariable (
>- VAR_ERROR_FLAG_NAME,
>- &gEdkiiVarErrorFlagGuid,
>- &Variable,
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE
>- );
>- if (!EFI_ERROR (Status)) {
>- VarErrFlag = *((VAR_ERROR_FLAG *) GetVariableDataPtr (Variable.CurrPtr));
>- if (VarErrFlag == Flag) {
>- return;
>- }
>- }
>-
>- UpdateVariable (
>- VAR_ERROR_FLAG_NAME,
>- &gEdkiiVarErrorFlagGuid,
>- &Flag,
>- sizeof (Flag),
>- VARIABLE_ATTRIBUTE_NV_BS_RT,
>- 0,
>- 0,
>- &Variable,
>- NULL
>- );
>-}
>-
>-/**
>- Is user variable?
>-
>- @param[in] Variable Pointer to variable header.
>-
>- @retval TRUE User variable.
>- @retval FALSE System variable.
>-
>-**/
>-BOOLEAN
>-IsUserVariable (
>- IN VARIABLE_HEADER *Variable
>- )
>-{
>- VAR_CHECK_VARIABLE_PROPERTY Property;
>-
>- //
>- // Only after End Of Dxe, the variables belong to system variable are fixed.
>- // If PcdMaxUserNvStorageVariableSize is 0, it means user variable share the same NV storage with system variable,
>- // then no need to check if the variable is user variable or not specially.
>- //
>- if (mEndOfDxe && (mVariableModuleGlobal->CommonMaxUserVariableSpace != mVariableModuleGlobal-
>>CommonVariableSpace)) {
>- if (InternalVarCheckVariablePropertyGet (GetVariableNamePtr (Variable), &Variable->VendorGuid, &Property) ==
>EFI_NOT_FOUND) {
>- return TRUE;
>- }
>- }
>- return FALSE;
>-}
>-
>-/**
>- Calculate common user variable total size.
>-
>-**/
>-VOID
>-CalculateCommonUserVariableTotalSize (
>- VOID
>- )
>-{
>- VARIABLE_HEADER *Variable;
>- VARIABLE_HEADER *NextVariable;
>- UINTN VariableSize;
>- VAR_CHECK_VARIABLE_PROPERTY Property;
>-
>- //
>- // Only after End Of Dxe, the variables belong to system variable are fixed.
>- // If PcdMaxUserNvStorageVariableSize is 0, it means user variable share the same NV storage with system variable,
>- // then no need to calculate the common user variable total size specially.
>- //
>- if (mEndOfDxe && (mVariableModuleGlobal->CommonMaxUserVariableSpace != mVariableModuleGlobal-
>>CommonVariableSpace)) {
>- Variable = GetStartPointer (mNvVariableCache);
>- while (IsValidVariableHeader (Variable, GetEndPointer (mNvVariableCache))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- VariableSize = (UINTN) NextVariable - (UINTN) Variable;
>- if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) != EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- if (InternalVarCheckVariablePropertyGet (GetVariableNamePtr (Variable), &Variable->VendorGuid, &Property) ==
>EFI_NOT_FOUND) {
>- //
>- // No property, it is user variable.
>- //
>- mVariableModuleGlobal->CommonUserVariableTotalSize += VariableSize;
>- }
>- }
>-
>- Variable = NextVariable;
>- }
>- }
>-}
>-
>-/**
>- Initialize variable quota.
>-
>-**/
>-VOID
>-InitializeVariableQuota (
>- VOID
>- )
>-{
>- STATIC BOOLEAN Initialized;
>-
>- if (!mEndOfDxe || Initialized) {
>- return;
>- }
>- Initialized = TRUE;
>-
>- InitializeVarErrorFlag ();
>- CalculateCommonUserVariableTotalSize ();
>-}
>-
>-/**
>-
>- Check the PubKeyIndex is a valid key or not.
>-
>- This function will iterate the NV storage to see if this PubKeyIndex is still referenced
>- by any valid count-based auth variabe.
>-
>- @param[in] PubKeyIndex Index of the public key in public key store.
>-
>- @retval TRUE The PubKeyIndex is still in use.
>- @retval FALSE The PubKeyIndex is not referenced by any count-based auth variabe.
>-
>-**/
>-BOOLEAN
>-IsValidPubKeyIndex (
>- IN UINT32 PubKeyIndex
>- )
>-{
>- VARIABLE_HEADER *Variable;
>- VARIABLE_HEADER *VariableStoreEnd;
>-
>- if (PubKeyIndex > mPubKeyNumber) {
>- return FALSE;
>- }
>-
>- Variable = GetStartPointer ((VARIABLE_STORE_HEADER *) (UINTN) mVariableModuleGlobal-
>>VariableGlobal.NonVolatileVariableBase);
>- VariableStoreEnd = GetEndPointer ((VARIABLE_STORE_HEADER *) (UINTN) mVariableModuleGlobal-
>>VariableGlobal.NonVolatileVariableBase);
>-
>- while (IsValidVariableHeader (Variable, VariableStoreEnd)) {
>- if ((Variable->State == VAR_ADDED || Variable->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) &&
>- Variable->PubKeyIndex == PubKeyIndex) {
>- return TRUE;
>- }
>- Variable = GetNextVariablePtr (Variable);
>- }
>-
>- return FALSE;
>-}
>-
>-/**
>-
>- Get the number of valid public key in PubKeyStore.
>-
>- @param[in] PubKeyNumber Number of the public key in public key store.
>-
>- @return Number of valid public key in PubKeyStore.
>-
>-**/
>-UINT32
>-GetValidPubKeyNumber (
>- IN UINT32 PubKeyNumber
>- )
>-{
>- UINT32 PubKeyIndex;
>- UINT32 Counter;
>-
>- Counter = 0;
>-
>- for (PubKeyIndex = 1; PubKeyIndex <= PubKeyNumber; PubKeyIndex++) {
>- if (IsValidPubKeyIndex (PubKeyIndex)) {
>- Counter++;
>- }
>- }
>-
>- return Counter;
>-}
>-
>-/**
>-
>- Filter the useless key in public key store.
>-
>- This function will find out all valid public keys in public key database, save them in new allocated
>- buffer NewPubKeyStore, and give the new PubKeyIndex. The caller is responsible for freeing buffer
>- NewPubKeyIndex and NewPubKeyStore with FreePool().
>-
>- @param[in] PubKeyStore Point to the public key database.
>- @param[in] PubKeyNumber Number of the public key in PubKeyStore.
>- @param[out] NewPubKeyIndex Point to an array of new PubKeyIndex corresponds to NewPubKeyStore.
>- @param[out] NewPubKeyStore Saved all valid public keys in PubKeyStore.
>- @param[out] NewPubKeySize Buffer size of the NewPubKeyStore.
>-
>- @retval EFI_SUCCESS Trim operation is complete successfully.
>- @retval EFI_OUT_OF_RESOURCES No enough memory resources, or no useless key in PubKeyStore.
>-
>-**/
>-EFI_STATUS
>-PubKeyStoreFilter (
>- IN UINT8 *PubKeyStore,
>- IN UINT32 PubKeyNumber,
>- OUT UINT32 **NewPubKeyIndex,
>- OUT UINT8 **NewPubKeyStore,
>- OUT UINT32 *NewPubKeySize
>- )
>-{
>- UINT32 PubKeyIndex;
>- UINT32 CopiedKey;
>- UINT32 NewPubKeyNumber;
>-
>- NewPubKeyNumber = GetValidPubKeyNumber (PubKeyNumber);
>- if (NewPubKeyNumber == PubKeyNumber) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- if (NewPubKeyNumber != 0) {
>- *NewPubKeySize = NewPubKeyNumber * EFI_CERT_TYPE_RSA2048_SIZE;
>- } else {
>- *NewPubKeySize = sizeof (UINT8);
>- }
>-
>- *NewPubKeyStore = AllocatePool (*NewPubKeySize);
>- if (*NewPubKeyStore == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- *NewPubKeyIndex = AllocateZeroPool ((PubKeyNumber + 1) * sizeof (UINT32));
>- if (*NewPubKeyIndex == NULL) {
>- FreePool (*NewPubKeyStore);
>- *NewPubKeyStore = NULL;
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- CopiedKey = 0;
>- for (PubKeyIndex = 1; PubKeyIndex <= PubKeyNumber; PubKeyIndex++) {
>- if (IsValidPubKeyIndex (PubKeyIndex)) {
>- CopyMem (
>- *NewPubKeyStore + CopiedKey * EFI_CERT_TYPE_RSA2048_SIZE,
>- PubKeyStore + (PubKeyIndex - 1) * EFI_CERT_TYPE_RSA2048_SIZE,
>- EFI_CERT_TYPE_RSA2048_SIZE
>- );
>- (*NewPubKeyIndex)[PubKeyIndex] = ++CopiedKey;
>- }
>- }
>- return EFI_SUCCESS;
>-}
>-
>-/**
>-
>- Variable store garbage collection and reclaim operation.
>-
>- If ReclaimPubKeyStore is FALSE, reclaim variable space by deleting the obsoleted varaibles.
>- If ReclaimPubKeyStore is TRUE, reclaim invalid key in public key database and update the PubKeyIndex
>- for all the count-based authenticate variable in NV storage.
>-
>- @param[in] VariableBase Base address of variable store.
>- @param[out] LastVariableOffset Offset of last variable.
>- @param[in] IsVolatile The variable store is volatile or not;
>- if it is non-volatile, need FTW.
>- @param[in, out] UpdatingPtrTrack Pointer to updating variable pointer track structure.
>- @param[in] NewVariable Pointer to new variable.
>- @param[in] NewVariableSize New variable size.
>- @param[in] ReclaimPubKeyStore Reclaim for public key database or not.
>-
>- @return EFI_SUCCESS Reclaim operation has finished successfully.
>- @return EFI_OUT_OF_RESOURCES No enough memory resources or variable space.
>- @return EFI_DEVICE_ERROR The public key database doesn't exist.
>- @return Others Unexpect error happened during reclaim operation.
>-
>-**/
>-EFI_STATUS
>-Reclaim (
>- IN EFI_PHYSICAL_ADDRESS VariableBase,
>- OUT UINTN *LastVariableOffset,
>- IN BOOLEAN IsVolatile,
>- IN OUT VARIABLE_POINTER_TRACK *UpdatingPtrTrack,
>- IN VARIABLE_HEADER *NewVariable,
>- IN UINTN NewVariableSize,
>- IN BOOLEAN ReclaimPubKeyStore
>- )
>-{
>- VARIABLE_HEADER *Variable;
>- VARIABLE_HEADER *AddedVariable;
>- VARIABLE_HEADER *NextVariable;
>- VARIABLE_HEADER *NextAddedVariable;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- UINT8 *ValidBuffer;
>- UINTN MaximumBufferSize;
>- UINTN VariableSize;
>- UINTN NameSize;
>- UINT8 *CurrPtr;
>- VOID *Point0;
>- VOID *Point1;
>- BOOLEAN FoundAdded;
>- EFI_STATUS Status;
>- UINTN CommonVariableTotalSize;
>- UINTN CommonUserVariableTotalSize;
>- UINTN HwErrVariableTotalSize;
>- UINT32 *NewPubKeyIndex;
>- UINT8 *NewPubKeyStore;
>- UINT32 NewPubKeySize;
>- VARIABLE_HEADER *PubKeyHeader;
>- VARIABLE_HEADER *UpdatingVariable;
>- VARIABLE_HEADER *UpdatingInDeletedTransition;
>-
>- UpdatingVariable = NULL;
>- UpdatingInDeletedTransition = NULL;
>- if (UpdatingPtrTrack != NULL) {
>- UpdatingVariable = UpdatingPtrTrack->CurrPtr;
>- UpdatingInDeletedTransition = UpdatingPtrTrack->InDeletedTransitionPtr;
>- }
>-
>- VariableStoreHeader = (VARIABLE_STORE_HEADER *) ((UINTN) VariableBase);
>-
>- CommonVariableTotalSize = 0;
>- CommonUserVariableTotalSize = 0;
>- HwErrVariableTotalSize = 0;
>- NewPubKeyIndex = NULL;
>- NewPubKeyStore = NULL;
>- NewPubKeySize = 0;
>- PubKeyHeader = NULL;
>-
>- if (IsVolatile) {
>- //
>- // Start Pointers for the variable.
>- //
>- Variable = GetStartPointer (VariableStoreHeader);
>- MaximumBufferSize = sizeof (VARIABLE_STORE_HEADER);
>-
>- while (IsValidVariableHeader (Variable, GetEndPointer (VariableStoreHeader))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- if ((Variable->State == VAR_ADDED || Variable->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) &&
>- Variable != UpdatingVariable &&
>- Variable != UpdatingInDeletedTransition
>- ) {
>- VariableSize = (UINTN) NextVariable - (UINTN) Variable;
>- MaximumBufferSize += VariableSize;
>- }
>-
>- Variable = NextVariable;
>- }
>-
>- if (NewVariable != NULL) {
>- //
>- // Add the new variable size.
>- //
>- MaximumBufferSize += NewVariableSize;
>- }
>-
>- //
>- // Reserve the 1 Bytes with Oxff to identify the
>- // end of the variable buffer.
>- //
>- MaximumBufferSize += 1;
>- ValidBuffer = AllocatePool (MaximumBufferSize);
>- if (ValidBuffer == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>- } else {
>- //
>- // For NV variable reclaim, don't allocate pool here and just use mNvVariableCache
>- // as the buffer to reduce SMRAM consumption for SMM variable driver.
>- //
>- MaximumBufferSize = mNvVariableCache->Size;
>- ValidBuffer = (UINT8 *) mNvVariableCache;
>- }
>-
>- SetMem (ValidBuffer, MaximumBufferSize, 0xff);
>-
>- //
>- // Copy variable store header.
>- //
>- CopyMem (ValidBuffer, VariableStoreHeader, sizeof (VARIABLE_STORE_HEADER));
>- CurrPtr = (UINT8 *) GetStartPointer ((VARIABLE_STORE_HEADER *) ValidBuffer);
>-
>- if (ReclaimPubKeyStore) {
>- ASSERT (IsVolatile == FALSE);
>- //
>- // Trim the PubKeyStore and get new PubKeyIndex.
>- //
>- Status = PubKeyStoreFilter (
>- mPubKeyStore,
>- mPubKeyNumber,
>- &NewPubKeyIndex,
>- &NewPubKeyStore,
>- &NewPubKeySize
>- );
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT ((NewPubKeyIndex != NULL) && (NewPubKeyStore != NULL));
>-
>- //
>- // Refresh the PubKeyIndex for all valid variables (ADDED and IN_DELETED_TRANSITION).
>- //
>- Variable = GetStartPointer (VariableStoreHeader);
>- while (IsValidVariableHeader (Variable, GetEndPointer (VariableStoreHeader))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- if (Variable->State == VAR_ADDED || Variable->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- if ((StrCmp (GetVariableNamePtr (Variable), AUTHVAR_KEYDB_NAME) == 0) &&
>- (CompareGuid (&Variable->VendorGuid, &gEfiAuthenticatedVariableGuid))) {
>- //
>- // Skip the public key database, it will be reinstalled later.
>- //
>- PubKeyHeader = Variable;
>- Variable = NextVariable;
>- continue;
>- }
>-
>- VariableSize = (UINTN) NextVariable - (UINTN) Variable;
>- CopyMem (CurrPtr, (UINT8 *) Variable, VariableSize);
>- ((VARIABLE_HEADER*) CurrPtr)->PubKeyIndex = NewPubKeyIndex[Variable->PubKeyIndex];
>- CurrPtr += VariableSize;
>- if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- HwErrVariableTotalSize += VariableSize;
>- } else if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) != EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- CommonVariableTotalSize += VariableSize;
>- if (IsUserVariable (Variable)) {
>- CommonUserVariableTotalSize += VariableSize;
>- }
>- }
>- }
>- Variable = NextVariable;
>- }
>-
>- //
>- // Reinstall the new public key database.
>- //
>- ASSERT (PubKeyHeader != NULL);
>- if (PubKeyHeader == NULL) {
>- Status = EFI_DEVICE_ERROR;
>- goto Done;
>- }
>- CopyMem (CurrPtr, (UINT8*) PubKeyHeader, sizeof (VARIABLE_HEADER));
>- Variable = (VARIABLE_HEADER*) CurrPtr;
>- Variable->DataSize = NewPubKeySize;
>- StrCpy (GetVariableNamePtr (Variable), GetVariableNamePtr (PubKeyHeader));
>- CopyMem (GetVariableDataPtr (Variable), NewPubKeyStore, NewPubKeySize);
>- CurrPtr = (UINT8*) GetNextVariablePtr (Variable);
>- CommonVariableTotalSize += (UINTN) CurrPtr - (UINTN) Variable;
>- if (IsUserVariable (Variable)) {
>- CommonUserVariableTotalSize += (UINTN) CurrPtr - (UINTN) Variable;
>- }
>- } else {
>- //
>- // Reinstall all ADDED variables as long as they are not identical to Updating Variable.
>- //
>- Variable = GetStartPointer (VariableStoreHeader);
>- while (IsValidVariableHeader (Variable, GetEndPointer (VariableStoreHeader))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- if (Variable != UpdatingVariable && Variable->State == VAR_ADDED) {
>- VariableSize = (UINTN) NextVariable - (UINTN) Variable;
>- CopyMem (CurrPtr, (UINT8 *) Variable, VariableSize);
>- CurrPtr += VariableSize;
>- if ((!IsVolatile) && ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) ==
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>- HwErrVariableTotalSize += VariableSize;
>- } else if ((!IsVolatile) && ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) !=
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>- CommonVariableTotalSize += VariableSize;
>- if (IsUserVariable (Variable)) {
>- CommonUserVariableTotalSize += VariableSize;
>- }
>- }
>- }
>- Variable = NextVariable;
>- }
>-
>- //
>- // Reinstall all in delete transition variables.
>- //
>- Variable = GetStartPointer (VariableStoreHeader);
>- while (IsValidVariableHeader (Variable, GetEndPointer (VariableStoreHeader))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- if (Variable != UpdatingVariable && Variable != UpdatingInDeletedTransition && Variable->State ==
>(VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>-
>- //
>- // Buffer has cached all ADDED variable.
>- // Per IN_DELETED variable, we have to guarantee that
>- // no ADDED one in previous buffer.
>- //
>-
>- FoundAdded = FALSE;
>- AddedVariable = GetStartPointer ((VARIABLE_STORE_HEADER *) ValidBuffer);
>- while (IsValidVariableHeader (AddedVariable, GetEndPointer ((VARIABLE_STORE_HEADER *) ValidBuffer))) {
>- NextAddedVariable = GetNextVariablePtr (AddedVariable);
>- NameSize = NameSizeOfVariable (AddedVariable);
>- if (CompareGuid (&AddedVariable->VendorGuid, &Variable->VendorGuid) &&
>- NameSize == NameSizeOfVariable (Variable)
>- ) {
>- Point0 = (VOID *) GetVariableNamePtr (AddedVariable);
>- Point1 = (VOID *) GetVariableNamePtr (Variable);
>- if (CompareMem (Point0, Point1, NameSize) == 0) {
>- FoundAdded = TRUE;
>- break;
>- }
>- }
>- AddedVariable = NextAddedVariable;
>- }
>- if (!FoundAdded) {
>- //
>- // Promote VAR_IN_DELETED_TRANSITION to VAR_ADDED.
>- //
>- VariableSize = (UINTN) NextVariable - (UINTN) Variable;
>- CopyMem (CurrPtr, (UINT8 *) Variable, VariableSize);
>- ((VARIABLE_HEADER *) CurrPtr)->State = VAR_ADDED;
>- CurrPtr += VariableSize;
>- if ((!IsVolatile) && ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) ==
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>- HwErrVariableTotalSize += VariableSize;
>- } else if ((!IsVolatile) && ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) !=
>EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>- CommonVariableTotalSize += VariableSize;
>- if (IsUserVariable (Variable)) {
>- CommonUserVariableTotalSize += VariableSize;
>- }
>- }
>- }
>- }
>-
>- Variable = NextVariable;
>- }
>-
>- //
>- // Install the new variable if it is not NULL.
>- //
>- if (NewVariable != NULL) {
>- if ((UINTN) (CurrPtr - ValidBuffer) + NewVariableSize > VariableStoreHeader->Size) {
>- //
>- // No enough space to store the new variable.
>- //
>- Status = EFI_OUT_OF_RESOURCES;
>- goto Done;
>- }
>- if (!IsVolatile) {
>- if ((NewVariable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- HwErrVariableTotalSize += NewVariableSize;
>- } else if ((NewVariable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) !=
>EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- CommonVariableTotalSize += NewVariableSize;
>- if (IsUserVariable (NewVariable)) {
>- CommonUserVariableTotalSize += NewVariableSize;
>- }
>- }
>- if ((HwErrVariableTotalSize > PcdGet32 (PcdHwErrStorageSize)) ||
>- (CommonVariableTotalSize > mVariableModuleGlobal->CommonVariableSpace) ||
>- (CommonUserVariableTotalSize > mVariableModuleGlobal->CommonMaxUserVariableSpace)) {
>- //
>- // No enough space to store the new variable by NV or NV+HR attribute.
>- //
>- Status = EFI_OUT_OF_RESOURCES;
>- goto Done;
>- }
>- }
>-
>- CopyMem (CurrPtr, (UINT8 *) NewVariable, NewVariableSize);
>- ((VARIABLE_HEADER *) CurrPtr)->State = VAR_ADDED;
>- if (UpdatingVariable != NULL) {
>- UpdatingPtrTrack->CurrPtr = (VARIABLE_HEADER *)((UINTN)UpdatingPtrTrack->StartPtr + ((UINTN)CurrPtr -
>(UINTN)GetStartPointer ((VARIABLE_STORE_HEADER *) ValidBuffer)));
>- UpdatingPtrTrack->InDeletedTransitionPtr = NULL;
>- }
>- CurrPtr += NewVariableSize;
>- }
>- }
>-
>- if (IsVolatile) {
>- //
>- // If volatile variable store, just copy valid buffer.
>- //
>- SetMem ((UINT8 *) (UINTN) VariableBase, VariableStoreHeader->Size, 0xff);
>- CopyMem ((UINT8 *) (UINTN) VariableBase, ValidBuffer, (UINTN) (CurrPtr - ValidBuffer));
>- *LastVariableOffset = (UINTN) (CurrPtr - ValidBuffer);
>- Status = EFI_SUCCESS;
>- } else {
>- //
>- // If non-volatile variable store, perform FTW here.
>- //
>- Status = FtwVariableSpace (
>- VariableBase,
>- (VARIABLE_STORE_HEADER *) ValidBuffer
>- );
>- if (!EFI_ERROR (Status)) {
>- *LastVariableOffset = (UINTN) (CurrPtr - ValidBuffer);
>- mVariableModuleGlobal->HwErrVariableTotalSize = HwErrVariableTotalSize;
>- mVariableModuleGlobal->CommonVariableTotalSize = CommonVariableTotalSize;
>- mVariableModuleGlobal->CommonUserVariableTotalSize = CommonUserVariableTotalSize;
>- } else {
>- Variable = GetStartPointer ((VARIABLE_STORE_HEADER *)(UINTN)VariableBase);
>- while (IsValidVariableHeader (Variable, GetEndPointer ((VARIABLE_STORE_HEADER *)(UINTN)VariableBase))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- VariableSize = (UINTN) NextVariable - (UINTN) Variable;
>- if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- mVariableModuleGlobal->HwErrVariableTotalSize += VariableSize;
>- } else if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) != EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- mVariableModuleGlobal->CommonVariableTotalSize += VariableSize;
>- if (IsUserVariable (Variable)) {
>- mVariableModuleGlobal->CommonUserVariableTotalSize += VariableSize;
>- }
>- }
>-
>- Variable = NextVariable;
>- }
>- *LastVariableOffset = (UINTN) Variable - (UINTN) VariableBase;
>- }
>- }
>-
>-Done:
>- if (IsVolatile) {
>- FreePool (ValidBuffer);
>- } else {
>- //
>- // For NV variable reclaim, we use mNvVariableCache as the buffer, so copy the data back.
>- //
>- CopyMem (mNvVariableCache, (UINT8 *)(UINTN)VariableBase, VariableStoreHeader->Size);
>-
>- if (NewPubKeyStore != NULL) {
>- FreePool (NewPubKeyStore);
>- }
>-
>- if (NewPubKeyIndex != NULL) {
>- FreePool (NewPubKeyIndex);
>- }
>- }
>-
>- return Status;
>-}
>-
>-/**
>- Find the variable in the specified variable store.
>-
>- @param[in] VariableName Name of the variable to be found
>- @param[in] VendorGuid Vendor GUID to be found.
>- @param[in] IgnoreRtCheck Ignore EFI_VARIABLE_RUNTIME_ACCESS attribute
>- check at runtime when searching variable.
>- @param[in, out] PtrTrack Variable Track Pointer structure that contains Variable Information.
>-
>- @retval EFI_SUCCESS Variable found successfully
>- @retval EFI_NOT_FOUND Variable not found
>-**/
>-EFI_STATUS
>-FindVariableEx (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN BOOLEAN IgnoreRtCheck,
>- IN OUT VARIABLE_POINTER_TRACK *PtrTrack
>- )
>-{
>- VARIABLE_HEADER *InDeletedVariable;
>- VOID *Point;
>-
>- PtrTrack->InDeletedTransitionPtr = NULL;
>-
>- //
>- // Find the variable by walk through HOB, volatile and non-volatile variable store.
>- //
>- InDeletedVariable = NULL;
>-
>- for ( PtrTrack->CurrPtr = PtrTrack->StartPtr
>- ; IsValidVariableHeader (PtrTrack->CurrPtr, PtrTrack->EndPtr)
>- ; PtrTrack->CurrPtr = GetNextVariablePtr (PtrTrack->CurrPtr)
>- ) {
>- if (PtrTrack->CurrPtr->State == VAR_ADDED ||
>- PtrTrack->CurrPtr->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)
>- ) {
>- if (IgnoreRtCheck || !AtRuntime () || ((PtrTrack->CurrPtr->Attributes & EFI_VARIABLE_RUNTIME_ACCESS) != 0)) {
>- if (VariableName[0] == 0) {
>- if (PtrTrack->CurrPtr->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- InDeletedVariable = PtrTrack->CurrPtr;
>- } else {
>- PtrTrack->InDeletedTransitionPtr = InDeletedVariable;
>- return EFI_SUCCESS;
>- }
>- } else {
>- if (CompareGuid (VendorGuid, &PtrTrack->CurrPtr->VendorGuid)) {
>- Point = (VOID *) GetVariableNamePtr (PtrTrack->CurrPtr);
>-
>- ASSERT (NameSizeOfVariable (PtrTrack->CurrPtr) != 0);
>- if (CompareMem (VariableName, Point, NameSizeOfVariable (PtrTrack->CurrPtr)) == 0) {
>- if (PtrTrack->CurrPtr->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- InDeletedVariable = PtrTrack->CurrPtr;
>- } else {
>- PtrTrack->InDeletedTransitionPtr = InDeletedVariable;
>- return EFI_SUCCESS;
>- }
>- }
>- }
>- }
>- }
>- }
>- }
>-
>- PtrTrack->CurrPtr = InDeletedVariable;
>- return (PtrTrack->CurrPtr == NULL) ? EFI_NOT_FOUND : EFI_SUCCESS;
>-}
>-
>-
>-/**
>- Finds variable in storage blocks of volatile and non-volatile storage areas.
>-
>- This code finds variable in storage blocks of volatile and non-volatile storage areas.
>- If VariableName is an empty string, then we just return the first
>- qualified variable without comparing VariableName and VendorGuid.
>- If IgnoreRtCheck is TRUE, then we ignore the EFI_VARIABLE_RUNTIME_ACCESS attribute check
>- at runtime when searching existing variable, only VariableName and VendorGuid are compared.
>- Otherwise, variables without EFI_VARIABLE_RUNTIME_ACCESS are not visible at runtime.
>-
>- @param[in] VariableName Name of the variable to be found.
>- @param[in] VendorGuid Vendor GUID to be found.
>- @param[out] PtrTrack VARIABLE_POINTER_TRACK structure for output,
>- including the range searched and the target position.
>- @param[in] Global Pointer to VARIABLE_GLOBAL structure, including
>- base of volatile variable storage area, base of
>- NV variable storage area, and a lock.
>- @param[in] IgnoreRtCheck Ignore EFI_VARIABLE_RUNTIME_ACCESS attribute
>- check at runtime when searching variable.
>-
>- @retval EFI_INVALID_PARAMETER If VariableName is not an empty string, while
>- VendorGuid is NULL.
>- @retval EFI_SUCCESS Variable successfully found.
>- @retval EFI_NOT_FOUND Variable not found
>-
>-**/
>-EFI_STATUS
>-FindVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- OUT VARIABLE_POINTER_TRACK *PtrTrack,
>- IN VARIABLE_GLOBAL *Global,
>- IN BOOLEAN IgnoreRtCheck
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_STORE_HEADER *VariableStoreHeader[VariableStoreTypeMax];
>- VARIABLE_STORE_TYPE Type;
>-
>- if (VariableName[0] != 0 && VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // 0: Volatile, 1: HOB, 2: Non-Volatile.
>- // The index and attributes mapping must be kept in this order as RuntimeServiceGetNextVariableName
>- // make use of this mapping to implement search algorithm.
>- //
>- VariableStoreHeader[VariableStoreTypeVolatile] = (VARIABLE_STORE_HEADER *) (UINTN) Global->VolatileVariableBase;
>- VariableStoreHeader[VariableStoreTypeHob] = (VARIABLE_STORE_HEADER *) (UINTN) Global->HobVariableBase;
>- VariableStoreHeader[VariableStoreTypeNv] = mNvVariableCache;
>-
>- //
>- // Find the variable by walk through HOB, volatile and non-volatile variable store.
>- //
>- for (Type = (VARIABLE_STORE_TYPE) 0; Type < VariableStoreTypeMax; Type++) {
>- if (VariableStoreHeader[Type] == NULL) {
>- continue;
>- }
>-
>- PtrTrack->StartPtr = GetStartPointer (VariableStoreHeader[Type]);
>- PtrTrack->EndPtr = GetEndPointer (VariableStoreHeader[Type]);
>- PtrTrack->Volatile = (BOOLEAN) (Type == VariableStoreTypeVolatile);
>-
>- Status = FindVariableEx (VariableName, VendorGuid, IgnoreRtCheck, PtrTrack);
>- if (!EFI_ERROR (Status)) {
>- return Status;
>- }
>- }
>- return EFI_NOT_FOUND;
>-}
>-
>-/**
>- Get index from supported language codes according to language string.
>-
>- This code is used to get corresponding index in supported language codes. It can handle
>- RFC4646 and ISO639 language tags.
>- In ISO639 language tags, take 3-characters as a delimitation to find matched string and calculate the index.
>- In RFC4646 language tags, take semicolon as a delimitation to find matched string and calculate the index.
>-
>- For example:
>- SupportedLang = "engfraengfra"
>- Lang = "eng"
>- Iso639Language = TRUE
>- The return value is "0".
>- Another example:
>- SupportedLang = "en;fr;en-US;fr-FR"
>- Lang = "fr-FR"
>- Iso639Language = FALSE
>- The return value is "3".
>-
>- @param SupportedLang Platform supported language codes.
>- @param Lang Configured language.
>- @param Iso639Language A bool value to signify if the handler is operated on ISO639 or RFC4646.
>-
>- @retval The index of language in the language codes.
>-
>-**/
>-UINTN
>-GetIndexFromSupportedLangCodes(
>- IN CHAR8 *SupportedLang,
>- IN CHAR8 *Lang,
>- IN BOOLEAN Iso639Language
>- )
>-{
>- UINTN Index;
>- UINTN CompareLength;
>- UINTN LanguageLength;
>-
>- if (Iso639Language) {
>- CompareLength = ISO_639_2_ENTRY_SIZE;
>- for (Index = 0; Index < AsciiStrLen (SupportedLang); Index += CompareLength) {
>- if (AsciiStrnCmp (Lang, SupportedLang + Index, CompareLength) == 0) {
>- //
>- // Successfully find the index of Lang string in SupportedLang string.
>- //
>- Index = Index / CompareLength;
>- return Index;
>- }
>- }
>- ASSERT (FALSE);
>- return 0;
>- } else {
>- //
>- // Compare RFC4646 language code
>- //
>- Index = 0;
>- for (LanguageLength = 0; Lang[LanguageLength] != '\0'; LanguageLength++);
>-
>- for (Index = 0; *SupportedLang != '\0'; Index++, SupportedLang += CompareLength) {
>- //
>- // Skip ';' characters in SupportedLang
>- //
>- for (; *SupportedLang != '\0' && *SupportedLang == ';'; SupportedLang++);
>- //
>- // Determine the length of the next language code in SupportedLang
>- //
>- for (CompareLength = 0; SupportedLang[CompareLength] != '\0' && SupportedLang[CompareLength] != ';'; CompareLength++);
>-
>- if ((CompareLength == LanguageLength) &&
>- (AsciiStrnCmp (Lang, SupportedLang, CompareLength) == 0)) {
>- //
>- // Successfully find the index of Lang string in SupportedLang string.
>- //
>- return Index;
>- }
>- }
>- ASSERT (FALSE);
>- return 0;
>- }
>-}
>-
>-/**
>- Get language string from supported language codes according to index.
>-
>- This code is used to get corresponding language strings in supported language codes. It can handle
>- RFC4646 and ISO639 language tags.
>- In ISO639 language tags, take 3-characters as a delimitation. Find language string according to the index.
>- In RFC4646 language tags, take semicolon as a delimitation. Find language string according to the index.
>-
>- For example:
>- SupportedLang = "engfraengfra"
>- Index = "1"
>- Iso639Language = TRUE
>- The return value is "fra".
>- Another example:
>- SupportedLang = "en;fr;en-US;fr-FR"
>- Index = "1"
>- Iso639Language = FALSE
>- The return value is "fr".
>-
>- @param SupportedLang Platform supported language codes.
>- @param Index The index in supported language codes.
>- @param Iso639Language A bool value to signify if the handler is operated on ISO639 or RFC4646.
>-
>- @retval The language string in the language codes.
>-
>-**/
>-CHAR8 *
>-GetLangFromSupportedLangCodes (
>- IN CHAR8 *SupportedLang,
>- IN UINTN Index,
>- IN BOOLEAN Iso639Language
>-)
>-{
>- UINTN SubIndex;
>- UINTN CompareLength;
>- CHAR8 *Supported;
>-
>- SubIndex = 0;
>- Supported = SupportedLang;
>- if (Iso639Language) {
>- //
>- // According to the index of Lang string in SupportedLang string to get the language.
>- // This code will be invoked in RUNTIME, therefore there is not a memory allocate/free operation.
>- // In driver entry, it pre-allocates a runtime attribute memory to accommodate this string.
>- //
>- CompareLength = ISO_639_2_ENTRY_SIZE;
>- mVariableModuleGlobal->Lang[CompareLength] = '\0';
>- return CopyMem (mVariableModuleGlobal->Lang, SupportedLang + Index * CompareLength, CompareLength);
>-
>- } else {
>- while (TRUE) {
>- //
>- // Take semicolon as delimitation, sequentially traverse supported language codes.
>- //
>- for (CompareLength = 0; *Supported != ';' && *Supported != '\0'; CompareLength++) {
>- Supported++;
>- }
>- if ((*Supported == '\0') && (SubIndex != Index)) {
>- //
>- // Have completed the traverse, but not find corrsponding string.
>- // This case is not allowed to happen.
>- //
>- ASSERT(FALSE);
>- return NULL;
>- }
>- if (SubIndex == Index) {
>- //
>- // According to the index of Lang string in SupportedLang string to get the language.
>- // As this code will be invoked in RUNTIME, therefore there is not memory allocate/free operation.
>- // In driver entry, it pre-allocates a runtime attribute memory to accommodate this string.
>- //
>- mVariableModuleGlobal->PlatformLang[CompareLength] = '\0';
>- return CopyMem (mVariableModuleGlobal->PlatformLang, Supported - CompareLength, CompareLength);
>- }
>- SubIndex++;
>-
>- //
>- // Skip ';' characters in Supported
>- //
>- for (; *Supported != '\0' && *Supported == ';'; Supported++);
>- }
>- }
>-}
>-
>-/**
>- Returns a pointer to an allocated buffer that contains the best matching language
>- from a set of supported languages.
>-
>- This function supports both ISO 639-2 and RFC 4646 language codes, but language
>- code types may not be mixed in a single call to this function. This function
>- supports a variable argument list that allows the caller to pass in a prioritized
>- list of language codes to test against all the language codes in SupportedLanguages.
>-
>- If SupportedLanguages is NULL, then ASSERT().
>-
>- @param[in] SupportedLanguages A pointer to a Null-terminated ASCII string that
>- contains a set of language codes in the format
>- specified by Iso639Language.
>- @param[in] Iso639Language If TRUE, then all language codes are assumed to be
>- in ISO 639-2 format. If FALSE, then all language
>- codes are assumed to be in RFC 4646 language format
>- @param[in] ... A variable argument list that contains pointers to
>- Null-terminated ASCII strings that contain one or more
>- language codes in the format specified by Iso639Language.
>- The first language code from each of these language
>- code lists is used to determine if it is an exact or
>- close match to any of the language codes in
>- SupportedLanguages. Close matches only apply to RFC 4646
>- language codes, and the matching algorithm from RFC 4647
>- is used to determine if a close match is present. If
>- an exact or close match is found, then the matching
>- language code from SupportedLanguages is returned. If
>- no matches are found, then the next variable argument
>- parameter is evaluated. The variable argument list
>- is terminated by a NULL.
>-
>- @retval NULL The best matching language could not be found in SupportedLanguages.
>- @retval NULL There are not enough resources available to return the best matching
>- language.
>- @retval Other A pointer to a Null-terminated ASCII string that is the best matching
>- language in SupportedLanguages.
>-
>-**/
>-CHAR8 *
>-EFIAPI
>-VariableGetBestLanguage (
>- IN CONST CHAR8 *SupportedLanguages,
>- IN BOOLEAN Iso639Language,
>- ...
>- )
>-{
>- VA_LIST Args;
>- CHAR8 *Language;
>- UINTN CompareLength;
>- UINTN LanguageLength;
>- CONST CHAR8 *Supported;
>- CHAR8 *Buffer;
>-
>- if (SupportedLanguages == NULL) {
>- return NULL;
>- }
>-
>- VA_START (Args, Iso639Language);
>- while ((Language = VA_ARG (Args, CHAR8 *)) != NULL) {
>- //
>- // Default to ISO 639-2 mode
>- //
>- CompareLength = 3;
>- LanguageLength = MIN (3, AsciiStrLen (Language));
>-
>- //
>- // If in RFC 4646 mode, then determine the length of the first RFC 4646 language code in Language
>- //
>- if (!Iso639Language) {
>- for (LanguageLength = 0; Language[LanguageLength] != 0 && Language[LanguageLength] != ';'; LanguageLength++);
>- }
>-
>- //
>- // Trim back the length of Language used until it is empty
>- //
>- while (LanguageLength > 0) {
>- //
>- // Loop through all language codes in SupportedLanguages
>- //
>- for (Supported = SupportedLanguages; *Supported != '\0'; Supported += CompareLength) {
>- //
>- // In RFC 4646 mode, then Loop through all language codes in SupportedLanguages
>- //
>- if (!Iso639Language) {
>- //
>- // Skip ';' characters in Supported
>- //
>- for (; *Supported != '\0' && *Supported == ';'; Supported++);
>- //
>- // Determine the length of the next language code in Supported
>- //
>- for (CompareLength = 0; Supported[CompareLength] != 0 && Supported[CompareLength] != ';'; CompareLength++);
>- //
>- // If Language is longer than the Supported, then skip to the next language
>- //
>- if (LanguageLength > CompareLength) {
>- continue;
>- }
>- }
>- //
>- // See if the first LanguageLength characters in Supported match Language
>- //
>- if (AsciiStrnCmp (Supported, Language, LanguageLength) == 0) {
>- VA_END (Args);
>-
>- Buffer = Iso639Language ? mVariableModuleGlobal->Lang : mVariableModuleGlobal->PlatformLang;
>- Buffer[CompareLength] = '\0';
>- return CopyMem (Buffer, Supported, CompareLength);
>- }
>- }
>-
>- if (Iso639Language) {
>- //
>- // If ISO 639 mode, then each language can only be tested once
>- //
>- LanguageLength = 0;
>- } else {
>- //
>- // If RFC 4646 mode, then trim Language from the right to the next '-' character
>- //
>- for (LanguageLength--; LanguageLength > 0 && Language[LanguageLength] != '-'; LanguageLength--);
>- }
>- }
>- }
>- VA_END (Args);
>-
>- //
>- // No matches were found
>- //
>- return NULL;
>-}
>-
>-/**
>- This function is to check if the remaining variable space is enough to set
>- all Variables from argument list successfully. The purpose of the check
>- is to keep the consistency of the Variables to be in variable storage.
>-
>- Note: Variables are assumed to be in same storage.
>- The set sequence of Variables will be same with the sequence of VariableEntry from argument list,
>- so follow the argument sequence to check the Variables.
>-
>- @param[in] Attributes Variable attributes for Variable entries.
>- @param ... The variable argument list with type VARIABLE_ENTRY_CONSISTENCY *.
>- A NULL terminates the list. The VariableSize of
>- VARIABLE_ENTRY_CONSISTENCY is the variable data size as input.
>- It will be changed to variable total size as output.
>-
>- @retval TRUE Have enough variable space to set the Variables successfully.
>- @retval FALSE No enough variable space to set the Variables successfully.
>-
>-**/
>-BOOLEAN
>-EFIAPI
>-CheckRemainingSpaceForConsistency (
>- IN UINT32 Attributes,
>- ...
>- )
>-{
>- EFI_STATUS Status;
>- VA_LIST Args;
>- VARIABLE_ENTRY_CONSISTENCY *VariableEntry;
>- UINT64 MaximumVariableStorageSize;
>- UINT64 RemainingVariableStorageSize;
>- UINT64 MaximumVariableSize;
>- UINTN TotalNeededSize;
>- UINTN OriginalVarSize;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- VARIABLE_POINTER_TRACK VariablePtrTrack;
>- VARIABLE_HEADER *NextVariable;
>- UINTN VarNameSize;
>- UINTN VarDataSize;
>-
>- //
>- // Non-Volatile related.
>- //
>- VariableStoreHeader = mNvVariableCache;
>-
>- Status = VariableServiceQueryVariableInfoInternal (
>- Attributes,
>- &MaximumVariableStorageSize,
>- &RemainingVariableStorageSize,
>- &MaximumVariableSize
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- TotalNeededSize = 0;
>- VA_START (Args, Attributes);
>- VariableEntry = VA_ARG (Args, VARIABLE_ENTRY_CONSISTENCY *);
>- while (VariableEntry != NULL) {
>- //
>- // Calculate variable total size.
>- //
>- VarNameSize = StrSize (VariableEntry->Name);
>- VarNameSize += GET_PAD_SIZE (VarNameSize);
>- VarDataSize = VariableEntry->VariableSize;
>- VarDataSize += GET_PAD_SIZE (VarDataSize);
>- VariableEntry->VariableSize = HEADER_ALIGN (sizeof (VARIABLE_HEADER) + VarNameSize + VarDataSize);
>-
>- TotalNeededSize += VariableEntry->VariableSize;
>- VariableEntry = VA_ARG (Args, VARIABLE_ENTRY_CONSISTENCY *);
>- }
>- VA_END (Args);
>-
>- if (RemainingVariableStorageSize >= TotalNeededSize) {
>- //
>- // Already have enough space.
>- //
>- return TRUE;
>- } else if (AtRuntime ()) {
>- //
>- // At runtime, no reclaim.
>- // The original variable space of Variables can't be reused.
>- //
>- return FALSE;
>- }
>-
>- VA_START (Args, Attributes);
>- VariableEntry = VA_ARG (Args, VARIABLE_ENTRY_CONSISTENCY *);
>- while (VariableEntry != NULL) {
>- //
>- // Check if Variable[Index] has been present and get its size.
>- //
>- OriginalVarSize = 0;
>- VariablePtrTrack.StartPtr = GetStartPointer (VariableStoreHeader);
>- VariablePtrTrack.EndPtr = GetEndPointer (VariableStoreHeader);
>- Status = FindVariableEx (
>- VariableEntry->Name,
>- VariableEntry->Guid,
>- FALSE,
>- &VariablePtrTrack
>- );
>- if (!EFI_ERROR (Status)) {
>- //
>- // Get size of Variable[Index].
>- //
>- NextVariable = GetNextVariablePtr (VariablePtrTrack.CurrPtr);
>- OriginalVarSize = (UINTN) NextVariable - (UINTN) VariablePtrTrack.CurrPtr;
>- //
>- // Add the original size of Variable[Index] to remaining variable storage size.
>- //
>- RemainingVariableStorageSize += OriginalVarSize;
>- }
>- if (VariableEntry->VariableSize > RemainingVariableStorageSize) {
>- //
>- // No enough space for Variable[Index].
>- //
>- VA_END (Args);
>- return FALSE;
>- }
>- //
>- // Sub the (new) size of Variable[Index] from remaining variable storage size.
>- //
>- RemainingVariableStorageSize -= VariableEntry->VariableSize;
>- VariableEntry = VA_ARG (Args, VARIABLE_ENTRY_CONSISTENCY *);
>- }
>- VA_END (Args);
>-
>- return TRUE;
>-}
>-
>-/**
>- Hook the operations in PlatformLangCodes, LangCodes, PlatformLang and Lang.
>-
>- When setting Lang/LangCodes, simultaneously update PlatformLang/PlatformLangCodes.
>-
>- According to UEFI spec, PlatformLangCodes/LangCodes are only set once in firmware initialization,
>- and are read-only. Therefore, in variable driver, only store the original value for other use.
>-
>- @param[in] VariableName Name of variable.
>-
>- @param[in] Data Variable data.
>-
>- @param[in] DataSize Size of data. 0 means delete.
>-
>- @retval EFI_SUCCESS The update operation is successful or ignored.
>- @retval EFI_WRITE_PROTECTED Update PlatformLangCodes/LangCodes at runtime.
>- @retval EFI_OUT_OF_RESOURCES No enough variable space to do the update operation.
>- @retval Others Other errors happened during the update operation.
>-
>-**/
>-EFI_STATUS
>-AutoUpdateLangVariable (
>- IN CHAR16 *VariableName,
>- IN VOID *Data,
>- IN UINTN DataSize
>- )
>-{
>- EFI_STATUS Status;
>- CHAR8 *BestPlatformLang;
>- CHAR8 *BestLang;
>- UINTN Index;
>- UINT32 Attributes;
>- VARIABLE_POINTER_TRACK Variable;
>- BOOLEAN SetLanguageCodes;
>- VARIABLE_ENTRY_CONSISTENCY VariableEntry[2];
>-
>- //
>- // Don't do updates for delete operation
>- //
>- if (DataSize == 0) {
>- return EFI_SUCCESS;
>- }
>-
>- SetLanguageCodes = FALSE;
>-
>- if (StrCmp (VariableName, EFI_PLATFORM_LANG_CODES_VARIABLE_NAME) == 0) {
>- //
>- // PlatformLangCodes is a volatile variable, so it can not be updated at runtime.
>- //
>- if (AtRuntime ()) {
>- return EFI_WRITE_PROTECTED;
>- }
>-
>- SetLanguageCodes = TRUE;
>-
>- //
>- // According to UEFI spec, PlatformLangCodes is only set once in firmware initialization, and is read-only
>- // Therefore, in variable driver, only store the original value for other use.
>- //
>- if (mVariableModuleGlobal->PlatformLangCodes != NULL) {
>- FreePool (mVariableModuleGlobal->PlatformLangCodes);
>- }
>- mVariableModuleGlobal->PlatformLangCodes = AllocateRuntimeCopyPool (DataSize, Data);
>- ASSERT (mVariableModuleGlobal->PlatformLangCodes != NULL);
>-
>- //
>- // PlatformLang holds a single language from PlatformLangCodes,
>- // so the size of PlatformLangCodes is enough for the PlatformLang.
>- //
>- if (mVariableModuleGlobal->PlatformLang != NULL) {
>- FreePool (mVariableModuleGlobal->PlatformLang);
>- }
>- mVariableModuleGlobal->PlatformLang = AllocateRuntimePool (DataSize);
>- ASSERT (mVariableModuleGlobal->PlatformLang != NULL);
>-
>- } else if (StrCmp (VariableName, EFI_LANG_CODES_VARIABLE_NAME) == 0) {
>- //
>- // LangCodes is a volatile variable, so it can not be updated at runtime.
>- //
>- if (AtRuntime ()) {
>- return EFI_WRITE_PROTECTED;
>- }
>-
>- SetLanguageCodes = TRUE;
>-
>- //
>- // According to UEFI spec, LangCodes is only set once in firmware initialization, and is read-only
>- // Therefore, in variable driver, only store the original value for other use.
>- //
>- if (mVariableModuleGlobal->LangCodes != NULL) {
>- FreePool (mVariableModuleGlobal->LangCodes);
>- }
>- mVariableModuleGlobal->LangCodes = AllocateRuntimeCopyPool (DataSize, Data);
>- ASSERT (mVariableModuleGlobal->LangCodes != NULL);
>- }
>-
>- if (SetLanguageCodes
>- && (mVariableModuleGlobal->PlatformLangCodes != NULL)
>- && (mVariableModuleGlobal->LangCodes != NULL)) {
>- //
>- // Update Lang if PlatformLang is already set
>- // Update PlatformLang if Lang is already set
>- //
>- Status = FindVariable (EFI_PLATFORM_LANG_VARIABLE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>- if (!EFI_ERROR (Status)) {
>- //
>- // Update Lang
>- //
>- VariableName = EFI_PLATFORM_LANG_VARIABLE_NAME;
>- Data = GetVariableDataPtr (Variable.CurrPtr);
>- DataSize = Variable.CurrPtr->DataSize;
>- } else {
>- Status = FindVariable (EFI_LANG_VARIABLE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>- if (!EFI_ERROR (Status)) {
>- //
>- // Update PlatformLang
>- //
>- VariableName = EFI_LANG_VARIABLE_NAME;
>- Data = GetVariableDataPtr (Variable.CurrPtr);
>- DataSize = Variable.CurrPtr->DataSize;
>- } else {
>- //
>- // Neither PlatformLang nor Lang is set, directly return
>- //
>- return EFI_SUCCESS;
>- }
>- }
>- }
>-
>- Status = EFI_SUCCESS;
>-
>- //
>- // According to UEFI spec, "Lang" and "PlatformLang" is NV|BS|RT attributions.
>- //
>- Attributes = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS;
>-
>- if (StrCmp (VariableName, EFI_PLATFORM_LANG_VARIABLE_NAME) == 0) {
>- //
>- // Update Lang when PlatformLangCodes/LangCodes were set.
>- //
>- if ((mVariableModuleGlobal->PlatformLangCodes != NULL) && (mVariableModuleGlobal->LangCodes != NULL)) {
>- //
>- // When setting PlatformLang, firstly get most matched language string from supported language codes.
>- //
>- BestPlatformLang = VariableGetBestLanguage (mVariableModuleGlobal->PlatformLangCodes, FALSE, Data, NULL);
>- if (BestPlatformLang != NULL) {
>- //
>- // Get the corresponding index in language codes.
>- //
>- Index = GetIndexFromSupportedLangCodes (mVariableModuleGlobal->PlatformLangCodes, BestPlatformLang, FALSE);
>-
>- //
>- // Get the corresponding ISO639 language tag according to RFC4646 language tag.
>- //
>- BestLang = GetLangFromSupportedLangCodes (mVariableModuleGlobal->LangCodes, Index, TRUE);
>-
>- //
>- // Check the variable space for both Lang and PlatformLang variable.
>- //
>- VariableEntry[0].VariableSize = ISO_639_2_ENTRY_SIZE + 1;
>- VariableEntry[0].Guid = &gEfiGlobalVariableGuid;
>- VariableEntry[0].Name = EFI_LANG_VARIABLE_NAME;
>-
>- VariableEntry[1].VariableSize = AsciiStrSize (BestPlatformLang);
>- VariableEntry[1].Guid = &gEfiGlobalVariableGuid;
>- VariableEntry[1].Name = EFI_PLATFORM_LANG_VARIABLE_NAME;
>- if (!CheckRemainingSpaceForConsistency (VARIABLE_ATTRIBUTE_NV_BS_RT, &VariableEntry[0], &VariableEntry[1], NULL)) {
>- //
>- // No enough variable space to set both Lang and PlatformLang successfully.
>- //
>- Status = EFI_OUT_OF_RESOURCES;
>- } else {
>- //
>- // Successfully convert PlatformLang to Lang, and set the BestLang value into Lang variable simultaneously.
>- //
>- FindVariable (EFI_LANG_VARIABLE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal->VariableGlobal,
>FALSE);
>-
>- Status = UpdateVariable (EFI_LANG_VARIABLE_NAME, &gEfiGlobalVariableGuid, BestLang,
>- ISO_639_2_ENTRY_SIZE + 1, Attributes, 0, 0, &Variable, NULL);
>- }
>-
>- DEBUG ((EFI_D_INFO, "Variable Driver Auto Update PlatformLang, PlatformLang:%a, Lang:%a Status: %r\n", BestPlatformLang,
>BestLang, Status));
>- }
>- }
>-
>- } else if (StrCmp (VariableName, EFI_LANG_VARIABLE_NAME) == 0) {
>- //
>- // Update PlatformLang when PlatformLangCodes/LangCodes were set.
>- //
>- if ((mVariableModuleGlobal->PlatformLangCodes != NULL) && (mVariableModuleGlobal->LangCodes != NULL)) {
>- //
>- // When setting Lang, firstly get most matched language string from supported language codes.
>- //
>- BestLang = VariableGetBestLanguage (mVariableModuleGlobal->LangCodes, TRUE, Data, NULL);
>- if (BestLang != NULL) {
>- //
>- // Get the corresponding index in language codes.
>- //
>- Index = GetIndexFromSupportedLangCodes (mVariableModuleGlobal->LangCodes, BestLang, TRUE);
>-
>- //
>- // Get the corresponding RFC4646 language tag according to ISO639 language tag.
>- //
>- BestPlatformLang = GetLangFromSupportedLangCodes (mVariableModuleGlobal->PlatformLangCodes, Index, FALSE);
>-
>- //
>- // Check the variable space for both PlatformLang and Lang variable.
>- //
>- VariableEntry[0].VariableSize = AsciiStrSize (BestPlatformLang);
>- VariableEntry[0].Guid = &gEfiGlobalVariableGuid;
>- VariableEntry[0].Name = EFI_PLATFORM_LANG_VARIABLE_NAME;
>-
>- VariableEntry[1].VariableSize = ISO_639_2_ENTRY_SIZE + 1;
>- VariableEntry[1].Guid = &gEfiGlobalVariableGuid;
>- VariableEntry[1].Name = EFI_LANG_VARIABLE_NAME;
>- if (!CheckRemainingSpaceForConsistency (VARIABLE_ATTRIBUTE_NV_BS_RT, &VariableEntry[0], &VariableEntry[1], NULL)) {
>- //
>- // No enough variable space to set both PlatformLang and Lang successfully.
>- //
>- Status = EFI_OUT_OF_RESOURCES;
>- } else {
>- //
>- // Successfully convert Lang to PlatformLang, and set the BestPlatformLang value into PlatformLang variable simultaneously.
>- //
>- FindVariable (EFI_PLATFORM_LANG_VARIABLE_NAME, &gEfiGlobalVariableGuid, &Variable, &mVariableModuleGlobal-
>>VariableGlobal, FALSE);
>-
>- Status = UpdateVariable (EFI_PLATFORM_LANG_VARIABLE_NAME, &gEfiGlobalVariableGuid, BestPlatformLang,
>- AsciiStrSize (BestPlatformLang), Attributes, 0, 0, &Variable, NULL);
>- }
>-
>- DEBUG ((EFI_D_INFO, "Variable Driver Auto Update Lang, Lang:%a, PlatformLang:%a Status: %r\n", BestLang, BestPlatformLang,
>Status));
>- }
>- }
>- }
>-
>- if (SetLanguageCodes) {
>- //
>- // Continue to set PlatformLangCodes or LangCodes.
>- //
>- return EFI_SUCCESS;
>- } else {
>- return Status;
>- }
>-}
>-
>-/**
>- Update the variable region with Variable information. If EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS is set,
>- index of associated public key is needed.
>-
>- @param[in] VariableName Name of variable.
>- @param[in] VendorGuid Guid of variable.
>- @param[in] Data Variable data.
>- @param[in] DataSize Size of data. 0 means delete.
>- @param[in] Attributes Attributes of the variable.
>- @param[in] KeyIndex Index of associated public key.
>- @param[in] MonotonicCount Value of associated monotonic count.
>- @param[in, out] CacheVariable The variable information which is used to keep track of variable usage.
>- @param[in] TimeStamp Value of associated TimeStamp.
>-
>- @retval EFI_SUCCESS The update operation is success.
>- @retval EFI_OUT_OF_RESOURCES Variable region is full, can not write other data into this region.
>-
>-**/
>-EFI_STATUS
>-UpdateVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN UINT32 Attributes OPTIONAL,
>- IN UINT32 KeyIndex OPTIONAL,
>- IN UINT64 MonotonicCount OPTIONAL,
>- IN OUT VARIABLE_POINTER_TRACK *CacheVariable,
>- IN EFI_TIME *TimeStamp OPTIONAL
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_HEADER *NextVariable;
>- UINTN ScratchSize;
>- UINTN MaxDataSize;
>- UINTN VarNameOffset;
>- UINTN VarDataOffset;
>- UINTN VarNameSize;
>- UINTN VarSize;
>- BOOLEAN Volatile;
>- EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL *Fvb;
>- UINT8 State;
>- VARIABLE_POINTER_TRACK *Variable;
>- VARIABLE_POINTER_TRACK NvVariable;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- UINTN CacheOffset;
>- UINT8 *BufferForMerge;
>- UINTN MergedBufSize;
>- BOOLEAN DataReady;
>- UINTN DataOffset;
>- BOOLEAN IsCommonVariable;
>- BOOLEAN IsCommonUserVariable;
>-
>- if (mVariableModuleGlobal->FvbInstance == NULL) {
>- //
>- // The FVB protocol is not installed, so the EFI_VARIABLE_WRITE_ARCH_PROTOCOL is not installed.
>- //
>- if ((Attributes & EFI_VARIABLE_NON_VOLATILE) != 0) {
>- //
>- // Trying to update NV variable prior to the installation of EFI_VARIABLE_WRITE_ARCH_PROTOCOL
>- //
>- return EFI_NOT_AVAILABLE_YET;
>- } else if ((Attributes & VARIABLE_ATTRIBUTE_AT_AW) != 0) {
>- //
>- // Trying to update volatile authenticated variable prior to the installation of EFI_VARIABLE_WRITE_ARCH_PROTOCOL
>- // The authenticated variable perhaps is not initialized, just return here.
>- //
>- return EFI_NOT_AVAILABLE_YET;
>- }
>- }
>-
>- if ((CacheVariable->CurrPtr == NULL) || CacheVariable->Volatile) {
>- Variable = CacheVariable;
>- } else {
>- //
>- // Update/Delete existing NV variable.
>- // CacheVariable points to the variable in the memory copy of Flash area
>- // Now let Variable points to the same variable in Flash area.
>- //
>- VariableStoreHeader = (VARIABLE_STORE_HEADER *) ((UINTN) mVariableModuleGlobal-
>>VariableGlobal.NonVolatileVariableBase);
>- Variable = &NvVariable;
>- Variable->StartPtr = GetStartPointer (VariableStoreHeader);
>- Variable->EndPtr = GetEndPointer (VariableStoreHeader);
>- Variable->CurrPtr = (VARIABLE_HEADER *)((UINTN)Variable->StartPtr + ((UINTN)CacheVariable->CurrPtr - (UINTN)CacheVariable-
>>StartPtr));
>- if (CacheVariable->InDeletedTransitionPtr != NULL) {
>- Variable->InDeletedTransitionPtr = (VARIABLE_HEADER *)((UINTN)Variable->StartPtr + ((UINTN)CacheVariable-
>>InDeletedTransitionPtr - (UINTN)CacheVariable->StartPtr));
>- } else {
>- Variable->InDeletedTransitionPtr = NULL;
>- }
>- Variable->Volatile = FALSE;
>- }
>-
>- Fvb = mVariableModuleGlobal->FvbInstance;
>-
>- //
>- // Tricky part: Use scratch data area at the end of volatile variable store
>- // as a temporary storage.
>- //
>- NextVariable = GetEndPointer ((VARIABLE_STORE_HEADER *) ((UINTN) mVariableModuleGlobal-
>>VariableGlobal.VolatileVariableBase));
>- ScratchSize = mVariableModuleGlobal->ScratchBufferSize;
>- SetMem (NextVariable, ScratchSize, 0xff);
>- DataReady = FALSE;
>-
>- if (Variable->CurrPtr != NULL) {
>- //
>- // Update/Delete existing variable.
>- //
>- if (AtRuntime ()) {
>- //
>- // If AtRuntime and the variable is Volatile and Runtime Access,
>- // the volatile is ReadOnly, and SetVariable should be aborted and
>- // return EFI_WRITE_PROTECTED.
>- //
>- if (Variable->Volatile) {
>- Status = EFI_WRITE_PROTECTED;
>- goto Done;
>- }
>- //
>- // Only variable that have NV attributes can be updated/deleted in Runtime.
>- //
>- if ((Variable->CurrPtr->Attributes & EFI_VARIABLE_NON_VOLATILE) == 0) {
>- Status = EFI_INVALID_PARAMETER;
>- goto Done;
>- }
>-
>- //
>- // Only variable that have RT attributes can be updated/deleted in Runtime.
>- //
>- if ((Variable->CurrPtr->Attributes & EFI_VARIABLE_RUNTIME_ACCESS) == 0) {
>- Status = EFI_INVALID_PARAMETER;
>- goto Done;
>- }
>- }
>-
>- //
>- // Setting a data variable with no access, or zero DataSize attributes
>- // causes it to be deleted.
>- // When the EFI_VARIABLE_APPEND_WRITE attribute is set, DataSize of zero will
>- // not delete the variable.
>- //
>- if ((((Attributes & EFI_VARIABLE_APPEND_WRITE) == 0) && (DataSize == 0))|| ((Attributes & (EFI_VARIABLE_RUNTIME_ACCESS |
>EFI_VARIABLE_BOOTSERVICE_ACCESS)) == 0)) {
>- if (Variable->InDeletedTransitionPtr != NULL) {
>- //
>- // Both ADDED and IN_DELETED_TRANSITION variable are present,
>- // set IN_DELETED_TRANSITION one to DELETED state first.
>- //
>- State = Variable->InDeletedTransitionPtr->State;
>- State &= VAR_DELETED;
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- Variable->Volatile,
>- FALSE,
>- Fvb,
>- (UINTN) &Variable->InDeletedTransitionPtr->State,
>- sizeof (UINT8),
>- &State
>- );
>- if (!EFI_ERROR (Status)) {
>- if (!Variable->Volatile) {
>- ASSERT (CacheVariable->InDeletedTransitionPtr != NULL);
>- CacheVariable->InDeletedTransitionPtr->State = State;
>- }
>- } else {
>- goto Done;
>- }
>- }
>-
>- State = Variable->CurrPtr->State;
>- State &= VAR_DELETED;
>-
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- Variable->Volatile,
>- FALSE,
>- Fvb,
>- (UINTN) &Variable->CurrPtr->State,
>- sizeof (UINT8),
>- &State
>- );
>- if (!EFI_ERROR (Status)) {
>- UpdateVariableInfo (VariableName, VendorGuid, Variable->Volatile, FALSE, FALSE, TRUE, FALSE);
>- if (!Variable->Volatile) {
>- CacheVariable->CurrPtr->State = State;
>- FlushHobVariableToFlash (VariableName, VendorGuid);
>- }
>- }
>- goto Done;
>- }
>- //
>- // If the variable is marked valid, and the same data has been passed in,
>- // then return to the caller immediately.
>- //
>- if (DataSizeOfVariable (Variable->CurrPtr) == DataSize &&
>- (CompareMem (Data, GetVariableDataPtr (Variable->CurrPtr), DataSize) == 0) &&
>- ((Attributes & EFI_VARIABLE_APPEND_WRITE) == 0) &&
>- (TimeStamp == NULL)) {
>- //
>- // Variable content unchanged and no need to update timestamp, just return.
>- //
>- UpdateVariableInfo (VariableName, VendorGuid, Variable->Volatile, FALSE, TRUE, FALSE, FALSE);
>- Status = EFI_SUCCESS;
>- goto Done;
>- } else if ((Variable->CurrPtr->State == VAR_ADDED) ||
>- (Variable->CurrPtr->State == (VAR_ADDED & VAR_IN_DELETED_TRANSITION))) {
>-
>- //
>- // EFI_VARIABLE_APPEND_WRITE attribute only effects for existing variable
>- //
>- if ((Attributes & EFI_VARIABLE_APPEND_WRITE) != 0) {
>- //
>- // NOTE: From 0 to DataOffset of NextVariable is reserved for Variable Header and Name.
>- // From DataOffset of NextVariable is to save the existing variable data.
>- //
>- DataOffset = sizeof (VARIABLE_HEADER) + Variable->CurrPtr->NameSize + GET_PAD_SIZE (Variable->CurrPtr->NameSize);
>- BufferForMerge = (UINT8 *) ((UINTN) NextVariable + DataOffset);
>- CopyMem (BufferForMerge, (UINT8 *) ((UINTN) Variable->CurrPtr + DataOffset), Variable->CurrPtr->DataSize);
>-
>- //
>- // Set Max Common/Auth Variable Data Size as default MaxDataSize
>- //
>- if ((Attributes & VARIABLE_ATTRIBUTE_AT_AW) != 0) {
>- MaxDataSize = mVariableModuleGlobal->MaxAuthVariableSize - DataOffset;
>- } else {
>- MaxDataSize = mVariableModuleGlobal->MaxVariableSize - DataOffset;
>- }
>-
>- if ((CompareGuid (VendorGuid, &gEfiImageSecurityDatabaseGuid) &&
>- ((StrCmp (VariableName, EFI_IMAGE_SECURITY_DATABASE) == 0) || (StrCmp (VariableName,
>EFI_IMAGE_SECURITY_DATABASE1) == 0) ||
>- (StrCmp (VariableName, EFI_IMAGE_SECURITY_DATABASE2) == 0))) ||
>- (CompareGuid (VendorGuid, &gEfiGlobalVariableGuid) && (StrCmp (VariableName, EFI_KEY_EXCHANGE_KEY_NAME) == 0))) {
>- //
>- // For variables with formatted as EFI_SIGNATURE_LIST, the driver shall not perform an append of
>- // EFI_SIGNATURE_DATA values that are already part of the existing variable value.
>- //
>- Status = AppendSignatureList (
>- BufferForMerge,
>- Variable->CurrPtr->DataSize,
>- MaxDataSize - Variable->CurrPtr->DataSize,
>- Data,
>- DataSize,
>- &MergedBufSize
>- );
>- if (Status == EFI_BUFFER_TOO_SMALL) {
>- //
>- // Signature List is too long, Failed to Append.
>- //
>- Status = EFI_INVALID_PARAMETER;
>- goto Done;
>- }
>-
>- if (MergedBufSize == Variable->CurrPtr->DataSize) {
>- if ((TimeStamp == NULL) || CompareTimeStamp (TimeStamp, &Variable->CurrPtr->TimeStamp)) {
>- //
>- // New EFI_SIGNATURE_DATA is not found and timestamp is not later
>- // than current timestamp, return EFI_SUCCESS directly.
>- //
>- UpdateVariableInfo (VariableName, VendorGuid, Variable->Volatile, FALSE, TRUE, FALSE, FALSE);
>- Status = EFI_SUCCESS;
>- goto Done;
>- }
>- }
>- } else {
>- //
>- // For other Variables, append the new data to the end of existing data.
>- // Max Harware error record variable data size is different from common/auth variable
>- //
>- if ((Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- MaxDataSize = PcdGet32 (PcdMaxHardwareErrorVariableSize) - DataOffset;
>- }
>-
>- if (Variable->CurrPtr->DataSize + DataSize > MaxDataSize) {
>- //
>- // Existing data size + new data size exceed maximum variable size limitation.
>- //
>- Status = EFI_INVALID_PARAMETER;
>- goto Done;
>- }
>- CopyMem ((UINT8*) ((UINTN) BufferForMerge + Variable->CurrPtr->DataSize), Data, DataSize);
>- MergedBufSize = Variable->CurrPtr->DataSize + DataSize;
>- }
>-
>- //
>- // BufferForMerge(from DataOffset of NextVariable) has included the merged existing and new data.
>- //
>- Data = BufferForMerge;
>- DataSize = MergedBufSize;
>- DataReady = TRUE;
>- }
>-
>- //
>- // Mark the old variable as in delete transition.
>- //
>- State = Variable->CurrPtr->State;
>- State &= VAR_IN_DELETED_TRANSITION;
>-
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- Variable->Volatile,
>- FALSE,
>- Fvb,
>- (UINTN) &Variable->CurrPtr->State,
>- sizeof (UINT8),
>- &State
>- );
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- if (!Variable->Volatile) {
>- CacheVariable->CurrPtr->State = State;
>- }
>- }
>- } else {
>- //
>- // Not found existing variable. Create a new variable.
>- //
>-
>- if ((DataSize == 0) && ((Attributes & EFI_VARIABLE_APPEND_WRITE) != 0)) {
>- Status = EFI_SUCCESS;
>- goto Done;
>- }
>-
>- //
>- // Make sure we are trying to create a new variable.
>- // Setting a data variable with zero DataSize or no access attributes means to delete it.
>- //
>- if (DataSize == 0 || (Attributes & (EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS)) == 0) {
>- Status = EFI_NOT_FOUND;
>- goto Done;
>- }
>-
>- //
>- // Only variable have NV|RT attribute can be created in Runtime.
>- //
>- if (AtRuntime () &&
>- (((Attributes & EFI_VARIABLE_RUNTIME_ACCESS) == 0) || ((Attributes & EFI_VARIABLE_NON_VOLATILE) == 0))) {
>- Status = EFI_INVALID_PARAMETER;
>- goto Done;
>- }
>- }
>-
>- //
>- // Function part - create a new variable and copy the data.
>- // Both update a variable and create a variable will come here.
>- //
>- NextVariable->StartId = VARIABLE_DATA;
>- //
>- // NextVariable->State = VAR_ADDED;
>- //
>- NextVariable->Reserved = 0;
>- NextVariable->PubKeyIndex = KeyIndex;
>- NextVariable->MonotonicCount = MonotonicCount;
>- ZeroMem (&NextVariable->TimeStamp, sizeof (EFI_TIME));
>-
>- if (((Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) != 0) &&
>- (TimeStamp != NULL)) {
>- if ((Attributes & EFI_VARIABLE_APPEND_WRITE) == 0) {
>- CopyMem (&NextVariable->TimeStamp, TimeStamp, sizeof (EFI_TIME));
>- } else {
>- //
>- // In the case when the EFI_VARIABLE_APPEND_WRITE attribute is set, only
>- // when the new TimeStamp value is later than the current timestamp associated
>- // with the variable, we need associate the new timestamp with the updated value.
>- //
>- if (Variable->CurrPtr != NULL) {
>- if (CompareTimeStamp (&Variable->CurrPtr->TimeStamp, TimeStamp)) {
>- CopyMem (&NextVariable->TimeStamp, TimeStamp, sizeof (EFI_TIME));
>- }
>- }
>- }
>- }
>-
>- //
>- // The EFI_VARIABLE_APPEND_WRITE attribute will never be set in the returned
>- // Attributes bitmask parameter of a GetVariable() call.
>- //
>- NextVariable->Attributes = Attributes & (~EFI_VARIABLE_APPEND_WRITE);
>-
>- VarNameOffset = sizeof (VARIABLE_HEADER);
>- VarNameSize = StrSize (VariableName);
>- CopyMem (
>- (UINT8 *) ((UINTN) NextVariable + VarNameOffset),
>- VariableName,
>- VarNameSize
>- );
>- VarDataOffset = VarNameOffset + VarNameSize + GET_PAD_SIZE (VarNameSize);
>-
>- //
>- // If DataReady is TRUE, it means the variable data has been saved into
>- // NextVariable during EFI_VARIABLE_APPEND_WRITE operation preparation.
>- //
>- if (!DataReady) {
>- CopyMem (
>- (UINT8 *) ((UINTN) NextVariable + VarDataOffset),
>- Data,
>- DataSize
>- );
>- }
>-
>- CopyMem (&NextVariable->VendorGuid, VendorGuid, sizeof (EFI_GUID));
>- //
>- // There will be pad bytes after Data, the NextVariable->NameSize and
>- // NextVariable->DataSize should not include pad size so that variable
>- // service can get actual size in GetVariable.
>- //
>- NextVariable->NameSize = (UINT32)VarNameSize;
>- NextVariable->DataSize = (UINT32)DataSize;
>-
>- //
>- // The actual size of the variable that stores in storage should
>- // include pad size.
>- //
>- VarSize = VarDataOffset + DataSize + GET_PAD_SIZE (DataSize);
>- if ((Attributes & EFI_VARIABLE_NON_VOLATILE) != 0) {
>- //
>- // Create a nonvolatile variable.
>- //
>- Volatile = FALSE;
>-
>- IsCommonVariable = FALSE;
>- IsCommonUserVariable = FALSE;
>- if ((Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == 0) {
>- IsCommonVariable = TRUE;
>- IsCommonUserVariable = IsUserVariable (NextVariable);
>- }
>- if ((((Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) != 0)
>- && ((VarSize + mVariableModuleGlobal->HwErrVariableTotalSize) > PcdGet32 (PcdHwErrStorageSize)))
>- || (IsCommonVariable && ((VarSize + mVariableModuleGlobal->CommonVariableTotalSize) > mVariableModuleGlobal-
>>CommonVariableSpace))
>- || (IsCommonVariable && AtRuntime () && ((VarSize + mVariableModuleGlobal->CommonVariableTotalSize) >
>mVariableModuleGlobal->CommonRuntimeVariableSpace))
>- || (IsCommonUserVariable && ((VarSize + mVariableModuleGlobal->CommonUserVariableTotalSize) > mVariableModuleGlobal-
>>CommonMaxUserVariableSpace))) {
>- if (AtRuntime ()) {
>- if (IsCommonUserVariable && ((VarSize + mVariableModuleGlobal->CommonUserVariableTotalSize) > mVariableModuleGlobal-
>>CommonMaxUserVariableSpace)) {
>- RecordVarErrorFlag (VAR_ERROR_FLAG_USER_ERROR, VariableName, VendorGuid, Attributes, VarSize);
>- }
>- if (IsCommonVariable && ((VarSize + mVariableModuleGlobal->CommonVariableTotalSize) > mVariableModuleGlobal-
>>CommonRuntimeVariableSpace)) {
>- RecordVarErrorFlag (VAR_ERROR_FLAG_SYSTEM_ERROR, VariableName, VendorGuid, Attributes, VarSize);
>- }
>- Status = EFI_OUT_OF_RESOURCES;
>- goto Done;
>- }
>- //
>- // Perform garbage collection & reclaim operation, and integrate the new variable at the same time.
>- //
>- Status = Reclaim (
>- mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase,
>- &mVariableModuleGlobal->NonVolatileLastVariableOffset,
>- FALSE,
>- Variable,
>- NextVariable,
>- HEADER_ALIGN (VarSize),
>- FALSE
>- );
>- if (!EFI_ERROR (Status)) {
>- //
>- // The new variable has been integrated successfully during reclaiming.
>- //
>- if (Variable->CurrPtr != NULL) {
>- CacheVariable->CurrPtr = (VARIABLE_HEADER *)((UINTN) CacheVariable->StartPtr + ((UINTN) Variable->CurrPtr - (UINTN)
>Variable->StartPtr));
>- CacheVariable->InDeletedTransitionPtr = NULL;
>- }
>- UpdateVariableInfo (VariableName, VendorGuid, FALSE, FALSE, TRUE, FALSE, FALSE);
>- FlushHobVariableToFlash (VariableName, VendorGuid);
>- } else {
>- if (IsCommonUserVariable && ((VarSize + mVariableModuleGlobal->CommonUserVariableTotalSize) > mVariableModuleGlobal-
>>CommonMaxUserVariableSpace)) {
>- RecordVarErrorFlag (VAR_ERROR_FLAG_USER_ERROR, VariableName, VendorGuid, Attributes, VarSize);
>- }
>- if (IsCommonVariable && ((VarSize + mVariableModuleGlobal->CommonVariableTotalSize) > mVariableModuleGlobal-
>>CommonVariableSpace)) {
>- RecordVarErrorFlag (VAR_ERROR_FLAG_SYSTEM_ERROR, VariableName, VendorGuid, Attributes, VarSize);
>- }
>- }
>- goto Done;
>- }
>- //
>- // Four steps
>- // 1. Write variable header
>- // 2. Set variable state to header valid
>- // 3. Write variable data
>- // 4. Set variable state to valid
>- //
>- //
>- // Step 1:
>- //
>- CacheOffset = mVariableModuleGlobal->NonVolatileLastVariableOffset;
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE,
>- TRUE,
>- Fvb,
>- mVariableModuleGlobal->NonVolatileLastVariableOffset,
>- sizeof (VARIABLE_HEADER),
>- (UINT8 *) NextVariable
>- );
>-
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- //
>- // Step 2:
>- //
>- NextVariable->State = VAR_HEADER_VALID_ONLY;
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE,
>- TRUE,
>- Fvb,
>- mVariableModuleGlobal->NonVolatileLastVariableOffset + OFFSET_OF (VARIABLE_HEADER, State),
>- sizeof (UINT8),
>- &NextVariable->State
>- );
>-
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- //
>- // Step 3:
>- //
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE,
>- TRUE,
>- Fvb,
>- mVariableModuleGlobal->NonVolatileLastVariableOffset + sizeof (VARIABLE_HEADER),
>- (UINT32) VarSize - sizeof (VARIABLE_HEADER),
>- (UINT8 *) NextVariable + sizeof (VARIABLE_HEADER)
>- );
>-
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- //
>- // Step 4:
>- //
>- NextVariable->State = VAR_ADDED;
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- FALSE,
>- TRUE,
>- Fvb,
>- mVariableModuleGlobal->NonVolatileLastVariableOffset + OFFSET_OF (VARIABLE_HEADER, State),
>- sizeof (UINT8),
>- &NextVariable->State
>- );
>-
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- mVariableModuleGlobal->NonVolatileLastVariableOffset += HEADER_ALIGN (VarSize);
>-
>- if ((Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) != 0) {
>- mVariableModuleGlobal->HwErrVariableTotalSize += HEADER_ALIGN (VarSize);
>- } else {
>- mVariableModuleGlobal->CommonVariableTotalSize += HEADER_ALIGN (VarSize);
>- if (IsCommonUserVariable) {
>- mVariableModuleGlobal->CommonUserVariableTotalSize += HEADER_ALIGN (VarSize);
>- }
>- }
>- //
>- // update the memory copy of Flash region.
>- //
>- CopyMem ((UINT8 *)mNvVariableCache + CacheOffset, (UINT8 *)NextVariable, VarSize);
>- } else {
>- //
>- // Create a volatile variable.
>- //
>- Volatile = TRUE;
>-
>- if ((UINT32) (VarSize + mVariableModuleGlobal->VolatileLastVariableOffset) >
>- ((VARIABLE_STORE_HEADER *) ((UINTN) (mVariableModuleGlobal->VariableGlobal.VolatileVariableBase)))->Size) {
>- //
>- // Perform garbage collection & reclaim operation, and integrate the new variable at the same time.
>- //
>- Status = Reclaim (
>- mVariableModuleGlobal->VariableGlobal.VolatileVariableBase,
>- &mVariableModuleGlobal->VolatileLastVariableOffset,
>- TRUE,
>- Variable,
>- NextVariable,
>- HEADER_ALIGN (VarSize),
>- FALSE
>- );
>- if (!EFI_ERROR (Status)) {
>- //
>- // The new variable has been integrated successfully during reclaiming.
>- //
>- if (Variable->CurrPtr != NULL) {
>- CacheVariable->CurrPtr = (VARIABLE_HEADER *)((UINTN) CacheVariable->StartPtr + ((UINTN) Variable->CurrPtr - (UINTN)
>Variable->StartPtr));
>- CacheVariable->InDeletedTransitionPtr = NULL;
>- }
>- UpdateVariableInfo (VariableName, VendorGuid, TRUE, FALSE, TRUE, FALSE, FALSE);
>- }
>- goto Done;
>- }
>-
>- NextVariable->State = VAR_ADDED;
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- TRUE,
>- TRUE,
>- Fvb,
>- mVariableModuleGlobal->VolatileLastVariableOffset,
>- (UINT32) VarSize,
>- (UINT8 *) NextVariable
>- );
>-
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- mVariableModuleGlobal->VolatileLastVariableOffset += HEADER_ALIGN (VarSize);
>- }
>-
>- //
>- // Mark the old variable as deleted.
>- //
>- if (!EFI_ERROR (Status) && Variable->CurrPtr != NULL) {
>- if (Variable->InDeletedTransitionPtr != NULL) {
>- //
>- // Both ADDED and IN_DELETED_TRANSITION old variable are present,
>- // set IN_DELETED_TRANSITION one to DELETED state first.
>- //
>- State = Variable->InDeletedTransitionPtr->State;
>- State &= VAR_DELETED;
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- Variable->Volatile,
>- FALSE,
>- Fvb,
>- (UINTN) &Variable->InDeletedTransitionPtr->State,
>- sizeof (UINT8),
>- &State
>- );
>- if (!EFI_ERROR (Status)) {
>- if (!Variable->Volatile) {
>- ASSERT (CacheVariable->InDeletedTransitionPtr != NULL);
>- CacheVariable->InDeletedTransitionPtr->State = State;
>- }
>- } else {
>- goto Done;
>- }
>- }
>-
>- State = Variable->CurrPtr->State;
>- State &= VAR_DELETED;
>-
>- Status = UpdateVariableStore (
>- &mVariableModuleGlobal->VariableGlobal,
>- Variable->Volatile,
>- FALSE,
>- Fvb,
>- (UINTN) &Variable->CurrPtr->State,
>- sizeof (UINT8),
>- &State
>- );
>- if (!EFI_ERROR (Status) && !Variable->Volatile) {
>- CacheVariable->CurrPtr->State = State;
>- }
>- }
>-
>- if (!EFI_ERROR (Status)) {
>- UpdateVariableInfo (VariableName, VendorGuid, Volatile, FALSE, TRUE, FALSE, FALSE);
>- if (!Volatile) {
>- FlushHobVariableToFlash (VariableName, VendorGuid);
>- }
>- }
>-
>-Done:
>- return Status;
>-}
>-
>-/**
>- Check if a Unicode character is a hexadecimal character.
>-
>- This function checks if a Unicode character is a
>- hexadecimal character. The valid hexadecimal character is
>- L'0' to L'9', L'a' to L'f', or L'A' to L'F'.
>-
>-
>- @param Char The character to check against.
>-
>- @retval TRUE If the Char is a hexadecmial character.
>- @retval FALSE If the Char is not a hexadecmial character.
>-
>-**/
>-BOOLEAN
>-EFIAPI
>-IsHexaDecimalDigitCharacter (
>- IN CHAR16 Char
>- )
>-{
>- return (BOOLEAN) ((Char >= L'0' && Char <= L'9') || (Char >= L'A' && Char <= L'F') || (Char >= L'a' && Char <= L'f'));
>-}
>-
>-/**
>-
>- This code checks if variable is hardware error record variable or not.
>-
>- According to UEFI spec, hardware error record variable should use the EFI_HARDWARE_ERROR_VARIABLE VendorGuid
>- and have the L"HwErrRec####" name convention, #### is a printed hex value and no 0x or h is included in the hex value.
>-
>- @param VariableName Pointer to variable name.
>- @param VendorGuid Variable Vendor Guid.
>-
>- @retval TRUE Variable is hardware error record variable.
>- @retval FALSE Variable is not hardware error record variable.
>-
>-**/
>-BOOLEAN
>-EFIAPI
>-IsHwErrRecVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- if (!CompareGuid (VendorGuid, &gEfiHardwareErrorVariableGuid) ||
>- (StrLen (VariableName) != StrLen (L"HwErrRec####")) ||
>- (StrnCmp(VariableName, L"HwErrRec", StrLen (L"HwErrRec")) != 0) ||
>- !IsHexaDecimalDigitCharacter (VariableName[0x8]) ||
>- !IsHexaDecimalDigitCharacter (VariableName[0x9]) ||
>- !IsHexaDecimalDigitCharacter (VariableName[0xA]) ||
>- !IsHexaDecimalDigitCharacter (VariableName[0xB])) {
>- return FALSE;
>- }
>-
>- return TRUE;
>-}
>-
>-/**
>- Mark a variable that will become read-only after leaving the DXE phase of execution.
>-
>- @param[in] This The VARIABLE_LOCK_PROTOCOL instance.
>- @param[in] VariableName A pointer to the variable name that will be made read-only subsequently.
>- @param[in] VendorGuid A pointer to the vendor GUID that will be made read-only subsequently.
>-
>- @retval EFI_SUCCESS The variable specified by the VariableName and the VendorGuid was marked
>- as pending to be read-only.
>- @retval EFI_INVALID_PARAMETER VariableName or VendorGuid is NULL.
>- Or VariableName is an empty string.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource to hold the lock request.
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableLockRequestToLock (
>- IN CONST EDKII_VARIABLE_LOCK_PROTOCOL *This,
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- VARIABLE_ENTRY *Entry;
>- CHAR16 *Name;
>- LIST_ENTRY *Link;
>- VARIABLE_ENTRY *LockedEntry;
>-
>- if (VariableName == NULL || VariableName[0] == 0 || VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (mEndOfDxe) {
>- return EFI_ACCESS_DENIED;
>- }
>-
>- Entry = AllocateRuntimeZeroPool (sizeof (*Entry) + StrSize (VariableName));
>- if (Entry == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- DEBUG ((EFI_D_INFO, "[Variable] Lock: %g:%s\n", VendorGuid, VariableName));
>-
>- AcquireLockOnlyAtBootTime(&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- for ( Link = GetFirstNode (&mLockedVariableList)
>- ; !IsNull (&mLockedVariableList, Link)
>- ; Link = GetNextNode (&mLockedVariableList, Link)
>- ) {
>- LockedEntry = BASE_CR (Link, VARIABLE_ENTRY, Link);
>- Name = (CHAR16 *) ((UINTN) LockedEntry + sizeof (*LockedEntry));
>- if (CompareGuid (&LockedEntry->Guid, VendorGuid) && (StrCmp (Name, VariableName) == 0)) {
>- goto Done;
>- }
>- }
>-
>- Name = (CHAR16 *) ((UINTN) Entry + sizeof (*Entry));
>- StrnCpy (Name, VariableName, StrLen (VariableName));
>- CopyGuid (&Entry->Guid, VendorGuid);
>- InsertTailList (&mLockedVariableList, &Entry->Link);
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- return EFI_SUCCESS;
>-}
>-
>-/**
>-
>- This code finds variable in storage blocks (Volatile or Non-Volatile).
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize is external input.
>- This function will do basic validation, before parse the data.
>-
>- @param VariableName Name of Variable to be found.
>- @param VendorGuid Variable vendor GUID.
>- @param Attributes Attribute value of the variable found.
>- @param DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param Data Data pointer.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Find the specified variable.
>- @return EFI_NOT_FOUND Not found.
>- @return EFI_BUFFER_TO_SMALL DataSize is too small for the result.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceGetVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- OUT UINT32 *Attributes OPTIONAL,
>- IN OUT UINTN *DataSize,
>- OUT VOID *Data
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK Variable;
>- UINTN VarDataSize;
>-
>- if (VariableName == NULL || VendorGuid == NULL || DataSize == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- Status = FindVariable (VariableName, VendorGuid, &Variable, &mVariableModuleGlobal->VariableGlobal, FALSE);
>- if (Variable.CurrPtr == NULL || EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- //
>- // Get data size
>- //
>- VarDataSize = DataSizeOfVariable (Variable.CurrPtr);
>- ASSERT (VarDataSize != 0);
>-
>- if (*DataSize >= VarDataSize) {
>- if (Data == NULL) {
>- Status = EFI_INVALID_PARAMETER;
>- goto Done;
>- }
>-
>- CopyMem (Data, GetVariableDataPtr (Variable.CurrPtr), VarDataSize);
>- if (Attributes != NULL) {
>- *Attributes = Variable.CurrPtr->Attributes;
>- }
>-
>- *DataSize = VarDataSize;
>- UpdateVariableInfo (VariableName, VendorGuid, Variable.Volatile, TRUE, FALSE, FALSE, FALSE);
>-
>- Status = EFI_SUCCESS;
>- goto Done;
>- } else {
>- *DataSize = VarDataSize;
>- Status = EFI_BUFFER_TOO_SMALL;
>- goto Done;
>- }
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>- return Status;
>-}
>-
>-
>-
>-/**
>-
>- This code Finds the Next available variable.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode. This function will do basic validation, before parse the data.
>-
>- @param VariableNameSize Size of the variable name.
>- @param VariableName Pointer to variable name.
>- @param VendorGuid Variable Vendor Guid.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Find the specified variable.
>- @return EFI_NOT_FOUND Not found.
>- @return EFI_BUFFER_TO_SMALL DataSize is too small for the result.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceGetNextVariableName (
>- IN OUT UINTN *VariableNameSize,
>- IN OUT CHAR16 *VariableName,
>- IN OUT EFI_GUID *VendorGuid
>- )
>-{
>- VARIABLE_STORE_TYPE Type;
>- VARIABLE_POINTER_TRACK Variable;
>- VARIABLE_POINTER_TRACK VariableInHob;
>- VARIABLE_POINTER_TRACK VariablePtrTrack;
>- UINTN VarNameSize;
>- EFI_STATUS Status;
>- VARIABLE_STORE_HEADER *VariableStoreHeader[VariableStoreTypeMax];
>-
>- if (VariableNameSize == NULL || VariableName == NULL || VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- Status = FindVariable (VariableName, VendorGuid, &Variable, &mVariableModuleGlobal->VariableGlobal, FALSE);
>- if (Variable.CurrPtr == NULL || EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- if (VariableName[0] != 0) {
>- //
>- // If variable name is not NULL, get next variable.
>- //
>- Variable.CurrPtr = GetNextVariablePtr (Variable.CurrPtr);
>- }
>-
>- //
>- // 0: Volatile, 1: HOB, 2: Non-Volatile.
>- // The index and attributes mapping must be kept in this order as FindVariable
>- // makes use of this mapping to implement search algorithm.
>- //
>- VariableStoreHeader[VariableStoreTypeVolatile] = (VARIABLE_STORE_HEADER *) (UINTN) mVariableModuleGlobal-
>>VariableGlobal.VolatileVariableBase;
>- VariableStoreHeader[VariableStoreTypeHob] = (VARIABLE_STORE_HEADER *) (UINTN) mVariableModuleGlobal-
>>VariableGlobal.HobVariableBase;
>- VariableStoreHeader[VariableStoreTypeNv] = mNvVariableCache;
>-
>- while (TRUE) {
>- //
>- // Switch from Volatile to HOB, to Non-Volatile.
>- //
>- while (!IsValidVariableHeader (Variable.CurrPtr, Variable.EndPtr)) {
>- //
>- // Find current storage index
>- //
>- for (Type = (VARIABLE_STORE_TYPE) 0; Type < VariableStoreTypeMax; Type++) {
>- if ((VariableStoreHeader[Type] != NULL) && (Variable.StartPtr == GetStartPointer (VariableStoreHeader[Type]))) {
>- break;
>- }
>- }
>- ASSERT (Type < VariableStoreTypeMax);
>- //
>- // Switch to next storage
>- //
>- for (Type++; Type < VariableStoreTypeMax; Type++) {
>- if (VariableStoreHeader[Type] != NULL) {
>- break;
>- }
>- }
>- //
>- // Capture the case that
>- // 1. current storage is the last one, or
>- // 2. no further storage
>- //
>- if (Type == VariableStoreTypeMax) {
>- Status = EFI_NOT_FOUND;
>- goto Done;
>- }
>- Variable.StartPtr = GetStartPointer (VariableStoreHeader[Type]);
>- Variable.EndPtr = GetEndPointer (VariableStoreHeader[Type]);
>- Variable.CurrPtr = Variable.StartPtr;
>- }
>-
>- //
>- // Variable is found
>- //
>- if (Variable.CurrPtr->State == VAR_ADDED || Variable.CurrPtr->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- if (!AtRuntime () || ((Variable.CurrPtr->Attributes & EFI_VARIABLE_RUNTIME_ACCESS) != 0)) {
>- if (Variable.CurrPtr->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- //
>- // If it is a IN_DELETED_TRANSITION variable,
>- // and there is also a same ADDED one at the same time,
>- // don't return it.
>- //
>- VariablePtrTrack.StartPtr = Variable.StartPtr;
>- VariablePtrTrack.EndPtr = Variable.EndPtr;
>- Status = FindVariableEx (
>- GetVariableNamePtr (Variable.CurrPtr),
>- &Variable.CurrPtr->VendorGuid,
>- FALSE,
>- &VariablePtrTrack
>- );
>- if (!EFI_ERROR (Status) && VariablePtrTrack.CurrPtr->State == VAR_ADDED) {
>- Variable.CurrPtr = GetNextVariablePtr (Variable.CurrPtr);
>- continue;
>- }
>- }
>-
>- //
>- // Don't return NV variable when HOB overrides it
>- //
>- if ((VariableStoreHeader[VariableStoreTypeHob] != NULL) && (VariableStoreHeader[VariableStoreTypeNv] != NULL) &&
>- (Variable.StartPtr == GetStartPointer (VariableStoreHeader[VariableStoreTypeNv]))
>- ) {
>- VariableInHob.StartPtr = GetStartPointer (VariableStoreHeader[VariableStoreTypeHob]);
>- VariableInHob.EndPtr = GetEndPointer (VariableStoreHeader[VariableStoreTypeHob]);
>- Status = FindVariableEx (
>- GetVariableNamePtr (Variable.CurrPtr),
>- &Variable.CurrPtr->VendorGuid,
>- FALSE,
>- &VariableInHob
>- );
>- if (!EFI_ERROR (Status)) {
>- Variable.CurrPtr = GetNextVariablePtr (Variable.CurrPtr);
>- continue;
>- }
>- }
>-
>- VarNameSize = NameSizeOfVariable (Variable.CurrPtr);
>- ASSERT (VarNameSize != 0);
>-
>- if (VarNameSize <= *VariableNameSize) {
>- CopyMem (VariableName, GetVariableNamePtr (Variable.CurrPtr), VarNameSize);
>- CopyMem (VendorGuid, &Variable.CurrPtr->VendorGuid, sizeof (EFI_GUID));
>- Status = EFI_SUCCESS;
>- } else {
>- Status = EFI_BUFFER_TOO_SMALL;
>- }
>-
>- *VariableNameSize = VarNameSize;
>- goto Done;
>- }
>- }
>-
>- Variable.CurrPtr = GetNextVariablePtr (Variable.CurrPtr);
>- }
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>- return Status;
>-}
>-
>-/**
>-
>- This code sets variable in storage blocks (Volatile or Non-Volatile).
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param VariableName Name of Variable to be found.
>- @param VendorGuid Variable vendor GUID.
>- @param Attributes Attribute value of the variable found
>- @param DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param Data Data pointer.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Set successfully.
>- @return EFI_OUT_OF_RESOURCES Resource not enough to set variable.
>- @return EFI_NOT_FOUND Not found.
>- @return EFI_WRITE_PROTECTED Variable is read-only.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceSetVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT32 Attributes,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- VARIABLE_POINTER_TRACK Variable;
>- EFI_STATUS Status;
>- VARIABLE_HEADER *NextVariable;
>- EFI_PHYSICAL_ADDRESS Point;
>- UINTN PayloadSize;
>- LIST_ENTRY *Link;
>- VARIABLE_ENTRY *Entry;
>- CHAR16 *Name;
>-
>- //
>- // Check input parameters.
>- //
>- if (VariableName == NULL || VariableName[0] == 0 || VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (DataSize != 0 && Data == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // Check for reserverd bit in variable attribute.
>- //
>- if ((Attributes & (~EFI_VARIABLE_ATTRIBUTES_MASK)) != 0) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // Make sure if runtime bit is set, boot service bit is set also.
>- //
>- if ((Attributes & (EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS)) == EFI_VARIABLE_RUNTIME_ACCESS)
>{
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS and EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS attribute
>- // cannot be set both.
>- //
>- if (((Attributes & EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) == EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS)
>- && ((Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) ==
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if ((Attributes & EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) == EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS) {
>- if (DataSize < AUTHINFO_SIZE) {
>- //
>- // Try to write Authenticated Variable without AuthInfo.
>- //
>- return EFI_SECURITY_VIOLATION;
>- }
>- PayloadSize = DataSize - AUTHINFO_SIZE;
>- } else if ((Attributes & EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) ==
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS) {
>- //
>- // Sanity check for EFI_VARIABLE_AUTHENTICATION_2 descriptor.
>- //
>- if (DataSize < OFFSET_OF_AUTHINFO2_CERT_DATA ||
>- ((EFI_VARIABLE_AUTHENTICATION_2 *) Data)->AuthInfo.Hdr.dwLength > DataSize - (OFFSET_OF
>(EFI_VARIABLE_AUTHENTICATION_2, AuthInfo)) ||
>- ((EFI_VARIABLE_AUTHENTICATION_2 *) Data)->AuthInfo.Hdr.dwLength < OFFSET_OF (WIN_CERTIFICATE_UEFI_GUID, CertData))
>{
>- return EFI_SECURITY_VIOLATION;
>- }
>- PayloadSize = DataSize - AUTHINFO2_SIZE (Data);
>- } else {
>- PayloadSize = DataSize;
>- }
>-
>- if ((UINTN)(~0) - PayloadSize < StrSize(VariableName)){
>- //
>- // Prevent whole variable size overflow
>- //
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- //
>- // The size of the VariableName, including the Unicode Null in bytes plus
>- // the DataSize is limited to maximum size of PcdGet32 (PcdMaxHardwareErrorVariableSize)
>- // bytes for HwErrRec.
>- //
>- if ((Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- if (StrSize (VariableName) + PayloadSize > PcdGet32 (PcdMaxHardwareErrorVariableSize) - sizeof (VARIABLE_HEADER)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- if (!IsHwErrRecVariable(VariableName, VendorGuid)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- } else {
>- //
>- // The size of the VariableName, including the Unicode Null in bytes plus
>- // the DataSize is limited to maximum size of Max(Auth)VariableSize bytes.
>- //
>- if ((Attributes & VARIABLE_ATTRIBUTE_AT_AW) != 0) {
>- if (StrSize (VariableName) + PayloadSize > mVariableModuleGlobal->MaxAuthVariableSize - sizeof (VARIABLE_HEADER)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- } else {
>- if (StrSize (VariableName) + PayloadSize > mVariableModuleGlobal->MaxVariableSize - sizeof (VARIABLE_HEADER)) {
>- return EFI_INVALID_PARAMETER;
>- }
>- }
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- //
>- // Consider reentrant in MCA/INIT/NMI. It needs be reupdated.
>- //
>- if (1 < InterlockedIncrement (&mVariableModuleGlobal->VariableGlobal.ReentrantState)) {
>- Point = mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase;
>- //
>- // Parse non-volatile variable data and get last variable offset.
>- //
>- NextVariable = GetStartPointer ((VARIABLE_STORE_HEADER *) (UINTN) Point);
>- while (IsValidVariableHeader (NextVariable, GetEndPointer ((VARIABLE_STORE_HEADER *) (UINTN) Point))) {
>- NextVariable = GetNextVariablePtr (NextVariable);
>- }
>- mVariableModuleGlobal->NonVolatileLastVariableOffset = (UINTN) NextVariable - (UINTN) Point;
>- }
>-
>- if (mEndOfDxe && mEnableLocking) {
>- //
>- // Treat the variables listed in the forbidden variable list as read-only after leaving DXE phase.
>- //
>- for ( Link = GetFirstNode (&mLockedVariableList)
>- ; !IsNull (&mLockedVariableList, Link)
>- ; Link = GetNextNode (&mLockedVariableList, Link)
>- ) {
>- Entry = BASE_CR (Link, VARIABLE_ENTRY, Link);
>- Name = (CHAR16 *) ((UINTN) Entry + sizeof (*Entry));
>- if (CompareGuid (&Entry->Guid, VendorGuid) && (StrCmp (Name, VariableName) == 0)) {
>- Status = EFI_WRITE_PROTECTED;
>- DEBUG ((EFI_D_INFO, "[Variable]: Changing readonly variable after leaving DXE phase - %g:%s\n", VendorGuid, VariableName));
>- goto Done;
>- }
>- }
>- }
>-
>- Status = InternalVarCheckSetVariableCheck (VariableName, VendorGuid, Attributes, PayloadSize, (VOID *) ((UINTN) Data +
>DataSize - PayloadSize));
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- //
>- // Check whether the input variable is already existed.
>- //
>- Status = FindVariable (VariableName, VendorGuid, &Variable, &mVariableModuleGlobal->VariableGlobal, TRUE);
>- if (!EFI_ERROR (Status)) {
>- if (((Variable.CurrPtr->Attributes & EFI_VARIABLE_RUNTIME_ACCESS) == 0) && AtRuntime ()) {
>- Status = EFI_WRITE_PROTECTED;
>- goto Done;
>- }
>- if (Attributes != 0 && (Attributes & (~EFI_VARIABLE_APPEND_WRITE)) != Variable.CurrPtr->Attributes) {
>- //
>- // If a preexisting variable is rewritten with different attributes, SetVariable() shall not
>- // modify the variable and shall return EFI_INVALID_PARAMETER. Two exceptions to this rule:
>- // 1. No access attributes specified
>- // 2. The only attribute differing is EFI_VARIABLE_APPEND_WRITE
>- //
>- Status = EFI_INVALID_PARAMETER;
>- DEBUG ((EFI_D_INFO, "[Variable]: Rewritten a preexisting variable(0x%08x) with different attributes(0x%08x) - %g:%s\n",
>Variable.CurrPtr->Attributes, Attributes, VendorGuid, VariableName));
>- goto Done;
>- }
>- }
>-
>- if (!FeaturePcdGet (PcdUefiVariableDefaultLangDeprecate)) {
>- //
>- // Hook the operation of setting PlatformLangCodes/PlatformLang and LangCodes/Lang.
>- //
>- Status = AutoUpdateLangVariable (VariableName, Data, DataSize);
>- if (EFI_ERROR (Status)) {
>- //
>- // The auto update operation failed, directly return to avoid inconsistency between PlatformLang and Lang.
>- //
>- goto Done;
>- }
>- }
>-
>- //
>- // Process PK, KEK, Sigdb seperately.
>- //
>- if (CompareGuid (VendorGuid, &gEfiGlobalVariableGuid) && (StrCmp (VariableName, EFI_PLATFORM_KEY_NAME) == 0)){
>- Status = ProcessVarWithPk (VariableName, VendorGuid, Data, DataSize, &Variable, Attributes, TRUE);
>- } else if (CompareGuid (VendorGuid, &gEfiGlobalVariableGuid) && (StrCmp (VariableName, EFI_KEY_EXCHANGE_KEY_NAME) == 0))
>{
>- Status = ProcessVarWithPk (VariableName, VendorGuid, Data, DataSize, &Variable, Attributes, FALSE);
>- } else if (CompareGuid (VendorGuid, &gEfiImageSecurityDatabaseGuid) &&
>- ((StrCmp (VariableName, EFI_IMAGE_SECURITY_DATABASE) == 0) ||
>- (StrCmp (VariableName, EFI_IMAGE_SECURITY_DATABASE1) == 0) ||
>- (StrCmp (VariableName, EFI_IMAGE_SECURITY_DATABASE2) == 0)
>- )
>- ) {
>- Status = ProcessVarWithPk (VariableName, VendorGuid, Data, DataSize, &Variable, Attributes, FALSE);
>- if (EFI_ERROR (Status)) {
>- Status = ProcessVarWithKek (VariableName, VendorGuid, Data, DataSize, &Variable, Attributes);
>- }
>- } else {
>- Status = ProcessVariable (VariableName, VendorGuid, Data, DataSize, &Variable, Attributes);
>- }
>-
>-Done:
>- InterlockedDecrement (&mVariableModuleGlobal->VariableGlobal.ReentrantState);
>- ReleaseLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- if (!AtRuntime ()) {
>- if (!EFI_ERROR (Status)) {
>- SecureBootHook (
>- VariableName,
>- VendorGuid
>- );
>- }
>- }
>-
>- return Status;
>-}
>-
>-/**
>-
>- This code returns information about the EFI variables.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode. This function will do basic validation, before parse the data.
>-
>- @param Attributes Attributes bitmask to specify the type of variables
>- on which to return information.
>- @param MaximumVariableStorageSize Pointer to the maximum size of the storage space available
>- for the EFI variables associated with the attributes specified.
>- @param RemainingVariableStorageSize Pointer to the remaining size of the storage space available
>- for EFI variables associated with the attributes specified.
>- @param MaximumVariableSize Pointer to the maximum size of an individual EFI variables
>- associated with the attributes specified.
>-
>- @return EFI_SUCCESS Query successfully.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceQueryVariableInfoInternal (
>- IN UINT32 Attributes,
>- OUT UINT64 *MaximumVariableStorageSize,
>- OUT UINT64 *RemainingVariableStorageSize,
>- OUT UINT64 *MaximumVariableSize
>- )
>-{
>- VARIABLE_HEADER *Variable;
>- VARIABLE_HEADER *NextVariable;
>- UINT64 VariableSize;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- UINT64 CommonVariableTotalSize;
>- UINT64 HwErrVariableTotalSize;
>- EFI_STATUS Status;
>- VARIABLE_POINTER_TRACK VariablePtrTrack;
>-
>- CommonVariableTotalSize = 0;
>- HwErrVariableTotalSize = 0;
>-
>- if((Attributes & EFI_VARIABLE_NON_VOLATILE) == 0) {
>- //
>- // Query is Volatile related.
>- //
>- VariableStoreHeader = (VARIABLE_STORE_HEADER *) ((UINTN) mVariableModuleGlobal->VariableGlobal.VolatileVariableBase);
>- } else {
>- //
>- // Query is Non-Volatile related.
>- //
>- VariableStoreHeader = mNvVariableCache;
>- }
>-
>- //
>- // Now let's fill *MaximumVariableStorageSize *RemainingVariableStorageSize
>- // with the storage size (excluding the storage header size).
>- //
>- *MaximumVariableStorageSize = VariableStoreHeader->Size - sizeof (VARIABLE_STORE_HEADER);
>-
>- //
>- // Harware error record variable needs larger size.
>- //
>- if ((Attributes & (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) ==
>(EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>- *MaximumVariableStorageSize = PcdGet32 (PcdHwErrStorageSize);
>- *MaximumVariableSize = PcdGet32 (PcdMaxHardwareErrorVariableSize) - sizeof (VARIABLE_HEADER);
>- } else {
>- if ((Attributes & EFI_VARIABLE_NON_VOLATILE) != 0) {
>- if (AtRuntime ()) {
>- *MaximumVariableStorageSize = mVariableModuleGlobal->CommonRuntimeVariableSpace;
>- } else {
>- *MaximumVariableStorageSize = mVariableModuleGlobal->CommonVariableSpace;
>- }
>- }
>-
>- //
>- // Let *MaximumVariableSize be Max(Auth)VariableSize with the exception of the variable header size.
>- //
>- if ((Attributes & VARIABLE_ATTRIBUTE_AT_AW) != 0) {
>- *MaximumVariableSize = mVariableModuleGlobal->MaxAuthVariableSize - sizeof (VARIABLE_HEADER);
>- } else {
>- *MaximumVariableSize = mVariableModuleGlobal->MaxVariableSize - sizeof (VARIABLE_HEADER);
>- }
>- }
>-
>- //
>- // Point to the starting address of the variables.
>- //
>- Variable = GetStartPointer (VariableStoreHeader);
>-
>- //
>- // Now walk through the related variable store.
>- //
>- while (IsValidVariableHeader (Variable, GetEndPointer (VariableStoreHeader))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- VariableSize = (UINT64) (UINTN) NextVariable - (UINT64) (UINTN) Variable;
>-
>- if (AtRuntime ()) {
>- //
>- // We don't take the state of the variables in mind
>- // when calculating RemainingVariableStorageSize,
>- // since the space occupied by variables not marked with
>- // VAR_ADDED is not allowed to be reclaimed in Runtime.
>- //
>- if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- HwErrVariableTotalSize += VariableSize;
>- } else {
>- CommonVariableTotalSize += VariableSize;
>- }
>- } else {
>- //
>- // Only care about Variables with State VAR_ADDED, because
>- // the space not marked as VAR_ADDED is reclaimable now.
>- //
>- if (Variable->State == VAR_ADDED) {
>- if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- HwErrVariableTotalSize += VariableSize;
>- } else {
>- CommonVariableTotalSize += VariableSize;
>- }
>- } else if (Variable->State == (VAR_IN_DELETED_TRANSITION & VAR_ADDED)) {
>- //
>- // If it is a IN_DELETED_TRANSITION variable,
>- // and there is not also a same ADDED one at the same time,
>- // this IN_DELETED_TRANSITION variable is valid.
>- //
>- VariablePtrTrack.StartPtr = GetStartPointer (VariableStoreHeader);
>- VariablePtrTrack.EndPtr = GetEndPointer (VariableStoreHeader);
>- Status = FindVariableEx (
>- GetVariableNamePtr (Variable),
>- &Variable->VendorGuid,
>- FALSE,
>- &VariablePtrTrack
>- );
>- if (!EFI_ERROR (Status) && VariablePtrTrack.CurrPtr->State != VAR_ADDED) {
>- if ((Variable->Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- HwErrVariableTotalSize += VariableSize;
>- } else {
>- CommonVariableTotalSize += VariableSize;
>- }
>- }
>- }
>- }
>-
>- //
>- // Go to the next one.
>- //
>- Variable = NextVariable;
>- }
>-
>- if ((Attributes & EFI_VARIABLE_HARDWARE_ERROR_RECORD) == EFI_VARIABLE_HARDWARE_ERROR_RECORD){
>- *RemainingVariableStorageSize = *MaximumVariableStorageSize - HwErrVariableTotalSize;
>- } else {
>- if (*MaximumVariableStorageSize < CommonVariableTotalSize) {
>- *RemainingVariableStorageSize = 0;
>- } else {
>- *RemainingVariableStorageSize = *MaximumVariableStorageSize - CommonVariableTotalSize;
>- }
>- }
>-
>- if (*RemainingVariableStorageSize < sizeof (VARIABLE_HEADER)) {
>- *MaximumVariableSize = 0;
>- } else if ((*RemainingVariableStorageSize - sizeof (VARIABLE_HEADER)) < *MaximumVariableSize) {
>- *MaximumVariableSize = *RemainingVariableStorageSize - sizeof (VARIABLE_HEADER);
>- }
>-
>- return EFI_SUCCESS;
>-}
>-
>-/**
>-
>- This code returns information about the EFI variables.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode. This function will do basic validation, before parse the data.
>-
>- @param Attributes Attributes bitmask to specify the type of variables
>- on which to return information.
>- @param MaximumVariableStorageSize Pointer to the maximum size of the storage space available
>- for the EFI variables associated with the attributes specified.
>- @param RemainingVariableStorageSize Pointer to the remaining size of the storage space available
>- for EFI variables associated with the attributes specified.
>- @param MaximumVariableSize Pointer to the maximum size of an individual EFI variables
>- associated with the attributes specified.
>-
>- @return EFI_INVALID_PARAMETER An invalid combination of attribute bits was supplied.
>- @return EFI_SUCCESS Query successfully.
>- @return EFI_UNSUPPORTED The attribute is not supported on this platform.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceQueryVariableInfo (
>- IN UINT32 Attributes,
>- OUT UINT64 *MaximumVariableStorageSize,
>- OUT UINT64 *RemainingVariableStorageSize,
>- OUT UINT64 *MaximumVariableSize
>- )
>-{
>- EFI_STATUS Status;
>-
>- if(MaximumVariableStorageSize == NULL || RemainingVariableStorageSize == NULL || MaximumVariableSize == NULL || Attributes
>== 0) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if ((Attributes & VARIABLE_ATTRIBUTE_NV_BS_RT_AT_HR_AW) == 0) {
>- //
>- // Make sure the Attributes combination is supported by the platform.
>- //
>- return EFI_UNSUPPORTED;
>- } else if ((Attributes & (EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS)) ==
>EFI_VARIABLE_RUNTIME_ACCESS) {
>- //
>- // Make sure if runtime bit is set, boot service bit is set also.
>- //
>- return EFI_INVALID_PARAMETER;
>- } else if (AtRuntime () && ((Attributes & EFI_VARIABLE_RUNTIME_ACCESS) == 0)) {
>- //
>- // Make sure RT Attribute is set if we are in Runtime phase.
>- //
>- return EFI_INVALID_PARAMETER;
>- } else if ((Attributes & (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) ==
>EFI_VARIABLE_HARDWARE_ERROR_RECORD) {
>- //
>- // Make sure Hw Attribute is set with NV.
>- //
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>-
>- Status = VariableServiceQueryVariableInfoInternal (
>- Attributes,
>- MaximumVariableStorageSize,
>- RemainingVariableStorageSize,
>- MaximumVariableSize
>- );
>-
>- ReleaseLockOnlyAtBootTime (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock);
>- return Status;
>-}
>-
>-/**
>- This function reclaims variable storage if free size is below the threshold.
>-
>- Caution: This function may be invoked at SMM mode.
>- Care must be taken to make sure not security issue.
>-
>-**/
>-VOID
>-ReclaimForOS(
>- VOID
>- )
>-{
>- EFI_STATUS Status;
>- UINTN RemainingCommonRuntimeVariableSpace;
>- UINTN RemainingHwErrVariableSpace;
>- STATIC BOOLEAN Reclaimed;
>-
>- //
>- // This function will be called only once at EndOfDxe or ReadyToBoot event.
>- //
>- if (Reclaimed) {
>- return;
>- }
>- Reclaimed = TRUE;
>-
>- Status = EFI_SUCCESS;
>-
>- if (mVariableModuleGlobal->CommonRuntimeVariableSpace < mVariableModuleGlobal->CommonVariableTotalSize) {
>- RemainingCommonRuntimeVariableSpace = 0;
>- } else {
>- RemainingCommonRuntimeVariableSpace = mVariableModuleGlobal->CommonRuntimeVariableSpace - mVariableModuleGlobal-
>>CommonVariableTotalSize;
>- }
>-
>- RemainingHwErrVariableSpace = PcdGet32 (PcdHwErrStorageSize) - mVariableModuleGlobal->HwErrVariableTotalSize;
>-
>- //
>- // Check if the free area is below a threshold.
>- //
>- if (((RemainingCommonRuntimeVariableSpace < mVariableModuleGlobal->MaxVariableSize) ||
>- (RemainingCommonRuntimeVariableSpace < mVariableModuleGlobal->MaxAuthVariableSize)) ||
>- ((PcdGet32 (PcdHwErrStorageSize) != 0) &&
>- (RemainingHwErrVariableSpace < PcdGet32 (PcdMaxHardwareErrorVariableSize)))){
>- Status = Reclaim (
>- mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase,
>- &mVariableModuleGlobal->NonVolatileLastVariableOffset,
>- FALSE,
>- NULL,
>- NULL,
>- 0,
>- FALSE
>- );
>- ASSERT_EFI_ERROR (Status);
>- }
>-}
>-
>-/**
>- Init non-volatile variable store.
>-
>- @retval EFI_SUCCESS Function successfully executed.
>- @retval EFI_OUT_OF_RESOURCES Fail to allocate enough memory resource.
>- @retval EFI_VOLUME_CORRUPTED Variable Store or Firmware Volume for Variable Store is corrupted.
>-
>-**/
>-EFI_STATUS
>-InitNonVolatileVariableStore (
>- VOID
>- )
>-{
>- EFI_FIRMWARE_VOLUME_HEADER *FvHeader;
>- VARIABLE_HEADER *Variable;
>- VARIABLE_HEADER *NextVariable;
>- EFI_PHYSICAL_ADDRESS VariableStoreBase;
>- UINT64 VariableStoreLength;
>- UINTN VariableSize;
>- EFI_HOB_GUID_TYPE *GuidHob;
>- EFI_PHYSICAL_ADDRESS NvStorageBase;
>- UINT8 *NvStorageData;
>- UINT32 NvStorageSize;
>- FAULT_TOLERANT_WRITE_LAST_WRITE_DATA *FtwLastWriteData;
>- UINT32 BackUpOffset;
>- UINT32 BackUpSize;
>- UINT32 HwErrStorageSize;
>- UINT32 MaxUserNvVariableSpaceSize;
>- UINT32 BoottimeReservedNvVariableSpaceSize;
>-
>- mVariableModuleGlobal->FvbInstance = NULL;
>-
>- //
>- // Allocate runtime memory used for a memory copy of the FLASH region.
>- // Keep the memory and the FLASH in sync as updates occur.
>- //
>- NvStorageSize = PcdGet32 (PcdFlashNvStorageVariableSize);
>- NvStorageData = AllocateRuntimeZeroPool (NvStorageSize);
>- if (NvStorageData == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- NvStorageBase = (EFI_PHYSICAL_ADDRESS) PcdGet64 (PcdFlashNvStorageVariableBase64);
>- if (NvStorageBase == 0) {
>- NvStorageBase = (EFI_PHYSICAL_ADDRESS) PcdGet32 (PcdFlashNvStorageVariableBase);
>- }
>- //
>- // Copy NV storage data to the memory buffer.
>- //
>- CopyMem (NvStorageData, (UINT8 *) (UINTN) NvStorageBase, NvStorageSize);
>-
>- //
>- // Check the FTW last write data hob.
>- //
>- GuidHob = GetFirstGuidHob (&gEdkiiFaultTolerantWriteGuid);
>- if (GuidHob != NULL) {
>- FtwLastWriteData = (FAULT_TOLERANT_WRITE_LAST_WRITE_DATA *) GET_GUID_HOB_DATA (GuidHob);
>- if (FtwLastWriteData->TargetAddress == NvStorageBase) {
>- DEBUG ((EFI_D_INFO, "Variable: NV storage is backed up in spare block: 0x%x\n", (UINTN) FtwLastWriteData->SpareAddress));
>- //
>- // Copy the backed up NV storage data to the memory buffer from spare block.
>- //
>- CopyMem (NvStorageData, (UINT8 *) (UINTN) (FtwLastWriteData->SpareAddress), NvStorageSize);
>- } else if ((FtwLastWriteData->TargetAddress > NvStorageBase) &&
>- (FtwLastWriteData->TargetAddress < (NvStorageBase + NvStorageSize))) {
>- //
>- // Flash NV storage from the Offset is backed up in spare block.
>- //
>- BackUpOffset = (UINT32) (FtwLastWriteData->TargetAddress - NvStorageBase);
>- BackUpSize = NvStorageSize - BackUpOffset;
>- DEBUG ((EFI_D_INFO, "Variable: High partial NV storage from offset: %x is backed up in spare block: 0x%x\n", BackUpOffset,
>(UINTN) FtwLastWriteData->SpareAddress));
>- //
>- // Copy the partial backed up NV storage data to the memory buffer from spare block.
>- //
>- CopyMem (NvStorageData + BackUpOffset, (UINT8 *) (UINTN) FtwLastWriteData->SpareAddress, BackUpSize);
>- }
>- }
>-
>- FvHeader = (EFI_FIRMWARE_VOLUME_HEADER *) NvStorageData;
>-
>- //
>- // Check if the Firmware Volume is not corrupted
>- //
>- if ((FvHeader->Signature != EFI_FVH_SIGNATURE) || (!CompareGuid (&gEfiSystemNvDataFvGuid, &FvHeader->FileSystemGuid))) {
>- FreePool (NvStorageData);
>- DEBUG ((EFI_D_ERROR, "Firmware Volume for Variable Store is corrupted\n"));
>- return EFI_VOLUME_CORRUPTED;
>- }
>-
>- VariableStoreBase = (EFI_PHYSICAL_ADDRESS) ((UINTN) FvHeader + FvHeader->HeaderLength);
>- VariableStoreLength = (UINT64) (NvStorageSize - FvHeader->HeaderLength);
>-
>- mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase = VariableStoreBase;
>- mNvVariableCache = (VARIABLE_STORE_HEADER *) (UINTN) VariableStoreBase;
>- if (GetVariableStoreStatus (mNvVariableCache) != EfiValid) {
>- FreePool (NvStorageData);
>- DEBUG((EFI_D_ERROR, "Variable Store header is corrupted\n"));
>- return EFI_VOLUME_CORRUPTED;
>- }
>- ASSERT(mNvVariableCache->Size == VariableStoreLength);
>-
>-
>- ASSERT (sizeof (VARIABLE_STORE_HEADER) <= VariableStoreLength);
>-
>- HwErrStorageSize = PcdGet32 (PcdHwErrStorageSize);
>- MaxUserNvVariableSpaceSize = PcdGet32 (PcdMaxUserNvVariableSpaceSize);
>- BoottimeReservedNvVariableSpaceSize = PcdGet32 (PcdBoottimeReservedNvVariableSpaceSize);
>-
>- //
>- // Note that in EdkII variable driver implementation, Hardware Error Record type variable
>- // is stored with common variable in the same NV region. So the platform integrator should
>- // ensure that the value of PcdHwErrStorageSize is less than the value of
>- // (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER)).
>- //
>- ASSERT (HwErrStorageSize < (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER)));
>- //
>- // Ensure that the value of PcdMaxUserNvVariableSpaceSize is less than the value of
>- // (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER)) - PcdGet32 (PcdHwErrStorageSize).
>- //
>- ASSERT (MaxUserNvVariableSpaceSize < (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER) - HwErrStorageSize));
>- //
>- // Ensure that the value of PcdBoottimeReservedNvVariableSpaceSize is less than the value of
>- // (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER)) - PcdGet32 (PcdHwErrStorageSize).
>- //
>- ASSERT (BoottimeReservedNvVariableSpaceSize < (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER) - HwErrStorageSize));
>-
>- mVariableModuleGlobal->CommonVariableSpace = ((UINTN) VariableStoreLength - sizeof (VARIABLE_STORE_HEADER) -
>HwErrStorageSize);
>- mVariableModuleGlobal->CommonMaxUserVariableSpace = ((MaxUserNvVariableSpaceSize != 0) ? MaxUserNvVariableSpaceSize :
>mVariableModuleGlobal->CommonVariableSpace);
>- mVariableModuleGlobal->CommonRuntimeVariableSpace = mVariableModuleGlobal->CommonVariableSpace -
>BoottimeReservedNvVariableSpaceSize;
>-
>- DEBUG ((EFI_D_INFO, "Variable driver common space: 0x%x 0x%x 0x%x\n", mVariableModuleGlobal->CommonVariableSpace,
>mVariableModuleGlobal->CommonMaxUserVariableSpace, mVariableModuleGlobal->CommonRuntimeVariableSpace));
>-
>- //
>- // The max NV variable size should be < (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER)).
>- //
>- ASSERT (MAX_NV_VARIABLE_SIZE < (VariableStoreLength - sizeof (VARIABLE_STORE_HEADER)));
>-
>- mVariableModuleGlobal->MaxVariableSize = PcdGet32 (PcdMaxVariableSize);
>- mVariableModuleGlobal->MaxAuthVariableSize = ((PcdGet32 (PcdMaxAuthVariableSize) != 0) ? PcdGet32
>(PcdMaxAuthVariableSize) : mVariableModuleGlobal->MaxVariableSize);
>-
>- //
>- // Parse non-volatile variable data and get last variable offset.
>- //
>- Variable = GetStartPointer ((VARIABLE_STORE_HEADER *)(UINTN)VariableStoreBase);
>- while (IsValidVariableHeader (Variable, GetEndPointer ((VARIABLE_STORE_HEADER *)(UINTN)VariableStoreBase))) {
>- NextVariable = GetNextVariablePtr (Variable);
>- VariableSize = (UINTN) NextVariable - (UINTN) Variable;
>- if ((Variable->Attributes & (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) ==
>(EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_HARDWARE_ERROR_RECORD)) {
>- mVariableModuleGlobal->HwErrVariableTotalSize += VariableSize;
>- } else {
>- mVariableModuleGlobal->CommonVariableTotalSize += VariableSize;
>- }
>-
>- Variable = NextVariable;
>- }
>- mVariableModuleGlobal->NonVolatileLastVariableOffset = (UINTN) Variable - (UINTN) VariableStoreBase;
>-
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- Flush the HOB variable to flash.
>-
>- @param[in] VariableName Name of variable has been updated or deleted.
>- @param[in] VendorGuid Guid of variable has been updated or deleted.
>-
>-**/
>-VOID
>-FlushHobVariableToFlash (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- VARIABLE_HEADER *Variable;
>- VOID *VariableData;
>- BOOLEAN ErrorFlag;
>-
>- ErrorFlag = FALSE;
>-
>- //
>- // Flush the HOB variable to flash.
>- //
>- if (mVariableModuleGlobal->VariableGlobal.HobVariableBase != 0) {
>- VariableStoreHeader = (VARIABLE_STORE_HEADER *) (UINTN) mVariableModuleGlobal->VariableGlobal.HobVariableBase;
>- //
>- // Set HobVariableBase to 0, it can avoid SetVariable to call back.
>- //
>- mVariableModuleGlobal->VariableGlobal.HobVariableBase = 0;
>- for ( Variable = GetStartPointer (VariableStoreHeader)
>- ; IsValidVariableHeader (Variable, GetEndPointer (VariableStoreHeader))
>- ; Variable = GetNextVariablePtr (Variable)
>- ) {
>- if (Variable->State != VAR_ADDED) {
>- //
>- // The HOB variable has been set to DELETED state in local.
>- //
>- continue;
>- }
>- ASSERT ((Variable->Attributes & EFI_VARIABLE_NON_VOLATILE) != 0);
>- if (VendorGuid == NULL || VariableName == NULL ||
>- !CompareGuid (VendorGuid, &Variable->VendorGuid) ||
>- StrCmp (VariableName, GetVariableNamePtr (Variable)) != 0) {
>- VariableData = GetVariableDataPtr (Variable);
>- Status = VariableServiceSetVariable (
>- GetVariableNamePtr (Variable),
>- &Variable->VendorGuid,
>- Variable->Attributes,
>- Variable->DataSize,
>- VariableData
>- );
>- DEBUG ((EFI_D_INFO, "Variable driver flush the HOB variable to flash: %g %s %r\n", &Variable->VendorGuid,
>GetVariableNamePtr (Variable), Status));
>- } else {
>- //
>- // The updated or deleted variable is matched with the HOB variable.
>- // Don't break here because we will try to set other HOB variables
>- // since this variable could be set successfully.
>- //
>- Status = EFI_SUCCESS;
>- }
>- if (!EFI_ERROR (Status)) {
>- //
>- // If set variable successful, or the updated or deleted variable is matched with the HOB variable,
>- // set the HOB variable to DELETED state in local.
>- //
>- DEBUG ((EFI_D_INFO, "Variable driver set the HOB variable to DELETED state in local: %g %s\n", &Variable->VendorGuid,
>GetVariableNamePtr (Variable)));
>- Variable->State &= VAR_DELETED;
>- } else {
>- ErrorFlag = TRUE;
>- }
>- }
>- if (ErrorFlag) {
>- //
>- // We still have HOB variable(s) not flushed in flash.
>- //
>- mVariableModuleGlobal->VariableGlobal.HobVariableBase = (EFI_PHYSICAL_ADDRESS) (UINTN) VariableStoreHeader;
>- } else {
>- //
>- // All HOB variables have been flushed in flash.
>- //
>- DEBUG ((EFI_D_INFO, "Variable driver: all HOB variables have been flushed in flash.\n"));
>- if (!AtRuntime ()) {
>- FreePool ((VOID *) VariableStoreHeader);
>- }
>- }
>- }
>-
>-}
>-
>-/**
>- Initializes variable write service after FTW was ready.
>-
>- @retval EFI_SUCCESS Function successfully executed.
>- @retval Others Fail to initialize the variable service.
>-
>-**/
>-EFI_STATUS
>-VariableWriteServiceInitialize (
>- VOID
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- UINTN Index;
>- UINT8 Data;
>- EFI_PHYSICAL_ADDRESS VariableStoreBase;
>- EFI_PHYSICAL_ADDRESS NvStorageBase;
>-
>- NvStorageBase = (EFI_PHYSICAL_ADDRESS) PcdGet64 (PcdFlashNvStorageVariableBase64);
>- if (NvStorageBase == 0) {
>- NvStorageBase = (EFI_PHYSICAL_ADDRESS) PcdGet32 (PcdFlashNvStorageVariableBase);
>- }
>- VariableStoreBase = NvStorageBase + (((EFI_FIRMWARE_VOLUME_HEADER *)(UINTN)(NvStorageBase))->HeaderLength);
>-
>- //
>- // Let NonVolatileVariableBase point to flash variable store base directly after FTW ready.
>- //
>- mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase = VariableStoreBase;
>- VariableStoreHeader = (VARIABLE_STORE_HEADER *)(UINTN)VariableStoreBase;
>-
>- //
>- // Check if the free area is really free.
>- //
>- for (Index = mVariableModuleGlobal->NonVolatileLastVariableOffset; Index < VariableStoreHeader->Size; Index++) {
>- Data = ((UINT8 *) mNvVariableCache)[Index];
>- if (Data != 0xff) {
>- //
>- // There must be something wrong in variable store, do reclaim operation.
>- //
>- Status = Reclaim (
>- mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase,
>- &mVariableModuleGlobal->NonVolatileLastVariableOffset,
>- FALSE,
>- NULL,
>- NULL,
>- 0,
>- FALSE
>- );
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>- break;
>- }
>- }
>-
>- FlushHobVariableToFlash (NULL, NULL);
>-
>- //
>- // Authenticated variable initialize.
>- //
>- Status = AutenticatedVariableServiceInitialize (mVariableModuleGlobal->MaxAuthVariableSize - sizeof (VARIABLE_HEADER));
>-
>- return Status;
>-}
>-
>-
>-/**
>- Initializes variable store area for non-volatile and volatile variable.
>-
>- @retval EFI_SUCCESS Function successfully executed.
>- @retval EFI_OUT_OF_RESOURCES Fail to allocate enough memory resource.
>-
>-**/
>-EFI_STATUS
>-VariableCommonInitialize (
>- VOID
>- )
>-{
>- EFI_STATUS Status;
>- VARIABLE_STORE_HEADER *VolatileVariableStore;
>- VARIABLE_STORE_HEADER *VariableStoreHeader;
>- UINT64 VariableStoreLength;
>- UINTN ScratchSize;
>- EFI_HOB_GUID_TYPE *GuidHob;
>-
>- //
>- // Allocate runtime memory for variable driver global structure.
>- //
>- mVariableModuleGlobal = AllocateRuntimeZeroPool (sizeof (VARIABLE_MODULE_GLOBAL));
>- if (mVariableModuleGlobal == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- InitializeLock (&mVariableModuleGlobal->VariableGlobal.VariableServicesLock, TPL_NOTIFY);
>-
>- //
>- // Get HOB variable store.
>- //
>- GuidHob = GetFirstGuidHob (&gEfiAuthenticatedVariableGuid);
>- if (GuidHob != NULL) {
>- VariableStoreHeader = GET_GUID_HOB_DATA (GuidHob);
>- VariableStoreLength = (UINT64) (GuidHob->Header.HobLength - sizeof (EFI_HOB_GUID_TYPE));
>- if (GetVariableStoreStatus (VariableStoreHeader) == EfiValid) {
>- mVariableModuleGlobal->VariableGlobal.HobVariableBase = (EFI_PHYSICAL_ADDRESS) (UINTN) AllocateRuntimeCopyPool
>((UINTN) VariableStoreLength, (VOID *) VariableStoreHeader);
>- if (mVariableModuleGlobal->VariableGlobal.HobVariableBase == 0) {
>- FreePool (mVariableModuleGlobal);
>- return EFI_OUT_OF_RESOURCES;
>- }
>- } else {
>- DEBUG ((EFI_D_ERROR, "HOB Variable Store header is corrupted!\n"));
>- }
>- }
>-
>- //
>- // Allocate memory for volatile variable store, note that there is a scratch space to store scratch data.
>- //
>- ScratchSize = MAX_NV_VARIABLE_SIZE;
>- mVariableModuleGlobal->ScratchBufferSize = ScratchSize;
>- VolatileVariableStore = AllocateRuntimePool (PcdGet32 (PcdVariableStoreSize) + ScratchSize);
>- if (VolatileVariableStore == NULL) {
>- if (mVariableModuleGlobal->VariableGlobal.HobVariableBase != 0) {
>- FreePool ((VOID *) (UINTN) mVariableModuleGlobal->VariableGlobal.HobVariableBase);
>- }
>- FreePool (mVariableModuleGlobal);
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- SetMem (VolatileVariableStore, PcdGet32 (PcdVariableStoreSize) + ScratchSize, 0xff);
>-
>- //
>- // Initialize Variable Specific Data.
>- //
>- mVariableModuleGlobal->VariableGlobal.VolatileVariableBase = (EFI_PHYSICAL_ADDRESS) (UINTN) VolatileVariableStore;
>- mVariableModuleGlobal->VolatileLastVariableOffset = (UINTN) GetStartPointer (VolatileVariableStore) - (UINTN)
>VolatileVariableStore;
>-
>- CopyGuid (&VolatileVariableStore->Signature, &gEfiAuthenticatedVariableGuid);
>- VolatileVariableStore->Size = PcdGet32 (PcdVariableStoreSize);
>- VolatileVariableStore->Format = VARIABLE_STORE_FORMATTED;
>- VolatileVariableStore->State = VARIABLE_STORE_HEALTHY;
>- VolatileVariableStore->Reserved = 0;
>- VolatileVariableStore->Reserved1 = 0;
>-
>- //
>- // Init non-volatile variable store.
>- //
>- Status = InitNonVolatileVariableStore ();
>- if (EFI_ERROR (Status)) {
>- if (mVariableModuleGlobal->VariableGlobal.HobVariableBase != 0) {
>- FreePool ((VOID *) (UINTN) mVariableModuleGlobal->VariableGlobal.HobVariableBase);
>- }
>- FreePool (mVariableModuleGlobal);
>- FreePool (VolatileVariableStore);
>- }
>-
>- return Status;
>-}
>-
>-
>-/**
>- Get the proper fvb handle and/or fvb protocol by the given Flash address.
>-
>- @param[in] Address The Flash address.
>- @param[out] FvbHandle In output, if it is not NULL, it points to the proper FVB handle.
>- @param[out] FvbProtocol In output, if it is not NULL, it points to the proper FVB protocol.
>-
>-**/
>-EFI_STATUS
>-GetFvbInfoByAddress (
>- IN EFI_PHYSICAL_ADDRESS Address,
>- OUT EFI_HANDLE *FvbHandle OPTIONAL,
>- OUT EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL **FvbProtocol OPTIONAL
>- )
>-{
>- EFI_STATUS Status;
>- EFI_HANDLE *HandleBuffer;
>- UINTN HandleCount;
>- UINTN Index;
>- EFI_PHYSICAL_ADDRESS FvbBaseAddress;
>- EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL *Fvb;
>- EFI_FVB_ATTRIBUTES_2 Attributes;
>- UINTN BlockSize;
>- UINTN NumberOfBlocks;
>-
>- HandleBuffer = NULL;
>- //
>- // Get all FVB handles.
>- //
>- Status = GetFvbCountAndBuffer (&HandleCount, &HandleBuffer);
>- if (EFI_ERROR (Status)) {
>- return EFI_NOT_FOUND;
>- }
>-
>- //
>- // Get the FVB to access variable store.
>- //
>- Fvb = NULL;
>- for (Index = 0; Index < HandleCount; Index += 1, Status = EFI_NOT_FOUND, Fvb = NULL) {
>- Status = GetFvbByHandle (HandleBuffer[Index], &Fvb);
>- if (EFI_ERROR (Status)) {
>- Status = EFI_NOT_FOUND;
>- break;
>- }
>-
>- //
>- // Ensure this FVB protocol supported Write operation.
>- //
>- Status = Fvb->GetAttributes (Fvb, &Attributes);
>- if (EFI_ERROR (Status) || ((Attributes & EFI_FVB2_WRITE_STATUS) == 0)) {
>- continue;
>- }
>-
>- //
>- // Compare the address and select the right one.
>- //
>- Status = Fvb->GetPhysicalAddress (Fvb, &FvbBaseAddress);
>- if (EFI_ERROR (Status)) {
>- continue;
>- }
>-
>- //
>- // Assume one FVB has one type of BlockSize.
>- //
>- Status = Fvb->GetBlockSize (Fvb, 0, &BlockSize, &NumberOfBlocks);
>- if (EFI_ERROR (Status)) {
>- continue;
>- }
>-
>- if ((Address >= FvbBaseAddress) && (Address < (FvbBaseAddress + BlockSize * NumberOfBlocks))) {
>- if (FvbHandle != NULL) {
>- *FvbHandle = HandleBuffer[Index];
>- }
>- if (FvbProtocol != NULL) {
>- *FvbProtocol = Fvb;
>- }
>- Status = EFI_SUCCESS;
>- break;
>- }
>- }
>- FreePool (HandleBuffer);
>-
>- if (Fvb == NULL) {
>- Status = EFI_NOT_FOUND;
>- }
>-
>- return Status;
>-}
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.h b/SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.h
>deleted file mode 100644
>index 20f60d4..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/Variable.h
>+++ /dev/null
>@@ -1,836 +0,0 @@
>-/** @file
>- The internal header file includes the common header files, defines
>- internal structure and functions used by Variable modules.
>-
>-Copyright (c) 2009 - 2015, 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
>-
>-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 _VARIABLE_H_
>-#define _VARIABLE_H_
>-
>-#include <PiDxe.h>
>-#include <Protocol/VariableWrite.h>
>-#include <Protocol/FaultTolerantWrite.h>
>-#include <Protocol/FirmwareVolumeBlock.h>
>-#include <Protocol/Variable.h>
>-#include <Protocol/VariableLock.h>
>-#include <Protocol/VarCheck.h>
>-#include <Library/PcdLib.h>
>-#include <Library/HobLib.h>
>-#include <Library/UefiDriverEntryPoint.h>
>-#include <Library/DxeServicesTableLib.h>
>-#include <Library/UefiRuntimeLib.h>
>-#include <Library/DebugLib.h>
>-#include <Library/BaseMemoryLib.h>
>-#include <Library/UefiBootServicesTableLib.h>
>-#include <Library/UefiLib.h>
>-#include <Library/BaseLib.h>
>-#include <Library/SynchronizationLib.h>
>-#include <Library/MemoryAllocationLib.h>
>-#include <Library/BaseCryptLib.h>
>-#include <Library/PlatformSecureLib.h>
>-#include <Guid/GlobalVariable.h>
>-#include <Guid/EventGroup.h>
>-#include <Guid/AuthenticatedVariableFormat.h>
>-#include <Guid/ImageAuthentication.h>
>-#include <Guid/SystemNvDataGuid.h>
>-#include <Guid/FaultTolerantWrite.h>
>-#include <Guid/HardwareErrorVariable.h>
>-#include <Guid/VarErrorFlag.h>
>-
>-#define EFI_VARIABLE_ATTRIBUTES_MASK (EFI_VARIABLE_NON_VOLATILE | \
>- EFI_VARIABLE_BOOTSERVICE_ACCESS | \
>- EFI_VARIABLE_RUNTIME_ACCESS | \
>- EFI_VARIABLE_HARDWARE_ERROR_RECORD | \
>- EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS | \
>- EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS | \
>- EFI_VARIABLE_APPEND_WRITE)
>-
>-#define VARIABLE_ATTRIBUTE_NV_BS (EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_BS_RT (EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT (VARIABLE_ATTRIBUTE_BS_RT | EFI_VARIABLE_NON_VOLATILE)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_AT (VARIABLE_ATTRIBUTE_NV_BS_RT |
>EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_HR (VARIABLE_ATTRIBUTE_NV_BS_RT | EFI_VARIABLE_HARDWARE_ERROR_RECORD)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_AW (VARIABLE_ATTRIBUTE_NV_BS_RT |
>EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_NV_BS_RT_AT_HR_AW (VARIABLE_ATTRIBUTE_NV_BS_RT_AT |
>EFI_VARIABLE_HARDWARE_ERROR_RECORD | EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS)
>-#define VARIABLE_ATTRIBUTE_AT_AW (EFI_VARIABLE_TIME_BASED_AUTHENTICATED_WRITE_ACCESS |
>EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS)
>-
>-#define MAX_NV_VARIABLE_SIZE (MAX (MAX (PcdGet32 (PcdMaxVariableSize), \
>- PcdGet32 (PcdMaxAuthVariableSize)), \
>- PcdGet32 (PcdMaxHardwareErrorVariableSize)))
>-
>-///
>-/// The size of a 3 character ISO639 language code.
>-///
>-#define ISO_639_2_ENTRY_SIZE 3
>-
>-typedef enum {
>- VariableStoreTypeVolatile,
>- VariableStoreTypeHob,
>- VariableStoreTypeNv,
>- VariableStoreTypeMax
>-} VARIABLE_STORE_TYPE;
>-
>-typedef struct {
>- VARIABLE_HEADER *CurrPtr;
>- //
>- // If both ADDED and IN_DELETED_TRANSITION variable are present,
>- // InDeletedTransitionPtr will point to the IN_DELETED_TRANSITION one.
>- // Otherwise, CurrPtr will point to the ADDED or IN_DELETED_TRANSITION one,
>- // and InDeletedTransitionPtr will be NULL at the same time.
>- //
>- VARIABLE_HEADER *InDeletedTransitionPtr;
>- VARIABLE_HEADER *EndPtr;
>- VARIABLE_HEADER *StartPtr;
>- BOOLEAN Volatile;
>-} VARIABLE_POINTER_TRACK;
>-
>-typedef struct {
>- EFI_PHYSICAL_ADDRESS HobVariableBase;
>- EFI_PHYSICAL_ADDRESS VolatileVariableBase;
>- EFI_PHYSICAL_ADDRESS NonVolatileVariableBase;
>- EFI_LOCK VariableServicesLock;
>- UINT32 ReentrantState;
>-} VARIABLE_GLOBAL;
>-
>-typedef struct {
>- VARIABLE_GLOBAL VariableGlobal;
>- UINTN VolatileLastVariableOffset;
>- UINTN NonVolatileLastVariableOffset;
>- UINTN CommonVariableSpace;
>- UINTN CommonMaxUserVariableSpace;
>- UINTN CommonRuntimeVariableSpace;
>- UINTN CommonVariableTotalSize;
>- UINTN CommonUserVariableTotalSize;
>- UINTN HwErrVariableTotalSize;
>- UINTN MaxVariableSize;
>- UINTN MaxAuthVariableSize;
>- UINTN ScratchBufferSize;
>- CHAR8 *PlatformLangCodes;
>- CHAR8 *LangCodes;
>- CHAR8 *PlatformLang;
>- CHAR8 Lang[ISO_639_2_ENTRY_SIZE + 1];
>- EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL *FvbInstance;
>-} VARIABLE_MODULE_GLOBAL;
>-
>-typedef struct {
>- LIST_ENTRY Link;
>- EFI_GUID Guid;
>- //CHAR16 *Name;
>-} VARIABLE_ENTRY;
>-
>-/**
>- Flush the HOB variable to flash.
>-
>- @param[in] VariableName Name of variable has been updated or deleted.
>- @param[in] VendorGuid Guid of variable has been updated or deleted.
>-
>-**/
>-VOID
>-FlushHobVariableToFlash (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- );
>-
>-/**
>- Writes a buffer to variable storage space, in the working block.
>-
>- This function writes a buffer to variable storage space into a firmware
>- volume block device. The destination is specified by the parameter
>- VariableBase. Fault Tolerant Write protocol is used for writing.
>-
>- @param VariableBase Base address of the variable to write.
>- @param VariableBuffer Point to the variable data buffer.
>-
>- @retval EFI_SUCCESS The function completed successfully.
>- @retval EFI_NOT_FOUND Fail to locate Fault Tolerant Write protocol.
>- @retval EFI_ABORTED The function could not complete successfully.
>-
>-**/
>-EFI_STATUS
>-FtwVariableSpace (
>- IN EFI_PHYSICAL_ADDRESS VariableBase,
>- IN VARIABLE_STORE_HEADER *VariableBuffer
>- );
>-
>-/**
>- Finds variable in storage blocks of volatile and non-volatile storage areas.
>-
>- This code finds variable in storage blocks of volatile and non-volatile storage areas.
>- If VariableName is an empty string, then we just return the first
>- qualified variable without comparing VariableName and VendorGuid.
>- If IgnoreRtCheck is TRUE, then we ignore the EFI_VARIABLE_RUNTIME_ACCESS attribute check
>- at runtime when searching existing variable, only VariableName and VendorGuid are compared.
>- Otherwise, variables without EFI_VARIABLE_RUNTIME_ACCESS are not visible at runtime.
>-
>- @param[in] VariableName Name of the variable to be found.
>- @param[in] VendorGuid Vendor GUID to be found.
>- @param[out] PtrTrack VARIABLE_POINTER_TRACK structure for output,
>- including the range searched and the target position.
>- @param[in] Global Pointer to VARIABLE_GLOBAL structure, including
>- base of volatile variable storage area, base of
>- NV variable storage area, and a lock.
>- @param[in] IgnoreRtCheck Ignore EFI_VARIABLE_RUNTIME_ACCESS attribute
>- check at runtime when searching variable.
>-
>- @retval EFI_INVALID_PARAMETER If VariableName is not an empty string, while
>- VendorGuid is NULL.
>- @retval EFI_SUCCESS Variable successfully found.
>- @retval EFI_NOT_FOUND Variable not found
>-
>-**/
>-EFI_STATUS
>-FindVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- OUT VARIABLE_POINTER_TRACK *PtrTrack,
>- IN VARIABLE_GLOBAL *Global,
>- IN BOOLEAN IgnoreRtCheck
>- );
>-
>-/**
>-
>- Gets the pointer to the end of the variable storage area.
>-
>- This function gets pointer to the end of the variable storage
>- area, according to the input variable store header.
>-
>- @param VarStoreHeader Pointer to the Variable Store Header.
>-
>- @return Pointer to the end of the variable storage area.
>-
>-**/
>-VARIABLE_HEADER *
>-GetEndPointer (
>- IN VARIABLE_STORE_HEADER *VarStoreHeader
>- );
>-
>-/**
>-
>- This code gets the pointer to the variable data.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Pointer to Variable Data.
>-
>-**/
>-UINT8 *
>-GetVariableDataPtr (
>- IN VARIABLE_HEADER *Variable
>- );
>-
>-/**
>-
>- This code gets the size of variable data.
>-
>- @param Variable Pointer to the Variable Header.
>-
>- @return Size of variable in bytes.
>-
>-**/
>-UINTN
>-DataSizeOfVariable (
>- IN VARIABLE_HEADER *Variable
>- );
>-
>-/**
>- This function is to check if the remaining variable space is enough to set
>- all Variables from argument list successfully. The purpose of the check
>- is to keep the consistency of the Variables to be in variable storage.
>-
>- Note: Variables are assumed to be in same storage.
>- The set sequence of Variables will be same with the sequence of VariableEntry from argument list,
>- so follow the argument sequence to check the Variables.
>-
>- @param[in] Attributes Variable attributes for Variable entries.
>- @param ... The variable argument list with type VARIABLE_ENTRY_CONSISTENCY *.
>- A NULL terminates the list. The VariableSize of
>- VARIABLE_ENTRY_CONSISTENCY is the variable data size as input.
>- It will be changed to variable total size as output.
>-
>- @retval TRUE Have enough variable space to set the Variables successfully.
>- @retval FALSE No enough variable space to set the Variables successfully.
>-
>-**/
>-BOOLEAN
>-EFIAPI
>-CheckRemainingSpaceForConsistency (
>- IN UINT32 Attributes,
>- ...
>- );
>-
>-/**
>- Update the variable region with Variable information. If EFI_VARIABLE_AUTHENTICATED_WRITE_ACCESS is set,
>- index of associated public key is needed.
>-
>- @param[in] VariableName Name of variable.
>- @param[in] VendorGuid Guid of variable.
>- @param[in] Data Variable data.
>- @param[in] DataSize Size of data. 0 means delete.
>- @param[in] Attributes Attributes of the variable.
>- @param[in] KeyIndex Index of associated public key.
>- @param[in] MonotonicCount Value of associated monotonic count.
>- @param[in, out] Variable The variable information that is used to keep track of variable usage.
>-
>- @param[in] TimeStamp Value of associated TimeStamp.
>-
>- @retval EFI_SUCCESS The update operation is success.
>- @retval EFI_OUT_OF_RESOURCES Variable region is full, cannot write other data into this region.
>-
>-**/
>-EFI_STATUS
>-UpdateVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN VOID *Data,
>- IN UINTN DataSize,
>- IN UINT32 Attributes OPTIONAL,
>- IN UINT32 KeyIndex OPTIONAL,
>- IN UINT64 MonotonicCount OPTIONAL,
>- IN OUT VARIABLE_POINTER_TRACK *Variable,
>- IN EFI_TIME *TimeStamp OPTIONAL
>- );
>-
>-
>-/**
>- Return TRUE if ExitBootServices () has been called.
>-
>- @retval TRUE If ExitBootServices () has been called.
>-**/
>-BOOLEAN
>-AtRuntime (
>- VOID
>- );
>-
>-/**
>- Initializes a basic mutual exclusion lock.
>-
>- This function initializes a basic mutual exclusion lock to the released state
>- and returns the lock. Each lock provides mutual exclusion access at its task
>- priority level. Since there is no preemption or multiprocessor support in EFI,
>- acquiring the lock only consists of raising to the locks TPL.
>- If Lock is NULL, then ASSERT().
>- If Priority is not a valid TPL value, then ASSERT().
>-
>- @param Lock A pointer to the lock data structure to initialize.
>- @param Priority EFI TPL is associated with the lock.
>-
>- @return The lock.
>-
>-**/
>-EFI_LOCK *
>-InitializeLock (
>- IN OUT EFI_LOCK *Lock,
>- IN EFI_TPL Priority
>- );
>-
>-
>-/**
>- Acquires lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function that will be removed when
>- EfiAcquireLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiAcquireLock() at boot time, and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to acquire.
>-
>-**/
>-VOID
>-AcquireLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- );
>-
>-
>-/**
>- Releases lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function which will be removed when
>- EfiReleaseLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiReleaseLock() at boot time and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to release.
>-
>-**/
>-VOID
>-ReleaseLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- );
>-
>-/**
>- Retrive the FVB protocol interface by HANDLE.
>-
>- @param[in] FvBlockHandle The handle of FVB protocol that provides services for
>- reading, writing, and erasing the target block.
>- @param[out] FvBlock The interface of FVB protocol
>-
>- @retval EFI_SUCCESS The interface information for the specified protocol was returned.
>- @retval EFI_UNSUPPORTED The device does not support the FVB protocol.
>- @retval EFI_INVALID_PARAMETER FvBlockHandle is not a valid EFI_HANDLE or FvBlock is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFvbByHandle (
>- IN EFI_HANDLE FvBlockHandle,
>- OUT EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL **FvBlock
>- );
>-
>-
>-/**
>- Retrive the Swap Address Range protocol interface.
>-
>- @param[out] SarProtocol The interface of SAR protocol
>-
>- @retval EFI_SUCCESS The SAR protocol instance was found and returned in SarProtocol.
>- @retval EFI_NOT_FOUND The SAR protocol instance was not found.
>- @retval EFI_INVALID_PARAMETER SarProtocol is NULL.
>-
>-**/
>-EFI_STATUS
>-GetSarProtocol (
>- OUT VOID **SarProtocol
>- );
>-
>-/**
>- Function returns an array of handles that support the FVB protocol
>- in a buffer allocated from pool.
>-
>- @param[out] NumberHandles The number of handles returned in Buffer.
>- @param[out] Buffer A pointer to the buffer to return the requested
>- array of handles that support FVB protocol.
>-
>- @retval EFI_SUCCESS The array of handles was returned in Buffer, and the number of
>- handles in Buffer was returned in NumberHandles.
>- @retval EFI_NOT_FOUND No FVB handle was found.
>- @retval EFI_OUT_OF_RESOURCES There is not enough pool memory to store the matching results.
>- @retval EFI_INVALID_PARAMETER NumberHandles is NULL or Buffer is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFvbCountAndBuffer (
>- OUT UINTN *NumberHandles,
>- OUT EFI_HANDLE **Buffer
>- );
>-
>-/**
>- Initializes variable store area for non-volatile and volatile variable.
>-
>- @retval EFI_SUCCESS Function successfully executed.
>- @retval EFI_OUT_OF_RESOURCES Fail to allocate enough memory resource.
>-
>-**/
>-EFI_STATUS
>-VariableCommonInitialize (
>- VOID
>- );
>-
>-/**
>-
>- Variable store garbage collection and reclaim operation.
>-
>- If ReclaimPubKeyStore is FALSE, reclaim variable space by deleting the obsoleted varaibles.
>- If ReclaimPubKeyStore is TRUE, reclaim invalid key in public key database and update the PubKeyIndex
>- for all the count-based authenticate variable in NV storage.
>-
>- @param[in] VariableBase Base address of variable store.
>- @param[out] LastVariableOffset Offset of last variable.
>- @param[in] IsVolatile The variable store is volatile or not;
>- if it is non-volatile, need FTW.
>- @param[in, out] UpdatingPtrTrack Pointer to updating variable pointer track structure.
>- @param[in] NewVariable Pointer to new variable.
>- @param[in] NewVariableSize New variable size.
>- @param[in] ReclaimPubKeyStore Reclaim for public key database or not.
>-
>- @return EFI_SUCCESS Reclaim operation has finished successfully.
>- @return EFI_OUT_OF_RESOURCES No enough memory resources or variable space.
>- @return EFI_DEVICE_ERROR The public key database doesn't exist.
>- @return Others Unexpect error happened during reclaim operation.
>-
>-**/
>-EFI_STATUS
>-Reclaim (
>- IN EFI_PHYSICAL_ADDRESS VariableBase,
>- OUT UINTN *LastVariableOffset,
>- IN BOOLEAN IsVolatile,
>- IN OUT VARIABLE_POINTER_TRACK *UpdatingPtrTrack,
>- IN VARIABLE_HEADER *NewVariable,
>- IN UINTN NewVariableSize,
>- IN BOOLEAN ReclaimPubKeyStore
>- );
>-
>-/**
>- This function reclaims variable storage if free size is below the threshold.
>-
>-**/
>-VOID
>-ReclaimForOS(
>- VOID
>- );
>-
>-
>-/**
>- Initializes variable write service after FVB was ready.
>-
>- @retval EFI_SUCCESS Function successfully executed.
>- @retval Others Fail to initialize the variable service.
>-
>-**/
>-EFI_STATUS
>-VariableWriteServiceInitialize (
>- VOID
>- );
>-
>-/**
>- Retrive the SMM Fault Tolerent Write protocol interface.
>-
>- @param[out] FtwProtocol The interface of SMM Ftw protocol
>-
>- @retval EFI_SUCCESS The SMM SAR protocol instance was found and returned in SarProtocol.
>- @retval EFI_NOT_FOUND The SMM SAR protocol instance was not found.
>- @retval EFI_INVALID_PARAMETER SarProtocol is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFtwProtocol (
>- OUT VOID **FtwProtocol
>- );
>-
>-/**
>- Get the proper fvb handle and/or fvb protocol by the given Flash address.
>-
>- @param[in] Address The Flash address.
>- @param[out] FvbHandle In output, if it is not NULL, it points to the proper FVB handle.
>- @param[out] FvbProtocol In output, if it is not NULL, it points to the proper FVB protocol.
>-
>-**/
>-EFI_STATUS
>-GetFvbInfoByAddress (
>- IN EFI_PHYSICAL_ADDRESS Address,
>- OUT EFI_HANDLE *FvbHandle OPTIONAL,
>- OUT EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL **FvbProtocol OPTIONAL
>- );
>-
>-/**
>-
>- This code finds variable in storage blocks (Volatile or Non-Volatile).
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>-
>- @param VariableName Name of Variable to be found.
>- @param VendorGuid Variable vendor GUID.
>- @param Attributes Attribute value of the variable found.
>- @param DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param Data Data pointer.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Find the specified variable.
>- @return EFI_NOT_FOUND Not found.
>- @return EFI_BUFFER_TO_SMALL DataSize is too small for the result.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceGetVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- OUT UINT32 *Attributes OPTIONAL,
>- IN OUT UINTN *DataSize,
>- OUT VOID *Data
>- );
>-
>-/**
>-
>- This code Finds the Next available variable.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode. This function will do basic validation, before parse the data.
>-
>- @param VariableNameSize Size of the variable name.
>- @param VariableName Pointer to variable name.
>- @param VendorGuid Variable Vendor Guid.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Find the specified variable.
>- @return EFI_NOT_FOUND Not found.
>- @return EFI_BUFFER_TO_SMALL DataSize is too small for the result.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceGetNextVariableName (
>- IN OUT UINTN *VariableNameSize,
>- IN OUT CHAR16 *VariableName,
>- IN OUT EFI_GUID *VendorGuid
>- );
>-
>-/**
>-
>- This code sets variable in storage blocks (Volatile or Non-Volatile).
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode, and datasize and data are external input.
>- This function will do basic validation, before parse the data.
>- This function will parse the authentication carefully to avoid security issues, like
>- buffer overflow, integer overflow.
>- This function will check attribute carefully to avoid authentication bypass.
>-
>- @param VariableName Name of Variable to be found.
>- @param VendorGuid Variable vendor GUID.
>- @param Attributes Attribute value of the variable found
>- @param DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param Data Data pointer.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Set successfully.
>- @return EFI_OUT_OF_RESOURCES Resource not enough to set variable.
>- @return EFI_NOT_FOUND Not found.
>- @return EFI_WRITE_PROTECTED Variable is read-only.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceSetVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT32 Attributes,
>- IN UINTN DataSize,
>- IN VOID *Data
>- );
>-
>-/**
>-
>- This code returns information about the EFI variables.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode. This function will do basic validation, before parse the data.
>-
>- @param Attributes Attributes bitmask to specify the type of variables
>- on which to return information.
>- @param MaximumVariableStorageSize Pointer to the maximum size of the storage space available
>- for the EFI variables associated with the attributes specified.
>- @param RemainingVariableStorageSize Pointer to the remaining size of the storage space available
>- for EFI variables associated with the attributes specified.
>- @param MaximumVariableSize Pointer to the maximum size of an individual EFI variables
>- associated with the attributes specified.
>-
>- @return EFI_SUCCESS Query successfully.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceQueryVariableInfoInternal (
>- IN UINT32 Attributes,
>- OUT UINT64 *MaximumVariableStorageSize,
>- OUT UINT64 *RemainingVariableStorageSize,
>- OUT UINT64 *MaximumVariableSize
>- );
>-
>-/**
>-
>- This code returns information about the EFI variables.
>-
>- Caution: This function may receive untrusted input.
>- This function may be invoked in SMM mode. This function will do basic validation, before parse the data.
>-
>- @param Attributes Attributes bitmask to specify the type of variables
>- on which to return information.
>- @param MaximumVariableStorageSize Pointer to the maximum size of the storage space available
>- for the EFI variables associated with the attributes specified.
>- @param RemainingVariableStorageSize Pointer to the remaining size of the storage space available
>- for EFI variables associated with the attributes specified.
>- @param MaximumVariableSize Pointer to the maximum size of an individual EFI variables
>- associated with the attributes specified.
>-
>- @return EFI_INVALID_PARAMETER An invalid combination of attribute bits was supplied.
>- @return EFI_SUCCESS Query successfully.
>- @return EFI_UNSUPPORTED The attribute is not supported on this platform.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceQueryVariableInfo (
>- IN UINT32 Attributes,
>- OUT UINT64 *MaximumVariableStorageSize,
>- OUT UINT64 *RemainingVariableStorageSize,
>- OUT UINT64 *MaximumVariableSize
>- );
>-
>-/**
>- Mark a variable that will become read-only after leaving the DXE phase of execution.
>-
>- @param[in] This The VARIABLE_LOCK_PROTOCOL instance.
>- @param[in] VariableName A pointer to the variable name that will be made read-only subsequently.
>- @param[in] VendorGuid A pointer to the vendor GUID that will be made read-only subsequently.
>-
>- @retval EFI_SUCCESS The variable specified by the VariableName and the VendorGuid was marked
>- as pending to be read-only.
>- @retval EFI_INVALID_PARAMETER VariableName or VendorGuid is NULL.
>- Or VariableName is an empty string.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource to hold the lock request.
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableLockRequestToLock (
>- IN CONST EDKII_VARIABLE_LOCK_PROTOCOL *This,
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- );
>-
>-/**
>- Check if a Unicode character is a hexadecimal character.
>-
>- This function checks if a Unicode character is a
>- hexadecimal character. The valid hexadecimal character is
>- L'0' to L'9', L'a' to L'f', or L'A' to L'F'.
>-
>-
>- @param Char The character to check against.
>-
>- @retval TRUE If the Char is a hexadecmial character.
>- @retval FALSE If the Char is not a hexadecmial character.
>-
>-**/
>-BOOLEAN
>-EFIAPI
>-IsHexaDecimalDigitCharacter (
>- IN CHAR16 Char
>- );
>-
>-/**
>- Internal SetVariable check.
>-
>- @param[in] VariableName Name of Variable to set.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Attributes Attribute value of the variable.
>- @param[in] DataSize Size of Data to set.
>- @param[in] Data Data pointer.
>-
>- @retval EFI_SUCCESS The SetVariable check result was success.
>- @retval EFI_INVALID_PARAMETER An invalid combination of attribute bits, name, and GUID were supplied,
>- or the DataSize exceeds the minimum or maximum allowed,
>- or the Data value is not following UEFI spec for UEFI defined variables.
>- @retval EFI_WRITE_PROTECTED The variable in question is read-only.
>- @retval Others The return status from check handler.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckSetVariableCheck (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT32 Attributes,
>- IN UINTN DataSize,
>- IN VOID *Data
>- );
>-
>-/**
>- Register SetVariable check handler.
>-
>- @param[in] Handler Pointer to check handler.
>-
>- @retval EFI_SUCCESS The SetVariable check handler was registered successfully.
>- @retval EFI_INVALID_PARAMETER Handler is NULL.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource for the SetVariable check handler register request.
>- @retval EFI_UNSUPPORTED This interface is not implemented.
>- For example, it is unsupported in VarCheck protocol if both VarCheck and SmmVarCheck protocols are present.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckRegisterSetVariableCheckHandler (
>- IN VAR_CHECK_SET_VARIABLE_CHECK_HANDLER Handler
>- );
>-
>-/**
>- Internal variable property get.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[out] VariableProperty Pointer to the output variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was got successfully.
>- @retval EFI_NOT_FOUND The property of variable specified by the Name and Guid was not found.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-InternalVarCheckVariablePropertyGet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- OUT VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- );
>-
>-/**
>- Variable property set.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[in] VariableProperty Pointer to the input variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was set successfully.
>- @retval EFI_INVALID_PARAMETER Name, Guid or VariableProperty is NULL, or Name is an empty string,
>- or the fields of VariableProperty are not valid.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource for the variable property set request.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckVariablePropertySet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- );
>-
>-/**
>- Variable property get.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[out] VariableProperty Pointer to the output variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was got successfully.
>- @retval EFI_INVALID_PARAMETER Name, Guid or VariableProperty is NULL, or Name is an empty string.
>- @retval EFI_NOT_FOUND The property of variable specified by the Name and Guid was not found.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckVariablePropertyGet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- OUT VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- );
>-
>-/**
>- Initialize variable quota.
>-
>-**/
>-VOID
>-InitializeVariableQuota (
>- VOID
>- );
>-
>-extern VARIABLE_MODULE_GLOBAL *mVariableModuleGlobal;
>-
>-#endif
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthRuntimeDxe.uni
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthRuntimeDxe.uni
>deleted file mode 100644
>index 47a09d55c9b458802df5fed4a180c218a239bdcd..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 3204
>zcmdUxTW`}q5QXO%iT|)lUjUUB5HBEv=p{***@NJ5%Wc&gIeYAH7ox21m`_|9(ab()0o
>zP(+cH*gHFWX6EeKv48&9wrz9#9&tH)V|`0(Xg#}c_poZNZZn(MIrc90IhMAaS!$<@
>z#@***@U`ZKunLFoshOKQU9>=kwhehi<JY~4q-B}Z)#N&>L(*;}c9kwyn6r>@S;x1z=
>zR)***@rasFQgbu$UmNx5GXLR8+RL1gJk07)RIjcYBy`0TrrE`19>O-QW_SwgYtZXv#
>z?uMBv^WRsjt%5bW$~{#03C_gv<x-pq9Q3JTE9c!6p7ub}P9}JaeYWfNVg~*<d=sK%
>z8tB4qlCRb-IX^3=dUnC+;z}***@2B%qPa|vOZy#Rf|?ji9$UkPgxy5F{1e~
>zHqA*TQ(uL%$BdVErHiLjv^wVR5l0|PgAO$-zR-un446UjQomT~<***@e9gP))Vg?
>zPC*9`RhW7oX?~6+@TsSu<Tlo*vJ>***@Tp`QB0nRt#Ti~<YdWw6FC)*g}fK$wz=
>zG8(|Ks(e5W54k_HCtNRh5~mtHwdW?)N>Pd=?u9S|L;vD9=xB?X9nXaHkYVfm2JI++
>zRUs9;vR!M~>%88WT~tLl*#jSA1WI<UQ?D+KJO0d%$V79O#2izRR2TY^***@2B!
>zu!g>*UK92+!`***@K`Vn53yD02i-%u?M*p7Eq;cES$Eb-Q$lea0Ua
>za*15%94Slnx$D*HtO-#$gf6OB(yXeMdW!oZR#j1^Rjmsr;CfDryaX<#>~Id$Qvw6Z
>zD9!gzXEo)T(oOXCkiztqn0tS9+8(<uy$qOLj4{***@f@***@aEzWF#a>_3<(zN$hCYw6y
>zsnJOrDDETU3QRh<)V+zdg1%Zjl|8>Lt8y=6*IOqbMD8o-xs1o5N3QWC9qYfuUARIm
>zao_c0jW!E89WgJ|nvdx02(O0Etctw?sxWFkdV`U2mrXI7_{v97gV$Sp75yvs17?)D
>z&R_W|N~of2Uviv?UV)1`YEsPoLf?!0>21I5bC*rOja)O~>;(RfL8^h#0<CPvWF)@C
>z><(--$!FcQ;ZKXO&***@lDhYpy>0mlOJsPP-xa02nm?;VIyj^TX{4TWzp9#>E77U?
>of4*Q=y(91Pmy6yr|L!}b_<j1fzfX#>?&f!i`v2{GkHqu(3r&I=y#N3J
>
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthSmm.uni
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthSmm.uni
>deleted file mode 100644
>index 0de43d00c671012f1ccd3cc2241e81a2cde5a117..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 4488
>zcmd6qU2hs!5QgWvQvbt|bJJF7+(x~Msw#F&***@Og4gu&QI23){){O8lY&x{Xe
>zmo****@G0!-92Z{e7^I+zwdT!*OKlZbR~OgBOBX=o!YndjaJz^w7JdfTI)ltFSOFL
>z7rK)5?aG#RuGOiYV;g8?sjs2-uJu0GTHj8bU((4_t-xoXx6D63lO2iE*!fQ+Zz$gA
>zk+e3|>QbC8bXDayWn8+hOPwF+zPLNhchR~@GjzStwC`FzTxpl=#<d#***@SUNJx^S(
>zE2qWQ6T7YOAG+PwZtX*@_oY8n|HqEvCAfq=`-(%dZLHbOir_kxuZZQyZHnj?-*pw0
>zi1nlr!(<2c)_qd7J&Dh`dp6#PWkyaja&>gzEh0S^*S@@WYmX{1*@TpZ<jov65fvns
>zDBXxB8Wk<-)?mfo*3y0*fB5B0dW0|L(j>52F#NF`***@DK-gX{^^H6xr6wSKCg<i;^b
>zE`q<!oHF9^*G!QumaOxxd!-tUBK4VMQ4z+@>&cy;?#pT7`j2SG9$_L)l!qRnI8C-k
>z{HYkH%ELf0wI=HVO4%E3Kt~;o#GeY19F^o}(*0KYQkSOEAlHjaw<6h(qG<XdSBsL_
>z)S8Jda-&p1>cW*Y96A5U|Ki`k*y#q%->(;vsED}|q2q-lhh|ZKsl|ACBwDPdLPdu6
>zWz)>5qb3hTL8V?g4bfU?B`Q5{fkG-{iFDmEx&uBONzTk8HPcsEjCaW%zSrpriVEjv
>zqPmnOXmqAXVdZzy;d?zF+fVkh?ubl${bJPEwmgp{A_#}Mc<@U<3Otdud+rHPm3ikH
>zldDf)=~vsguKl*Mw`f-?Ph{np%b19F&dI0}d=GSii%Z|TmCUIu0=v;AqdU^k3jc^%
>zlAh5e>3k8-%%9WrVI&ZDFkN~q2xJ#;XH5d%6LBh9q8XG#J^aJ&Oc5;S=r0HQeqPh1
>z=vwWJ>(-K$a72g5e`JAKtOh+<ZmFheg;mZ)2CVB;_e=N^WJgCH$%60zmM$xP1xHIo
>z;)%~RAdEV)aC)jEc?e$4v|pF8(8`***@hpGnkok!wwuDf{T$o};HaVYe3><|6!`JB}D
>zPJJMh_B7>m_1w2(y|vuG$M#asme%Pj!J+uREj+hG(***@6wXcl7M(3D+Gx_x+o%
>z>iqIb`*7{J#AL5T)pgBYYP~***@aVYouD;NnHDn%%78;}m)$gK3`fEM^(hi!Ff2}(y
>zVMR-QH1jFk+w#Ss(1gr`O5H2|V+P%If3n8?V1=2;o$%iqaq5W2vADJDjWohvcy>?T
>zI+8w{***@VXL0s7v&KsbYKV7VdnaX?JI3)pizvhn{Q!D~GEX+-KE?Eh;suKG!s-
>zkj>Lsa|Ypb^pkw5Ns~Keo-#m6wQA6#rds>_^K|Y_{4e<Ob99+J>k|vrlR8#va`ts|
>zD#;xz`o?|p^X7k8pL=dDQ_yx3coV5j``<U^=HA&n_37ti=8-Qq6<1?k$JW<64Ocb(
>UI;Y_Exqf}BWoFrK`Ym1IKV<6k=l}o!
>
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthSmmRuntimeDxe.uni
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableAuthSmmRuntimeDxe.uni
>deleted file mode 100644
>index db931c4cd005a0ffedeb65e0ac58f50a0fc376ef..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 3320
>zcmd6pUr!TJ5XI-&#P4teFKQ6f_(Y76KUEu*5@>@ynL<n1SX$h+pkH47of)^***@Pt(
>zB%5~k&Yhh(bMCpb_xrasTeHOP0avmYc5H?9t!sDf4pz<W*~A7m#(s)D*|xp68uv46
>zTZui{kqvn&nH^yr;@!b}U_Iu>jFau#JFdhV6D%iqM#***@4h3&OKhi|DhvD<Qp<G
>***@ao#U^<`Gfbyw~^ntC5BLi1$@***@AAj{EP5h;9EFeRdRiVs5v5^
>z^G1gXGw!QsM$DJgUx1-&tK`0}wgL0O)&*!w`-HEu^{@u7C6)_Esp|fm_thEXxrQz3
>z*Gd-***@zQ~h^30p_!gj*KEzyyOFYKgTBqc*VxS9pRS+7f*0yk6s`6PpnWYZz7ceLu
>***@B1+q>iJ32C)cgRO=A_UwuOit)##h&+gQs+~IOoj~Pl+rQCe*B5qv(BdM$A}4
>zsb8!d<14&***@eAz;_0YW&QM%}2;uVhFN2(uT2|o1{T5e;***@7CLIu9k|K9R+-
>z^b;(I7b!^N%YM1`9C-_`Gmwb$9vrL6dtkWF{fRxY$NYlR7(KNW#&zHGUGgVWgwlIO
>z=^Td=r2GwMLVBoTOEaMzA=Da61<!1g&h&g*Z$***@5j(KQTWxxYlovZYc8bPFTtnv6
>z%LY_bb*)pzp%(Qcb&(uD)+}L-{***@Sa*0YMQx3%Y$LF=xLn!B31sb<A?g(PyF5-Fn;
>zvgoAMPSNa;70mB#vctC-zn#O9v1%U)rFy~TYPHuCQ5d3+YFA3L;$G^h@>U&56;)c*
>zd$9v9W18nhJGkwtjeT%T1;Kz2jc0h3j>fFSx_@`1FnuLP?yp{}&M4LNn4ixv!g7db
>zhkZOhvr3c`ewmS`z4ouyF6wF6EB-h9%T$L+ecN<zVy&aE7Ed+jw`DurYuMGBBSPlB
>zj-G3H?0e(}Ptvjem$)mgqAqdY^sz=OGnfvTSJZ}QOm=|Ro+I1AUMH$zG(7trBVm_K
>zIh**(M_I$`CBDl3f%_X~gk1Zt_A^UVQR6FK#***@aIuS;lyiHg?`8gUPFQp7vgx-x
>z)l7WxgTIeNY7nDEw3>***@ym`8?e;`&vn<b?-s?Hpb+&Xb?*Ud+wuyRh;bWEBui5k
>zevbj^XP?@ot=;LGEn?x<4CEd+dq%pgXP-si*4usN(HH9fop5H)fB*VqGn?***@jJ}
>L`a36?ykma=imxvx
>
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableDxe.c
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableDxe.c
>deleted file mode 100644
>index f5bb996..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableDxe.c
>+++ /dev/null
>@@ -1,530 +0,0 @@
>-/** @file
>- Implement all four UEFI Runtime Variable services for the nonvolatile
>- and volatile storage space and install variable architecture protocol.
>-
>-Copyright (C) 2013, Red Hat, Inc.
>-Copyright (c) 2009 - 2015, 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
>-
>-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 "Variable.h"
>-#include "AuthService.h"
>-
>-extern VARIABLE_STORE_HEADER *mNvVariableCache;
>-extern VARIABLE_INFO_ENTRY *gVariableInfo;
>-EFI_HANDLE mHandle = NULL;
>-EFI_EVENT mVirtualAddressChangeEvent = NULL;
>-EFI_EVENT mFtwRegistration = NULL;
>-extern LIST_ENTRY mLockedVariableList;
>-extern LIST_ENTRY mVarCheckVariableList;
>-extern UINT32 mNumberOfHandler;
>-extern VAR_CHECK_SET_VARIABLE_CHECK_HANDLER *mHandlerTable;
>-extern BOOLEAN mEndOfDxe;
>-EDKII_VARIABLE_LOCK_PROTOCOL mVariableLock = { VariableLockRequestToLock };
>-EDKII_VAR_CHECK_PROTOCOL mVarCheck = { VarCheckRegisterSetVariableCheckHandler,
>- VarCheckVariablePropertySet,
>- VarCheckVariablePropertyGet };
>-
>-/**
>- Return TRUE if ExitBootServices () has been called.
>-
>- @retval TRUE If ExitBootServices () has been called.
>-**/
>-BOOLEAN
>-AtRuntime (
>- VOID
>- )
>-{
>- return EfiAtRuntime ();
>-}
>-
>-
>-/**
>- Initializes a basic mutual exclusion lock.
>-
>- This function initializes a basic mutual exclusion lock to the released state
>- and returns the lock. Each lock provides mutual exclusion access at its task
>- priority level. Since there is no preemption or multiprocessor support in EFI,
>- acquiring the lock only consists of raising to the locks TPL.
>- If Lock is NULL, then ASSERT().
>- If Priority is not a valid TPL value, then ASSERT().
>-
>- @param Lock A pointer to the lock data structure to initialize.
>- @param Priority EFI TPL is associated with the lock.
>-
>- @return The lock.
>-
>-**/
>-EFI_LOCK *
>-InitializeLock (
>- IN OUT EFI_LOCK *Lock,
>- IN EFI_TPL Priority
>- )
>-{
>- return EfiInitializeLock (Lock, Priority);
>-}
>-
>-
>-/**
>- Acquires lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function that will be removed when
>- EfiAcquireLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiAcquireLock() at boot time, and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to acquire.
>-
>-**/
>-VOID
>-AcquireLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- )
>-{
>- if (!AtRuntime ()) {
>- EfiAcquireLock (Lock);
>- }
>-}
>-
>-
>-/**
>- Releases lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function which will be removed when
>- EfiReleaseLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiReleaseLock() at boot time and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to release.
>-
>-**/
>-VOID
>-ReleaseLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- )
>-{
>- if (!AtRuntime ()) {
>- EfiReleaseLock (Lock);
>- }
>-}
>-
>-/**
>- Retrive the Fault Tolerent Write protocol interface.
>-
>- @param[out] FtwProtocol The interface of Ftw protocol
>-
>- @retval EFI_SUCCESS The FTW protocol instance was found and returned in FtwProtocol.
>- @retval EFI_NOT_FOUND The FTW protocol instance was not found.
>- @retval EFI_INVALID_PARAMETER SarProtocol is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFtwProtocol (
>- OUT VOID **FtwProtocol
>- )
>-{
>- EFI_STATUS Status;
>-
>- //
>- // Locate Fault Tolerent Write protocol
>- //
>- Status = gBS->LocateProtocol (
>- &gEfiFaultTolerantWriteProtocolGuid,
>- NULL,
>- FtwProtocol
>- );
>- return Status;
>-}
>-
>-/**
>- Retrive the FVB protocol interface by HANDLE.
>-
>- @param[in] FvBlockHandle The handle of FVB protocol that provides services for
>- reading, writing, and erasing the target block.
>- @param[out] FvBlock The interface of FVB protocol
>-
>- @retval EFI_SUCCESS The interface information for the specified protocol was returned.
>- @retval EFI_UNSUPPORTED The device does not support the FVB protocol.
>- @retval EFI_INVALID_PARAMETER FvBlockHandle is not a valid EFI_HANDLE or FvBlock is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFvbByHandle (
>- IN EFI_HANDLE FvBlockHandle,
>- OUT EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL **FvBlock
>- )
>-{
>- //
>- // To get the FVB protocol interface on the handle
>- //
>- return gBS->HandleProtocol (
>- FvBlockHandle,
>- &gEfiFirmwareVolumeBlockProtocolGuid,
>- (VOID **) FvBlock
>- );
>-}
>-
>-
>-/**
>- Function returns an array of handles that support the FVB protocol
>- in a buffer allocated from pool.
>-
>- @param[out] NumberHandles The number of handles returned in Buffer.
>- @param[out] Buffer A pointer to the buffer to return the requested
>- array of handles that support FVB protocol.
>-
>- @retval EFI_SUCCESS The array of handles was returned in Buffer, and the number of
>- handles in Buffer was returned in NumberHandles.
>- @retval EFI_NOT_FOUND No FVB handle was found.
>- @retval EFI_OUT_OF_RESOURCES There is not enough pool memory to store the matching results.
>- @retval EFI_INVALID_PARAMETER NumberHandles is NULL or Buffer is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFvbCountAndBuffer (
>- OUT UINTN *NumberHandles,
>- OUT EFI_HANDLE **Buffer
>- )
>-{
>- EFI_STATUS Status;
>-
>- //
>- // Locate all handles of Fvb protocol
>- //
>- Status = gBS->LocateHandleBuffer (
>- ByProtocol,
>- &gEfiFirmwareVolumeBlockProtocolGuid,
>- NULL,
>- NumberHandles,
>- Buffer
>- );
>- return Status;
>-}
>-
>-
>-/**
>- Notification function of EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE.
>-
>- This is a notification function registered on EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE event.
>- It convers pointer to new virtual address.
>-
>- @param Event Event whose notification function is being invoked.
>- @param Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-VariableClassAddressChangeEvent (
>- IN EFI_EVENT Event,
>- IN VOID *Context
>- )
>-{
>- EFI_STATUS Status;
>- UINTN Index;
>-
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance->GetBlockSize);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance->GetPhysicalAddress);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance->GetAttributes);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance->SetAttributes);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance->Read);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance->Write);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance->EraseBlocks);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->FvbInstance);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->PlatformLangCodes);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->LangCodes);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->PlatformLang);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->VariableGlobal.NonVolatileVariableBase);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->VariableGlobal.VolatileVariableBase);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal->VariableGlobal.HobVariableBase);
>- EfiConvertPointer (0x0, (VOID **) &mVariableModuleGlobal);
>- EfiConvertPointer (0x0, (VOID **) &mHashCtx);
>- EfiConvertPointer (0x0, (VOID **) &mNvVariableCache);
>- EfiConvertPointer (0x0, (VOID **) &mPubKeyStore);
>- EfiConvertPointer (0x0, (VOID **) &mCertDbStore);
>- EfiConvertPointer (0x0, (VOID **) &mHandlerTable);
>- for (Index = 0; Index < mNumberOfHandler; Index++) {
>- EfiConvertPointer (0x0, (VOID **) &mHandlerTable[Index]);
>- }
>-
>- Status = EfiConvertList (0x0, &mLockedVariableList);
>- ASSERT_EFI_ERROR (Status);
>-
>- Status = EfiConvertList (0x0, &mVarCheckVariableList);
>- ASSERT_EFI_ERROR (Status);
>-}
>-
>-
>-/**
>- Notification function of EVT_GROUP_READY_TO_BOOT event group.
>-
>- This is a notification function registered on EVT_GROUP_READY_TO_BOOT event group.
>- When the Boot Manager is about to load and execute a boot option, it reclaims variable
>- storage if free size is below the threshold.
>-
>- @param Event Event whose notification function is being invoked.
>- @param Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-OnReadyToBoot (
>- EFI_EVENT Event,
>- VOID *Context
>- )
>-{
>- //
>- // Set the End Of DXE bit in case the EFI_END_OF_DXE_EVENT_GROUP_GUID event is not signaled.
>- //
>- mEndOfDxe = TRUE;
>- //
>- // The initialization for variable quota.
>- //
>- InitializeVariableQuota ();
>- ReclaimForOS ();
>- if (FeaturePcdGet (PcdVariableCollectStatistics)) {
>- gBS->InstallConfigurationTable (&gEfiAuthenticatedVariableGuid, gVariableInfo);
>- }
>-}
>-
>-/**
>- Notification function of EFI_END_OF_DXE_EVENT_GROUP_GUID event group.
>-
>- This is a notification function registered on EFI_END_OF_DXE_EVENT_GROUP_GUID event group.
>-
>- @param Event Event whose notification function is being invoked.
>- @param Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-OnEndOfDxe (
>- EFI_EVENT Event,
>- VOID *Context
>- )
>-{
>- mEndOfDxe = TRUE;
>- //
>- // The initialization for variable quota.
>- //
>- InitializeVariableQuota ();
>- if (PcdGetBool (PcdReclaimVariableSpaceAtEndOfDxe)) {
>- ReclaimForOS ();
>- }
>-}
>-
>-/**
>- Fault Tolerant Write protocol notification event handler.
>-
>- Non-Volatile variable write may needs FTW protocol to reclaim when
>- writting variable.
>-
>- @param[in] Event Event whose notification function is being invoked.
>- @param[in] Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-FtwNotificationEvent (
>- IN EFI_EVENT Event,
>- IN VOID *Context
>- )
>-{
>- EFI_STATUS Status;
>- EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL *FvbProtocol;
>- EFI_FAULT_TOLERANT_WRITE_PROTOCOL *FtwProtocol;
>- EFI_PHYSICAL_ADDRESS NvStorageVariableBase;
>- EFI_GCD_MEMORY_SPACE_DESCRIPTOR GcdDescriptor;
>- EFI_PHYSICAL_ADDRESS BaseAddress;
>- UINT64 Length;
>- EFI_PHYSICAL_ADDRESS VariableStoreBase;
>- UINT64 VariableStoreLength;
>- UINTN FtwMaxBlockSize;
>-
>- //
>- // Ensure FTW protocol is installed.
>- //
>- Status = GetFtwProtocol ((VOID**) &FtwProtocol);
>- if (EFI_ERROR (Status)) {
>- return ;
>- }
>-
>- Status = FtwProtocol->GetMaxBlockSize (FtwProtocol, &FtwMaxBlockSize);
>- if (!EFI_ERROR (Status)) {
>- ASSERT (PcdGet32 (PcdFlashNvStorageVariableSize) <= FtwMaxBlockSize);
>- }
>-
>- //
>- // Find the proper FVB protocol for variable.
>- //
>- NvStorageVariableBase = (EFI_PHYSICAL_ADDRESS) PcdGet64 (PcdFlashNvStorageVariableBase64);
>- if (NvStorageVariableBase == 0) {
>- NvStorageVariableBase = (EFI_PHYSICAL_ADDRESS) PcdGet32 (PcdFlashNvStorageVariableBase);
>- }
>- Status = GetFvbInfoByAddress (NvStorageVariableBase, NULL, &FvbProtocol);
>- if (EFI_ERROR (Status)) {
>- return ;
>- }
>- mVariableModuleGlobal->FvbInstance = FvbProtocol;
>-
>- //
>- // Mark the variable storage region of the FLASH as RUNTIME.
>- //
>- VariableStoreBase = NvStorageVariableBase + (((EFI_FIRMWARE_VOLUME_HEADER *)(UINTN)(NvStorageVariableBase))-
>>HeaderLength);
>- VariableStoreLength = ((VARIABLE_STORE_HEADER *)(UINTN)VariableStoreBase)->Size;
>- BaseAddress = VariableStoreBase & (~EFI_PAGE_MASK);
>- Length = VariableStoreLength + (VariableStoreBase - BaseAddress);
>- Length = (Length + EFI_PAGE_SIZE - 1) & (~EFI_PAGE_MASK);
>-
>- Status = gDS->GetMemorySpaceDescriptor (BaseAddress, &GcdDescriptor);
>- if (EFI_ERROR (Status)) {
>- DEBUG ((DEBUG_WARN, "Variable driver failed to get flash memory attribute.\n"));
>- } else {
>- Status = gDS->SetMemorySpaceAttributes (
>- BaseAddress,
>- Length,
>- GcdDescriptor.Attributes | EFI_MEMORY_RUNTIME
>- );
>- if (EFI_ERROR (Status)) {
>- DEBUG ((DEBUG_WARN, "Variable driver failed to add EFI_MEMORY_RUNTIME attribute to Flash.\n"));
>- }
>- }
>-
>- Status = VariableWriteServiceInitialize ();
>- if (EFI_ERROR (Status)) {
>- DEBUG ((DEBUG_ERROR, "Variable write service initialization failed. Status = %r\n", Status));
>- }
>-
>- //
>- // Install the Variable Write Architectural protocol.
>- //
>- Status = gBS->InstallProtocolInterface (
>- &mHandle,
>- &gEfiVariableWriteArchProtocolGuid,
>- EFI_NATIVE_INTERFACE,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Close the notify event to avoid install gEfiVariableWriteArchProtocolGuid again.
>- //
>- gBS->CloseEvent (Event);
>-
>-}
>-
>-
>-/**
>- Variable Driver main entry point. The Variable driver places the 4 EFI
>- runtime services in the EFI System Table and installs arch protocols
>- for variable read and write services being available. It also registers
>- a notification function for an EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE event.
>-
>- @param[in] ImageHandle The firmware allocated handle for the EFI image.
>- @param[in] SystemTable A pointer to the EFI System Table.
>-
>- @retval EFI_SUCCESS Variable service successfully initialized.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceInitialize (
>- IN EFI_HANDLE ImageHandle,
>- IN EFI_SYSTEM_TABLE *SystemTable
>- )
>-{
>- EFI_STATUS Status;
>- EFI_EVENT ReadyToBootEvent;
>- EFI_EVENT EndOfDxeEvent;
>-
>- Status = VariableCommonInitialize ();
>- ASSERT_EFI_ERROR (Status);
>-
>- Status = gBS->InstallMultipleProtocolInterfaces (
>- &mHandle,
>- &gEdkiiVariableLockProtocolGuid,
>- &mVariableLock,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- Status = gBS->InstallMultipleProtocolInterfaces (
>- &mHandle,
>- &gEdkiiVarCheckProtocolGuid,
>- &mVarCheck,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- SystemTable->RuntimeServices->GetVariable = VariableServiceGetVariable;
>- SystemTable->RuntimeServices->GetNextVariableName = VariableServiceGetNextVariableName;
>- SystemTable->RuntimeServices->SetVariable = VariableServiceSetVariable;
>- SystemTable->RuntimeServices->QueryVariableInfo = VariableServiceQueryVariableInfo;
>-
>- //
>- // Now install the Variable Runtime Architectural protocol on a new handle.
>- //
>- Status = gBS->InstallProtocolInterface (
>- &mHandle,
>- &gEfiVariableArchProtocolGuid,
>- EFI_NATIVE_INTERFACE,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Register FtwNotificationEvent () notify function.
>- //
>- EfiCreateProtocolNotifyEvent (
>- &gEfiFaultTolerantWriteProtocolGuid,
>- TPL_CALLBACK,
>- FtwNotificationEvent,
>- (VOID *)SystemTable,
>- &mFtwRegistration
>- );
>-
>- Status = gBS->CreateEventEx (
>- EVT_NOTIFY_SIGNAL,
>- TPL_NOTIFY,
>- VariableClassAddressChangeEvent,
>- NULL,
>- &gEfiEventVirtualAddressChangeGuid,
>- &mVirtualAddressChangeEvent
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Register the event handling function to reclaim variable for OS usage.
>- //
>- Status = EfiCreateEventReadyToBootEx (
>- TPL_NOTIFY,
>- OnReadyToBoot,
>- NULL,
>- &ReadyToBootEvent
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Register the event handling function to set the End Of DXE flag.
>- //
>- Status = gBS->CreateEventEx (
>- EVT_NOTIFY_SIGNAL,
>- TPL_NOTIFY,
>- OnEndOfDxe,
>- NULL,
>- &gEfiEndOfDxeEventGroupGuid,
>- &EndOfDxeEvent
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- return EFI_SUCCESS;
>-}
>-
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxe.inf
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxe.inf
>deleted file mode 100644
>index 2b1b1c0..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxe.inf
>+++ /dev/null
>@@ -1,158 +0,0 @@
>-## @file
>-# Provides authenticated variable service
>-#
>-# This module installs variable arch protocol and variable write arch protocol to provide
>-# variable services: SetVariable, GetVariable, GetNextVariableName and QueryVariableInfo.
>-#
>-# Caution: This module requires additional review when modified.
>-# This driver will have external input - variable data.
>-# This external input must be validated carefully to avoid security issues such as
>-# buffer overflow or integer overflow.
>-#
>-# Copyright (c) 2009 - 2015, 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
>-# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
>-# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
>-#
>-##
>-
>-[Defines]
>- INF_VERSION = 0x00010005
>- BASE_NAME = VariableAuthRuntimeDxe
>- MODULE_UNI_FILE = VariableAuthRuntimeDxe.uni
>- FILE_GUID = 2226F30F-3D5B-402d-9936-A97184EB4516
>- MODULE_TYPE = DXE_RUNTIME_DRIVER
>- VERSION_STRING = 1.0
>- ENTRY_POINT = VariableServiceInitialize
>-
>-#
>-# The following information is for reference only and not required by the build tools.
>-#
>-# VALID_ARCHITECTURES = IA32 X64 EBC
>-#
>-# VIRTUAL_ADDRESS_MAP_CALLBACK = VariableClassAddressChangeEvent
>-#
>-
>-[Sources]
>- Reclaim.c
>- Variable.c
>- VariableDxe.c
>- Variable.h
>- AuthService.c
>- AuthService.h
>- Measurement.c
>- VarCheck.c
>-
>-[Packages]
>- MdePkg/MdePkg.dec
>- MdeModulePkg/MdeModulePkg.dec
>- CryptoPkg/CryptoPkg.dec
>- SecurityPkg/SecurityPkg.dec
>-
>-[LibraryClasses]
>- MemoryAllocationLib
>- BaseLib
>- SynchronizationLib
>- UefiLib
>- UefiBootServicesTableLib
>- BaseMemoryLib
>- DebugLib
>- UefiRuntimeLib
>- DxeServicesTableLib
>- UefiDriverEntryPoint
>- PcdLib
>- BaseCryptLib
>- PlatformSecureLib
>- HobLib
>- TpmMeasurementLib
>- DevicePathLib
>-
>-[Protocols]
>- gEfiFirmwareVolumeBlockProtocolGuid ## CONSUMES
>- ## CONSUMES
>- ## NOTIFY
>- gEfiFaultTolerantWriteProtocolGuid
>- gEfiVariableWriteArchProtocolGuid ## PRODUCES
>- gEfiVariableArchProtocolGuid ## PRODUCES
>- gEdkiiVariableLockProtocolGuid ## PRODUCES
>- gEdkiiVarCheckProtocolGuid ## PRODUCES
>-
>-
>-[Guids]
>- ## PRODUCES ## GUID # Variable store header
>- ## CONSUMES ## GUID # Variable store header
>- ## SOMETIMES_CONSUMES ## HOB
>- ## SOMETIMES_PRODUCES ## SystemTable
>- gEfiAuthenticatedVariableGuid
>-
>- ## SOMETIMES_CONSUMES ## Variable:L"PlatformLang"
>- ## SOMETIMES_PRODUCES ## Variable:L"PlatformLang"
>- ## SOMETIMES_CONSUMES ## Variable:L"Lang"
>- ## SOMETIMES_PRODUCES ## Variable:L"Lang"
>- ## SOMETIMES_CONSUMES ## Variable:L"HwErrRecSupport"
>- ## CONSUMES ## Variable:L"SetupMode"
>- ## PRODUCES ## Variable:L"SetupMode"
>- ## SOMETIMES_CONSUMES ## Variable:L"PK"
>- ## SOMETIMES_CONSUMES ## Variable:L"KEK"
>- ## CONSUMES ## Variable:L"SecureBoot"
>- ## PRODUCES ## Variable:L"SecureBoot"
>- ## CONSUMES ## Variable:L"SignatureSupport"
>- ## PRODUCES ## Variable:L"SignatureSupport"
>- ## PRODUCES ## Variable:L"VendorKeys"
>- gEfiGlobalVariableGuid
>-
>- ## SOMETIMES_CONSUMES ## Variable:L"DB"
>- ## SOMETIMES_CONSUMES ## Variable:L"DBX"
>- gEfiImageSecurityDatabaseGuid
>-
>- ## CONSUMES ## Variable:L"SecureBootEnable"
>- ## PRODUCES ## Variable:L"SecureBootEnable"
>- gEfiSecureBootEnableDisableGuid
>-
>- ## CONSUMES ## Variable:L"CustomMode"
>- ## PRODUCES ## Variable:L"CustomMode"
>- gEfiCustomModeEnableGuid
>-
>- ## CONSUMES ## Variable:L"certdb"
>- ## PRODUCES ## Variable:L"certdb"
>- gEfiCertDbGuid
>-
>- ## CONSUMES ## Variable:L"VendorKeysNv"
>- ## PRODUCES ## Variable:L"VendorKeysNv"
>- gEfiVendorKeysNvGuid
>-
>- gEfiEndOfDxeEventGroupGuid ## CONSUMES ## Event
>- gEfiEventVirtualAddressChangeGuid ## CONSUMES ## Event
>- gEfiCertTypeRsa2048Sha256Guid ## SOMETIMES_CONSUMES ## GUID # Unique ID for the type of the certificate.
>- gEfiCertPkcs7Guid ## SOMETIMES_CONSUMES ## GUID # Unique ID for the type of the certificate.
>- gEfiCertX509Guid ## SOMETIMES_CONSUMES ## GUID # Unique ID for the type of the signature.
>- gEfiSystemNvDataFvGuid ## CONSUMES ## GUID
>- gEfiHardwareErrorVariableGuid ## SOMETIMES_CONSUMES ## Variable:L"HwErrRec####"
>- gEdkiiFaultTolerantWriteGuid ## SOMETIMES_CONSUMES ## HOB
>- gEdkiiVarErrorFlagGuid ## CONSUMES ## GUID
>-
>-[Pcd]
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase ## SOMETIMES_CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase64 ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxAuthVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdVariableStoreSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdHwErrStorageSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxUserNvVariableSpaceSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdBoottimeReservedNvVariableSpaceSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdReclaimVariableSpaceAtEndOfDxe ## CONSUMES
>-
>-[FeaturePcd]
>- gEfiMdeModulePkgTokenSpaceGuid.PcdVariableCollectStatistics ## CONSUMES # statistic the information of variable.
>- gEfiMdePkgTokenSpaceGuid.PcdUefiVariableDefaultLangDeprecate ## CONSUMES # Auto update PlatformLang/Lang
>-
>-[Depex]
>- TRUE
>-
>-[UserExtensions.TianoCore."ExtraFiles"]
>- VariableRuntimeDxeExtra.uni
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxeExtra.uni
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableRuntimeDxeExtra.uni
>deleted file mode 100644
>index 577f005ace2b26acb15d4211d0e6fe2e092954fc..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 1376
>zcmZXUTW=FF5QXO%iT_}wFM!&F+Y>^FhAgmZn?z|s;i<}{O(W%|O<Ed$Jn)_IUfNVq
>z?D2Sf=J?F4|NU)P!vg<T{DOV9Yn$2JuI#xz!>hd?***@y&_=$~vs+u*7SDpXmfbT3
>zJGGUKiJ9a7gJ**8oG6`K+SE3zhgkA|Ayx=iJ{FmZIqt7*=VzyOLu9ZQpuc2(Yp?B%
>zy~8>xSMTi*JIyiY*vgRE+Q*@DRmM6y$1qfcctvb6%iyx%pV^&ruiHm!TF*X}I#lfX
>zFq-*&*2J$s$++19l;VC{BBaR>&SN4LFwx#F*COB%E9H}}bI>Y$sjbsea*VZfX40*|
>z*Xc=~;SO6BE2<N`I@--RQ80<Q7S6gr5i`|***@qR&+phu1O7BtWO_tskr`jEyj#b
>zZ##p75XB+trCb}<y7dU2>Y<`8QdPIU#vdyr&iBOZb9$^x)N)7EC_lf-6%eEC16|ce
>zTPpFv`+9{HwN-rPO4nhNQP0Mn_8UASm`~`r$Jy(k-0-gy>DzZpVAG|0I`)n6*v?p|
>zC>hXFb02R?e+{q_*LPrT<^+Gh7ZED$Q~Eg};@putSn6YqHD=)owZ`1^wN{***@I9;$W
>z)Q)Eic0p9nnYHn!pbDeo*?X+ST|VXP6RQ|yjZt5TRrX)ZC+vv1zP}{T5^s^%&l0CX
>***@FHz{X}@3GLWn1jDV4fo4;Q1*-75WOhU?lM=m3rerN!6n!oPzT^A#I#{~h7}y`
>vz`qfp+|n0Q?-kYmh<Nc+HmRwuR42w4PA{7JP+#BvI~d6Q^d+p7+=cibbl=vE
>
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.c
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.c
>deleted file mode 100644
>index 1eb169a..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.c
>+++ /dev/null
>@@ -1,988 +0,0 @@
>-/** @file
>- The sample implementation for SMM variable protocol. And this driver
>- implements an SMI handler to communicate with the DXE runtime driver
>- to provide variable services.
>-
>- Caution: This module requires additional review when modified.
>- This driver will have external input - variable data and communicate buffer in SMM mode.
>- This external input must be validated carefully to avoid security issue like
>- buffer overflow, integer overflow.
>-
>- SmmVariableHandler() will receive untrusted input and do basic validation.
>-
>- Each sub function VariableServiceGetVariable(), VariableServiceGetNextVariableName(),
>- VariableServiceSetVariable(), VariableServiceQueryVariableInfo(), ReclaimForOS(),
>- SmmVariableGetStatistics() should also do validation based on its own knowledge.
>-
>-Copyright (c) 2010 - 2015, 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
>-
>-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 <Protocol/SmmVariable.h>
>-#include <Protocol/SmmFirmwareVolumeBlock.h>
>-#include <Protocol/SmmFaultTolerantWrite.h>
>-#include <Protocol/SmmEndOfDxe.h>
>-#include <Protocol/SmmVarCheck.h>
>-
>-#include <Library/SmmServicesTableLib.h>
>-#include <Library/SmmMemLib.h>
>-
>-#include <Guid/AuthenticatedVariableFormat.h>
>-#include <Guid/SmmVariableCommon.h>
>-#include "Variable.h"
>-
>-extern VARIABLE_INFO_ENTRY *gVariableInfo;
>-EFI_HANDLE mSmmVariableHandle = NULL;
>-EFI_HANDLE mVariableHandle = NULL;
>-BOOLEAN mAtRuntime = FALSE;
>-EFI_GUID mZeroGuid = {0, 0, 0, {0, 0, 0, 0, 0, 0, 0, 0}};
>-UINT8 *mVariableBufferPayload = NULL;
>-UINTN mVariableBufferPayloadSize;
>-extern BOOLEAN mEndOfDxe;
>-extern BOOLEAN mEnableLocking;
>-
>-/**
>- SecureBoot Hook for SetVariable.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>-
>-**/
>-VOID
>-EFIAPI
>-SecureBootHook (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- return ;
>-}
>-
>-/**
>-
>- This code sets variable in storage blocks (Volatile or Non-Volatile).
>-
>- @param VariableName Name of Variable to be found.
>- @param VendorGuid Variable vendor GUID.
>- @param Attributes Attribute value of the variable found
>- @param DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param Data Data pointer.
>-
>- @return EFI_INVALID_PARAMETER Invalid parameter.
>- @return EFI_SUCCESS Set successfully.
>- @return EFI_OUT_OF_RESOURCES Resource not enough to set variable.
>- @return EFI_NOT_FOUND Not found.
>- @return EFI_WRITE_PROTECTED Variable is read-only.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-SmmVariableSetVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT32 Attributes,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- EFI_STATUS Status;
>-
>- //
>- // Disable write protection when the calling SetVariable() through EFI_SMM_VARIABLE_PROTOCOL.
>- //
>- mEnableLocking = FALSE;
>- Status = VariableServiceSetVariable (
>- VariableName,
>- VendorGuid,
>- Attributes,
>- DataSize,
>- Data
>- );
>- mEnableLocking = TRUE;
>- return Status;
>-}
>-
>-EFI_SMM_VARIABLE_PROTOCOL gSmmVariable = {
>- VariableServiceGetVariable,
>- VariableServiceGetNextVariableName,
>- SmmVariableSetVariable,
>- VariableServiceQueryVariableInfo
>-};
>-
>-EDKII_SMM_VAR_CHECK_PROTOCOL mSmmVarCheck = { VarCheckRegisterSetVariableCheckHandler,
>- VarCheckVariablePropertySet,
>- VarCheckVariablePropertyGet };
>-
>-/**
>- Return TRUE if ExitBootServices () has been called.
>-
>- @retval TRUE If ExitBootServices () has been called.
>-**/
>-BOOLEAN
>-AtRuntime (
>- VOID
>- )
>-{
>- return mAtRuntime;
>-}
>-
>-/**
>- Initializes a basic mutual exclusion lock.
>-
>- This function initializes a basic mutual exclusion lock to the released state
>- and returns the lock. Each lock provides mutual exclusion access at its task
>- priority level. Since there is no preemption or multiprocessor support in EFI,
>- acquiring the lock only consists of raising to the locks TPL.
>- If Lock is NULL, then ASSERT().
>- If Priority is not a valid TPL value, then ASSERT().
>-
>- @param Lock A pointer to the lock data structure to initialize.
>- @param Priority EFI TPL is associated with the lock.
>-
>- @return The lock.
>-
>-**/
>-EFI_LOCK *
>-InitializeLock (
>- IN OUT EFI_LOCK *Lock,
>- IN EFI_TPL Priority
>- )
>-{
>- return Lock;
>-}
>-
>-/**
>- Acquires lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function that will be removed when
>- EfiAcquireLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiAcquireLock() at boot time, and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to acquire.
>-
>-**/
>-VOID
>-AcquireLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- )
>-{
>-
>-}
>-
>-
>-/**
>- Releases lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function which will be removed when
>- EfiReleaseLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiReleaseLock() at boot time and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to release.
>-
>-**/
>-VOID
>-ReleaseLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- )
>-{
>-
>-}
>-
>-/**
>- Retrive the SMM Fault Tolerent Write protocol interface.
>-
>- @param[out] FtwProtocol The interface of SMM Ftw protocol
>-
>- @retval EFI_SUCCESS The SMM FTW protocol instance was found and returned in FtwProtocol.
>- @retval EFI_NOT_FOUND The SMM FTW protocol instance was not found.
>- @retval EFI_INVALID_PARAMETER SarProtocol is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFtwProtocol (
>- OUT VOID **FtwProtocol
>- )
>-{
>- EFI_STATUS Status;
>-
>- //
>- // Locate Smm Fault Tolerent Write protocol
>- //
>- Status = gSmst->SmmLocateProtocol (
>- &gEfiSmmFaultTolerantWriteProtocolGuid,
>- NULL,
>- FtwProtocol
>- );
>- return Status;
>-}
>-
>-
>-/**
>- Retrive the SMM FVB protocol interface by HANDLE.
>-
>- @param[in] FvBlockHandle The handle of SMM FVB protocol that provides services for
>- reading, writing, and erasing the target block.
>- @param[out] FvBlock The interface of SMM FVB protocol
>-
>- @retval EFI_SUCCESS The interface information for the specified protocol was returned.
>- @retval EFI_UNSUPPORTED The device does not support the SMM FVB protocol.
>- @retval EFI_INVALID_PARAMETER FvBlockHandle is not a valid EFI_HANDLE or FvBlock is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFvbByHandle (
>- IN EFI_HANDLE FvBlockHandle,
>- OUT EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL **FvBlock
>- )
>-{
>- //
>- // To get the SMM FVB protocol interface on the handle
>- //
>- return gSmst->SmmHandleProtocol (
>- FvBlockHandle,
>- &gEfiSmmFirmwareVolumeBlockProtocolGuid,
>- (VOID **) FvBlock
>- );
>-}
>-
>-
>-/**
>- Function returns an array of handles that support the SMM FVB protocol
>- in a buffer allocated from pool.
>-
>- @param[out] NumberHandles The number of handles returned in Buffer.
>- @param[out] Buffer A pointer to the buffer to return the requested
>- array of handles that support SMM FVB protocol.
>-
>- @retval EFI_SUCCESS The array of handles was returned in Buffer, and the number of
>- handles in Buffer was returned in NumberHandles.
>- @retval EFI_NOT_FOUND No SMM FVB handle was found.
>- @retval EFI_OUT_OF_RESOURCES There is not enough pool memory to store the matching results.
>- @retval EFI_INVALID_PARAMETER NumberHandles is NULL or Buffer is NULL.
>-
>-**/
>-EFI_STATUS
>-GetFvbCountAndBuffer (
>- OUT UINTN *NumberHandles,
>- OUT EFI_HANDLE **Buffer
>- )
>-{
>- EFI_STATUS Status;
>- UINTN BufferSize;
>-
>- if ((NumberHandles == NULL) || (Buffer == NULL)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- BufferSize = 0;
>- *NumberHandles = 0;
>- *Buffer = NULL;
>- Status = gSmst->SmmLocateHandle (
>- ByProtocol,
>- &gEfiSmmFirmwareVolumeBlockProtocolGuid,
>- NULL,
>- &BufferSize,
>- *Buffer
>- );
>- if (EFI_ERROR(Status) && Status != EFI_BUFFER_TOO_SMALL) {
>- return EFI_NOT_FOUND;
>- }
>-
>- *Buffer = AllocatePool (BufferSize);
>- if (*Buffer == NULL) {
>- return EFI_OUT_OF_RESOURCES;
>- }
>-
>- Status = gSmst->SmmLocateHandle (
>- ByProtocol,
>- &gEfiSmmFirmwareVolumeBlockProtocolGuid,
>- NULL,
>- &BufferSize,
>- *Buffer
>- );
>-
>- *NumberHandles = BufferSize / sizeof(EFI_HANDLE);
>- if (EFI_ERROR(Status)) {
>- *NumberHandles = 0;
>- FreePool (*Buffer);
>- *Buffer = NULL;
>- }
>-
>- return Status;
>-}
>-
>-
>-/**
>- Get the variable statistics information from the information buffer pointed by gVariableInfo.
>-
>- Caution: This function may be invoked at SMM runtime.
>- InfoEntry and InfoSize are external input. Care must be taken to make sure not security issue at runtime.
>-
>- @param[in, out] InfoEntry A pointer to the buffer of variable information entry.
>- On input, point to the variable information returned last time. if
>- InfoEntry->VendorGuid is zero, return the first information.
>- On output, point to the next variable information.
>- @param[in, out] InfoSize On input, the size of the variable information buffer.
>- On output, the returned variable information size.
>-
>- @retval EFI_SUCCESS The variable information is found and returned successfully.
>- @retval EFI_UNSUPPORTED No variable inoformation exists in variable driver. The
>- PcdVariableCollectStatistics should be set TRUE to support it.
>- @retval EFI_BUFFER_TOO_SMALL The buffer is too small to hold the next variable information.
>- @retval EFI_INVALID_PARAMETER Input parameter is invalid.
>-
>-**/
>-EFI_STATUS
>-SmmVariableGetStatistics (
>- IN OUT VARIABLE_INFO_ENTRY *InfoEntry,
>- IN OUT UINTN *InfoSize
>- )
>-{
>- VARIABLE_INFO_ENTRY *VariableInfo;
>- UINTN NameLength;
>- UINTN StatisticsInfoSize;
>- CHAR16 *InfoName;
>- EFI_GUID VendorGuid;
>-
>- if (InfoEntry == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- VariableInfo = gVariableInfo;
>- if (VariableInfo == NULL) {
>- return EFI_UNSUPPORTED;
>- }
>-
>- StatisticsInfoSize = sizeof (VARIABLE_INFO_ENTRY) + StrSize (VariableInfo->Name);
>- if (*InfoSize < StatisticsInfoSize) {
>- *InfoSize = StatisticsInfoSize;
>- return EFI_BUFFER_TOO_SMALL;
>- }
>- InfoName = (CHAR16 *)(InfoEntry + 1);
>-
>- CopyGuid (&VendorGuid, &InfoEntry->VendorGuid);
>-
>- if (CompareGuid (&VendorGuid, &mZeroGuid)) {
>- //
>- // Return the first variable info
>- //
>- CopyMem (InfoEntry, VariableInfo, sizeof (VARIABLE_INFO_ENTRY));
>- CopyMem (InfoName, VariableInfo->Name, StrSize (VariableInfo->Name));
>- *InfoSize = StatisticsInfoSize;
>- return EFI_SUCCESS;
>- }
>-
>- //
>- // Get the next variable info
>- //
>- while (VariableInfo != NULL) {
>- if (CompareGuid (&VariableInfo->VendorGuid, &VendorGuid)) {
>- NameLength = StrSize (VariableInfo->Name);
>- if (NameLength == StrSize (InfoName)) {
>- if (CompareMem (VariableInfo->Name, InfoName, NameLength) == 0) {
>- //
>- // Find the match one
>- //
>- VariableInfo = VariableInfo->Next;
>- break;
>- }
>- }
>- }
>- VariableInfo = VariableInfo->Next;
>- };
>-
>- if (VariableInfo == NULL) {
>- *InfoSize = 0;
>- return EFI_SUCCESS;
>- }
>-
>- //
>- // Output the new variable info
>- //
>- StatisticsInfoSize = sizeof (VARIABLE_INFO_ENTRY) + StrSize (VariableInfo->Name);
>- if (*InfoSize < StatisticsInfoSize) {
>- *InfoSize = StatisticsInfoSize;
>- return EFI_BUFFER_TOO_SMALL;
>- }
>-
>- CopyMem (InfoEntry, VariableInfo, sizeof (VARIABLE_INFO_ENTRY));
>- CopyMem (InfoName, VariableInfo->Name, StrSize (VariableInfo->Name));
>- *InfoSize = StatisticsInfoSize;
>-
>- return EFI_SUCCESS;
>-}
>-
>-
>-/**
>- Communication service SMI Handler entry.
>-
>- This SMI handler provides services for the variable wrapper driver.
>-
>- Caution: This function may receive untrusted input.
>- This variable data and communicate buffer are external input, so this function will do basic validation.
>- Each sub function VariableServiceGetVariable(), VariableServiceGetNextVariableName(),
>- VariableServiceSetVariable(), VariableServiceQueryVariableInfo(), ReclaimForOS(),
>- SmmVariableGetStatistics() should also do validation based on its own knowledge.
>-
>- @param[in] DispatchHandle The unique handle assigned to this handler by SmiHandlerRegister().
>- @param[in] RegisterContext Points to an optional handler context which was specified when the
>- handler was registered.
>- @param[in, out] CommBuffer A pointer to a collection of data in memory that will
>- be conveyed from a non-SMM environment into an SMM environment.
>- @param[in, out] CommBufferSize The size of the CommBuffer.
>-
>- @retval EFI_SUCCESS The interrupt was handled and quiesced. No other handlers
>- should still be called.
>- @retval EFI_WARN_INTERRUPT_SOURCE_QUIESCED The interrupt has been quiesced but other handlers should
>- still be called.
>- @retval EFI_WARN_INTERRUPT_SOURCE_PENDING The interrupt is still pending and other handlers should still
>- be called.
>- @retval EFI_INTERRUPT_PENDING The interrupt could not be quiesced.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-SmmVariableHandler (
>- IN EFI_HANDLE DispatchHandle,
>- IN CONST VOID *RegisterContext,
>- IN OUT VOID *CommBuffer,
>- IN OUT UINTN *CommBufferSize
>- )
>-{
>- EFI_STATUS Status;
>- SMM_VARIABLE_COMMUNICATE_HEADER *SmmVariableFunctionHeader;
>- SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE *SmmVariableHeader;
>- SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME *GetNextVariableName;
>- SMM_VARIABLE_COMMUNICATE_QUERY_VARIABLE_INFO *QueryVariableInfo;
>- VARIABLE_INFO_ENTRY *VariableInfo;
>- SMM_VARIABLE_COMMUNICATE_LOCK_VARIABLE *VariableToLock;
>- SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY *CommVariableProperty;
>- UINTN InfoSize;
>- UINTN NameBufferSize;
>- UINTN CommBufferPayloadSize;
>- UINTN TempCommBufferSize;
>-
>- //
>- // If input is invalid, stop processing this SMI
>- //
>- if (CommBuffer == NULL || CommBufferSize == NULL) {
>- return EFI_SUCCESS;
>- }
>-
>- TempCommBufferSize = *CommBufferSize;
>-
>- if (TempCommBufferSize < SMM_VARIABLE_COMMUNICATE_HEADER_SIZE) {
>- DEBUG ((EFI_D_ERROR, "SmmVariableHandler: SMM communication buffer size invalid!\n"));
>- return EFI_SUCCESS;
>- }
>- CommBufferPayloadSize = TempCommBufferSize - SMM_VARIABLE_COMMUNICATE_HEADER_SIZE;
>- if (CommBufferPayloadSize > mVariableBufferPayloadSize) {
>- DEBUG ((EFI_D_ERROR, "SmmVariableHandler: SMM communication buffer payload size invalid!\n"));
>- return EFI_SUCCESS;
>- }
>-
>- if (!SmmIsBufferOutsideSmmValid ((UINTN)CommBuffer, TempCommBufferSize)) {
>- DEBUG ((EFI_D_ERROR, "SmmVariableHandler: SMM communication buffer in SMRAM or overflow!\n"));
>- return EFI_SUCCESS;
>- }
>-
>- SmmVariableFunctionHeader = (SMM_VARIABLE_COMMUNICATE_HEADER *)CommBuffer;
>-
>- switch (SmmVariableFunctionHeader->Function) {
>- case SMM_VARIABLE_FUNCTION_GET_VARIABLE:
>- if (CommBufferPayloadSize < OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name)) {
>- DEBUG ((EFI_D_ERROR, "GetVariable: SMM communication buffer size invalid!\n"));
>- return EFI_SUCCESS;
>- }
>- //
>- // Copy the input communicate buffer payload to pre-allocated SMM variable buffer payload.
>- //
>- CopyMem (mVariableBufferPayload, SmmVariableFunctionHeader->Data, CommBufferPayloadSize);
>- SmmVariableHeader = (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE *) mVariableBufferPayload;
>- if (((UINTN)(~0) - SmmVariableHeader->DataSize < OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name)) ||
>- ((UINTN)(~0) - SmmVariableHeader->NameSize < OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name) +
>SmmVariableHeader->DataSize)) {
>- //
>- // Prevent InfoSize overflow happen
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>- InfoSize = OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name)
>- + SmmVariableHeader->DataSize + SmmVariableHeader->NameSize;
>-
>- //
>- // SMRAM range check already covered before
>- //
>- if (InfoSize > CommBufferPayloadSize) {
>- DEBUG ((EFI_D_ERROR, "GetVariable: Data size exceed communication buffer size limit!\n"));
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- if (SmmVariableHeader->NameSize < sizeof (CHAR16) || SmmVariableHeader->Name[SmmVariableHeader->NameSize/sizeof
>(CHAR16) - 1] != L'\0') {
>- //
>- // Make sure VariableName is A Null-terminated string.
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- Status = VariableServiceGetVariable (
>- SmmVariableHeader->Name,
>- &SmmVariableHeader->Guid,
>- &SmmVariableHeader->Attributes,
>- &SmmVariableHeader->DataSize,
>- (UINT8 *)SmmVariableHeader->Name + SmmVariableHeader->NameSize
>- );
>- CopyMem (SmmVariableFunctionHeader->Data, mVariableBufferPayload, CommBufferPayloadSize);
>- break;
>-
>- case SMM_VARIABLE_FUNCTION_GET_NEXT_VARIABLE_NAME:
>- if (CommBufferPayloadSize < OFFSET_OF(SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME, Name)) {
>- DEBUG ((EFI_D_ERROR, "GetNextVariableName: SMM communication buffer size invalid!\n"));
>- return EFI_SUCCESS;
>- }
>- //
>- // Copy the input communicate buffer payload to pre-allocated SMM variable buffer payload.
>- //
>- CopyMem (mVariableBufferPayload, SmmVariableFunctionHeader->Data, CommBufferPayloadSize);
>- GetNextVariableName = (SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME *) mVariableBufferPayload;
>- if ((UINTN)(~0) - GetNextVariableName->NameSize <
>OFFSET_OF(SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME, Name)) {
>- //
>- // Prevent InfoSize overflow happen
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>- InfoSize = OFFSET_OF(SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME, Name) + GetNextVariableName-
>>NameSize;
>-
>- //
>- // SMRAM range check already covered before
>- //
>- if (InfoSize > CommBufferPayloadSize) {
>- DEBUG ((EFI_D_ERROR, "GetNextVariableName: Data size exceed communication buffer size limit!\n"));
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- NameBufferSize = CommBufferPayloadSize - OFFSET_OF(SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME,
>Name);
>- if (NameBufferSize < sizeof (CHAR16) || GetNextVariableName->Name[NameBufferSize/sizeof (CHAR16) - 1] != L'\0') {
>- //
>- // Make sure input VariableName is A Null-terminated string.
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- Status = VariableServiceGetNextVariableName (
>- &GetNextVariableName->NameSize,
>- GetNextVariableName->Name,
>- &GetNextVariableName->Guid
>- );
>- CopyMem (SmmVariableFunctionHeader->Data, mVariableBufferPayload, CommBufferPayloadSize);
>- break;
>-
>- case SMM_VARIABLE_FUNCTION_SET_VARIABLE:
>- if (CommBufferPayloadSize < OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name)) {
>- DEBUG ((EFI_D_ERROR, "SetVariable: SMM communication buffer size invalid!\n"));
>- return EFI_SUCCESS;
>- }
>- //
>- // Copy the input communicate buffer payload to pre-allocated SMM variable buffer payload.
>- //
>- CopyMem (mVariableBufferPayload, SmmVariableFunctionHeader->Data, CommBufferPayloadSize);
>- SmmVariableHeader = (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE *) mVariableBufferPayload;
>- if (((UINTN)(~0) - SmmVariableHeader->DataSize < OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name)) ||
>- ((UINTN)(~0) - SmmVariableHeader->NameSize < OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name) +
>SmmVariableHeader->DataSize)) {
>- //
>- // Prevent InfoSize overflow happen
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>- InfoSize = OFFSET_OF(SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name)
>- + SmmVariableHeader->DataSize + SmmVariableHeader->NameSize;
>-
>- //
>- // SMRAM range check already covered before
>- // Data buffer should not contain SMM range
>- //
>- if (InfoSize > CommBufferPayloadSize) {
>- DEBUG ((EFI_D_ERROR, "SetVariable: Data size exceed communication buffer size limit!\n"));
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- if (SmmVariableHeader->NameSize < sizeof (CHAR16) || SmmVariableHeader->Name[SmmVariableHeader->NameSize/sizeof
>(CHAR16) - 1] != L'\0') {
>- //
>- // Make sure VariableName is A Null-terminated string.
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- Status = VariableServiceSetVariable (
>- SmmVariableHeader->Name,
>- &SmmVariableHeader->Guid,
>- SmmVariableHeader->Attributes,
>- SmmVariableHeader->DataSize,
>- (UINT8 *)SmmVariableHeader->Name + SmmVariableHeader->NameSize
>- );
>- break;
>-
>- case SMM_VARIABLE_FUNCTION_QUERY_VARIABLE_INFO:
>- if (CommBufferPayloadSize < sizeof (SMM_VARIABLE_COMMUNICATE_QUERY_VARIABLE_INFO)) {
>- DEBUG ((EFI_D_ERROR, "QueryVariableInfo: SMM communication buffer size invalid!\n"));
>- return EFI_SUCCESS;
>- }
>- QueryVariableInfo = (SMM_VARIABLE_COMMUNICATE_QUERY_VARIABLE_INFO *) SmmVariableFunctionHeader->Data;
>-
>- Status = VariableServiceQueryVariableInfo (
>- QueryVariableInfo->Attributes,
>- &QueryVariableInfo->MaximumVariableStorageSize,
>- &QueryVariableInfo->RemainingVariableStorageSize,
>- &QueryVariableInfo->MaximumVariableSize
>- );
>- break;
>-
>- case SMM_VARIABLE_FUNCTION_READY_TO_BOOT:
>- mEndOfDxe = TRUE;
>- //
>- // The initialization for variable quota.
>- //
>- InitializeVariableQuota ();
>- if (AtRuntime()) {
>- Status = EFI_UNSUPPORTED;
>- break;
>- }
>- ReclaimForOS ();
>- Status = EFI_SUCCESS;
>- break;
>-
>- case SMM_VARIABLE_FUNCTION_EXIT_BOOT_SERVICE:
>- mAtRuntime = TRUE;
>- Status = EFI_SUCCESS;
>- break;
>-
>- case SMM_VARIABLE_FUNCTION_GET_STATISTICS:
>- VariableInfo = (VARIABLE_INFO_ENTRY *) SmmVariableFunctionHeader->Data;
>- InfoSize = TempCommBufferSize - SMM_VARIABLE_COMMUNICATE_HEADER_SIZE;
>-
>- //
>- // Do not need to check SmmVariableFunctionHeader->Data in SMRAM here.
>- // It is covered by previous CommBuffer check
>- //
>-
>- if (!SmmIsBufferOutsideSmmValid ((EFI_PHYSICAL_ADDRESS)(UINTN)CommBufferSize, sizeof(UINTN))) {
>- DEBUG ((EFI_D_ERROR, "GetStatistics: SMM communication buffer in SMRAM!\n"));
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- Status = SmmVariableGetStatistics (VariableInfo, &InfoSize);
>- *CommBufferSize = InfoSize + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE;
>- break;
>-
>- case SMM_VARIABLE_FUNCTION_LOCK_VARIABLE:
>- if (mEndOfDxe) {
>- Status = EFI_ACCESS_DENIED;
>- } else {
>- VariableToLock = (SMM_VARIABLE_COMMUNICATE_LOCK_VARIABLE *) SmmVariableFunctionHeader->Data;
>- Status = VariableLockRequestToLock (
>- NULL,
>- VariableToLock->Name,
>- &VariableToLock->Guid
>- );
>- }
>- break;
>- case SMM_VARIABLE_FUNCTION_VAR_CHECK_VARIABLE_PROPERTY_SET:
>- if (mEndOfDxe) {
>- Status = EFI_ACCESS_DENIED;
>- } else {
>- CommVariableProperty = (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY *)
>SmmVariableFunctionHeader->Data;
>- Status = VarCheckVariablePropertySet (
>- CommVariableProperty->Name,
>- &CommVariableProperty->Guid,
>- &CommVariableProperty->VariableProperty
>- );
>- }
>- break;
>- case SMM_VARIABLE_FUNCTION_VAR_CHECK_VARIABLE_PROPERTY_GET:
>- if (CommBufferPayloadSize < OFFSET_OF (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name)) {
>- DEBUG ((EFI_D_ERROR, "VarCheckVariablePropertyGet: SMM communication buffer size invalid!\n"));
>- return EFI_SUCCESS;
>- }
>- //
>- // Copy the input communicate buffer payload to pre-allocated SMM variable buffer payload.
>- //
>- CopyMem (mVariableBufferPayload, SmmVariableFunctionHeader->Data, CommBufferPayloadSize);
>- CommVariableProperty = (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY *) mVariableBufferPayload;
>- if ((UINTN) (~0) - CommVariableProperty->NameSize < OFFSET_OF
>(SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name)) {
>- //
>- // Prevent InfoSize overflow happen
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>- InfoSize = OFFSET_OF (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name) + CommVariableProperty-
>>NameSize;
>-
>- //
>- // SMRAM range check already covered before
>- //
>- if (InfoSize > CommBufferPayloadSize) {
>- DEBUG ((EFI_D_ERROR, "VarCheckVariablePropertyGet: Data size exceed communication buffer size limit!\n"));
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- if (CommVariableProperty->NameSize < sizeof (CHAR16) || CommVariableProperty->Name[CommVariableProperty-
>>NameSize/sizeof (CHAR16) - 1] != L'\0') {
>- //
>- // Make sure VariableName is A Null-terminated string.
>- //
>- Status = EFI_ACCESS_DENIED;
>- goto EXIT;
>- }
>-
>- Status = VarCheckVariablePropertyGet (
>- CommVariableProperty->Name,
>- &CommVariableProperty->Guid,
>- &CommVariableProperty->VariableProperty
>- );
>- CopyMem (SmmVariableFunctionHeader->Data, mVariableBufferPayload, CommBufferPayloadSize);
>- break;
>-
>- default:
>- Status = EFI_UNSUPPORTED;
>- }
>-
>-EXIT:
>-
>- SmmVariableFunctionHeader->ReturnStatus = Status;
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- SMM END_OF_DXE protocol notification event handler.
>-
>- @param Protocol Points to the protocol's unique identifier
>- @param Interface Points to the interface instance
>- @param Handle The handle on which the interface was installed
>-
>- @retval EFI_SUCCESS SmmEndOfDxeCallback runs successfully
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-SmmEndOfDxeCallback (
>- IN CONST EFI_GUID *Protocol,
>- IN VOID *Interface,
>- IN EFI_HANDLE Handle
>- )
>-{
>- DEBUG ((EFI_D_INFO, "[Variable]END_OF_DXE is signaled\n"));
>- mEndOfDxe = TRUE;
>- //
>- // The initialization for variable quota.
>- //
>- InitializeVariableQuota ();
>- if (PcdGetBool (PcdReclaimVariableSpaceAtEndOfDxe)) {
>- ReclaimForOS ();
>- }
>- return EFI_SUCCESS;
>-}
>-
>-/**
>- SMM Fault Tolerant Write protocol notification event handler.
>-
>- Non-Volatile variable write may needs FTW protocol to reclaim when
>- writting variable.
>-
>- @param Protocol Points to the protocol's unique identifier
>- @param Interface Points to the interface instance
>- @param Handle The handle on which the interface was installed
>-
>- @retval EFI_SUCCESS SmmEventCallback runs successfully
>- @retval EFI_NOT_FOUND The Fvb protocol for variable is not found.
>-
>- **/
>-EFI_STATUS
>-EFIAPI
>-SmmFtwNotificationEvent (
>- IN CONST EFI_GUID *Protocol,
>- IN VOID *Interface,
>- IN EFI_HANDLE Handle
>- )
>-{
>- EFI_STATUS Status;
>- EFI_SMM_FIRMWARE_VOLUME_BLOCK_PROTOCOL *FvbProtocol;
>- EFI_SMM_FAULT_TOLERANT_WRITE_PROTOCOL *FtwProtocol;
>- EFI_PHYSICAL_ADDRESS NvStorageVariableBase;
>- UINTN FtwMaxBlockSize;
>-
>- if (mVariableModuleGlobal->FvbInstance != NULL) {
>- return EFI_SUCCESS;
>- }
>-
>- //
>- // Ensure SMM FTW protocol is installed.
>- //
>- Status = GetFtwProtocol ((VOID **)&FtwProtocol);
>- if (EFI_ERROR (Status)) {
>- return Status;
>- }
>-
>- Status = FtwProtocol->GetMaxBlockSize (FtwProtocol, &FtwMaxBlockSize);
>- if (!EFI_ERROR (Status)) {
>- ASSERT (PcdGet32 (PcdFlashNvStorageVariableSize) <= FtwMaxBlockSize);
>- }
>-
>- //
>- // Find the proper FVB protocol for variable.
>- //
>- NvStorageVariableBase = (EFI_PHYSICAL_ADDRESS) PcdGet64 (PcdFlashNvStorageVariableBase64);
>- if (NvStorageVariableBase == 0) {
>- NvStorageVariableBase = (EFI_PHYSICAL_ADDRESS) PcdGet32 (PcdFlashNvStorageVariableBase);
>- }
>- Status = GetFvbInfoByAddress (NvStorageVariableBase, NULL, &FvbProtocol);
>- if (EFI_ERROR (Status)) {
>- return EFI_NOT_FOUND;
>- }
>-
>- mVariableModuleGlobal->FvbInstance = FvbProtocol;
>-
>- Status = VariableWriteServiceInitialize ();
>- if (EFI_ERROR (Status)) {
>- DEBUG ((DEBUG_ERROR, "Variable write service initialization failed. Status = %r\n", Status));
>- }
>-
>- //
>- // Notify the variable wrapper driver the variable write service is ready
>- //
>- Status = gBS->InstallProtocolInterface (
>- &mSmmVariableHandle,
>- &gSmmVariableWriteGuid,
>- EFI_NATIVE_INTERFACE,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- return EFI_SUCCESS;
>-}
>-
>-
>-/**
>- Variable Driver main entry point. The Variable driver places the 4 EFI
>- runtime services in the EFI System Table and installs arch protocols
>- for variable read and write services being available. It also registers
>- a notification function for an EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE event.
>-
>- @param[in] ImageHandle The firmware allocated handle for the EFI image.
>- @param[in] SystemTable A pointer to the EFI System Table.
>-
>- @retval EFI_SUCCESS Variable service successfully initialized.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableServiceInitialize (
>- IN EFI_HANDLE ImageHandle,
>- IN EFI_SYSTEM_TABLE *SystemTable
>- )
>-{
>- EFI_STATUS Status;
>- EFI_HANDLE VariableHandle;
>- VOID *SmmFtwRegistration;
>- VOID *SmmEndOfDxeRegistration;
>-
>- //
>- // Variable initialize.
>- //
>- Status = VariableCommonInitialize ();
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Install the Smm Variable Protocol on a new handle.
>- //
>- VariableHandle = NULL;
>- Status = gSmst->SmmInstallProtocolInterface (
>- &VariableHandle,
>- &gEfiSmmVariableProtocolGuid,
>- EFI_NATIVE_INTERFACE,
>- &gSmmVariable
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- Status = gSmst->SmmInstallProtocolInterface (
>- &VariableHandle,
>- &gEdkiiSmmVarCheckProtocolGuid,
>- EFI_NATIVE_INTERFACE,
>- &mSmmVarCheck
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- mVariableBufferPayloadSize = MAX_NV_VARIABLE_SIZE +
>- OFFSET_OF (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name) - sizeof
>(VARIABLE_HEADER);
>-
>- Status = gSmst->SmmAllocatePool (
>- EfiRuntimeServicesData,
>- mVariableBufferPayloadSize,
>- (VOID **)&mVariableBufferPayload
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- ///
>- /// Register SMM variable SMI handler
>- ///
>- VariableHandle = NULL;
>- Status = gSmst->SmiHandlerRegister (SmmVariableHandler, &gEfiSmmVariableProtocolGuid, &VariableHandle);
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Notify the variable wrapper driver the variable service is ready
>- //
>- Status = SystemTable->BootServices->InstallProtocolInterface (
>- &mVariableHandle,
>- &gEfiSmmVariableProtocolGuid,
>- EFI_NATIVE_INTERFACE,
>- &gSmmVariable
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Register EFI_SMM_END_OF_DXE_PROTOCOL_GUID notify function.
>- //
>- Status = gSmst->SmmRegisterProtocolNotify (
>- &gEfiSmmEndOfDxeProtocolGuid,
>- SmmEndOfDxeCallback,
>- &SmmEndOfDxeRegistration
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Register FtwNotificationEvent () notify function.
>- //
>- Status = gSmst->SmmRegisterProtocolNotify (
>- &gEfiSmmFaultTolerantWriteProtocolGuid,
>- SmmFtwNotificationEvent,
>- &SmmFtwRegistration
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- SmmFtwNotificationEvent (NULL, NULL, NULL);
>-
>- return EFI_SUCCESS;
>-}
>-
>-
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.inf
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.inf
>deleted file mode 100644
>index 00181db..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmm.inf
>+++ /dev/null
>@@ -1,165 +0,0 @@
>-## @file
>-# Provides SMM authenticated variable service
>-#
>-# This module installs SMM variable protocol into SMM protocol database,
>-# which can be used by SMM driver, and installs SMM variable protocol
>-# into BS protocol database, which can be used to notify the SMM Runtime
>-# Dxe driver that the SMM variable service is ready.
>-# This module should be used with SMM Runtime DXE module together. The
>-# SMM Runtime DXE module installs variable arch protocol and variable
>-# write arch protocol based on SMM variable module.
>-#
>-# Caution: This module requires additional review when modified.
>-# This driver will have external input - variable data and communicate buffer in SMM mode.
>-# This external input must be validated carefully to avoid security issues such as
>-# buffer overflow or integer overflow.
>-# The whole SMM authentication variable design relies on the integrity of flash part and SMM.
>-# which is assumed to be protected by platform. All variable code and metadata in flash/SMM Memory
>-# may not be modified without authorization. If platform fails to protect these resources,
>-# the authentication service provided in this driver will be broken, and the behavior is undefined.
>-#
>-# Copyright (c) 2010 - 2015, 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
>-# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
>-# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
>-#
>-##
>-
>-[Defines]
>- INF_VERSION = 0x00010005
>- BASE_NAME = VariableAuthSmm
>- MODULE_UNI_FILE = VariableAuthSmm.uni
>- FILE_GUID = D34BDC5E-968A-40f5-A48C-E594F45AE211
>- MODULE_TYPE = DXE_SMM_DRIVER
>- VERSION_STRING = 1.0
>- PI_SPECIFICATION_VERSION = 0x0001000A
>- ENTRY_POINT = VariableServiceInitialize
>-
>-#
>-# The following information is for reference only and not required by the build tools.
>-#
>-# VALID_ARCHITECTURES = IA32 X64
>-#
>-
>-
>-[Sources]
>- Reclaim.c
>- Variable.c
>- VariableSmm.c
>- AuthService.c
>- VarCheck.c
>- Variable.h
>- AuthService.h
>-
>-[Packages]
>- MdePkg/MdePkg.dec
>- MdeModulePkg/MdeModulePkg.dec
>- CryptoPkg/CryptoPkg.dec
>- SecurityPkg/SecurityPkg.dec
>-
>-[LibraryClasses]
>- UefiDriverEntryPoint
>- MemoryAllocationLib
>- BaseLib
>- SynchronizationLib
>- UefiLib
>- SmmServicesTableLib
>- BaseMemoryLib
>- DebugLib
>- DxeServicesTableLib
>- BaseCryptLib
>- PlatformSecureLib
>- HobLib
>- PcdLib
>- DevicePathLib
>- SmmMemLib
>-
>-[Protocols]
>- gEfiSmmFirmwareVolumeBlockProtocolGuid ## CONSUMES
>-
>- ## PRODUCES
>- ## UNDEFINED # SmiHandlerRegister
>- gEfiSmmVariableProtocolGuid
>-
>- ## CONSUMES
>- ## NOTIFY
>- gEfiSmmFaultTolerantWriteProtocolGuid
>- gEfiSmmEndOfDxeProtocolGuid ## NOTIFY
>- gEdkiiSmmVarCheckProtocolGuid ## PRODUCES
>-
>-[Guids]
>- ## PRODUCES ## GUID # Variable store header
>- ## CONSUMES ## GUID # Variable store header
>- ## SOMETIMES_CONSUMES ## HOB
>- gEfiAuthenticatedVariableGuid
>-
>- ## SOMETIMES_CONSUMES ## Variable:L"PlatformLang"
>- ## SOMETIMES_PRODUCES ## Variable:L"PlatformLang"
>- ## SOMETIMES_CONSUMES ## Variable:L"Lang"
>- ## SOMETIMES_PRODUCES ## Variable:L"Lang"
>- ## SOMETIMES_CONSUMES ## Variable:L"HwErrRecSupport"
>- ## CONSUMES ## Variable:L"SetupMode"
>- ## PRODUCES ## Variable:L"SetupMode"
>- ## SOMETIMES_CONSUMES ## Variable:L"PK"
>- ## SOMETIMES_CONSUMES ## Variable:L"KEK"
>- ## CONSUMES ## Variable:L"SecureBoot"
>- ## PRODUCES ## Variable:L"SecureBoot"
>- ## CONSUMES ## Variable:L"SignatureSupport"
>- ## PRODUCES ## Variable:L"SignatureSupport"
>- ## PRODUCES ## Variable:L"VendorKeys"
>- gEfiGlobalVariableGuid
>-
>- ## SOMETIMES_CONSUMES ## Variable:L"DB"
>- ## SOMETIMES_CONSUMES ## Variable:L"DBX"
>- gEfiImageSecurityDatabaseGuid
>-
>- ## CONSUMES ## Variable:L"SecureBootEnable"
>- ## PRODUCES ## Variable:L"SecureBootEnable"
>- gEfiSecureBootEnableDisableGuid
>-
>- ## CONSUMES ## Variable:L"CustomMode"
>- ## PRODUCES ## Variable:L"CustomMode"
>- gEfiCustomModeEnableGuid
>-
>- ## CONSUMES ## Variable:L"certdb"
>- ## PRODUCES ## Variable:L"certdb"
>- gEfiCertDbGuid
>-
>- ## CONSUMES ## Variable:L"VendorKeysNv"
>- ## PRODUCES ## Variable:L"VendorKeysNv"
>- gEfiVendorKeysNvGuid
>-
>- gSmmVariableWriteGuid ## PRODUCES ## GUID # Install protocol
>- gEfiCertTypeRsa2048Sha256Guid ## SOMETIMES_CONSUMES ## GUID # Unique ID for the format of the CertData.
>- gEfiCertPkcs7Guid ## SOMETIMES_CONSUMES ## GUID # Unique ID for the format of the CertData.
>- gEfiCertX509Guid ## SOMETIMES_CONSUMES ## GUID # Unique ID for the type of the signature.
>- gEfiSystemNvDataFvGuid ## CONSUMES ## GUID
>- gEfiHardwareErrorVariableGuid ## SOMETIMES_CONSUMES ## Variable:L"HwErrRec####"
>- gEdkiiFaultTolerantWriteGuid ## SOMETIMES_CONSUMES ## HOB
>- gEdkiiVarErrorFlagGuid ## CONSUMES ## GUID
>-
>-[Pcd]
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase ## SOMETIMES_CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase64 ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxAuthVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdVariableStoreSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdHwErrStorageSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxUserNvVariableSpaceSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdBoottimeReservedNvVariableSpaceSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdReclaimVariableSpaceAtEndOfDxe ## CONSUMES
>-
>-[FeaturePcd]
>- gEfiMdeModulePkgTokenSpaceGuid.PcdVariableCollectStatistics ## CONSUMES # statistic the information of variable.
>- gEfiMdePkgTokenSpaceGuid.PcdUefiVariableDefaultLangDeprecate ## CONSUMES # Auto update PlatformLang/Lang
>-
>-[Depex]
>- TRUE
>-
>-[UserExtensions.TianoCore."ExtraFiles"]
>- VariableSmmExtra.uni
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmExtra.uni
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmExtra.uni
>deleted file mode 100644
>index 0ac11fefb2d1de8636623a0f54b0c507b3436162..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 1332
>zcmZ{kS#Q%&5QXO%iT_}Q7eH;o_Jk0kp$4p$I?6)fDazI~QW8f_S_nTL_|9A}NhK87
>z_ug5~oO@=RzkgcRvWVw7zsNq=jV)|xGka{0u*&z%MwVk8+1NcjTk(tR(lVQ1UE=#q
>z#uQu6b{@O7xotU*Z0+`s#IEtp{9R&~Yh?0oZ11^qyCpKRr=UM$ePu7~rM+f%TAkk5
>z3HzkLT(TEJ4u;+%@)usQiRTQ4iqIVbwwUE`+***@7$aA&f3<s_tnj7c6}Hv{5~7v
>zGf-4R8kG0j5i#@g1lAe8jr;cGNs9=JSgD?rT!L2POJ8M6$qBo)Gn1YrzOtu9g?sku
>zQQ42k?#PfgC!=H%YOS1gi6Ul-TvYl<iHx4td2M=l&iV3)OU?DCYcb(1cE`6}z(I)O
>z5cE>5Eoa?&49~;9NLAhX27Bm`IR7H%A*W+qf|h%t#zlTsC?H0=16?&oJ38^!Cs`8~
>zv{iiWN;kQEPJdbtwBKSG!+grj9anFHa?4XI(zh=b!=}UZr1qKjnSJG)pk#!WTKiZN
>z=4-$%c6|qS#TsLeumyx#`-FLpiRd|U%1(2vcY{^9LT#|N{jAf;0jF#HLQTD5WY<J>
>zo!J%k1XN+9UcJjn++|bEKCy~X)e!ZGSXKYQdVxpG_5H;~m2ivLzE?OkdV&@mrb#u=
>ztyyub_0vC3%k8o~spchoH$l5$p>7A1Zgqnp*eR$***@M9aoOUkPk0ZHG8Q0`dgJ}c_~
>YDe>Z`n8ttq-BwJ-)F*RBlw!;0ACN1~00000
>
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.c
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.c
>deleted file mode 100644
>index ffa0b07..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.c
>+++ /dev/null
>@@ -1,1118 +0,0 @@
>-/** @file
>- Implement all four UEFI Runtime Variable services for the nonvolatile
>- and volatile storage space and install variable architecture protocol
>- based on SMM variable module.
>-
>- Caution: This module requires additional review when modified.
>- This driver will have external input - variable data.
>- This external input must be validated carefully to avoid security issue like
>- buffer overflow, integer overflow.
>-
>- RuntimeServiceGetVariable() and RuntimeServiceSetVariable() are external API
>- to receive data buffer. The size should be checked carefully.
>-
>- InitCommunicateBuffer() is really function to check the variable data size.
>-
>-Copyright (c) 2010 - 2015, 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
>-
>-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 <PiDxe.h>
>-#include <Protocol/VariableWrite.h>
>-#include <Protocol/Variable.h>
>-#include <Protocol/SmmCommunication.h>
>-#include <Protocol/SmmVariable.h>
>-#include <Protocol/VariableLock.h>
>-#include <Protocol/VarCheck.h>
>-
>-#include <Library/UefiBootServicesTableLib.h>
>-#include <Library/UefiRuntimeServicesTableLib.h>
>-#include <Library/MemoryAllocationLib.h>
>-#include <Library/UefiDriverEntryPoint.h>
>-#include <Library/UefiRuntimeLib.h>
>-#include <Library/BaseMemoryLib.h>
>-#include <Library/DebugLib.h>
>-#include <Library/PcdLib.h>
>-#include <Library/UefiLib.h>
>-#include <Library/BaseLib.h>
>-
>-#include <Guid/EventGroup.h>
>-#include <Guid/AuthenticatedVariableFormat.h>
>-#include <Guid/SmmVariableCommon.h>
>-
>-EFI_HANDLE mHandle = NULL;
>-EFI_SMM_VARIABLE_PROTOCOL *mSmmVariable = NULL;
>-EFI_EVENT mVirtualAddressChangeEvent = NULL;
>-EFI_SMM_COMMUNICATION_PROTOCOL *mSmmCommunication = NULL;
>-UINT8 *mVariableBuffer = NULL;
>-UINT8 *mVariableBufferPhysical = NULL;
>-UINTN mVariableBufferSize;
>-UINTN mVariableBufferPayloadSize;
>-EFI_LOCK mVariableServicesLock;
>-EDKII_VARIABLE_LOCK_PROTOCOL mVariableLock;
>-EDKII_VAR_CHECK_PROTOCOL mVarCheck;
>-
>-#define MAX_NV_VARIABLE_SIZE (MAX (MAX (PcdGet32 (PcdMaxVariableSize), \
>- PcdGet32 (PcdMaxAuthVariableSize)), \
>- PcdGet32 (PcdMaxHardwareErrorVariableSize)))
>-
>-/**
>- SecureBoot Hook for SetVariable.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>-
>-**/
>-VOID
>-EFIAPI
>-SecureBootHook (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- );
>-
>-/**
>- Acquires lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function that will be removed when
>- EfiAcquireLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiAcquireLock() at boot time, and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to acquire.
>-
>-**/
>-VOID
>-AcquireLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- )
>-{
>- if (!EfiAtRuntime ()) {
>- EfiAcquireLock (Lock);
>- }
>-}
>-
>-/**
>- Releases lock only at boot time. Simply returns at runtime.
>-
>- This is a temperary function which will be removed when
>- EfiReleaseLock() in UefiLib can handle the call in UEFI
>- Runtimer driver in RT phase.
>- It calls EfiReleaseLock() at boot time and simply returns
>- at runtime.
>-
>- @param Lock A pointer to the lock to release.
>-
>-**/
>-VOID
>-ReleaseLockOnlyAtBootTime (
>- IN EFI_LOCK *Lock
>- )
>-{
>- if (!EfiAtRuntime ()) {
>- EfiReleaseLock (Lock);
>- }
>-}
>-
>-/**
>- Initialize the communicate buffer using DataSize and Function.
>-
>- The communicate size is: SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE +
>- DataSize.
>-
>- Caution: This function may receive untrusted input.
>- The data size external input, so this function will validate it carefully to avoid buffer overflow.
>-
>- @param[out] DataPtr Points to the data in the communicate buffer.
>- @param[in] DataSize The data size to send to SMM.
>- @param[in] Function The function number to initialize the communicate header.
>-
>- @retval EFI_INVALID_PARAMETER The data size is too big.
>- @retval EFI_SUCCESS Find the specified variable.
>-
>-**/
>-EFI_STATUS
>-InitCommunicateBuffer (
>- OUT VOID **DataPtr OPTIONAL,
>- IN UINTN DataSize,
>- IN UINTN Function
>- )
>-{
>- EFI_SMM_COMMUNICATE_HEADER *SmmCommunicateHeader;
>- SMM_VARIABLE_COMMUNICATE_HEADER *SmmVariableFunctionHeader;
>-
>-
>- if (DataSize + SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE > mVariableBufferSize) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- SmmCommunicateHeader = (EFI_SMM_COMMUNICATE_HEADER *) mVariableBuffer;
>- CopyGuid (&SmmCommunicateHeader->HeaderGuid, &gEfiSmmVariableProtocolGuid);
>- SmmCommunicateHeader->MessageLength = DataSize + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE;
>-
>- SmmVariableFunctionHeader = (SMM_VARIABLE_COMMUNICATE_HEADER *) SmmCommunicateHeader->Data;
>- SmmVariableFunctionHeader->Function = Function;
>- if (DataPtr != NULL) {
>- *DataPtr = SmmVariableFunctionHeader->Data;
>- }
>-
>- return EFI_SUCCESS;
>-}
>-
>-
>-/**
>- Send the data in communicate buffer to SMM.
>-
>- @param[in] DataSize This size of the function header and the data.
>-
>- @retval EFI_SUCCESS Success is returned from the functin in SMM.
>- @retval Others Failure is returned from the function in SMM.
>-
>-**/
>-EFI_STATUS
>-SendCommunicateBuffer (
>- IN UINTN DataSize
>- )
>-{
>- EFI_STATUS Status;
>- UINTN CommSize;
>- EFI_SMM_COMMUNICATE_HEADER *SmmCommunicateHeader;
>- SMM_VARIABLE_COMMUNICATE_HEADER *SmmVariableFunctionHeader;
>-
>- CommSize = DataSize + SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE;
>- Status = mSmmCommunication->Communicate (mSmmCommunication, mVariableBufferPhysical, &CommSize);
>- ASSERT_EFI_ERROR (Status);
>-
>- SmmCommunicateHeader = (EFI_SMM_COMMUNICATE_HEADER *) mVariableBuffer;
>- SmmVariableFunctionHeader = (SMM_VARIABLE_COMMUNICATE_HEADER *)SmmCommunicateHeader->Data;
>- return SmmVariableFunctionHeader->ReturnStatus;
>-}
>-
>-/**
>- Mark a variable that will become read-only after leaving the DXE phase of execution.
>-
>- @param[in] This The VARIABLE_LOCK_PROTOCOL instance.
>- @param[in] VariableName A pointer to the variable name that will be made read-only subsequently.
>- @param[in] VendorGuid A pointer to the vendor GUID that will be made read-only subsequently.
>-
>- @retval EFI_SUCCESS The variable specified by the VariableName and the VendorGuid was marked
>- as pending to be read-only.
>- @retval EFI_INVALID_PARAMETER VariableName or VendorGuid is NULL.
>- Or VariableName is an empty string.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource to hold the lock request.
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableLockRequestToLock (
>- IN CONST EDKII_VARIABLE_LOCK_PROTOCOL *This,
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid
>- )
>-{
>- EFI_STATUS Status;
>- UINTN VariableNameSize;
>- UINTN PayloadSize;
>- SMM_VARIABLE_COMMUNICATE_LOCK_VARIABLE *VariableToLock;
>-
>- if (VariableName == NULL || VariableName[0] == 0 || VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- VariableNameSize = StrSize (VariableName);
>- VariableToLock = NULL;
>-
>- //
>- // If VariableName exceeds SMM payload limit. Return failure
>- //
>- if (VariableNameSize > mVariableBufferPayloadSize - OFFSET_OF (SMM_VARIABLE_COMMUNICATE_LOCK_VARIABLE, Name)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableServicesLock);
>-
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE + PayloadSize.
>- //
>- PayloadSize = OFFSET_OF (SMM_VARIABLE_COMMUNICATE_LOCK_VARIABLE, Name) + VariableNameSize;
>- Status = InitCommunicateBuffer ((VOID **) &VariableToLock, PayloadSize, SMM_VARIABLE_FUNCTION_LOCK_VARIABLE);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT (VariableToLock != NULL);
>-
>- CopyGuid (&VariableToLock->Guid, VendorGuid);
>- VariableToLock->NameSize = VariableNameSize;
>- CopyMem (VariableToLock->Name, VariableName, VariableToLock->NameSize);
>-
>- //
>- // Send data to SMM.
>- //
>- Status = SendCommunicateBuffer (PayloadSize);
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableServicesLock);
>- return Status;
>-}
>-
>-/**
>- Register SetVariable check handler.
>-
>- @param[in] Handler Pointer to check handler.
>-
>- @retval EFI_SUCCESS The SetVariable check handler was registered successfully.
>- @retval EFI_INVALID_PARAMETER Handler is NULL.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource for the SetVariable check handler register request.
>- @retval EFI_UNSUPPORTED This interface is not implemented.
>- For example, it is unsupported in VarCheck protocol if both VarCheck and SmmVarCheck protocols are present.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckRegisterSetVariableCheckHandler (
>- IN VAR_CHECK_SET_VARIABLE_CHECK_HANDLER Handler
>- )
>-{
>- return EFI_UNSUPPORTED;
>-}
>-
>-/**
>- Variable property set.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[in] VariableProperty Pointer to the input variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was set successfully.
>- @retval EFI_INVALID_PARAMETER Name, Guid or VariableProperty is NULL, or Name is an empty string,
>- or the fields of VariableProperty are not valid.
>- @retval EFI_ACCESS_DENIED EFI_END_OF_DXE_EVENT_GROUP_GUID or EFI_EVENT_GROUP_READY_TO_BOOT has
>- already been signaled.
>- @retval EFI_OUT_OF_RESOURCES There is not enough resource for the variable property set request.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckVariablePropertySet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- IN VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- )
>-{
>- EFI_STATUS Status;
>- UINTN VariableNameSize;
>- UINTN PayloadSize;
>- SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY *CommVariableProperty;
>-
>- if (Name == NULL || Name[0] == 0 || Guid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (VariableProperty == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (VariableProperty->Revision != VAR_CHECK_VARIABLE_PROPERTY_REVISION) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- VariableNameSize = StrSize (Name);
>- CommVariableProperty = NULL;
>-
>- //
>- // If VariableName exceeds SMM payload limit. Return failure
>- //
>- if (VariableNameSize > mVariableBufferPayloadSize - OFFSET_OF
>(SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime (&mVariableServicesLock);
>-
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE + PayloadSize.
>- //
>- PayloadSize = OFFSET_OF (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name) + VariableNameSize;
>- Status = InitCommunicateBuffer ((VOID **) &CommVariableProperty, PayloadSize,
>SMM_VARIABLE_FUNCTION_VAR_CHECK_VARIABLE_PROPERTY_SET);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT (CommVariableProperty != NULL);
>-
>- CopyGuid (&CommVariableProperty->Guid, Guid);
>- CopyMem (&CommVariableProperty->VariableProperty, VariableProperty, sizeof (*VariableProperty));
>- CommVariableProperty->NameSize = VariableNameSize;
>- CopyMem (CommVariableProperty->Name, Name, CommVariableProperty->NameSize);
>-
>- //
>- // Send data to SMM.
>- //
>- Status = SendCommunicateBuffer (PayloadSize);
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableServicesLock);
>- return Status;
>-}
>-
>-/**
>- Variable property get.
>-
>- @param[in] Name Pointer to the variable name.
>- @param[in] Guid Pointer to the vendor GUID.
>- @param[out] VariableProperty Pointer to the output variable property.
>-
>- @retval EFI_SUCCESS The property of variable specified by the Name and Guid was got successfully.
>- @retval EFI_INVALID_PARAMETER Name, Guid or VariableProperty is NULL, or Name is an empty string.
>- @retval EFI_NOT_FOUND The property of variable specified by the Name and Guid was not found.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VarCheckVariablePropertyGet (
>- IN CHAR16 *Name,
>- IN EFI_GUID *Guid,
>- OUT VAR_CHECK_VARIABLE_PROPERTY *VariableProperty
>- )
>-{
>- EFI_STATUS Status;
>- UINTN VariableNameSize;
>- UINTN PayloadSize;
>- SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY *CommVariableProperty;
>-
>- if (Name == NULL || Name[0] == 0 || Guid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (VariableProperty == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- VariableNameSize = StrSize (Name);
>- CommVariableProperty = NULL;
>-
>- //
>- // If VariableName exceeds SMM payload limit. Return failure
>- //
>- if (VariableNameSize > mVariableBufferPayloadSize - OFFSET_OF
>(SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime (&mVariableServicesLock);
>-
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE + PayloadSize.
>- //
>- PayloadSize = OFFSET_OF (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name) + VariableNameSize;
>- Status = InitCommunicateBuffer ((VOID **) &CommVariableProperty, PayloadSize,
>SMM_VARIABLE_FUNCTION_VAR_CHECK_VARIABLE_PROPERTY_GET);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT (CommVariableProperty != NULL);
>-
>- CopyGuid (&CommVariableProperty->Guid, Guid);
>- CommVariableProperty->NameSize = VariableNameSize;
>- CopyMem (CommVariableProperty->Name, Name, CommVariableProperty->NameSize);
>-
>- //
>- // Send data to SMM.
>- //
>- Status = SendCommunicateBuffer (PayloadSize);
>- if (Status == EFI_SUCCESS) {
>- CopyMem (VariableProperty, &CommVariableProperty->VariableProperty, sizeof (*VariableProperty));
>- }
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableServicesLock);
>- return Status;
>-}
>-
>-/**
>- This code finds variable in storage blocks (Volatile or Non-Volatile).
>-
>- Caution: This function may receive untrusted input.
>- The data size is external input, so this function will validate it carefully to avoid buffer overflow.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[out] Attributes Attribute value of the variable found.
>- @param[in, out] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[out] Data Data pointer.
>-
>- @retval EFI_INVALID_PARAMETER Invalid parameter.
>- @retval EFI_SUCCESS Find the specified variable.
>- @retval EFI_NOT_FOUND Not found.
>- @retval EFI_BUFFER_TO_SMALL DataSize is too small for the result.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-RuntimeServiceGetVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- OUT UINT32 *Attributes OPTIONAL,
>- IN OUT UINTN *DataSize,
>- OUT VOID *Data
>- )
>-{
>- EFI_STATUS Status;
>- UINTN PayloadSize;
>- SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE *SmmVariableHeader;
>- UINTN TempDataSize;
>- UINTN VariableNameSize;
>-
>- if (VariableName == NULL || VendorGuid == NULL || DataSize == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- TempDataSize = *DataSize;
>- VariableNameSize = StrSize (VariableName);
>- SmmVariableHeader = NULL;
>-
>- //
>- // If VariableName exceeds SMM payload limit. Return failure
>- //
>- if (VariableNameSize > mVariableBufferPayloadSize - OFFSET_OF (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableServicesLock);
>-
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE + PayloadSize.
>- //
>- if (TempDataSize > mVariableBufferPayloadSize - OFFSET_OF (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name) -
>VariableNameSize) {
>- //
>- // If output data buffer exceed SMM payload limit. Trim output buffer to SMM payload size
>- //
>- TempDataSize = mVariableBufferPayloadSize - OFFSET_OF (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name) -
>VariableNameSize;
>- }
>- PayloadSize = OFFSET_OF (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name) + VariableNameSize + TempDataSize;
>-
>- Status = InitCommunicateBuffer ((VOID **)&SmmVariableHeader, PayloadSize, SMM_VARIABLE_FUNCTION_GET_VARIABLE);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT (SmmVariableHeader != NULL);
>-
>- CopyGuid (&SmmVariableHeader->Guid, VendorGuid);
>- SmmVariableHeader->DataSize = TempDataSize;
>- SmmVariableHeader->NameSize = VariableNameSize;
>- if (Attributes == NULL) {
>- SmmVariableHeader->Attributes = 0;
>- } else {
>- SmmVariableHeader->Attributes = *Attributes;
>- }
>- CopyMem (SmmVariableHeader->Name, VariableName, SmmVariableHeader->NameSize);
>-
>- //
>- // Send data to SMM.
>- //
>- Status = SendCommunicateBuffer (PayloadSize);
>-
>- //
>- // Get data from SMM.
>- //
>- if (Status == EFI_SUCCESS || Status == EFI_BUFFER_TOO_SMALL) {
>- //
>- // SMM CommBuffer DataSize can be a trimed value
>- // Only update DataSize when needed
>- //
>- *DataSize = SmmVariableHeader->DataSize;
>- }
>- if (Attributes != NULL) {
>- *Attributes = SmmVariableHeader->Attributes;
>- }
>-
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- if (Data != NULL) {
>- CopyMem (Data, (UINT8 *)SmmVariableHeader->Name + SmmVariableHeader->NameSize, SmmVariableHeader->DataSize);
>- } else {
>- Status = EFI_INVALID_PARAMETER;
>- }
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableServicesLock);
>- return Status;
>-}
>-
>-
>-/**
>- This code Finds the Next available variable.
>-
>- @param[in, out] VariableNameSize Size of the variable name.
>- @param[in, out] VariableName Pointer to variable name.
>- @param[in, out] VendorGuid Variable Vendor Guid.
>-
>- @retval EFI_INVALID_PARAMETER Invalid parameter.
>- @retval EFI_SUCCESS Find the specified variable.
>- @retval EFI_NOT_FOUND Not found.
>- @retval EFI_BUFFER_TO_SMALL DataSize is too small for the result.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-RuntimeServiceGetNextVariableName (
>- IN OUT UINTN *VariableNameSize,
>- IN OUT CHAR16 *VariableName,
>- IN OUT EFI_GUID *VendorGuid
>- )
>-{
>- EFI_STATUS Status;
>- UINTN PayloadSize;
>- SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME *SmmGetNextVariableName;
>- UINTN OutVariableNameSize;
>- UINTN InVariableNameSize;
>-
>- if (VariableNameSize == NULL || VariableName == NULL || VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- OutVariableNameSize = *VariableNameSize;
>- InVariableNameSize = StrSize (VariableName);
>- SmmGetNextVariableName = NULL;
>-
>- //
>- // If input string exceeds SMM payload limit. Return failure
>- //
>- if (InVariableNameSize > mVariableBufferPayloadSize - OFFSET_OF
>(SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME, Name)) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableServicesLock);
>-
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE + PayloadSize.
>- //
>- if (OutVariableNameSize > mVariableBufferPayloadSize - OFFSET_OF
>(SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME, Name)) {
>- //
>- // If output buffer exceed SMM payload limit. Trim output buffer to SMM payload size
>- //
>- OutVariableNameSize = mVariableBufferPayloadSize - OFFSET_OF
>(SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME, Name);
>- }
>- //
>- // Payload should be Guid + NameSize + MAX of Input & Output buffer
>- //
>- PayloadSize = OFFSET_OF (SMM_VARIABLE_COMMUNICATE_GET_NEXT_VARIABLE_NAME, Name) + MAX (OutVariableNameSize,
>InVariableNameSize);
>-
>- Status = InitCommunicateBuffer ((VOID **)&SmmGetNextVariableName, PayloadSize,
>SMM_VARIABLE_FUNCTION_GET_NEXT_VARIABLE_NAME);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT (SmmGetNextVariableName != NULL);
>-
>- //
>- // SMM comm buffer->NameSize is buffer size for return string
>- //
>- SmmGetNextVariableName->NameSize = OutVariableNameSize;
>-
>- CopyGuid (&SmmGetNextVariableName->Guid, VendorGuid);
>- //
>- // Copy whole string
>- //
>- CopyMem (SmmGetNextVariableName->Name, VariableName, InVariableNameSize);
>- if (OutVariableNameSize > InVariableNameSize) {
>- ZeroMem ((UINT8 *) SmmGetNextVariableName->Name + InVariableNameSize, OutVariableNameSize - InVariableNameSize);
>- }
>-
>- //
>- // Send data to SMM
>- //
>- Status = SendCommunicateBuffer (PayloadSize);
>-
>- //
>- // Get data from SMM.
>- //
>- if (Status == EFI_SUCCESS || Status == EFI_BUFFER_TOO_SMALL) {
>- //
>- // SMM CommBuffer NameSize can be a trimed value
>- // Only update VariableNameSize when needed
>- //
>- *VariableNameSize = SmmGetNextVariableName->NameSize;
>- }
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- CopyGuid (VendorGuid, &SmmGetNextVariableName->Guid);
>- CopyMem (VariableName, SmmGetNextVariableName->Name, SmmGetNextVariableName->NameSize);
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableServicesLock);
>- return Status;
>-}
>-
>-/**
>- This code sets variable in storage blocks (Volatile or Non-Volatile).
>-
>- Caution: This function may receive untrusted input.
>- The data size and data are external input, so this function will validate it carefully to avoid buffer overflow.
>-
>- @param[in] VariableName Name of Variable to be found.
>- @param[in] VendorGuid Variable vendor GUID.
>- @param[in] Attributes Attribute value of the variable found
>- @param[in] DataSize Size of Data found. If size is less than the
>- data, this value contains the required size.
>- @param[in] Data Data pointer.
>-
>- @retval EFI_INVALID_PARAMETER Invalid parameter.
>- @retval EFI_SUCCESS Set successfully.
>- @retval EFI_OUT_OF_RESOURCES Resource not enough to set variable.
>- @retval EFI_NOT_FOUND Not found.
>- @retval EFI_WRITE_PROTECTED Variable is read-only.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-RuntimeServiceSetVariable (
>- IN CHAR16 *VariableName,
>- IN EFI_GUID *VendorGuid,
>- IN UINT32 Attributes,
>- IN UINTN DataSize,
>- IN VOID *Data
>- )
>-{
>- EFI_STATUS Status;
>- UINTN PayloadSize;
>- SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE *SmmVariableHeader;
>- UINTN VariableNameSize;
>-
>- //
>- // Check input parameters.
>- //
>- if (VariableName == NULL || VariableName[0] == 0 || VendorGuid == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- if (DataSize != 0 && Data == NULL) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- VariableNameSize = StrSize (VariableName);
>- SmmVariableHeader = NULL;
>-
>- //
>- // If VariableName or DataSize exceeds SMM payload limit. Return failure
>- //
>- if ((VariableNameSize > mVariableBufferPayloadSize - OFFSET_OF (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name))
>||
>- (DataSize > mVariableBufferPayloadSize - OFFSET_OF (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name) -
>VariableNameSize)){
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableServicesLock);
>-
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE + PayloadSize.
>- //
>- PayloadSize = OFFSET_OF (SMM_VARIABLE_COMMUNICATE_ACCESS_VARIABLE, Name) + VariableNameSize + DataSize;
>- Status = InitCommunicateBuffer ((VOID **)&SmmVariableHeader, PayloadSize, SMM_VARIABLE_FUNCTION_SET_VARIABLE);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT (SmmVariableHeader != NULL);
>-
>- CopyGuid ((EFI_GUID *) &SmmVariableHeader->Guid, VendorGuid);
>- SmmVariableHeader->DataSize = DataSize;
>- SmmVariableHeader->NameSize = VariableNameSize;
>- SmmVariableHeader->Attributes = Attributes;
>- CopyMem (SmmVariableHeader->Name, VariableName, SmmVariableHeader->NameSize);
>- CopyMem ((UINT8 *) SmmVariableHeader->Name + SmmVariableHeader->NameSize, Data, DataSize);
>-
>- //
>- // Send data to SMM.
>- //
>- Status = SendCommunicateBuffer (PayloadSize);
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableServicesLock);
>-
>- if (!EfiAtRuntime ()) {
>- if (!EFI_ERROR (Status)) {
>- SecureBootHook (
>- VariableName,
>- VendorGuid
>- );
>- }
>- }
>- return Status;
>-}
>-
>-
>-/**
>- This code returns information about the EFI variables.
>-
>- @param[in] Attributes Attributes bitmask to specify the type of variables
>- on which to return information.
>- @param[out] MaximumVariableStorageSize Pointer to the maximum size of the storage space available
>- for the EFI variables associated with the attributes specified.
>- @param[out] RemainingVariableStorageSize Pointer to the remaining size of the storage space available
>- for EFI variables associated with the attributes specified.
>- @param[out] MaximumVariableSize Pointer to the maximum size of an individual EFI variables
>- associated with the attributes specified.
>-
>- @retval EFI_INVALID_PARAMETER An invalid combination of attribute bits was supplied.
>- @retval EFI_SUCCESS Query successfully.
>- @retval EFI_UNSUPPORTED The attribute is not supported on this platform.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-RuntimeServiceQueryVariableInfo (
>- IN UINT32 Attributes,
>- OUT UINT64 *MaximumVariableStorageSize,
>- OUT UINT64 *RemainingVariableStorageSize,
>- OUT UINT64 *MaximumVariableSize
>- )
>-{
>- EFI_STATUS Status;
>- UINTN PayloadSize;
>- SMM_VARIABLE_COMMUNICATE_QUERY_VARIABLE_INFO *SmmQueryVariableInfo;
>-
>- SmmQueryVariableInfo = NULL;
>-
>- if(MaximumVariableStorageSize == NULL || RemainingVariableStorageSize == NULL || MaximumVariableSize == NULL || Attributes
>== 0) {
>- return EFI_INVALID_PARAMETER;
>- }
>-
>- AcquireLockOnlyAtBootTime(&mVariableServicesLock);
>-
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE + PayloadSize;
>- //
>- PayloadSize = sizeof (SMM_VARIABLE_COMMUNICATE_QUERY_VARIABLE_INFO);
>- Status = InitCommunicateBuffer ((VOID **)&SmmQueryVariableInfo, PayloadSize,
>SMM_VARIABLE_FUNCTION_QUERY_VARIABLE_INFO);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>- ASSERT (SmmQueryVariableInfo != NULL);
>-
>- SmmQueryVariableInfo->Attributes = Attributes;
>-
>- //
>- // Send data to SMM.
>- //
>- Status = SendCommunicateBuffer (PayloadSize);
>- if (EFI_ERROR (Status)) {
>- goto Done;
>- }
>-
>- //
>- // Get data from SMM.
>- //
>- *MaximumVariableSize = SmmQueryVariableInfo->MaximumVariableSize;
>- *MaximumVariableStorageSize = SmmQueryVariableInfo->MaximumVariableStorageSize;
>- *RemainingVariableStorageSize = SmmQueryVariableInfo->RemainingVariableStorageSize;
>-
>-Done:
>- ReleaseLockOnlyAtBootTime (&mVariableServicesLock);
>- return Status;
>-}
>-
>-
>-/**
>- Exit Boot Services Event notification handler.
>-
>- Notify SMM variable driver about the event.
>-
>- @param[in] Event Event whose notification function is being invoked.
>- @param[in] Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-OnExitBootServices (
>- IN EFI_EVENT Event,
>- IN VOID *Context
>- )
>-{
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE.
>- //
>- InitCommunicateBuffer (NULL, 0, SMM_VARIABLE_FUNCTION_EXIT_BOOT_SERVICE);
>-
>- //
>- // Send data to SMM.
>- //
>- SendCommunicateBuffer (0);
>-}
>-
>-
>-/**
>- On Ready To Boot Services Event notification handler.
>-
>- Notify SMM variable driver about the event.
>-
>- @param[in] Event Event whose notification function is being invoked
>- @param[in] Context Pointer to the notification function's context
>-
>-**/
>-VOID
>-EFIAPI
>-OnReadyToBoot (
>- IN EFI_EVENT Event,
>- IN VOID *Context
>- )
>-{
>- //
>- // Init the communicate buffer. The buffer data size is:
>- // SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE.
>- //
>- InitCommunicateBuffer (NULL, 0, SMM_VARIABLE_FUNCTION_READY_TO_BOOT);
>-
>- //
>- // Send data to SMM.
>- //
>- SendCommunicateBuffer (0);
>-}
>-
>-
>-/**
>- Notification function of EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE.
>-
>- This is a notification function registered on EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE event.
>- It convers pointer to new virtual address.
>-
>- @param[in] Event Event whose notification function is being invoked.
>- @param[in] Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-VariableAddressChangeEvent (
>- IN EFI_EVENT Event,
>- IN VOID *Context
>- )
>-{
>- EfiConvertPointer (0x0, (VOID **) &mVariableBuffer);
>- EfiConvertPointer (0x0, (VOID **) &mSmmCommunication);
>-}
>-
>-
>-/**
>- Initialize variable service and install Variable Architectural protocol.
>-
>- @param[in] Event Event whose notification function is being invoked.
>- @param[in] Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-SmmVariableReady (
>- IN EFI_EVENT Event,
>- IN VOID *Context
>- )
>-{
>- EFI_STATUS Status;
>-
>- Status = gBS->LocateProtocol (&gEfiSmmVariableProtocolGuid, NULL, (VOID **)&mSmmVariable);
>- if (EFI_ERROR (Status)) {
>- return;
>- }
>-
>- Status = gBS->LocateProtocol (&gEfiSmmCommunicationProtocolGuid, NULL, (VOID **) &mSmmCommunication);
>- ASSERT_EFI_ERROR (Status);
>-
>- //
>- // Allocate memory for variable communicate buffer.
>- //
>- mVariableBufferPayloadSize = MAX_NV_VARIABLE_SIZE +
>- OFFSET_OF (SMM_VARIABLE_COMMUNICATE_VAR_CHECK_VARIABLE_PROPERTY, Name) - sizeof
>(VARIABLE_HEADER);
>- mVariableBufferSize = SMM_COMMUNICATE_HEADER_SIZE + SMM_VARIABLE_COMMUNICATE_HEADER_SIZE +
>mVariableBufferPayloadSize;
>- mVariableBuffer = AllocateRuntimePool (mVariableBufferSize);
>- ASSERT (mVariableBuffer != NULL);
>-
>- //
>- // Save the buffer physical address used for SMM conmunication.
>- //
>- mVariableBufferPhysical = mVariableBuffer;
>-
>- gRT->GetVariable = RuntimeServiceGetVariable;
>- gRT->GetNextVariableName = RuntimeServiceGetNextVariableName;
>- gRT->SetVariable = RuntimeServiceSetVariable;
>- gRT->QueryVariableInfo = RuntimeServiceQueryVariableInfo;
>-
>- //
>- // Install the Variable Architectural Protocol on a new handle.
>- //
>- Status = gBS->InstallProtocolInterface (
>- &mHandle,
>- &gEfiVariableArchProtocolGuid,
>- EFI_NATIVE_INTERFACE,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- mVariableLock.RequestToLock = VariableLockRequestToLock;
>- Status = gBS->InstallMultipleProtocolInterfaces (
>- &mHandle,
>- &gEdkiiVariableLockProtocolGuid,
>- &mVariableLock,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-
>- mVarCheck.RegisterSetVariableCheckHandler = VarCheckRegisterSetVariableCheckHandler;
>- mVarCheck.VariablePropertySet = VarCheckVariablePropertySet;
>- mVarCheck.VariablePropertyGet = VarCheckVariablePropertyGet;
>- Status = gBS->InstallMultipleProtocolInterfaces (
>- &mHandle,
>- &gEdkiiVarCheckProtocolGuid,
>- &mVarCheck,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-}
>-
>-
>-/**
>- SMM Non-Volatile variable write service is ready notify event handler.
>-
>- @param[in] Event Event whose notification function is being invoked.
>- @param[in] Context Pointer to the notification function's context.
>-
>-**/
>-VOID
>-EFIAPI
>-SmmVariableWriteReady (
>- IN EFI_EVENT Event,
>- IN VOID *Context
>- )
>-{
>- EFI_STATUS Status;
>- VOID *ProtocolOps;
>-
>- //
>- // Check whether the protocol is installed or not.
>- //
>- Status = gBS->LocateProtocol (&gSmmVariableWriteGuid, NULL, (VOID **) &ProtocolOps);
>- if (EFI_ERROR (Status)) {
>- return;
>- }
>-
>- Status = gBS->InstallProtocolInterface (
>- &mHandle,
>- &gEfiVariableWriteArchProtocolGuid,
>- EFI_NATIVE_INTERFACE,
>- NULL
>- );
>- ASSERT_EFI_ERROR (Status);
>-}
>-
>-
>-/**
>- Variable Driver main entry point. The Variable driver places the 4 EFI
>- runtime services in the EFI System Table and installs arch protocols
>- for variable read and write services being available. It also registers
>- a notification function for an EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE event.
>-
>- @param[in] ImageHandle The firmware allocated handle for the EFI image.
>- @param[in] SystemTable A pointer to the EFI System Table.
>-
>- @retval EFI_SUCCESS Variable service successfully initialized.
>-
>-**/
>-EFI_STATUS
>-EFIAPI
>-VariableSmmRuntimeInitialize (
>- IN EFI_HANDLE ImageHandle,
>- IN EFI_SYSTEM_TABLE *SystemTable
>- )
>-{
>- VOID *SmmVariableRegistration;
>- VOID *SmmVariableWriteRegistration;
>- EFI_EVENT OnReadyToBootEvent;
>- EFI_EVENT ExitBootServiceEvent;
>- EFI_EVENT LegacyBootEvent;
>-
>- EfiInitializeLock (&mVariableServicesLock, TPL_NOTIFY);
>-
>- //
>- // Smm variable service is ready
>- //
>- EfiCreateProtocolNotifyEvent (
>- &gEfiSmmVariableProtocolGuid,
>- TPL_CALLBACK,
>- SmmVariableReady,
>- NULL,
>- &SmmVariableRegistration
>- );
>-
>- //
>- // Smm Non-Volatile variable write service is ready
>- //
>- EfiCreateProtocolNotifyEvent (
>- &gSmmVariableWriteGuid,
>- TPL_CALLBACK,
>- SmmVariableWriteReady,
>- NULL,
>- &SmmVariableWriteRegistration
>- );
>-
>- //
>- // Register the event to reclaim variable for OS usage.
>- //
>- EfiCreateEventReadyToBootEx (
>- TPL_NOTIFY,
>- OnReadyToBoot,
>- NULL,
>- &OnReadyToBootEvent
>- );
>-
>- //
>- // Register the event to inform SMM variable that it is at runtime.
>- //
>- gBS->CreateEventEx (
>- EVT_NOTIFY_SIGNAL,
>- TPL_NOTIFY,
>- OnExitBootServices,
>- NULL,
>- &gEfiEventExitBootServicesGuid,
>- &ExitBootServiceEvent
>- );
>-
>- //
>- // Register the event to inform SMM variable that it is at runtime for legacy boot.
>- // Reuse OnExitBootServices() here.
>- //
>- EfiCreateEventLegacyBootEx(
>- TPL_NOTIFY,
>- OnExitBootServices,
>- NULL,
>- &LegacyBootEvent
>- );
>-
>- //
>- // Register the event to convert the pointer for runtime.
>- //
>- gBS->CreateEventEx (
>- EVT_NOTIFY_SIGNAL,
>- TPL_NOTIFY,
>- VariableAddressChangeEvent,
>- NULL,
>- &gEfiEventVirtualAddressChangeGuid,
>- &mVirtualAddressChangeEvent
>- );
>-
>- return EFI_SUCCESS;
>-}
>-
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.inf
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.inf
>deleted file mode 100644
>index db6a4de..0000000
>--- a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxe.inf
>+++ /dev/null
>@@ -1,102 +0,0 @@
>-## @file
>-# Runtime DXE part corresponding to SMM authenticated variable module
>-#
>-# This module installs variable arch protocol and variable write arch protocol to provide
>-# variable service. This module need work together with SMM authenticated variable module.
>-#
>-# Caution: This module requires additional review when modified.
>-# This driver will have external input - variable data.
>-# This external input must be validated carefully to avoid security issues such as
>-# buffer overflow or integer overflow.
>-# The whole SMM authentication variable design relies on the integrity of flash part and SMM.
>-# which is assumed to be protected by platform. All variable code and metadata in flash/SMM Memory
>-# may not be modified without authorization. If platform fails to protect these resources,
>-# the authentication service provided in this driver will be broken, and the behavior is undefined.
>-#
>-# Copyright (c) 2010 - 2015, 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
>-# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
>-# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
>-#
>-##
>-
>-[Defines]
>- INF_VERSION = 0x00010005
>- BASE_NAME = VariableAuthSmmRuntimeDxe
>- MODULE_UNI_FILE = VariableAuthSmmRuntimeDxe.uni
>- FILE_GUID = 067E2381-7234-4798-B49C-D5FECBFF6D07
>- MODULE_TYPE = DXE_RUNTIME_DRIVER
>- VERSION_STRING = 1.0
>- ENTRY_POINT = VariableSmmRuntimeInitialize
>-
>-#
>-# The following information is for reference only and not required by the build tools.
>-#
>-# VALID_ARCHITECTURES = IA32 X64
>-#
>-# VIRTUAL_ADDRESS_MAP_CALLBACK = VariableAddressChangeEvent
>-#
>-
>-[Sources]
>- VariableSmmRuntimeDxe.c
>- Measurement.c
>-
>-[Packages]
>- MdePkg/MdePkg.dec
>- MdeModulePkg/MdeModulePkg.dec
>- SecurityPkg/SecurityPkg.dec
>-
>-[LibraryClasses]
>- MemoryAllocationLib
>- BaseLib
>- UefiBootServicesTableLib
>- DebugLib
>- UefiRuntimeLib
>- DxeServicesTableLib
>- UefiDriverEntryPoint
>- PcdLib
>- TpmMeasurementLib
>-
>-[Protocols]
>- gEfiVariableWriteArchProtocolGuid ## PRODUCES
>- gEfiVariableArchProtocolGuid ## PRODUCES
>- gEfiSmmCommunicationProtocolGuid ## CONSUMES
>- gEdkiiVariableLockProtocolGuid ## PRODUCES
>-
>- ## CONSUMES
>- ## NOTIFY
>- ## UNDEFINED # Used to do smm communication
>- gEfiSmmVariableProtocolGuid
>- gEdkiiVarCheckProtocolGuid ## PRODUCES
>-
>-[Guids]
>- gEfiEventVirtualAddressChangeGuid ## CONSUMES ## Event
>- gEfiEventExitBootServicesGuid ## CONSUMES ## Event
>-
>- ## CONSUMES ## UNDEFINED # Locate protocol
>- ## CONSUMES ## UNDEFINED # Protocol notify
>- gSmmVariableWriteGuid
>-
>-
>- ## SOMETIMES_CONSUMES ## Variable:L"PK"
>- ## SOMETIMES_CONSUMES ## Variable:L"KEK"
>- ## SOMETIMES_CONSUMES ## Variable:L"SecureBoot"
>- gEfiGlobalVariableGuid
>-
>- ## SOMETIMES_CONSUMES ## Variable:L"DB"
>- ## SOMETIMES_CONSUMES ## Variable:L"DBX"
>- gEfiImageSecurityDatabaseGuid
>-
>-[Pcd]
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxAuthVariableSize ## CONSUMES
>- gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize ## CONSUMES
>-
>-[Depex]
>- gEfiSmmCommunicationProtocolGuid
>-
>-[UserExtensions.TianoCore."ExtraFiles"]
>- VariableSmmRuntimeDxeExtra.uni
>diff --git a/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxeExtra.uni
>b/SecurityPkg/VariableAuthenticated/RuntimeDxe/VariableSmmRuntimeDxeExtra.uni
>deleted file mode 100644
>index 86cbfbd1ce2029b96325d17eb822180ff7a34cb4..0000000000000000000000000000000000000000
>GIT binary patch
>literal 0
>HcmV?d00001
>
>literal 1390
>zcmZXUNpBND5QXcE#D8cx7eI*(gcCxD7!NQ?yvPfIQ{*LaEP2z|2{***@V%NXb~Kt^
>zs;ghUepTI%|7upV!2gCX*cZF8na%CmUfK(+***@Y<SRW}@OACZmbS&dz`J1&
>zw81WHWn(<&*#BagVC&(f{Y#tLhWU_@>|gN}!nL<~yu44>*S7P$***@h18*elRq)4#X3
>z_RdZjofNYVcFZ`=Fz1XFA+fc$L+7f9RaVYmC=c;UvBfNb%Z5L(d*@!YPgduop9?ig
>zc6}Jl{5)&?SD+-EYynDszAYZoWC-Um9t)UgZI@{gu!xo7N!>YUCB8J*ZYeotv~*_D
>***@2hlEzv%>l{VQl#f}VkCa$Z2j#vxIczY$*yB=i{o`7U
>zX`i2V1_vREL#mfzZJ6uSBY3KY^***@o%#lQnjvw1z~_+***@5O{#B-c7;T^E
>zsyf<|iH~***@Lid@=sjpDr^$+Sv$~vgJlHs2{pGLy$***@Lf2l~{epm#X4%***@3d#u
>zWFDhrKuh&~tTFX9U=+E&18dPo*aNl{q0~O6o+CVZj@)LXI#yeu7p_n%^mU(WcKn3X
>zCF??Md&FRucy*mw3wsQzFxnoy%S_y5Q_McT@=?^(>l?m`{+***@s6*1TSi?S%`DI)t-
>z;FRbwT6Cx;#cXgNbKUYj_-j;iyKF~Az32_miz4l=GIcwkbc+*Qf!zjm0Dgo|3zkhr
>z!***@QVjtJ$Bx|n*cDE}w;i=U!NO;***@53mqNxsb`wm}2v1#%JI6Qw5E5#Xv{2zxt
>B*v9|>
>
>--
>1.9.5.msysgit.0