MdeModulePkg/FaultTolerantWrite: Consume Variable Flash Info

REF:https://bugzilla.tianocore.org/show_bug.cgi?id=3479

Adds support to the UEFI variable fault tolerant write (FTW) drivers
to receive FTW base and size information dynamically via the Variable
Flash Information library.

Cc: Jian J Wang <jian.j.wang@intel.com>
Cc: Hao A Wu <hao.a.wu@intel.com>
Cc: Liming Gao <gaoliming@byosoft.com.cn>
Signed-off-by: Michael Kubacki <michael.kubacki@microsoft.com>
Acked-by: Ard Biesheuvel <ardb@kernel.org>
Reviewed-by: Liming Gao <gaoliming@byosoft.com.cn>
Reviewed-by: Sami Mujawar <sami.mujawar@arm.com>
diff --git a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWrite.h b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWrite.h
index c14e47b..5b84d06 100644
--- a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWrite.h
+++ b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWrite.h
@@ -26,6 +26,8 @@
 #include <Library/BaseMemoryLib.h>

 #include <Library/MemoryAllocationLib.h>

 #include <Library/ReportStatusCodeLib.h>

+#include <Library/SafeIntLib.h>

+#include <Library/VariableFlashInfoLib.h>

 

 //

 // Flash erase polarity is 1

@@ -708,10 +710,13 @@
 

   Since Signature and WriteQueueSize have been known, Crc can be calculated out,

   then the work space header will be fixed.

+

+  @param[in]  WorkSpaceLength     Length in bytes of the FTW workspace area.

