/** @file

  These are the common Fault Tolerant Write (FTW) functions that are shared 
  by DXE FTW driver and SMM FTW driver.

Copyright (c) 2006 - 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 "FaultTolerantWrite.h"

//
// Fault Tolerant Write Protocol API
//
/**
  Query the largest block that may be updated in a fault tolerant manner.


  @param This            The pointer to this protocol instance. 
  @param BlockSize       A pointer to a caller allocated UINTN that is updated to
                         indicate the size of the largest block that can be updated.

  @return EFI_SUCCESS   The function completed successfully

**/
EFI_STATUS
EFIAPI
FtwGetMaxBlockSize (
  IN EFI_FAULT_TOLERANT_WRITE_PROTOCOL    *This,
  OUT UINTN                               *BlockSize
  )
{
  EFI_FTW_DEVICE  *FtwDevice;

  if (!FeaturePcdGet(PcdFullFtwServiceEnable)) {
    return EFI_UNSUPPORTED;
  }

  FtwDevice   = FTW_CONTEXT_FROM_THIS (This);

  *BlockSize  = FtwDevice->SpareAreaLength;

  return EFI_SUCCESS;
}

/**
  Allocates space for the protocol to maintain information about writes.
  Since writes must be completed in a fault tolerant manner and multiple
  updates will require more resources to be successful, this function
  enables the protocol to ensure that enough space exists to track
  information about the upcoming writes.

  All writes must be completed or aborted before another fault tolerant write can occur.

  @param This            The pointer to this protocol instance. 
  @param CallerId        The GUID identifying the write.
  @param PrivateDataSize The size of the caller's private data
                         that must be recorded for each write.
  @param NumberOfWrites  The number of fault tolerant block writes
                         that will need to occur.

  @return EFI_SUCCESS        The function completed successfully
  @retval EFI_ABORTED        The function could not complete successfully.
  @retval EFI_ACCESS_DENIED  All allocated writes have not been completed.

**/
EFI_STATUS
EFIAPI
FtwAllocate (
  IN EFI_FAULT_TOLERANT_WRITE_PROTOCOL    *This,
  IN EFI_GUID                             *CallerId,
  IN UINTN                                PrivateDataSize,
  IN UINTN                                NumberOfWrites
  )
{
  EFI_STATUS                      Status;
  UINTN                           Offset;
  EFI_FTW_DEVICE                  *FtwDevice;
  EFI_FAULT_TOLERANT_WRITE_HEADER *FtwHeader;

  FtwDevice = FTW_CONTEXT_FROM_THIS (This);

  Status    = WorkSpaceRefresh (FtwDevice);
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }
  //
  // Check if there is enough space for the coming allocation
  //
  if (FTW_WRITE_TOTAL_SIZE (NumberOfWrites, PrivateDataSize) > FtwDevice->FtwWorkSpaceHeader->WriteQueueSize) {
    DEBUG ((EFI_D_ERROR, "Ftw: Allocate() request exceed Workspace, Caller: %g\n", CallerId));
    return EFI_BUFFER_TOO_SMALL;
  }
  //
  // Find the last write header and record.
  // If the FtwHeader is complete, skip the completed last write header/records
  //
  FtwHeader = FtwDevice->FtwLastWriteHeader;

  //
  // Previous write has not completed, access denied.
  //
  if ((FtwHeader->HeaderAllocated == FTW_VALID_STATE) || (FtwHeader->WritesAllocated == FTW_VALID_STATE)) {
    return EFI_ACCESS_DENIED;
  }
  //
  // If workspace is not enough, then reclaim workspace
  //
  Offset = (UINT8 *) FtwHeader - (UINT8 *) FtwDevice->FtwWorkSpace;
  if (Offset + FTW_WRITE_TOTAL_SIZE (NumberOfWrites, PrivateDataSize) > FtwDevice->FtwWorkSpaceSize) {
    Status = FtwReclaimWorkSpace (FtwDevice, TRUE);
    if (EFI_ERROR (Status)) {
      return EFI_ABORTED;
    }

    FtwHeader = FtwDevice->FtwLastWriteHeader;
  }
  //
  // Prepare FTW write header,
  // overwrite the buffer and write to workspace.
  //
  FtwHeader->WritesAllocated  = FTW_INVALID_STATE;
  FtwHeader->Complete         = FTW_INVALID_STATE;
  CopyMem (&FtwHeader->CallerId, CallerId, sizeof (EFI_GUID));
  FtwHeader->NumberOfWrites   = NumberOfWrites;
  FtwHeader->PrivateDataSize  = PrivateDataSize;
  FtwHeader->HeaderAllocated  = FTW_VALID_STATE;

  Status = WriteWorkSpaceData (
             FtwDevice->FtwFvBlock,
             FtwDevice->WorkBlockSize,
             FtwDevice->FtwWorkSpaceLba,
             FtwDevice->FtwWorkSpaceBase + Offset,
             sizeof (EFI_FAULT_TOLERANT_WRITE_HEADER),
             (UINT8 *) FtwHeader
             );
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }
  //
  // Update Header->WriteAllocated as VALID
  //
  Status = FtwUpdateFvState (
            FtwDevice->FtwFvBlock,
            FtwDevice->WorkBlockSize,
            FtwDevice->FtwWorkSpaceLba,
            FtwDevice->FtwWorkSpaceBase + Offset,
            WRITES_ALLOCATED
            );
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  DEBUG (
    (EFI_D_INFO,
    "Ftw: Allocate() success, Caller:%g, # %d\n",
    CallerId,
    NumberOfWrites)
    );

  return EFI_SUCCESS;
}


