]> git.proxmox.com Git - mirror_edk2.git/blobdiff - MdeModulePkg/Library/PiDxeS3BootScriptLib/BootScriptSave.c
MdeModulePkg: Remove NetLib and Ip4Config Protocol dependency.
[mirror_edk2.git] / MdeModulePkg / Library / PiDxeS3BootScriptLib / BootScriptSave.c
index bc3daad9160ef81298816cee4a5fca3f7bd3d134..586a205a532a22a29258c1b639d2cc5cb26f7626 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Save the S3 data to S3 boot script. \r
  \r
-  Copyright (c) 2006 - 2012, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2006 - 2015, Intel Corporation. All rights reserved.<BR>\r
 \r
   This program and the accompanying materials\r
   are licensed and made available under the terms and conditions\r
@@ -62,7 +62,7 @@ EFI_GUID                         mBootScriptHeaderDataGuid = {
   This is an internal function to add a terminate node the entry, recalculate the table \r
   length and fill into the table. \r
   \r
-  @return the base address of the boot script tble.   \r
+  @return the base address of the boot script table.   \r
  **/\r
 UINT8*\r
 S3BootScriptInternalCloseTable (\r
@@ -163,7 +163,7 @@ SaveBootScriptDataToLockBox (
   run time phase.\r
   \r
   @param  Event   Pointer to this event\r
-  @param  Context Event hanlder private data \r
+  @param  Context Event handler private data \r
  **/\r
 VOID\r
 EFIAPI\r
@@ -423,6 +423,7 @@ S3BootScriptGetBootTimeEntryAddAddress (
      ScriptTableInfo              = (EFI_BOOT_SCRIPT_TABLE_HEADER*)(UINTN)S3TableBase;\r
      ScriptTableInfo->OpCode      = S3_BOOT_SCRIPT_LIB_TABLE_OPCODE;\r
      ScriptTableInfo->Length      = (UINT8) sizeof (EFI_BOOT_SCRIPT_TABLE_HEADER);\r
+     ScriptTableInfo->Version     = BOOT_SCRIPT_TABLE_VERSION;\r
      ScriptTableInfo->TableLength = 0;   // will be calculate at CloseTable\r
      mS3BootScriptTablePtr->TableLength = sizeof (EFI_BOOT_SCRIPT_TABLE_HEADER);\r
      mS3BootScriptTablePtr->TableBase = (UINT8*)(UINTN)S3TableBase;\r
@@ -651,7 +652,7 @@ SyncBootScript (
   how to get the script to run on an S3 resume because the boot script maintained by the lib will be \r
   destroyed.\r
  \r
-  @return the base address of the new copy of the boot script tble.   \r
+  @return the base address of the new copy of the boot script table.   \r
   @note this function could only called in boot time phase\r
 \r
 **/\r
@@ -905,6 +906,8 @@ S3BootScriptSaveMemReadWrite (
 \r
   @retval RETURN_OUT_OF_RESOURCES  Not enough memory for the table do operation.\r
   @retval RETURN_SUCCESS           Opcode is added.\r
+  @note  A known Limitations in the implementation which is 64bits operations are not supported.\r
+\r
 **/\r
 RETURN_STATUS\r
 EFIAPI\r
@@ -920,6 +923,12 @@ S3BootScriptSavePciCfgWrite (
   UINT8                 WidthInByte;\r
   EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE  ScriptPciWrite;\r
 \r
+  if (Width == S3BootScriptWidthUint64 ||\r
+      Width == S3BootScriptWidthFifoUint64 ||\r
+      Width == S3BootScriptWidthFillUint64) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
+\r
   WidthInByte = (UINT8) (0x01 << (Width & 0x03));\r
   Length = (UINT8)(sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE) + (WidthInByte * Count));\r
   \r
@@ -953,6 +962,8 @@ S3BootScriptSavePciCfgWrite (
 \r
   @retval RETURN_OUT_OF_RESOURCES  Not enough memory for the table do operation.\r
   @retval RETURN__SUCCESS           Opcode is added.\r
+  @note  A known Limitations in the implementation which is 64bits operations are not supported.\r
+\r
 **/\r
 RETURN_STATUS\r
 EFIAPI\r
@@ -968,6 +979,12 @@ S3BootScriptSavePciCfgReadWrite (
   UINT8                 WidthInByte;\r
   EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE  ScriptPciReadWrite;\r
 \r
+  if (Width == S3BootScriptWidthUint64 ||\r
+      Width == S3BootScriptWidthFifoUint64 ||\r
+      Width == S3BootScriptWidthFillUint64) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
+\r
   WidthInByte = (UINT8) (0x01 << (Width & 0x03));\r
   Length = (UINT8)(sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE) + (WidthInByte * 2));\r
   \r
@@ -1006,6 +1023,8 @@ S3BootScriptSavePciCfgReadWrite (
 \r
   @retval RETURN_OUT_OF_RESOURCES  Not enough memory for the table do operation.\r
   @retval RETURN_SUCCESS           Opcode is added.\r
+  @note  A known Limitations in the implementation which is non-zero Segment and 64bits operations are not supported.\r
+\r
 **/\r
 RETURN_STATUS\r
 EFIAPI\r
@@ -1021,7 +1040,14 @@ S3BootScriptSavePciCfg2Write (
   UINT8                *Script;\r
   UINT8                 WidthInByte;\r
   EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE  ScriptPciWrite2;\r
-  \r
+\r
+  if (Segment != 0 ||\r
+      Width == S3BootScriptWidthUint64 ||\r
+      Width == S3BootScriptWidthFifoUint64 ||\r
+      Width == S3BootScriptWidthFillUint64) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
+\r
   WidthInByte = (UINT8) (0x01 << (Width & 0x03));\r
   Length = (UINT8)(sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE) + (WidthInByte * Count));\r
   \r
@@ -1057,6 +1083,8 @@ S3BootScriptSavePciCfg2Write (
 \r
   @retval RETURN_OUT_OF_RESOURCES  Not enough memory for the table do operation.\r
   @retval RETURN_SUCCESS           Opcode is added.\r
+  @note  A known Limitations in the implementation which is non-zero Segment and 64bits operations are not supported.\r
+\r
 **/\r
 RETURN_STATUS\r
 EFIAPI\r
@@ -1072,6 +1100,13 @@ S3BootScriptSavePciCfg2ReadWrite (
   UINT8                *Script;\r
   UINT8                 WidthInByte;\r
   EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE  ScriptPciReadWrite2;\r
+\r
+  if (Segment != 0 ||\r
+      Width == S3BootScriptWidthUint64 ||\r
+      Width == S3BootScriptWidthFifoUint64 ||\r
+      Width == S3BootScriptWidthFillUint64) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
   \r
   WidthInByte = (UINT8) (0x01 << (Width & 0x03));\r
   Length = (UINT8)(sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE) + (WidthInByte * 2));\r
@@ -1101,6 +1136,107 @@ S3BootScriptSavePciCfg2ReadWrite (
 \r
   return RETURN_SUCCESS;\r
 }\r
+\r
+/**\r
+  Checks the parameter of S3BootScriptSaveSmbusExecute().\r
+\r
+  This function checks the input parameters of SmbusExecute().  If the input parameters are valid\r
+  for certain SMBus bus protocol, it will return EFI_SUCCESS; otherwise, it will return certain\r
+  error code based on the input SMBus bus protocol.\r
+\r
+  @param  SmBusAddress            Address that encodes the SMBUS Slave Address, SMBUS Command, SMBUS Data Length, \r
+                                  and PEC.\r
+  @param  Operation               Signifies which particular SMBus hardware protocol instance that\r
+                                  it will use to execute the SMBus transactions. This SMBus\r
+                                  hardware protocol is defined by the SMBus Specification and is\r
+                                  not related to EFI.\r
+  @param  Length                  Signifies the number of bytes that this operation will do. The\r
+                                  maximum number of bytes can be revision specific and operation\r
+                                  specific. This field will contain the actual number of bytes that\r
+                                  are executed for this operation. Not all operations require this\r
+                                  argument.\r
+  @param  Buffer                  Contains the value of data to execute to the SMBus slave device.\r
+                                  Not all operations require this argument. The length of this\r
+                                  buffer is identified by Length.\r
+\r
+  @retval EFI_SUCCESS             All the parameters are valid for the corresponding SMBus bus\r
+                                  protocol. \r
+  @retval EFI_INVALID_PARAMETER   Operation is not defined in EFI_SMBUS_OPERATION.\r
+  @retval EFI_INVALID_PARAMETER   Length/Buffer is NULL for operations except for EfiSmbusQuickRead\r
+                                  and EfiSmbusQuickWrite. Length is outside the range of valid\r
+                                  values.\r
+  @retval EFI_UNSUPPORTED         The SMBus operation or PEC is not supported.\r
+  @retval EFI_BUFFER_TOO_SMALL    Buffer is not sufficient for this operation.\r
+\r
+**/\r
+EFI_STATUS\r
+CheckParameters (\r
+  IN     UINTN                    SmBusAddress,\r
+  IN     EFI_SMBUS_OPERATION      Operation,\r
+  IN OUT UINTN                    *Length,\r
+  IN     VOID                     *Buffer\r
+  )\r
+{\r
+  EFI_STATUS  Status;\r
+  UINTN       RequiredLen;\r
+  EFI_SMBUS_DEVICE_COMMAND Command;\r
+  BOOLEAN                  PecCheck;\r
\r
+  Command      = SMBUS_LIB_COMMAND (SmBusAddress);\r
+  PecCheck     = SMBUS_LIB_PEC (SmBusAddress);\r
+  //\r
+  // Set default value to be 2:\r
+  // for SmbusReadWord, SmbusWriteWord and SmbusProcessCall. \r
+  //\r
+  RequiredLen = 2;\r
+  Status      = EFI_SUCCESS;\r
+  switch (Operation) {\r
+    case EfiSmbusQuickRead:\r
+    case EfiSmbusQuickWrite:\r
+      if (PecCheck || Command != 0) {\r
+        return EFI_UNSUPPORTED;\r
+      }\r
+      break;\r
+    case EfiSmbusReceiveByte:\r
+    case EfiSmbusSendByte:\r
+      if (Command != 0) {\r
+        return EFI_UNSUPPORTED;\r
+      }\r
+      //\r
+      // Cascade to check length parameter.\r
+      //\r
+    case EfiSmbusReadByte:\r
+    case EfiSmbusWriteByte:\r
+      RequiredLen = 1;\r
+      //\r
+      // Cascade to check length parameter.\r
+      //\r
+    case EfiSmbusReadWord:\r
+    case EfiSmbusWriteWord:\r
+    case EfiSmbusProcessCall:\r
+      if (Buffer == NULL || Length == NULL) {\r
+        return EFI_INVALID_PARAMETER;\r
+      } else if (*Length < RequiredLen) {\r
+        Status = EFI_BUFFER_TOO_SMALL;\r
+      }\r
+      *Length = RequiredLen;\r
+      break;\r
+    case EfiSmbusReadBlock:\r
+    case EfiSmbusWriteBlock:\r
+    case EfiSmbusBWBRProcessCall:\r
+      if ((Buffer == NULL) || \r
+          (Length == NULL) || \r
+          (*Length < MIN_SMBUS_BLOCK_LEN) ||\r
+          (*Length > MAX_SMBUS_BLOCK_LEN)) {\r
+        return EFI_INVALID_PARAMETER;\r
+      }\r
+      break;\r
+    default:\r
+      return EFI_INVALID_PARAMETER;\r
+  }\r
+  return Status;\r
+}\r
+\r
 /**\r
   Adds a record for an SMBus command execution into a specified boot script table.\r
 \r
@@ -1122,11 +1258,24 @@ S3BootScriptSaveSmbusExecute (
   IN  VOID                              *Buffer\r
   )\r
 {\r
+  EFI_STATUS            Status;\r
+  UINTN                 BufferLength;\r
   UINT8                 DataSize;\r
   UINT8                *Script;\r
   EFI_BOOT_SCRIPT_SMBUS_EXECUTE  ScriptSmbusExecute;\r
 \r
-  DataSize = (UINT8)(sizeof (EFI_BOOT_SCRIPT_SMBUS_EXECUTE) + (*Length));\r
+  if (Length == NULL) {\r
+    BufferLength = 0;\r
+  } else {\r
+    BufferLength = *Length;\r
+  }\r
+\r
+  Status = CheckParameters (SmBusAddress, Operation, &BufferLength, Buffer);\r
+  if (EFI_ERROR (Status)) {\r
+    return Status;\r
+  }\r
+\r
+  DataSize = (UINT8)(sizeof (EFI_BOOT_SCRIPT_SMBUS_EXECUTE) + BufferLength);\r
   \r
   Script = S3BootScriptGetEntryAddAddress (DataSize);\r
   if (Script == NULL) {\r
@@ -1139,13 +1288,13 @@ S3BootScriptSaveSmbusExecute (
   ScriptSmbusExecute.Length       = DataSize;\r
   ScriptSmbusExecute.SmBusAddress = (UINT64) SmBusAddress;\r
   ScriptSmbusExecute.Operation    = Operation;\r
-  ScriptSmbusExecute.DataSize     = (UINT32) *Length;\r
+  ScriptSmbusExecute.DataSize     = (UINT32) BufferLength;\r
 \r
   CopyMem ((VOID*)Script, (VOID*)&ScriptSmbusExecute, sizeof (EFI_BOOT_SCRIPT_SMBUS_EXECUTE));\r
   CopyMem (\r
     (VOID*)(Script + sizeof (EFI_BOOT_SCRIPT_SMBUS_EXECUTE)),\r
     Buffer,\r
-    (*Length)\r
+    BufferLength\r
     );\r
 \r
   SyncBootScript (Script);\r
@@ -1232,7 +1381,12 @@ S3BootScriptSaveDispatch2 (
 /**\r
   Adds a record for memory reads of the memory location and continues when the exit criteria is\r
   satisfied or after a defined duration.\r
-  \r
+\r
+  Please aware, below interface is different with PI specification, Vol 5:\r
+  EFI_S3_SAVE_STATE_PROTOCOL.Write() for EFI_BOOT_SCRIPT_MEM_POLL_OPCODE.\r
+  "Duration" below is microseconds, while "Delay" in PI specification means\r
+  the number of 100ns units to poll.\r
+\r
   @param Width     The width of the memory operations.\r
   @param Address   The base address of the memory operations.\r
   @param BitMask   A pointer to the bit mask to be AND-ed with the data read from the register.\r
@@ -1461,6 +1615,7 @@ S3BootScriptSaveIoPoll (
 \r
  @retval RETURN_OUT_OF_RESOURCES  Not enough memory for the table do operation.\r
  @retval RETURN_SUCCESS           Opcode is added.\r
+  @note  A known Limitations in the implementation which is 64bits operations are not supported.\r
 \r
 **/\r
 RETURN_STATUS\r
@@ -1478,6 +1633,12 @@ S3BootScriptSavePciPoll (
   UINT8                    Length;\r
   EFI_BOOT_SCRIPT_PCI_CONFIG_POLL  ScriptPciPoll;\r
 \r
+  if (Width == S3BootScriptWidthUint64 ||\r
+      Width == S3BootScriptWidthFifoUint64 ||\r
+      Width == S3BootScriptWidthFillUint64) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
+\r
   WidthInByte = (UINT8) (0x01 << (Width & 0x03));\r
   Length = (UINT8)(sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG_POLL) + (WidthInByte * 2));\r
   \r
@@ -1517,9 +1678,8 @@ S3BootScriptSavePciPoll (
 \r
  @retval RETURN_OUT_OF_RESOURCES  Not enough memory for the table do operation.\r
  @retval RETURN_SUCCESS           Opcode is added.\r
- @note   A known Limitations in the implementation: When interpreting the opcode  EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE_OPCODE\r
-         EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE_OPCODE and EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL_OPCODE, the 'Segment' parameter is assumed as \r
-         Zero, or else, assert.\r
+  @note  A known Limitations in the implementation which is non-zero Segment and 64bits operations are not supported.\r
+\r
 **/\r
 RETURN_STATUS\r
 EFIAPI\r
@@ -1536,7 +1696,14 @@ S3BootScriptSavePci2Poll (
   UINT8                   *Script;\r
   UINT8                    Length;\r
   EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL  ScriptPci2Poll;\r
-  \r
+\r
+  if (Segment != 0 ||\r
+      Width == S3BootScriptWidthUint64 ||\r
+      Width == S3BootScriptWidthFifoUint64 ||\r
+      Width == S3BootScriptWidthFillUint64) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
+\r
   WidthInByte = (UINT8) (0x01 << (Width & 0x03));\r
   Length = (UINT8)(sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL) + (WidthInByte * 2));\r
   \r