+

 **/

 VOID

 InitializeLocalWorkSpaceHeader (

-  VOID

+  IN  UINTN  WorkSpaceLength

   );

 

 /**

diff --git a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteDxe.inf b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteDxe.inf
index 9616561..d524e18 100644
--- a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteDxe.inf
+++ b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteDxe.inf
@@ -46,6 +46,8 @@
   UefiLib

   PcdLib

   ReportStatusCodeLib

+  SafeIntLib

+  VariableFlashInfoLib

 

 [Guids]

   #

@@ -65,14 +67,6 @@
 [FeaturePcd]

   gEfiMdeModulePkgTokenSpaceGuid.PcdFullFtwServiceEnable    ## CONSUMES

 

-[Pcd]

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase    ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase64  ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingSize    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase      ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase64    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareSize      ## CONSUMES

-

 #

 # gBS->CalculateCrc32() is consumed in EntryPoint.

 # PI spec said: When the DXE Foundation is notified that the EFI_RUNTIME_ARCH_PROTOCOL

diff --git a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteSmm.inf b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteSmm.inf
index 8cc6028..8a4b9ad 100644
--- a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteSmm.inf
+++ b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteSmm.inf
@@ -52,6 +52,8 @@
   ReportStatusCodeLib

   SmmMemLib

   BaseLib

+  SafeIntLib

+  VariableFlashInfoLib

 

 [Guids]

   #

@@ -74,14 +76,6 @@
 [FeaturePcd]

   gEfiMdeModulePkgTokenSpaceGuid.PcdFullFtwServiceEnable    ## CONSUMES

 

-[Pcd]

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase    ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase64  ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingSize    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase      ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase64    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareSize      ## CONSUMES

-

 #

 # gBS->CalculateCrc32() is consumed in EntryPoint.

 # PI spec said: When the DXE Foundation is notified that the EFI_RUNTIME_ARCH_PROTOCOL

diff --git a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteStandaloneMm.inf b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteStandaloneMm.inf
index d0fab7d..0ac6edf 100644
--- a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteStandaloneMm.inf
+++ b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FaultTolerantWriteStandaloneMm.inf
@@ -50,7 +50,9 @@
   MmServicesTableLib

   PcdLib

   ReportStatusCodeLib

+  SafeIntLib

   StandaloneMmDriverEntryPoint

+  VariableFlashInfoLib

 

 [Guids]

   #

@@ -73,13 +75,5 @@
 [FeaturePcd]

   gEfiMdeModulePkgTokenSpaceGuid.PcdFullFtwServiceEnable    ## CONSUMES

 

-[Pcd]

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase    ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase64  ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingSize    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase      ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase64    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareSize      ## CONSUMES

-

 [Depex]

   TRUE

diff --git a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FtwMisc.c b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FtwMisc.c
index 661e148..f133587 100644
--- a/MdeModulePkg/Universal/FaultTolerantWriteDxe/FtwMisc.c
+++ b/MdeModulePkg/Universal/FaultTolerantWriteDxe/FtwMisc.c
@@ -987,22 +987,43 @@
   OUT EFI_FTW_DEVICE  **FtwData

   )

 {

-  EFI_FTW_DEVICE  *FtwDevice;

+  EFI_STATUS            Status;

+  EFI_PHYSICAL_ADDRESS  WorkSpaceAddress;

+  UINT64                Size;

+  UINTN                 FtwWorkingSize;

+  EFI_FTW_DEVICE        *FtwDevice;

+

+  FtwWorkingSize = 0;

+

+  Status = GetVariableFlashFtwWorkingInfo (&WorkSpaceAddress, &Size);

+  ASSERT_EFI_ERROR (Status);

+

+  Status = SafeUint64ToUintn (Size, &FtwWorkingSize);

+  // This driver currently assumes the size will be UINTN so assert the value is safe for now.

+  ASSERT_EFI_ERROR (Status);

 

   //

   // Allocate private data of this driver,

   // Including the FtwWorkSpace[FTW_WORK_SPACE_SIZE].

   //

-  FtwDevice = AllocateZeroPool (sizeof (EFI_FTW_DEVICE) + PcdGet32 (PcdFlashNvStorageFtwWorkingSize));

+  FtwDevice = AllocateZeroPool (sizeof (EFI_FTW_DEVICE) + FtwWorkingSize);

   if (FtwDevice == NULL) {

     return EFI_OUT_OF_RESOURCES;

   }

 

+  FtwDevice->WorkSpaceAddress = WorkSpaceAddress;

+  FtwDevice->WorkSpaceLength  = FtwWorkingSize;

+

+  Status = GetVariableFlashFtwSpareInfo (&FtwDevice->SpareAreaAddress, &Size);

+  ASSERT_EFI_ERROR (Status);

+

+  Status = SafeUint64ToUintn (Size, &FtwDevice->SpareAreaLength);

+  // This driver currently assumes the size will be UINTN so assert the value is safe for now.

+  ASSERT_EFI_ERROR (Status);

+

   //

   // Initialize other parameters, and set WorkSpace as FTW_ERASED_BYTE.

   //

-  FtwDevice->WorkSpaceLength = (UINTN)PcdGet32 (PcdFlashNvStorageFtwWorkingSize);

-  FtwDevice->SpareAreaLength = (UINTN)PcdGet32 (PcdFlashNvStorageFtwSpareSize);

   if ((FtwDevice->WorkSpaceLength == 0) || (FtwDevice->SpareAreaLength == 0)) {

     DEBUG ((DEBUG_ERROR, "Ftw: Workspace or Spare block does not exist!\n"));

     FreePool (FtwDevice);

@@ -1015,16 +1036,6 @@
   FtwDevice->FtwWorkSpaceLba = (EFI_LBA)(-1);

   FtwDevice->FtwSpareLba     = (EFI_LBA)(-1);

 

-  FtwDevice->WorkSpaceAddress = (EFI_PHYSICAL_ADDRESS)PcdGet64 (PcdFlashNvStorageFtwWorkingBase64);

-  if (FtwDevice->WorkSpaceAddress == 0) {

-    FtwDevice->WorkSpaceAddress = (EFI_PHYSICAL_ADDRESS)PcdGet32 (PcdFlashNvStorageFtwWorkingBase);

-  }

-

-  FtwDevice->SpareAreaAddress = (EFI_PHYSICAL_ADDRESS)PcdGet64 (PcdFlashNvStorageFtwSpareBase64);

-  if (FtwDevice->SpareAreaAddress == 0) {

-    FtwDevice->SpareAreaAddress = (EFI_PHYSICAL_ADDRESS)PcdGet32 (PcdFlashNvStorageFtwSpareBase);

-  }

-

   *FtwData = FtwDevice;

   return EFI_SUCCESS;

 }

@@ -1277,7 +1288,7 @@
   FtwDevice->FtwLastWriteHeader = NULL;

   FtwDevice->FtwLastWriteRecord = NULL;

 

-  InitializeLocalWorkSpaceHeader ();

+  InitializeLocalWorkSpaceHeader (FtwDevice->WorkSpaceLength);

 

   //

   // Refresh the working space data from working block

diff --git a/MdeModulePkg/Universal/FaultTolerantWriteDxe/UpdateWorkingBlock.c b/MdeModulePkg/Universal/FaultTolerantWriteDxe/UpdateWorkingBlock.c
index 61e7a92..fd56364 100644
--- a/MdeModulePkg/Universal/FaultTolerantWriteDxe/UpdateWorkingBlock.c
+++ b/MdeModulePkg/Universal/FaultTolerantWriteDxe/UpdateWorkingBlock.c
@@ -16,10 +16,13 @@
 

   Since Signature and WriteQueueSize have been known, Crc can be calculated out,

   then the work space header will be fixed.

+

+  @param[in]  WorkSpaceLength     Length in bytes of the FTW workspace area.

+

 **/

 VOID

 InitializeLocalWorkSpaceHeader (

-  VOID

+  IN  UINTN  WorkSpaceLength

   )

 {

   //

@@ -46,7 +49,7 @@
     &gEdkiiWorkingBlockSignatureGuid,

     sizeof (EFI_GUID)

     );