/**
  Write a record with fault tolerant manner.
  Since the content has already backuped in spare block, the write is
  guaranteed to be completed with fault tolerant manner.

  @param This            The pointer to this protocol instance. 
  @param Fvb             The FVB protocol that provides services for
                         reading, writing, and erasing the target block.
  @param BlockSize       The size of the block.

  @retval  EFI_SUCCESS          The function completed successfully
  @retval  EFI_ABORTED          The function could not complete successfully

**/
EFI_STATUS
FtwWriteRecord (
  IN EFI_FAULT_TOLERANT_WRITE_PROTOCOL     *This,
  IN EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL    *Fvb,
  IN UINTN                                 BlockSize
  )
{
  EFI_STATUS                      Status;
  EFI_FTW_DEVICE                  *FtwDevice;
  EFI_FAULT_TOLERANT_WRITE_HEADER *Header;
  EFI_FAULT_TOLERANT_WRITE_RECORD *Record;
  UINTN                           Offset;
  UINTN                           NumberOfWriteBlocks;

  FtwDevice = FTW_CONTEXT_FROM_THIS (This);

  //
  // Spare Complete but Destination not complete,
  // Recover the target block with the spare block.
  //
  Header  = FtwDevice->FtwLastWriteHeader;
  Record  = FtwDevice->FtwLastWriteRecord;

  //
  // IF target block is working block, THEN Flush Spare Block To Working Block;
  // ELSE flush spare block to target block, which may be boot block after all.
  //
  if (IsWorkingBlock (FtwDevice, Fvb, Record->Lba)) {
    //
    // If target block is working block,
    // it also need to set SPARE_COMPLETED to spare block.
    //
    Offset = (UINT8 *) Record - FtwDevice->FtwWorkSpace;
    Status = FtwUpdateFvState (
              FtwDevice->FtwBackupFvb,
              FtwDevice->SpareBlockSize,
              FtwDevice->FtwSpareLba + FtwDevice->FtwWorkSpaceLbaInSpare,
              FtwDevice->FtwWorkSpaceBaseInSpare + Offset,
              SPARE_COMPLETED
              );
    if (EFI_ERROR (Status)) {
      return EFI_ABORTED;
    }

    Status = FlushSpareBlockToWorkingBlock (FtwDevice);
  } else if (IsBootBlock (FtwDevice, Fvb)) {
    //
    // Update boot block
    //
    Status = FlushSpareBlockToBootBlock (FtwDevice);
  } else {
    //
    // Update blocks other than working block or boot block
    //
    NumberOfWriteBlocks = FTW_BLOCKS ((UINTN) (Record->Offset + Record->Length), BlockSize);
    Status = FlushSpareBlockToTargetBlock (FtwDevice, Fvb, Record->Lba, BlockSize, NumberOfWriteBlocks);
  }

  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }
  //
  // Record the DestionationComplete in record
  //
  Offset = (UINT8 *) Record - FtwDevice->FtwWorkSpace;
  Status = FtwUpdateFvState (
            FtwDevice->FtwFvBlock,
            FtwDevice->WorkBlockSize,
            FtwDevice->FtwWorkSpaceLba,
            FtwDevice->FtwWorkSpaceBase + Offset,
            DEST_COMPLETED
            );
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  Record->DestinationComplete = FTW_VALID_STATE;

  //
  // If this is the last Write in these write sequence,
  // set the complete flag of write header.
  //
  if (IsLastRecordOfWrites (Header, Record)) {
    Offset = (UINT8 *) Header - FtwDevice->FtwWorkSpace;
    Status = FtwUpdateFvState (
              FtwDevice->FtwFvBlock,
              FtwDevice->WorkBlockSize,
              FtwDevice->FtwWorkSpaceLba,
              FtwDevice->FtwWorkSpaceBase + Offset,
              WRITES_COMPLETED
              );
    Header->Complete = FTW_VALID_STATE;
    if (EFI_ERROR (Status)) {
      return EFI_ABORTED;
    }
  }

  return EFI_SUCCESS;
}

