:p
atchew
Login
REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4454 On Server platform, when the large variable "FspNvsBuffer" is already in the UEFI variable store and the remaining variable storage space is less than the large variable size. And also not in OS runtime then we need to add the size of the current data that will end up being replaced by the new data to the remaining space before we decide that there is not enough space to store the large variable. Cc: Chasel Chiu <chasel.chiu@intel.com> Cc: Nate DeSimone <nathaniel.l.desimone@intel.com> Cc: Liming Gao <gaoliming@byosoft.com.cn> Cc: Eric Dong <eric.dong@intel.com> Signed-off-by: Xiaoqiang Zhang <xiaoqiang.zhang@intel.com> --- Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c | 10 +++++++++- Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf | 1 + 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c +++ b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c @@ -XXX,XX +XXX,XX @@ #include <Library/PrintLib.h> #include <Library/VariableReadLib.h> #include <Library/VariableWriteLib.h> - +#include <Library/LargeVariableReadLib.h> #include "LargeVariableCommon.h" /** @@ -XXX,XX +XXX,XX @@ SetLargeVariable ( UINT8 *OffsetPtr; UINTN BytesRemaining; UINTN SizeToSave; + UINTN BufferSize = 0; // // Check input parameters. @@ -XXX,XX +XXX,XX @@ SetLargeVariable ( // Non-Volatile storage to store the data. // RemainingVariableStorage = GetRemainingVariableStorageSpace (); + // + // Check if current variable already existed in NV storage variable space + // + Status = GetLargeVariable (VariableName, VendorGuid, &BufferSize, NULL); + if ((Status == EFI_BUFFER_TOO_SMALL) && (BufferSize != 0)) { + RemainingVariableStorage = RemainingVariableStorage + BufferSize; + } if (DataSize > RemainingVariableStorage) { DEBUG ((DEBUG_ERROR, "SetLargeVariable: Not enough NV storage space to store the data\n")); Status = EFI_OUT_OF_RESOURCES; diff --git a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf +++ b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf @@ -XXX,XX +XXX,XX @@ PrintLib VariableReadLib VariableWriteLib + LargeVariableReadLib -- 2.39.1.windows.1 -=-=-=-=-=-=-=-=-=-=-=- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#104388): https://edk2.groups.io/g/devel/message/104388 Mute This Topic: https://groups.io/mt/98786447/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=-=-=-=-=-=-=-=-=-=-=-
REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4454 On Server platform, when the large variable "FspNvsBuffer" is already in the UEFI variable store and the remaining variable storage space is less than the large variable size, and also not in OS runtime, then we need to add the size of the current data that will end up being replaced by the new data to the remaining space before we decide that there is not enough space to store the large variable. Cc: Chasel Chiu <chasel.chiu@intel.com> Cc: Nate DeSimone <nathaniel.l.desimone@intel.com> Cc: Liming Gao <gaoliming@byosoft.com.cn> Cc: Eric Dong <eric.dong@intel.com> Co-authored-by: Xiaoqiang Zhang <xiaoqiang.zhang@intel.com> Signed-off-by: Miki Shindo <miki.shindo@intel.com> --- Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c | 10 +++++++++- Platform/Intel/MinPlatformPkg/Library/DxeRuntimeVariableWriteLib/DxeRuntimeVariableWriteLib.c | 15 +++++++++++++++ Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/SmmVariableWriteCommon.c | 16 ++++++++++++++++ Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLibConstructor.c | 30 ++++++++++++++++++++++++++++++ Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLibConstructor.c | 30 ++++++++++++++++++++++++++++++ Platform/Intel/MinPlatformPkg/Include/Library/VariableWriteLib.h | 12 ++++++++++++ Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf | 1 + Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLib.inf | 3 ++- Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLib.inf | 3 ++- 9 files changed, 117 insertions(+), 3 deletions(-) diff --git a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c +++ b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/LargeVariableWriteLib.c @@ -XXX,XX +XXX,XX @@ #include <Library/PrintLib.h> #include <Library/VariableReadLib.h> #include <Library/VariableWriteLib.h> - +#include <Library/LargeVariableReadLib.h> #include "LargeVariableCommon.h" /** @@ -XXX,XX +XXX,XX @@ SetLargeVariable ( UINT8 *OffsetPtr; UINTN BytesRemaining; UINTN SizeToSave; + UINTN BufferSize = 0; // // Check input parameters. @@ -XXX,XX +XXX,XX @@ SetLargeVariable ( // Non-Volatile storage to store the data. // RemainingVariableStorage = GetRemainingVariableStorageSpace (); + // + // Check if current variable already existed in NV storage variable space + // + Status = GetLargeVariable (VariableName, VendorGuid, &BufferSize, NULL); + if ((Status == EFI_BUFFER_TOO_SMALL) && (BufferSize != 0) && !VarLibAtOsRuntime ()) { + RemainingVariableStorage = RemainingVariableStorage + BufferSize; + } if (DataSize > RemainingVariableStorage) { DEBUG ((DEBUG_ERROR, "SetLargeVariable: Not enough NV storage space to store the data\n")); Status = EFI_OUT_OF_RESOURCES; diff --git a/Platform/Intel/MinPlatformPkg/Library/DxeRuntimeVariableWriteLib/DxeRuntimeVariableWriteLib.c b/Platform/Intel/MinPlatformPkg/Library/DxeRuntimeVariableWriteLib/DxeRuntimeVariableWriteLib.c index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/DxeRuntimeVariableWriteLib/DxeRuntimeVariableWriteLib.c +++ b/Platform/Intel/MinPlatformPkg/Library/DxeRuntimeVariableWriteLib/DxeRuntimeVariableWriteLib.c @@ -XXX,XX +XXX,XX @@ VarLibVariableRequestToLock ( return Status; } +/** + Indicator of whether it is runtime or not. + + @retval TRUE It is Runtime. + @retval FALSE It is not Runtime. +**/ +BOOLEAN +EFIAPI +VarLibAtOsRuntime ( + VOID + ) +{ + return (mVariableWriteLibVariablePolicy == NULL) ? TRUE : FALSE; +} + /** Close events when driver unloaded. diff --git a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/SmmVariableWriteCommon.c b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/SmmVariableWriteCommon.c index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/SmmVariableWriteCommon.c +++ b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/SmmVariableWriteCommon.c @@ -XXX,XX +XXX,XX @@ #include <Protocol/SmmVariable.h> EFI_SMM_VARIABLE_PROTOCOL *mVariableWriteLibSmmVariable = NULL; +BOOLEAN mEfiAtRuntime = FALSE; /** Sets the value of a variable. @@ -XXX,XX +XXX,XX @@ VarLibVariableRequestToLock ( // return EFI_UNSUPPORTED; } + +/** + Indicator of whether it is runtime or not. + + @retval TRUE It is Runtime. + @retval FALSE It is not Runtime. +**/ +BOOLEAN +EFIAPI +VarLibAtOsRuntime ( + VOID + ) +{ + return mEfiAtRuntime; +} diff --git a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLibConstructor.c b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLibConstructor.c index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLibConstructor.c +++ b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLibConstructor.c @@ -XXX,XX +XXX,XX @@ #include <Library/MmServicesTableLib.h> extern EFI_SMM_VARIABLE_PROTOCOL *mVariableWriteLibSmmVariable; +extern BOOLEAN mEfiAtRuntime; + +/** + Callback for ExitBootService, which is registered at the constructor. + This callback sets a global variable mEfiAtRuntime to indicate whether + it is after ExitBootService. + + @param[in] Protocol Protocol unique ID. + @param[in] Interface Interface instance. + @param[in] Handle The handle on which the interface is installed. +**/ +EFI_STATUS +EFIAPI +VarLibExitBootServicesCallback ( + IN CONST EFI_GUID *Protocol, + IN VOID *Interface, + IN EFI_HANDLE Handle + ) +{ + mEfiAtRuntime = TRUE; + return EFI_SUCCESS; +} /** The constructor function acquires the EFI SMM Variable Services @@ -XXX,XX +XXX,XX @@ StandaloneMmVariableWriteLibConstructor ( ) { EFI_STATUS Status; + VOID *Registration = NULL; // // Locate SmmVariableProtocol. // Status = gMmst->MmLocateProtocol (&gEfiSmmVariableProtocolGuid, NULL, (VOID **) &mVariableWriteLibSmmVariable); ASSERT_EFI_ERROR (Status); + + // + // Register VarLibExitBootServicesCallback for gEdkiiSmmExitBootServicesProtocolGuid. + // + Status = SmmRegisterProtocolNotify (&gEdkiiSmmExitBootServicesProtocolGuid, VarLibExitBootServicesCallback, &Registration); + ASSERT_EFI_ERROR (Status); + return Status; } diff --git a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLibConstructor.c b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLibConstructor.c index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLibConstructor.c +++ b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLibConstructor.c @@ -XXX,XX +XXX,XX @@ #include <Library/SmmServicesTableLib.h> extern EFI_SMM_VARIABLE_PROTOCOL *mVariableWriteLibSmmVariable; +extern BOOLEAN mEfiAtRuntime; + +/** + Callback for ExitBootService, which is registered at the constructor. + This callback sets a global variable mEfiAtRuntime to indicate whether + it is after ExitBootService. + + @param[in] Protocol Protocol unique ID. + @param[in] Interface Interface instance. + @param[in] Handle The handle on which the interface is installed. +**/ +EFI_STATUS +EFIAPI +VarLibExitBootServicesCallback ( + IN CONST EFI_GUID *Protocol, + IN VOID *Interface, + IN EFI_HANDLE Handle + ) +{ + mEfiAtRuntime = TRUE; + return EFI_SUCCESS; +} /** The constructor function acquires the EFI SMM Variable Services @@ -XXX,XX +XXX,XX @@ TraditionalMmVariableWriteLibConstructor ( ) { EFI_STATUS Status; + VOID *Registration = NULL; // // Locate SmmVariableProtocol. // Status = gSmst->SmmLocateProtocol (&gEfiSmmVariableProtocolGuid, NULL, (VOID **) &mVariableWriteLibSmmVariable); ASSERT_EFI_ERROR (Status); + + // + // Register VarLibExitBootServicesCallback for gEdkiiSmmExitBootServicesProtocolGuid. + // + Status = SmmRegisterProtocolNotify (&gEdkiiSmmExitBootServicesProtocolGuid, VarLibExitBootServicesCallback, &Registration); + ASSERT_EFI_ERROR (Status); + return Status; } diff --git a/Platform/Intel/MinPlatformPkg/Include/Library/VariableWriteLib.h b/Platform/Intel/MinPlatformPkg/Include/Library/VariableWriteLib.h index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Include/Library/VariableWriteLib.h +++ b/Platform/Intel/MinPlatformPkg/Include/Library/VariableWriteLib.h @@ -XXX,XX +XXX,XX @@ VarLibVariableRequestToLock ( IN EFI_GUID *VendorGuid ); +/** + Indicator of whether it is runtime or not. + + @retval TRUE It is Runtime. + @retval FALSE It is not Runtime. +**/ +BOOLEAN +EFIAPI +VarLibAtOsRuntime ( + VOID + ); + #endif // _VARIABLE_WRITE_LIB_H_ diff --git a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf +++ b/Platform/Intel/MinPlatformPkg/Library/BaseLargeVariableLib/BaseLargeVariableWriteLib.inf @@ -XXX,XX +XXX,XX @@ PrintLib VariableReadLib VariableWriteLib + LargeVariableReadLib diff --git a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLib.inf b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLib.inf index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLib.inf +++ b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/StandaloneMmVariableWriteLib.inf @@ -XXX,XX +XXX,XX @@ MmServicesTableLib [Protocols] - gEfiSmmVariableProtocolGuid ## CONSUMES + gEfiSmmVariableProtocolGuid ## CONSUMES + gEdkiiSmmExitBootServicesProtocolGuid ## CONSUMES [Depex] gEfiSmmVariableProtocolGuid diff --git a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLib.inf b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLib.inf index XXXXXXX..XXXXXXX 100644 --- a/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLib.inf +++ b/Platform/Intel/MinPlatformPkg/Library/SmmVariableWriteLib/TraditionalMmVariableWriteLib.inf @@ -XXX,XX +XXX,XX @@ SmmServicesTableLib [Protocols] - gEfiSmmVariableProtocolGuid ## CONSUMES + gEfiSmmVariableProtocolGuid ## CONSUMES + gEdkiiSmmExitBootServicesProtocolGuid ## CONSUMES [Depex] gEfiSmmVariableProtocolGuid -- 2.39.1.windows.1 -=-=-=-=-=-=-=-=-=-=-=- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#105209): https://edk2.groups.io/g/devel/message/105209 Mute This Topic: https://groups.io/mt/99099949/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=-=-=-=-=-=-=-=-=-=-=-