-  mWorkingBlockHeader.WriteQueueSize = PcdGet32 (PcdFlashNvStorageFtwWorkingSize) - sizeof (EFI_FAULT_TOLERANT_WORKING_BLOCK_HEADER);

+  mWorkingBlockHeader.WriteQueueSize = WorkSpaceLength - sizeof (EFI_FAULT_TOLERANT_WORKING_BLOCK_HEADER);

 

   //

   // Crc is calculated with all the fields except Crc and STATE, so leave them as FTW_ERASED_BYTE.

diff --git a/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.c b/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.c
index 15543f1..8c152dc 100644
--- a/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.c
+++ b/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.c
@@ -16,6 +16,8 @@
 #include <Library/DebugLib.h>

 #include <Library/BaseMemoryLib.h>

 #include <Library/HobLib.h>

+#include <Library/SafeIntLib.h>

+#include <Library/VariableFlashInfoLib.h>

 

 EFI_PEI_PPI_DESCRIPTOR  mPpiListVariable = {

   (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),

@@ -212,25 +214,31 @@
   EFI_PHYSICAL_ADDRESS                     SpareAreaAddress;

   UINTN                                    SpareAreaLength;

   EFI_PHYSICAL_ADDRESS                     WorkSpaceInSpareArea;

+  UINT64                                   Size;

   FAULT_TOLERANT_WRITE_LAST_WRITE_DATA     FtwLastWrite;

 

   FtwWorkingBlockHeader = NULL;

   FtwLastWriteHeader    = NULL;

   FtwLastWriteRecord    = NULL;

 

-  WorkSpaceAddress = (EFI_PHYSICAL_ADDRESS)PcdGet64 (PcdFlashNvStorageFtwWorkingBase64);

-  if (WorkSpaceAddress == 0) {

-    WorkSpaceAddress = (EFI_PHYSICAL_ADDRESS)PcdGet32 (PcdFlashNvStorageFtwWorkingBase);

-  }

+  SpareAreaAddress = 0;

+  SpareAreaLength  = 0;

+  WorkSpaceAddress = 0;

+  WorkSpaceLength  = 0;

 

-  WorkSpaceLength = (UINTN)PcdGet32 (PcdFlashNvStorageFtwWorkingSize);

+  Status = GetVariableFlashFtwWorkingInfo (&WorkSpaceAddress, &Size);

+  ASSERT_EFI_ERROR (Status);

 

-  SpareAreaAddress = (EFI_PHYSICAL_ADDRESS)PcdGet64 (PcdFlashNvStorageFtwSpareBase64);

-  if (SpareAreaAddress == 0) {

-    SpareAreaAddress = (EFI_PHYSICAL_ADDRESS)PcdGet32 (PcdFlashNvStorageFtwSpareBase);

-  }

+  Status = SafeUint64ToUintn (Size, &WorkSpaceLength);

+  // This driver currently assumes the size will be UINTN so assert the value is safe for now.

+  ASSERT_EFI_ERROR (Status);

 

-  SpareAreaLength = (UINTN)PcdGet32 (PcdFlashNvStorageFtwSpareSize);

+  Status = GetVariableFlashFtwSpareInfo (&SpareAreaAddress, &Size);

+  ASSERT_EFI_ERROR (Status);

+

+  Status = SafeUint64ToUintn (Size, &SpareAreaLength);

+  // This driver currently assumes the size will be UINTN so assert the value is safe for now.

+  ASSERT_EFI_ERROR (Status);

 

   //

   // The address of FTW working base and spare base must not be 0.

diff --git a/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.inf b/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.inf
index f90892a..2301382 100644
--- a/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.inf
+++ b/MdeModulePkg/Universal/FaultTolerantWritePei/FaultTolerantWritePei.inf
@@ -39,6 +39,8 @@
   HobLib

   BaseMemoryLib

   PcdLib

+  SafeIntLib

+  VariableFlashInfoLib

 

 [Guids]

   ## SOMETIMES_PRODUCES   ## HOB

@@ -47,14 +49,6 @@
   gEdkiiWorkingBlockSignatureGuid               ## SOMETIMES_CONSUMES   ## GUID

   gEfiSystemNvDataFvGuid                        ## SOMETIMES_CONSUMES   ## GUID

 

-[Pcd]

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase    ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase64  ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingSize    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase      ## SOMETIMES_CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase64    ## CONSUMES

-  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareSize      ## CONSUMES

-

 [Depex]

   TRUE