/**
  Starts a target block update. This function will record data about write
  in fault tolerant storage and will complete the write in a recoverable
  manner, ensuring at all times that either the original contents or
  the modified contents are available.

  @param This            The pointer to this protocol instance. 
  @param Lba             The logical block address of the target block.
  @param Offset          The offset within the target block to place the data.
  @param Length          The number of bytes to write to the target block.
  @param PrivateData     A pointer to private data that the caller requires to
                         complete any pending writes in the event of a fault.
  @param FvBlockHandle   The handle of FVB protocol that provides services for
                         reading, writing, and erasing the target block.
  @param Buffer          The data to write.

  @retval EFI_SUCCESS          The function completed successfully 
  @retval EFI_ABORTED          The function could not complete successfully. 
  @retval EFI_BAD_BUFFER_SIZE  The input data can't fit within the spare block. 
                               Offset + *NumBytes > SpareAreaLength.
  @retval EFI_ACCESS_DENIED    No writes have been allocated. 
  @retval EFI_OUT_OF_RESOURCES Cannot allocate enough memory resource.
  @retval EFI_NOT_FOUND        Cannot find FVB protocol by handle.

**/
EFI_STATUS
EFIAPI
FtwWrite (
  IN EFI_FAULT_TOLERANT_WRITE_PROTOCOL     *This,
  IN EFI_LBA                               Lba,
  IN UINTN                                 Offset,
  IN UINTN                                 Length,
  IN VOID                                  *PrivateData,
  IN EFI_HANDLE                            FvBlockHandle,
  IN VOID                                  *Buffer
  )
{
  EFI_STATUS                          Status;
  EFI_FTW_DEVICE                      *FtwDevice;
  EFI_FAULT_TOLERANT_WRITE_HEADER     *Header;
  EFI_FAULT_TOLERANT_WRITE_RECORD     *Record;
  EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL  *Fvb;
  UINTN                               MyLength;
  UINTN                               MyOffset;
  UINTN                               MyBufferSize;
  UINT8                               *MyBuffer;
  UINTN                               SpareBufferSize;
  UINT8                               *SpareBuffer;
  UINTN                               Index;
  UINT8                               *Ptr;
  EFI_PHYSICAL_ADDRESS                FvbPhysicalAddress;
  UINTN                               BlockSize;
  UINTN                               NumberOfBlocks;
  UINTN                               NumberOfWriteBlocks;
  UINTN                               WriteLength;

  FtwDevice = FTW_CONTEXT_FROM_THIS (This);

  Status    = WorkSpaceRefresh (FtwDevice);
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  Header  = FtwDevice->FtwLastWriteHeader;
  Record  = FtwDevice->FtwLastWriteRecord;
  
  if (IsErasedFlashBuffer ((UINT8 *) Header, sizeof (EFI_FAULT_TOLERANT_WRITE_HEADER))) {
    if (PrivateData == NULL) {
      //
      // Ftw Write Header is not allocated.
      // No additional private data, the private data size is zero. Number of record can be set to 1.
      //
      Status = FtwAllocate (This, &gEfiCallerIdGuid, 0, 1);
      if (EFI_ERROR (Status)) {
        return Status;
      }
    } else {
      //
      // Ftw Write Header is not allocated
      // Additional private data is not NULL, the private data size can't be determined.
      //
      DEBUG ((EFI_D_ERROR, "Ftw: no allocates space for write record!\n"));
      DEBUG ((EFI_D_ERROR, "Ftw: Allocate service should be called before Write service!\n"));
      return EFI_NOT_READY;
    }
  }

  //
  // If Record is out of the range of Header, return access denied.
  //
  if (((UINTN)((UINT8 *) Record - (UINT8 *) Header)) > FTW_WRITE_TOTAL_SIZE (Header->NumberOfWrites - 1, Header->PrivateDataSize)) {
    return EFI_ACCESS_DENIED;
  }

  //
  // Check the COMPLETE flag of last write header
  //
  if (Header->Complete == FTW_VALID_STATE) {
    return EFI_ACCESS_DENIED;
  }

  if (Record->DestinationComplete == FTW_VALID_STATE) {
    return EFI_ACCESS_DENIED;
  }

  if ((Record->SpareComplete == FTW_VALID_STATE) && (Record->DestinationComplete != FTW_VALID_STATE)) {
    return EFI_NOT_READY;
  }

  //
  // Get the FVB protocol by handle
  //
  Status = FtwGetFvbByHandle (FvBlockHandle, &Fvb);
  if (EFI_ERROR (Status)) {
    return EFI_NOT_FOUND;
  }

  Status = Fvb->GetPhysicalAddress (Fvb, &FvbPhysicalAddress);
  if (EFI_ERROR (Status)) {
    DEBUG ((EFI_D_ERROR, "Ftw: Write(), Get FVB physical address - %r\n", Status));
    return EFI_ABORTED;
  }

  //
  // Now, one FVB has one type of BlockSize.
  //
  Status = Fvb->GetBlockSize (Fvb, 0, &BlockSize, &NumberOfBlocks);
  if (EFI_ERROR (Status)) {
    DEBUG ((EFI_D_ERROR, "Ftw: Write(), Get block size - %r\n", Status));
    return EFI_ABORTED;
  }

  NumberOfWriteBlocks = FTW_BLOCKS (Offset + Length, BlockSize);
  DEBUG ((EFI_D_INFO, "Ftw: Write(), BlockSize - 0x%x, NumberOfWriteBlock - 0x%x\n", BlockSize, NumberOfWriteBlocks));
  WriteLength = NumberOfWriteBlocks * BlockSize;

  //
  // Check if the input data can fit within the spare block.
  //
  if (WriteLength > FtwDevice->SpareAreaLength) {
    return EFI_BAD_BUFFER_SIZE;
  }

  //
  // Set BootBlockUpdate FLAG if it's updating boot block.
  //
  if (IsBootBlock (FtwDevice, Fvb)) {
    Record->BootBlockUpdate = FTW_VALID_STATE;
    //
    // Boot Block and Spare Block should have same block size and block numbers.
    //
    ASSERT ((BlockSize == FtwDevice->SpareBlockSize) && (NumberOfWriteBlocks == FtwDevice->NumberOfSpareBlock));
  }
  //
  // Write the record to the work space.
  //
  Record->Lba     = Lba;
  Record->Offset  = Offset;
  Record->Length  = Length;
  Record->RelativeOffset = (INT64) (FvbPhysicalAddress + (UINTN) Lba * BlockSize) - (INT64) FtwDevice->SpareAreaAddress;
  if (PrivateData != NULL) {
    CopyMem ((Record + 1), PrivateData, (UINTN) Header->PrivateDataSize);
  }

  MyOffset  = (UINT8 *) Record - FtwDevice->FtwWorkSpace;
  MyLength  = FTW_RECORD_SIZE (Header->PrivateDataSize);

  Status = WriteWorkSpaceData (
             FtwDevice->FtwFvBlock,
             FtwDevice->WorkBlockSize,
             FtwDevice->FtwWorkSpaceLba,
             FtwDevice->FtwWorkSpaceBase + MyOffset,
             MyLength,
             (UINT8 *) Record
             );
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }
  //
  // Record has written to working block, then do the data.
  //
  //
  // Allocate a memory buffer
  //
  MyBufferSize  = WriteLength;
  MyBuffer      = AllocatePool (MyBufferSize);
  if (MyBuffer == NULL) {
    return EFI_OUT_OF_RESOURCES;
  }
  //
  // Read all original data from target block to memory buffer
  //
  Ptr = MyBuffer;
  for (Index = 0; Index < NumberOfWriteBlocks; Index += 1) {
    MyLength  = BlockSize;
    Status    = Fvb->Read (Fvb, Lba + Index, 0, &MyLength, Ptr);
    if (EFI_ERROR (Status)) {
      FreePool (MyBuffer);
      return EFI_ABORTED;
    }

    Ptr += MyLength;
  }
  //
  // Overwrite the updating range data with
  // the input buffer content
  //
  CopyMem (MyBuffer + Offset, Buffer, Length);

  //
  // Try to keep the content of spare block
  // Save spare block into a spare backup memory buffer (Sparebuffer)
  //
  SpareBufferSize = FtwDevice->SpareAreaLength;
  SpareBuffer     = AllocatePool (SpareBufferSize);
  if (SpareBuffer == NULL) {
    FreePool (MyBuffer);
    return EFI_OUT_OF_RESOURCES;
  }

  Ptr = SpareBuffer;
  for (Index = 0; Index < FtwDevice->NumberOfSpareBlock; Index += 1) {
    MyLength = FtwDevice->SpareBlockSize;
    Status = FtwDevice->FtwBackupFvb->Read (
                                        FtwDevice->FtwBackupFvb,
                                        FtwDevice->FtwSpareLba + Index,
                                        0,
                                        &MyLength,
                                        Ptr
                                        );
    if (EFI_ERROR (Status)) {
      FreePool (MyBuffer);
      FreePool (SpareBuffer);
      return EFI_ABORTED;
    }

    Ptr += MyLength;
  }
  //
  // Write the memory buffer to spare block
  // Do not assume Spare Block and Target Block have same block size
  //
  Status  = FtwEraseSpareBlock (FtwDevice);
  Ptr     = MyBuffer;
  for (Index = 0; MyBufferSize > 0; Index += 1) {
    if (MyBufferSize > FtwDevice->SpareBlockSize) {
      MyLength = FtwDevice->SpareBlockSize;
    } else {
      MyLength = MyBufferSize;
    }
    Status = FtwDevice->FtwBackupFvb->Write (
                                        FtwDevice->FtwBackupFvb,
                                        FtwDevice->FtwSpareLba + Index,
                                        0,
                                        &MyLength,
                                        Ptr
                                        );
    if (EFI_ERROR (Status)) {
      FreePool (MyBuffer);
      FreePool (SpareBuffer);
      return EFI_ABORTED;
    }

    Ptr += MyLength;
    MyBufferSize -= MyLength;
  }
  //
  // Free MyBuffer
  //
  FreePool (MyBuffer);

  //
  // Set the SpareComplete in the FTW record,
  //
  MyOffset = (UINT8 *) Record - FtwDevice->FtwWorkSpace;
  Status = FtwUpdateFvState (
            FtwDevice->FtwFvBlock,
            FtwDevice->WorkBlockSize,
            FtwDevice->FtwWorkSpaceLba,
            FtwDevice->FtwWorkSpaceBase + MyOffset,
            SPARE_COMPLETED
            );
  if (EFI_ERROR (Status)) {
    FreePool (SpareBuffer);
    return EFI_ABORTED;
  }

  Record->SpareComplete = FTW_VALID_STATE;

  //
  //  Since the content has already backuped in spare block, the write is
  //  guaranteed to be completed with fault tolerant manner.
  //
  Status = FtwWriteRecord (This, Fvb, BlockSize);
  if (EFI_ERROR (Status)) {
    FreePool (SpareBuffer);
    return EFI_ABORTED;
  }
  //
  // Restore spare backup buffer into spare block , if no failure happened during FtwWrite.
  //
  Status  = FtwEraseSpareBlock (FtwDevice);
  Ptr     = SpareBuffer;
  for (Index = 0; Index < FtwDevice->NumberOfSpareBlock; Index += 1) {
    MyLength = FtwDevice->SpareBlockSize;
    Status = FtwDevice->FtwBackupFvb->Write (
                                        FtwDevice->FtwBackupFvb,
                                        FtwDevice->FtwSpareLba + Index,
                                        0,
                                        &MyLength,
                                        Ptr
                                        );
    if (EFI_ERROR (Status)) {
      FreePool (SpareBuffer);
      return EFI_ABORTED;
    }

    Ptr += MyLength;
  }
  //
  // All success.
  //
  FreePool (SpareBuffer);

  DEBUG (
    (EFI_D_INFO,
    "Ftw: Write() success, (Lba:Offset)=(%lx:0x%x), Length: 0x%x\n",
    Lba,
    Offset,
    Length)
    );

  return EFI_SUCCESS;
}

