TianoCore EDK2 master
Loading...
Searching...
No Matches
VariableSmm.c File Reference
#include <Protocol/SmmVariable.h>
#include <Protocol/SmmFirmwareVolumeBlock.h>
#include <Protocol/SmmFaultTolerantWrite.h>
#include <Protocol/MmEndOfDxe.h>
#include <Protocol/SmmVarCheck.h>
#include <Library/MmServicesTableLib.h>
#include <Library/VariablePolicyLib.h>
#include <Guid/SmmVariableCommon.h>
#include "Variable.h"
#include "VariableParsing.h"
#include "VariableRuntimeCache.h"

Go to the source code of this file.

Functions

VOID EFIAPI SecureBootHook (IN CHAR16 *VariableName, IN EFI_GUID *VendorGuid)
 
EFI_STATUS EFIAPI SmmVariableSetVariable (IN CHAR16 *VariableName, IN EFI_GUID *VendorGuid, IN UINT32 Attributes, IN UINTN DataSize, IN VOID *Data)
 
BOOLEAN AtRuntime (VOID)
 
EFI_LOCKInitializeLock (IN OUT EFI_LOCK *Lock, IN EFI_TPL Priority)
 
VOID AcquireLockOnlyAtBootTime (IN EFI_LOCK *Lock)
 
VOID ReleaseLockOnlyAtBootTime (IN EFI_LOCK *Lock)
 
EFI_STATUS GetFtwProtocol (OUT VOID **FtwProtocol)
 
EFI_STATUS GetFvbByHandle (IN EFI_HANDLE FvBlockHandle, OUT EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL **FvBlock)
 
EFI_STATUS GetFvbCountAndBuffer (OUT UINTN *NumberHandles, OUT EFI_HANDLE **Buffer)
 
EFI_STATUS SmmVariableGetStatistics (IN OUT VARIABLE_INFO_ENTRY *InfoEntry, IN OUT UINTN *InfoSize)
 
EFI_STATUS EFIAPI SmmVariableHandler (IN EFI_HANDLE DispatchHandle, IN CONST VOID *RegisterContext, IN OUT VOID *CommBuffer, IN OUT UINTN *CommBufferSize)
 
EFI_STATUS EFIAPI SmmEndOfDxeCallback (IN CONST EFI_GUID *Protocol, IN VOID *Interface, IN EFI_HANDLE Handle)
 
VOID VariableWriteServiceInitializeSmm (VOID)
 
EFI_STATUS EFIAPI SmmFtwNotificationEvent (IN CONST EFI_GUID *Protocol, IN VOID *Interface, IN EFI_HANDLE Handle)
 
EFI_STATUS EFIAPI MmVariableServiceInitialize (VOID)
 

Variables

VARIABLE_STORE_HEADERmNvVariableCache
 
BOOLEAN mAtRuntime = FALSE
 
UINT8 * mVariableBufferPayload = NULL
 
UINTN mVariableBufferPayloadSize
 
EFI_SMM_VARIABLE_PROTOCOL gSmmVariable
 
EDKII_SMM_VAR_CHECK_PROTOCOL mSmmVarCheck
 

Detailed Description

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 - 2024, Intel Corporation. All rights reserved.
Copyright (c) 2018, Linaro, Ltd. All rights reserved.
SPDX-License-Identifier: BSD-2-Clause-Patent

Definition in file VariableSmm.c.

Function Documentation

◆ AcquireLockOnlyAtBootTime()