/**
  Restarts a previously interrupted write. The caller must provide the
  block protocol needed to complete the interrupted write.

  @param This            The pointer to this protocol instance. 
  @param FvBlockHandle   The handle of FVB protocol that provides services for
                         reading, writing, and erasing the target block.

  @retval  EFI_SUCCESS          The function completed successfully
  @retval  EFI_ACCESS_DENIED    No pending writes exist
  @retval  EFI_NOT_FOUND        FVB protocol not found by the handle
  @retval  EFI_ABORTED          The function could not complete successfully

**/
EFI_STATUS
EFIAPI
FtwRestart (
  IN EFI_FAULT_TOLERANT_WRITE_PROTOCOL     *This,
  IN EFI_HANDLE                            FvBlockHandle
  )
{
  EFI_STATUS                          Status;
  EFI_FTW_DEVICE                      *FtwDevice;
  EFI_FAULT_TOLERANT_WRITE_HEADER     *Header;
  EFI_FAULT_TOLERANT_WRITE_RECORD     *Record;
  EFI_FIRMWARE_VOLUME_BLOCK_PROTOCOL  *Fvb;
  UINTN                               BlockSize;
  UINTN                               NumberOfBlocks;

  FtwDevice = FTW_CONTEXT_FROM_THIS (This);

  Status    = WorkSpaceRefresh (FtwDevice);
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  Header  = FtwDevice->FtwLastWriteHeader;
  Record  = FtwDevice->FtwLastWriteRecord;

  //
  // Spare Complete but Destination not complete,
  // Recover the targt block with the spare block.
  //
  Status = FtwGetFvbByHandle (FvBlockHandle, &Fvb);
  if (EFI_ERROR (Status)) {
    return EFI_NOT_FOUND;
  }

  //
  // Now, one FVB has one type of BlockSize
  //
  Status = Fvb->GetBlockSize (Fvb, 0, &BlockSize, &NumberOfBlocks);
  if (EFI_ERROR (Status)) {
    DEBUG ((EFI_D_ERROR, "Ftw: Restart(), Get block size - %r\n", Status));
    return EFI_ABORTED;
  }

  //
  // Check the COMPLETE flag of last write header
  //
  if (Header->Complete == FTW_VALID_STATE) {
    return EFI_ACCESS_DENIED;
  }

  //
  // Check the flags of last write record
  //
  if (Record->DestinationComplete == FTW_VALID_STATE) {
    return EFI_ACCESS_DENIED;
  }

  if ((Record->SpareComplete != FTW_VALID_STATE)) {
    return EFI_ABORTED;
  }

  //
  //  Since the content has already backuped in spare block, the write is
  //  guaranteed to be completed with fault tolerant manner.
  //
  Status = FtwWriteRecord (This, Fvb, BlockSize);
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  //
  // Erase Spare block
  // This is restart, no need to keep spareblock content.
  //
  FtwEraseSpareBlock (FtwDevice);

  DEBUG ((EFI_D_ERROR, "Ftw: Restart() success \n"));
  return EFI_SUCCESS;
}

/**
  Aborts all previous allocated writes.

  @param This                  The pointer to this protocol instance. 

  @retval EFI_SUCCESS          The function completed successfully
  @retval EFI_ABORTED          The function could not complete successfully.
  @retval EFI_NOT_FOUND        No allocated writes exist.

**/
EFI_STATUS
EFIAPI
FtwAbort (
  IN EFI_FAULT_TOLERANT_WRITE_PROTOCOL     *This
  )
{
  EFI_STATUS      Status;
  UINTN           Offset;
  EFI_FTW_DEVICE  *FtwDevice;

  FtwDevice = FTW_CONTEXT_FROM_THIS (This);

  Status    = WorkSpaceRefresh (FtwDevice);
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  if (FtwDevice->FtwLastWriteHeader->HeaderAllocated != FTW_VALID_STATE) {
    return EFI_NOT_FOUND;
  }

  if (FtwDevice->FtwLastWriteHeader->Complete == FTW_VALID_STATE) {
    return EFI_NOT_FOUND;
  }
  //
  // Update the complete state of the header as VALID and abort.
  //
  Offset = (UINT8 *) FtwDevice->FtwLastWriteHeader - FtwDevice->FtwWorkSpace;
  Status = FtwUpdateFvState (
            FtwDevice->FtwFvBlock,
            FtwDevice->WorkBlockSize,
            FtwDevice->FtwWorkSpaceLba,
            FtwDevice->FtwWorkSpaceBase + Offset,
            WRITES_COMPLETED
            );
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  FtwDevice->FtwLastWriteHeader->Complete = FTW_VALID_STATE;

  DEBUG ((EFI_D_ERROR, "Ftw: Abort() success \n"));
  return EFI_SUCCESS;
}