VOID AcquireLockOnlyAtBootTime ( IN EFI_LOCK 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.

Parameters
LockA pointer to the lock to acquire.

Definition at line 169 of file VariableSmm.c.

◆ AtRuntime()

BOOLEAN AtRuntime ( VOID  )

Return TRUE if ExitBootServices () has been called.

Return values
TRUEIf ExitBootServices () has been called.

Definition at line 124 of file VariableSmm.c.

◆ GetFtwProtocol()

EFI_STATUS GetFtwProtocol ( OUT VOID **  FtwProtocol)

Retrieve the SMM Fault Tolerent Write protocol interface.

Parameters
[out]FtwProtocolThe interface of SMM Ftw protocol
Return values
EFI_SUCCESSThe SMM FTW protocol instance was found and returned in FtwProtocol.
EFI_NOT_FOUNDThe SMM FTW protocol instance was not found.
EFI_INVALID_PARAMETERSarProtocol is NULL.

Definition at line 205 of file VariableSmm.c.

◆ GetFvbByHandle()

EFI_STATUS GetFvbByHandle ( IN EFI_HANDLE  FvBlockHandle,
OUT EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL **  FvBlock 
)

Retrieve the SMM FVB protocol interface by HANDLE.

Parameters
[in]FvBlockHandleThe handle of SMM FVB protocol that provides services for reading, writing, and erasing the target block.
[out]FvBlockThe interface of SMM FVB protocol
Return values
EFI_SUCCESSThe interface information for the specified protocol was returned.
EFI_UNSUPPORTEDThe device does not support the SMM FVB protocol.
EFI_INVALID_PARAMETERFvBlockHandle is not a valid EFI_HANDLE or FvBlock is NULL.

Definition at line 235 of file VariableSmm.c.

◆ GetFvbCountAndBuffer()

EFI_STATUS GetFvbCountAndBuffer ( OUT UINTN NumberHandles,
OUT EFI_HANDLE **  Buffer 
)

Function returns an array of handles that support the SMM FVB protocol in a buffer allocated from pool.

Parameters
[out]NumberHandlesThe number of handles returned in Buffer.
[out]BufferA pointer to the buffer to return the requested array of handles that support SMM FVB protocol.
Return values
EFI_SUCCESSThe array of handles was returned in Buffer, and the number of handles in Buffer was returned in NumberHandles.
EFI_NOT_FOUNDNo SMM FVB handle was found.
EFI_OUT_OF_RESOURCESThere is not enough pool memory to store the matching results.
EFI_INVALID_PARAMETERNumberHandles is NULL or Buffer is NULL.

Definition at line 266 of file VariableSmm.c.

◆ InitializeLock()

EFI_LOCK * InitializeLock ( IN OUT EFI_LOCK Lock,
IN EFI_TPL  Priority 
)

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().

Parameters
LockA pointer to the lock data structure to initialize.
PriorityEFI TPL is associated with the lock.
Returns
The lock.

Definition at line 148 of file VariableSmm.c.

◆ MmVariableServiceInitialize()

EFI_STATUS EFIAPI MmVariableServiceInitialize ( VOID  )

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.

Return values
EFI_SUCCESSVariable service successfully initialized.

Register SMM variable SMI handler

Definition at line 1151 of file VariableSmm.c.

◆ ReleaseLockOnlyAtBootTime()

VOID ReleaseLockOnlyAtBootTime ( 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.

Parameters
LockA pointer to the lock to release.

Definition at line 188 of file VariableSmm.c.

◆ SecureBootHook()

VOID EFIAPI SecureBootHook ( IN CHAR16 *  VariableName,
IN EFI_GUID VendorGuid 
)

SecureBoot Hook for SetVariable.

Parameters
[in]VariableNameName of Variable to be found.
[in]VendorGuidVariable vendor GUID.

Definition at line 52 of file VariableSmm.c.

◆ SmmEndOfDxeCallback()

EFI_STATUS EFIAPI SmmEndOfDxeCallback ( IN CONST EFI_GUID Protocol,
IN VOID *  Interface,
IN EFI_HANDLE  Handle 
)

SMM END_OF_DXE protocol notification event handler.

Parameters
ProtocolPoints to the protocol's unique identifier
InterfacePoints to the interface instance
HandleThe handle on which the interface was installed
Return values
EFI_SUCCESSSmmEndOfDxeCallback runs successfully

Definition at line 1012 of file VariableSmm.c.

◆ SmmFtwNotificationEvent()

EFI_STATUS EFIAPI SmmFtwNotificationEvent ( IN CONST EFI_GUID Protocol,
IN VOID *  Interface,
IN EFI_HANDLE  Handle 
)

SMM Fault Tolerant Write protocol notification event handler.

Non-Volatile variable write may needs FTW protocol to reclaim when writting variable.

Parameters
ProtocolPoints to the protocol's unique identifier
InterfacePoints to the interface instance
HandleThe handle on which the interface was installed
Return values
EFI_SUCCESSSmmEventCallback runs successfully
EFI_NOT_FOUNDThe Fvb protocol for variable is not found.

Definition at line 1075 of file VariableSmm.c.

◆ SmmVariableGetStatistics()

EFI_STATUS SmmVariableGetStatistics ( IN OUT VARIABLE_INFO_ENTRY InfoEntry,
IN OUT UINTN InfoSize 
)

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.

Parameters
[in,out]InfoEntryA 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.
[in,out]InfoSizeOn input, the size of the variable information buffer. On output, the returned variable information size.
Return values
EFI_SUCCESSThe variable information is found and returned successfully.
EFI_UNSUPPORTEDNo variable inoformation exists in variable driver. The PcdVariableCollectStatistics should be set TRUE to support it.
EFI_BUFFER_TOO_SMALLThe buffer is too small to hold the next variable information.
EFI_INVALID_PARAMETERInput parameter is invalid.

Definition at line 336 of file VariableSmm.c.

◆ SmmVariableHandler()

EFI_STATUS EFIAPI SmmVariableHandler ( IN EFI_HANDLE  DispatchHandle,
IN CONST VOID *  RegisterContext,
IN OUT VOID *  CommBuffer,
IN OUT UINTN CommBufferSize 
)

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.

Parameters
[in]DispatchHandleThe unique handle assigned to this handler by SmiHandlerRegister().
[in]RegisterContextPoints to an optional handler context which was specified when the handler was registered.
[in,out]CommBufferA pointer to a collection of data in memory that will be conveyed from a non-SMM environment into an SMM environment.
[in,out]CommBufferSizeThe size of the CommBuffer.
Return values
EFI_SUCCESSThe interrupt was handled and quiesced. No other handlers should still be called.
EFI_WARN_INTERRUPT_SOURCE_QUIESCEDThe interrupt has been quiesced but other handlers should still be called.
EFI_WARN_INTERRUPT_SOURCE_PENDINGThe interrupt is still pending and other handlers should still be called.
EFI_INTERRUPT_PENDINGThe interrupt could not be quiesced.

Definition at line 455 of file VariableSmm.c.

◆ SmmVariableSetVariable()

EFI_STATUS EFIAPI SmmVariableSetVariable ( IN CHAR16 *  VariableName,
IN EFI_GUID VendorGuid,
IN UINT32  Attributes,
IN UINTN  DataSize,
IN VOID *  Data 
)

This code sets variable in storage blocks (Volatile or Non-Volatile).

Parameters
VariableNameName of Variable to be found.
VendorGuidVariable vendor GUID.
AttributesAttribute value of the variable found
DataSizeSize of Data found. If size is less than the data, this value contains the required size.
DataData pointer.
Returns
EFI_INVALID_PARAMETER Invalid parameter.
EFI_SUCCESS Set successfully.
EFI_OUT_OF_RESOURCES Resource not enough to set variable.
EFI_NOT_FOUND Not found.
EFI_WRITE_PROTECTED Variable is read-only.

Definition at line 80 of file VariableSmm.c.

◆ VariableWriteServiceInitializeSmm()

VOID VariableWriteServiceInitializeSmm ( VOID  )

Initializes variable write service for SMM.

Definition at line 1042 of file VariableSmm.c.

Variable Documentation

◆ gSmmVariable

Initial value:
= {
VariableServiceGetVariable,
}
EFI_STATUS EFIAPI VariableServiceGetNextVariableName(IN OUT UINTN *VariableNameSize, IN OUT CHAR16 *VariableName, IN OUT EFI_GUID *VendorGuid)
Definition: Variable.c:2502
EFI_STATUS EFIAPI VariableServiceQueryVariableInfo(IN UINT32 Attributes, OUT UINT64 *MaximumVariableStorageSize, OUT UINT64 *RemainingVariableStorageSize, OUT UINT64 *MaximumVariableSize)
Definition: Variable.c:3120
EFI_STATUS EFIAPI SmmVariableSetVariable(IN CHAR16 *VariableName, IN EFI_GUID *VendorGuid, IN UINT32 Attributes, IN UINTN DataSize, IN VOID *Data)
Definition: VariableSmm.c:80

Definition at line 105 of file VariableSmm.c.

◆ mAtRuntime

BOOLEAN mAtRuntime = FALSE

Definition at line 39 of file VariableSmm.c.

◆ mNvVariableCache

VARIABLE_STORE_HEADER* mNvVariableCache
extern

Define a memory cache that improves the search performance for a variable. For EmuNvMode == TRUE, it will be equal to NonVolatileVariableBase.

Definition at line 39 of file Variable.c.

◆ mSmmVarCheck

Initial value:
= {
}
EFI_STATUS EFIAPI VarCheckVariablePropertySet(IN CHAR16 *Name, IN EFI_GUID *Guid, IN VAR_CHECK_VARIABLE_PROPERTY *VariableProperty)
Definition: VarCheck.c:59
EFI_STATUS EFIAPI VarCheckRegisterSetVariableCheckHandler(IN VAR_CHECK_SET_VARIABLE_CHECK_HANDLER Handler)
Definition: VarCheck.c:29
EFI_STATUS EFIAPI VarCheckVariablePropertyGet(IN CHAR16 *Name, IN EFI_GUID *Guid, OUT VAR_CHECK_VARIABLE_PROPERTY *VariableProperty)
Definition: VarCheck.c:88

Definition at line 112 of file VariableSmm.c.

◆ mVariableBufferPayload

UINT8* mVariableBufferPayload = NULL

Definition at line 40 of file VariableSmm.c.

◆ mVariableBufferPayloadSize

UINTN mVariableBufferPayloadSize

Definition at line 41 of file VariableSmm.c.