/**
  Starts a target block update. This records information about the write
  in fault tolerant storage and will complete the write in a recoverable
  manner, ensuring at all times that either the original contents or
  the modified contents are available.

  @param This            The pointer to this protocol instance. 
  @param CallerId        The GUID identifying the last write.
  @param Lba             The logical block address of the last write.
  @param Offset          The offset within the block of the last write.
  @param Length          The length of the last write.
  @param PrivateDataSize bytes from the private data
                         stored for this write.
  @param PrivateData     A pointer to a buffer. The function will copy
  @param Complete        A Boolean value with TRUE indicating
                         that the write was completed.

  @retval EFI_SUCCESS           The function completed successfully
  @retval EFI_ABORTED           The function could not complete successfully
  @retval EFI_NOT_FOUND         No allocated writes exist
  @retval EFI_BUFFER_TOO_SMALL  Input buffer is not larget enough

**/
EFI_STATUS
EFIAPI
FtwGetLastWrite (
  IN EFI_FAULT_TOLERANT_WRITE_PROTOCOL     *This,
  OUT EFI_GUID                             *CallerId,
  OUT EFI_LBA                              *Lba,
  OUT UINTN                                *Offset,
  OUT UINTN                                *Length,
  IN OUT UINTN                             *PrivateDataSize,
  OUT VOID                                 *PrivateData,
  OUT BOOLEAN                              *Complete
  )
{
  EFI_STATUS                      Status;
  EFI_FTW_DEVICE                  *FtwDevice;
  EFI_FAULT_TOLERANT_WRITE_HEADER *Header;
  EFI_FAULT_TOLERANT_WRITE_RECORD *Record;

  if (!FeaturePcdGet(PcdFullFtwServiceEnable)) {
    return EFI_UNSUPPORTED;
  }

  FtwDevice = FTW_CONTEXT_FROM_THIS (This);

  Status    = WorkSpaceRefresh (FtwDevice);
  if (EFI_ERROR (Status)) {
    return EFI_ABORTED;
  }

  Header  = FtwDevice->FtwLastWriteHeader;
  Record  = FtwDevice->FtwLastWriteRecord;

  //
  // If Header is incompleted and the last record has completed, then
  // call Abort() to set the Header->Complete FLAG.
  //
  if ((Header->Complete != FTW_VALID_STATE) &&
      (Record->DestinationComplete == FTW_VALID_STATE) &&
      IsLastRecordOfWrites (Header, Record)
        ) {

    Status    = FtwAbort (This);
    *Complete = TRUE;
    return EFI_NOT_FOUND;
  }
  //
  // If there is no write header/record, return not found.
  //
  if (Header->HeaderAllocated != FTW_VALID_STATE) {
    *Complete = TRUE;
    return EFI_NOT_FOUND;
  }
  //
  // If this record SpareComplete has not set, then it can not restart.
  //
  if (Record->SpareComplete != FTW_VALID_STATE) {
    Status = GetPreviousRecordOfWrites (Header, &Record);
    if (EFI_ERROR (Status)) {
      FtwAbort (This);
      *Complete = TRUE;
      return EFI_NOT_FOUND;
    }
    ASSERT (Record != NULL);
  }

  //
  // Fill all the requested values
  //
  CopyMem (CallerId, &Header->CallerId, sizeof (EFI_GUID));
  *Lba      = Record->Lba;
  *Offset   = (UINTN) Record->Offset;
  *Length   = (UINTN) Record->Length;
  *Complete = (BOOLEAN) (Record->DestinationComplete == FTW_VALID_STATE);

  if (*PrivateDataSize < Header->PrivateDataSize) {
    *PrivateDataSize  = (UINTN) Header->PrivateDataSize;
    PrivateData       = NULL;
    Status            = EFI_BUFFER_TOO_SMALL;
  } else {
    *PrivateDataSize = (UINTN) Header->PrivateDataSize;
    CopyMem (PrivateData, Record + 1, *PrivateDataSize);
    Status = EFI_SUCCESS;
  }

  DEBUG ((EFI_D_ERROR, "Ftw: GetLasetWrite() success\n"));

  return Status;
}

