]> git.proxmox.com Git - mirror_edk2.git/blobdiff - NetworkPkg/IScsiDxe/IScsiConfig.c
Update for NetworkPkg.
[mirror_edk2.git] / NetworkPkg / IScsiDxe / IScsiConfig.c
index 3c299be94928354ce8c58ce3b3759f3d9b59bcb2..eea73a8ff15361a05806ae364f8fe665459f6f82 100644 (file)
@@ -14,7 +14,6 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
 \r
 #include "IScsiImpl.h"\r
 \r
-EFI_GUID        mVendorGuid              = ISCSI_CONFIG_GUID;\r
 CHAR16          mVendorStorageName[]     = L"ISCSI_CONFIG_IFR_NVDATA";\r
 BOOLEAN         mIScsiDeviceListUpdated  = FALSE;\r
 UINTN           mNumberOfIScsiDevices    = 0;\r
@@ -30,10 +29,7 @@ HII_VENDOR_DEVICE_PATH  mIScsiHiiVendorDevicePath = {
         (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8)\r
       }\r
     },\r
-    //\r
-    // {49D7B73E-143D-4716-977B-C45F1CB038CC}\r
-    //\r
-    { 0x49d7b73e, 0x143d, 0x4716, { 0x97, 0x7b, 0xc4, 0x5f, 0x1c, 0xb0, 0x38, 0xcc } }\r
+    ISCSI_CONFIG_GUID\r
   },\r
   {\r
     END_DEVICE_PATH_TYPE,\r
@@ -421,15 +417,16 @@ IScsiConvertAttemptConfigDataToIfrNvData (
   AsciiStrToUnicodeStr (Attempt->AttemptName, IfrNvData->AttemptName);\r
 }\r
 \r
-\r
 /**\r
   Convert the IFR data to iSCSI configuration data.\r
 \r
-  @param[in]       IfrNvData              The IFR nv data.\r
+  @param[in]       IfrNvData              Point to ISCSI_CONFIG_IFR_NVDATA.\r
   @param[in, out]  Attempt                The iSCSI attempt config data.\r
 \r
   @retval EFI_INVALID_PARAMETER  Any input or configured parameter is invalid.\r
   @retval EFI_NOT_FOUND          Cannot find the corresponding variable.\r
+  @retval EFI_OUT_OF_RESOURCES   The operation is failed due to lack of resources.\r
+  @retval EFI_ABORTED            The operation is aborted.\r
   @retval EFI_SUCCESS            The operation is completed successfully.\r
 \r
 **/\r
@@ -451,6 +448,11 @@ IScsiConvertIfrNvDataToAttemptConfigData (
   CHAR16                      IpMode[64];\r
   ISCSI_NIC_INFO              *NicInfo;\r
   EFI_INPUT_KEY               Key;\r
+  UINT8                       *AttemptConfigOrder;\r
+  UINTN                       AttemptConfigOrderSize;\r
+  UINT8                       *AttemptOrderTmp;\r
+  UINTN                       TotalNumber;\r
+  EFI_STATUS                  Status;\r
 \r
   if (IfrNvData == NULL || Attempt == NULL) {\r
     return EFI_INVALID_PARAMETER;\r
@@ -614,6 +616,61 @@ IScsiConvertIfrNvDataToAttemptConfigData (
     }\r
   }\r
 \r
+  //\r
+  // Update the iSCSI Mode data and record it in attempt help info.\r
+  //\r
+  Attempt->SessionConfigData.Enabled = IfrNvData->Enabled;\r
+  if (IfrNvData->Enabled == ISCSI_DISABLED) {\r
+    UnicodeSPrint (IScsiMode, 64, L"Disabled");\r
+  } else if (IfrNvData->Enabled == ISCSI_ENABLED) {\r
+    UnicodeSPrint (IScsiMode, 64, L"Enabled");\r
+  } else if (IfrNvData->Enabled == ISCSI_ENABLED_FOR_MPIO) {\r
+    UnicodeSPrint (IScsiMode, 64, L"Enabled for MPIO");\r
+  }\r
+\r
+  if (IfrNvData->IpMode == IP_MODE_IP4) {\r
+    UnicodeSPrint (IpMode, 64, L"IP4");\r
+  } else if (IfrNvData->IpMode == IP_MODE_IP6) {\r
+    UnicodeSPrint (IpMode, 64, L"IP6");\r
+  } else if (IfrNvData->IpMode == IP_MODE_AUTOCONFIG) {\r
+    UnicodeSPrint (IpMode, 64, L"Autoconfigure");\r
+  }\r
+\r
+  NicInfo = IScsiGetNicInfoByIndex (Attempt->NicIndex);\r
+  if (NicInfo == NULL) {\r
+    return EFI_NOT_FOUND;\r
+  }\r
+\r
+  MacString = (CHAR16 *) AllocateZeroPool (ISCSI_MAX_MAC_STRING_LEN * sizeof (CHAR16));\r
+  if (MacString == NULL) {\r
+    return EFI_OUT_OF_RESOURCES;\r
+  }\r
+\r
+  AsciiStrToUnicodeStr (Attempt->MacString, MacString);\r
+\r
+  UnicodeSPrint (\r
+    mPrivate->PortString,\r
+    (UINTN) ISCSI_NAME_IFR_MAX_SIZE,\r
+    L"MAC: %s, PFA: Bus %d | Dev %d | Func %d, iSCSI mode: %s, IP version: %s",\r
+    MacString,\r
+    NicInfo->BusNumber,\r
+    NicInfo->DeviceNumber,\r
+    NicInfo->FunctionNumber,\r
+    IScsiMode,\r
+    IpMode\r
+    );\r
+\r
+  Attempt->AttemptTitleHelpToken = HiiSetString (\r
+                                     mCallbackInfo->RegisteredHandle,\r
+                                     Attempt->AttemptTitleHelpToken,\r
+                                     mPrivate->PortString,\r
+                                     NULL\r
+                                     );\r
+  if (Attempt->AttemptTitleHelpToken == 0) {\r
+    FreePool (MacString);\r
+    return EFI_OUT_OF_RESOURCES;\r
+  }\r
+\r
   //\r
   // Check whether this attempt is an existing one.\r
   //\r
@@ -683,7 +740,70 @@ IScsiConvertIfrNvDataToAttemptConfigData (
       }\r
     }\r
 \r
-  } else if (ExistAttempt == NULL && IfrNvData->Enabled != ISCSI_DISABLED) {\r
+  } else if (ExistAttempt == NULL) {\r
+    //\r
+    // When a new attempt is created, pointer of the attempt is saved to\r
+    // mPrivate->NewAttempt, and also saved to mCallbackInfo->Current in\r
+    // IScsiConfigProcessDefault. If input Attempt does not match any existing\r
+    // attempt, it should be a new created attempt. Save it to system now.\r
+    //    \r
+    ASSERT (Attempt == mPrivate->NewAttempt);\r
+\r
+    //\r
+    // Save current order number for this attempt.\r
+    //\r
+    AttemptConfigOrder = IScsiGetVariableAndSize (\r
+                           L"AttemptOrder",\r
+                           &gIScsiConfigGuid,\r
+                           &AttemptConfigOrderSize\r
+                           );\r
+\r
+    TotalNumber = AttemptConfigOrderSize / sizeof (UINT8);\r
+    TotalNumber++;\r
+\r
+    //\r
+    // Append the new created attempt order to the end.\r
+    //\r
+    AttemptOrderTmp = AllocateZeroPool (TotalNumber * sizeof (UINT8));\r
+    if (AttemptOrderTmp == NULL) {\r
+      if (AttemptConfigOrder != NULL) {\r
+        FreePool (AttemptConfigOrder);\r
+      }\r
+      return EFI_OUT_OF_RESOURCES;\r
+    }\r
+\r
+    if (AttemptConfigOrder != NULL) {\r
+      CopyMem (AttemptOrderTmp, AttemptConfigOrder, AttemptConfigOrderSize);\r
+      FreePool (AttemptConfigOrder);\r
+    }\r
+\r
+    AttemptOrderTmp[TotalNumber - 1] = Attempt->AttemptConfigIndex;\r
+    AttemptConfigOrder               = AttemptOrderTmp;\r
+    AttemptConfigOrderSize           = TotalNumber * sizeof (UINT8);\r
+\r
+    Status = gRT->SetVariable (\r
+                    L"AttemptOrder",\r
+                    &gIScsiConfigGuid,\r
+                    EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_NON_VOLATILE,\r
+                    AttemptConfigOrderSize,\r
+                    AttemptConfigOrder\r
+                    );\r
+    FreePool (AttemptConfigOrder);\r
+    if (EFI_ERROR (Status)) {\r
+      return Status;\r
+    }\r
+\r
+    //\r
+    // Insert new created attempt to array.\r
+    //\r
+    InsertTailList (&mPrivate->AttemptConfigs, &Attempt->Link);\r
+    mPrivate->AttemptCount++;\r
+    //\r
+    // Reset mPrivate->NewAttempt to NULL, which indicates none attempt is created\r
+    // but not saved now.\r
+    //\r
+    mPrivate->NewAttempt = NULL;\r
+\r
     if (IfrNvData->Enabled == ISCSI_ENABLED_FOR_MPIO) {\r
       //\r
       // This new Attempt is enabled for MPIO; enable the multipath mode.\r
@@ -693,61 +813,8 @@ IScsiConvertIfrNvDataToAttemptConfigData (
     } else if (IfrNvData->Enabled == ISCSI_ENABLED) {\r
       mPrivate->SinglePathCount++;\r
     }\r
-  }\r
-\r
-  //\r
-  // Update the iSCSI Mode data and record it in attempt help info.\r
-  //\r
-  Attempt->SessionConfigData.Enabled = IfrNvData->Enabled;\r
-  if (IfrNvData->Enabled == ISCSI_DISABLED) {\r
-    UnicodeSPrint (IScsiMode, 64, L"Disabled");\r
-  } else if (IfrNvData->Enabled == ISCSI_ENABLED) {\r
-    UnicodeSPrint (IScsiMode, 64, L"Enabled");\r
-  } else if (IfrNvData->Enabled == ISCSI_ENABLED_FOR_MPIO) {\r
-    UnicodeSPrint (IScsiMode, 64, L"Enabled for MPIO");\r
-  }\r
-\r
-  if (IfrNvData->IpMode == IP_MODE_IP4) {\r
-    UnicodeSPrint (IpMode, 64, L"IP4");\r
-  } else if (IfrNvData->IpMode == IP_MODE_IP6) {\r
-    UnicodeSPrint (IpMode, 64, L"IP6");\r
-  } else if (IfrNvData->IpMode == IP_MODE_AUTOCONFIG) {\r
-    UnicodeSPrint (IpMode, 64, L"Autoconfigure");\r
-  }\r
-\r
-  NicInfo = IScsiGetNicInfoByIndex (Attempt->NicIndex);\r
-  if (NicInfo == NULL) {\r
-    return EFI_NOT_FOUND;\r
-  }\r
-\r
-  MacString = (CHAR16 *) AllocateZeroPool (ISCSI_MAX_MAC_STRING_LEN * sizeof (CHAR16));\r
-  if (MacString == NULL) {\r
-    return EFI_OUT_OF_RESOURCES;\r
-  }\r
-\r
-  AsciiStrToUnicodeStr (Attempt->MacString, MacString);\r
-\r
-  UnicodeSPrint (\r
-    mPrivate->PortString,\r
-    (UINTN) ISCSI_NAME_IFR_MAX_SIZE,\r
-    L"MAC: %s, PFA: Bus %d | Dev %d | Func %d, iSCSI mode: %s, IP version: %s",\r
-    MacString,\r
-    NicInfo->BusNumber,\r
-    NicInfo->DeviceNumber,\r
-    NicInfo->FunctionNumber,\r
-    IScsiMode,\r
-    IpMode\r
-    );\r
 \r
-  Attempt->AttemptTitleHelpToken = HiiSetString (\r
-                                     mCallbackInfo->RegisteredHandle,\r
-                                     Attempt->AttemptTitleHelpToken,\r
-                                     mPrivate->PortString,\r
-                                     NULL\r
-                                     );\r
-  if (Attempt->AttemptTitleHelpToken == 0) {\r
-    FreePool (MacString);\r
-    return EFI_OUT_OF_RESOURCES;\r
+    IScsiConfigUpdateAttempt ();\r
   }\r
 \r
   //\r
@@ -919,7 +986,7 @@ IScsiConfigAddAttempt (
       MacString\r
       );\r
 \r
-    UnicodeSPrint (mPrivate->PortString, (UINTN) ISCSI_NAME_IFR_MAX_SIZE, L"Port %s", MacString);\r
+    UnicodeSPrint (mPrivate->PortString, (UINTN) ISCSI_NAME_IFR_MAX_SIZE, L"MAC %s", MacString);\r
     PortTitleToken = HiiSetString (\r
                        mCallbackInfo->RegisteredHandle,\r
                        0,\r
@@ -957,7 +1024,7 @@ IScsiConfigAddAttempt (
 \r
   Status = HiiUpdateForm (\r
              mCallbackInfo->RegisteredHandle, // HII handle\r
-             &mVendorGuid,                    // Formset GUID\r
+             &gIScsiConfigGuid,               // Formset GUID\r
              FORMID_MAC_FORM,                 // Form ID\r
              StartOpCodeHandle,               // Label for where to insert opcodes\r
              EndOpCodeHandle                  // Replace data\r
@@ -1027,7 +1094,7 @@ IScsiConfigUpdateAttempt (
 \r
   HiiUpdateForm (\r
     mCallbackInfo->RegisteredHandle, // HII handle\r
-    &mVendorGuid,                    // Formset GUID\r
+    &gIScsiConfigGuid,               // Formset GUID\r
     FORMID_MAIN_FORM,                // Form ID\r
     StartOpCodeHandle,               // Label for where to insert opcodes\r
     EndOpCodeHandle                  // Replace data\r
@@ -1072,7 +1139,7 @@ IScsiConfigDeleteAttempts (
 \r
   AttemptConfigOrder = IScsiGetVariableAndSize (\r
                          L"AttemptOrder",\r
-                         &mVendorGuid,\r
+                         &gIScsiConfigGuid,\r
                          &AttemptConfigOrderSize\r
                          );\r
   if ((AttemptConfigOrder == NULL) || (AttemptConfigOrderSize == 0)) {\r
@@ -1081,7 +1148,8 @@ IScsiConfigDeleteAttempts (
 \r
   AttemptNewOrder = AllocateZeroPool (AttemptConfigOrderSize);\r
   if (AttemptNewOrder == NULL) {\r
-    return EFI_OUT_OF_RESOURCES;\r
+    Status = EFI_OUT_OF_RESOURCES;\r
+    goto Error;\r
   }\r
 \r
   Total    = AttemptConfigOrderSize / sizeof (UINT8);\r
@@ -1186,15 +1254,20 @@ IScsiConfigDeleteAttempts (
   //\r
   Status = gRT->SetVariable (\r
                   L"AttemptOrder",\r
-                  &mVendorGuid,\r
+                  &gIScsiConfigGuid,\r
                   Attribute,\r
                   NewTotal * sizeof (UINT8),\r
                   AttemptNewOrder\r
                   );\r
 \r
 Error:\r
-  FreePool (AttemptConfigOrder);\r
-  FreePool (AttemptNewOrder);\r
+  if (AttemptConfigOrder != NULL) {\r
+    FreePool (AttemptConfigOrder);\r
+  }\r
+\r
+  if (AttemptNewOrder != NULL) {\r
+    FreePool (AttemptNewOrder);\r
+  }\r
   \r
   return Status;\r
 }\r
@@ -1240,7 +1313,7 @@ IScsiConfigDisplayDeleteAttempts (
 \r
   AttemptConfigOrder = IScsiGetVariableAndSize (\r
                          L"AttemptOrder",\r
-                         &mVendorGuid,\r
+                         &gIScsiConfigGuid,\r
                          &AttemptConfigOrderSize\r
                          );\r
   if (AttemptConfigOrder != NULL) {\r
@@ -1277,7 +1350,7 @@ IScsiConfigDisplayDeleteAttempts (
 \r
   Status = HiiUpdateForm (\r
              mCallbackInfo->RegisteredHandle, // HII handle\r
-             &mVendorGuid,                    // Formset GUID\r
+             &gIScsiConfigGuid,               // Formset GUID\r
              FORMID_DELETE_FORM,              // Form ID\r
              StartOpCodeHandle,               // Label for where to insert opcodes\r
              EndOpCodeHandle                  // Replace data\r
@@ -1377,7 +1450,7 @@ IScsiConfigDisplayOrderAttempts (
 Exit:\r
   Status = HiiUpdateForm (\r
              mCallbackInfo->RegisteredHandle, // HII handle\r
-             &mVendorGuid,                    // Formset GUID\r
+             &gIScsiConfigGuid,               // Formset GUID\r
              FORMID_ORDER_FORM,               // Form ID\r
              StartOpCodeHandle,               // Label for where to insert opcodes\r
              EndOpCodeHandle                  // Replace data\r
@@ -1421,7 +1494,7 @@ IScsiConfigOrderAttempts (
 \r
   AttemptConfigOrder = IScsiGetVariableAndSize (\r
                          L"AttemptOrder",\r
-                         &mVendorGuid,\r
+                         &gIScsiConfigGuid,\r
                          &AttemptConfigOrderSize\r
                          );\r
   if (AttemptConfigOrder == NULL) {\r
@@ -1483,7 +1556,7 @@ IScsiConfigOrderAttempts (
 \r
   Status = gRT->SetVariable (\r
                   L"AttemptOrder",\r
-                  &mVendorGuid,\r
+                  &gIScsiConfigGuid,\r
                   EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_NON_VOLATILE,\r
                   AttemptConfigOrderSize,\r
                   AttemptConfigOrderTmp\r
@@ -1530,10 +1603,11 @@ IScsiConfigProcessDefault (
   UINT8                       *AttemptConfigOrder;\r
   UINTN                       AttemptConfigOrderSize;\r
   UINTN                       TotalNumber;\r
-  UINT8                       *AttemptOrderTmp;\r
   UINTN                       Index;\r
-  EFI_STATUS                  Status;\r
 \r
+  //\r
+  // Is User creating a new attempt?\r
+  //\r
   NewAttempt = FALSE;\r
 \r
   if ((KeyValue >= KEY_MAC_ENTRY_BASE) &&\r
@@ -1555,6 +1629,14 @@ IScsiConfigProcessDefault (
     //\r
     return EFI_SUCCESS;\r
   }\r
+  \r
+  //\r
+  // Free any attempt that is previously created but not saved to system.\r
+  //\r
+  if (mPrivate->NewAttempt != NULL) {\r
+    FreePool (mPrivate->NewAttempt);\r
+    mPrivate->NewAttempt = NULL;\r
+  }\r
 \r
   if (NewAttempt) {\r
     //\r
@@ -1567,7 +1649,7 @@ IScsiConfigProcessDefault (
     }\r
     \r
     //\r
-    // Create the new attempt and save to NVR.\r
+    // Create new attempt.\r
     //\r
 \r
     AttemptConfigData = AllocateZeroPool (sizeof (ISCSI_ATTEMPT_CONFIG_NVDATA));\r
@@ -1588,7 +1670,7 @@ IScsiConfigProcessDefault (
     //\r
     AttemptConfigOrder = IScsiGetVariableAndSize (\r
                            L"AttemptOrder",\r
-                           &mVendorGuid,\r
+                           &gIScsiConfigGuid,\r
                            &AttemptConfigOrderSize\r
                            );\r
 \r
@@ -1613,46 +1695,14 @@ IScsiConfigProcessDefault (
     TotalNumber++;\r
 \r
     //\r
-    // Append the new created attempt order to the end.\r
+    // Record the mapping between attempt order and attempt's configdata.\r
     //\r
-    AttemptOrderTmp = AllocateZeroPool (TotalNumber * sizeof (UINT8));\r
-    if (AttemptOrderTmp == NULL) {\r
-      FreePool (AttemptConfigData);\r
-      if (AttemptConfigOrder != NULL) {\r
-        FreePool (AttemptConfigOrder);\r
-      }\r
-      return EFI_OUT_OF_RESOURCES;\r
-    }\r
+    AttemptConfigData->AttemptConfigIndex  = CurrentAttemptConfigIndex;\r
 \r
     if (AttemptConfigOrder != NULL) {\r
-      CopyMem (AttemptOrderTmp, AttemptConfigOrder, AttemptConfigOrderSize);\r
-      FreePool (AttemptConfigOrder);      \r
-    }\r
-\r
-    AttemptOrderTmp[TotalNumber - 1] = CurrentAttemptConfigIndex;    \r
-    AttemptConfigOrder               = AttemptOrderTmp;\r
-    AttemptConfigOrderSize           = TotalNumber * sizeof (UINT8);\r
-\r
-    Status = gRT->SetVariable (\r
-                    L"AttemptOrder",\r
-                    &mVendorGuid,\r
-                    EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_NON_VOLATILE,\r
-                    AttemptConfigOrderSize,\r
-                    AttemptConfigOrder\r
-                    );\r
-    FreePool (AttemptConfigOrder);\r
-    if (EFI_ERROR (Status)) {\r
-      FreePool (AttemptConfigData);\r
-      return Status;\r
+      FreePool (AttemptConfigOrder);\r
     }\r
 \r
-    //\r
-    // Record the mapping between attempt order and attempt's configdata.\r
-    //\r
-    AttemptConfigData->AttemptConfigIndex  = CurrentAttemptConfigIndex;\r
-    InsertTailList (&mPrivate->AttemptConfigs, &AttemptConfigData->Link);\r
-    mPrivate->AttemptCount++;\r
-\r
     //\r
     // Record the MAC info in Config Data.\r
     //\r
@@ -1708,6 +1758,13 @@ IScsiConfigProcessDefault (
       );\r
     UnicodeStrToAsciiStr (mPrivate->PortString, AttemptConfigData->AttemptName);\r
 \r
+    //\r
+    // Save the created Attempt temporarily. If user does not save the attempt\r
+    // by press 'KEY_SAVE_ATTEMPT_CONFIG' later, iSCSI driver would know that\r
+    // and free resources.\r
+    //\r
+    mPrivate->NewAttempt = (VOID *) AttemptConfigData;\r
+\r
   } else {\r
     //\r
     // Determine which Attempt user has selected to configure.\r
@@ -1734,10 +1791,11 @@ IScsiConfigProcessDefault (
   \r
   IScsiConvertAttemptConfigDataToIfrNvData (AttemptConfigData, IfrNvData);\r
 \r
+  //\r
+  // Update current attempt to be a new created attempt or an existing attempt.\r
+  //\r
   mCallbackInfo->Current = AttemptConfigData;\r
 \r
-  IScsiConfigUpdateAttempt ();\r
-\r
   return EFI_SUCCESS;\r
 }\r
 \r
@@ -1837,7 +1895,7 @@ IScsiFormExtractConfig (
   }\r
 \r
   *Progress = Request;\r
-  if ((Request != NULL) && !HiiIsConfigHdrMatch (Request, &mVendorGuid, mVendorStorageName)) {\r
+  if ((Request != NULL) && !HiiIsConfigHdrMatch (Request, &gIScsiConfigGuid, mVendorStorageName)) {\r
     return EFI_NOT_FOUND;\r
   }\r
 \r
@@ -1881,7 +1939,7 @@ IScsiFormExtractConfig (
     // Allocate and fill a buffer large enough to hold the <ConfigHdr> template\r
     // followed by "&OFFSET=0&WIDTH=WWWWWWWWWWWWWWWW" followed by a Null-terminator\r
     //\r
-    ConfigRequestHdr = HiiConstructConfigHdr (&mVendorGuid, mVendorStorageName, Private->DriverHandle);\r
+    ConfigRequestHdr = HiiConstructConfigHdr (&gIScsiConfigGuid, mVendorStorageName, Private->DriverHandle);\r
     Size = (StrLen (ConfigRequestHdr) + 32 + 1) * sizeof (CHAR16);\r
     ConfigRequest = AllocateZeroPool (Size);\r
     ASSERT (ConfigRequest != NULL);\r
@@ -1977,7 +2035,7 @@ IScsiFormRouteConfig (
   // Check routing data in <ConfigHdr>.\r
   // Note: if only one Storage is used, then this checking could be skipped.\r
   //\r
-  if (!HiiIsConfigHdrMatch (Configuration, &mVendorGuid, mVendorStorageName)) {\r
+  if (!HiiIsConfigHdrMatch (Configuration, &gIScsiConfigGuid, mVendorStorageName)) {\r
     *Progress = Configuration;\r
     return EFI_NOT_FOUND;\r
   }\r
@@ -2045,37 +2103,75 @@ IScsiFormCallback (
     return EFI_SUCCESS;\r
   }\r
 \r
-  if (Action == EFI_BROWSER_ACTION_CHANGING) {\r
-    if (This == NULL || Value == NULL || ActionRequest == NULL) {\r
-      return EFI_INVALID_PARAMETER;\r
-    }\r
-\r
-    Private = ISCSI_FORM_CALLBACK_INFO_FROM_FORM_CALLBACK (This);\r
-\r
+  if ((Action != EFI_BROWSER_ACTION_CHANGING) && (Action != EFI_BROWSER_ACTION_CHANGED)) {\r
     //\r
-    // Retrieve uncommitted data from Browser\r
+    // All other type return unsupported.\r
     //\r
+    return EFI_UNSUPPORTED;\r
+  }\r
 \r
-    BufferSize = sizeof (ISCSI_CONFIG_IFR_NVDATA);\r
-    IfrNvData = AllocateZeroPool (BufferSize);\r
-    if (IfrNvData == NULL) {\r
-      return EFI_OUT_OF_RESOURCES;\r
-    }\r
-\r
-    IScsiName = (CHAR8 *) AllocateZeroPool (ISCSI_NAME_MAX_SIZE);\r
-    if (IScsiName == NULL) {\r
-      FreePool (IfrNvData);\r
-      return EFI_OUT_OF_RESOURCES;\r
-    }\r
-\r
-    Status = EFI_SUCCESS;\r
+  if ((Value == NULL) || (ActionRequest == NULL)) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
 \r
-    ZeroMem (&OldIfrNvData, BufferSize);\r
+  Private = ISCSI_FORM_CALLBACK_INFO_FROM_FORM_CALLBACK (This);\r
+  \r
+  //\r
+  // Retrieve uncommitted data from Browser\r
+  //\r
+  \r
+  BufferSize = sizeof (ISCSI_CONFIG_IFR_NVDATA);\r
+  IfrNvData = AllocateZeroPool (BufferSize);\r
+  if (IfrNvData == NULL) {\r
+    return EFI_OUT_OF_RESOURCES;\r
+  }\r
+  \r
+  IScsiName = (CHAR8 *) AllocateZeroPool (ISCSI_NAME_MAX_SIZE);\r
+  if (IScsiName == NULL) {\r
+    FreePool (IfrNvData);\r
+    return EFI_OUT_OF_RESOURCES;\r
+  }\r
+  \r
+  Status = EFI_SUCCESS;\r
+  \r
+  ZeroMem (&OldIfrNvData, BufferSize);\r
+  \r
+  HiiGetBrowserData (NULL, NULL, BufferSize, (UINT8 *) IfrNvData);\r
+  \r
+  CopyMem (&OldIfrNvData, IfrNvData, BufferSize);\r
 \r
-    HiiGetBrowserData (NULL, NULL, BufferSize, (UINT8 *) IfrNvData);\r
+  if (Action == EFI_BROWSER_ACTION_CHANGING) {\r
+    switch (QuestionId) {\r
+    case KEY_ADD_ATTEMPT:\r
+      Status = IScsiConfigAddAttempt ();\r
+      break;\r
 \r
-    CopyMem (&OldIfrNvData, IfrNvData, BufferSize);\r
+    case KEY_DELETE_ATTEMPT:\r
+      CopyMem (\r
+        OldIfrNvData.DeleteAttemptList,\r
+        IfrNvData->DeleteAttemptList,\r
+        sizeof (IfrNvData->DeleteAttemptList)\r
+        );\r
+      Status = IScsiConfigDisplayDeleteAttempts (IfrNvData);\r
+      break;\r
 \r
+    case KEY_ORDER_ATTEMPT_CONFIG:\r
+      //\r
+      // Order the attempt according to user input.\r
+      //\r
+      CopyMem (\r
+        OldIfrNvData.DynamicOrderedList,\r
+        IfrNvData->DynamicOrderedList,\r
+        sizeof (IfrNvData->DynamicOrderedList)\r
+        );\r
+      IScsiConfigDisplayOrderAttempts ();\r
+      break;\r
+    \r
+    default:\r
+      Status = IScsiConfigProcessDefault (QuestionId, IfrNvData);\r
+      break;\r
+    }\r
+  } else if (Action == EFI_BROWSER_ACTION_CHANGED) {  \r
     switch (QuestionId) {\r
     case KEY_INITIATOR_NAME:\r
       UnicodeStrToAsciiStr (IfrNvData->InitiatorName, IScsiName);\r
@@ -2091,54 +2187,34 @@ IScsiFormCallback (
           );      \r
       }\r
 \r
-      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_SUBMIT;\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_APPLY;\r
       break;\r
+    case KEY_ATTEMPT_NAME:\r
+      if (StrLen (IfrNvData->AttemptName) > ATTEMPT_NAME_SIZE) {\r
+        CopyMem (AttemptName, IfrNvData->AttemptName, ATTEMPT_NAME_SIZE * sizeof (CHAR16));\r
+        CopyMem (&AttemptName[ATTEMPT_NAME_SIZE], L"...", 4 * sizeof (CHAR16));\r
+      } else {\r
+        CopyMem (\r
+          AttemptName,\r
+          IfrNvData->AttemptName,\r
+          (StrLen (IfrNvData->AttemptName) + 1) * sizeof (CHAR16)\r
+          );\r
+      }\r
 \r
-    case KEY_ADD_ATTEMPT:\r
-      Status = IScsiConfigAddAttempt ();\r
-      break;\r
+      UnicodeStrToAsciiStr (IfrNvData->AttemptName, Private->Current->AttemptName);\r
 \r
-    case KEY_DELETE_ATTEMPT:\r
-      CopyMem (\r
-        OldIfrNvData.DeleteAttemptList,\r
-        IfrNvData->DeleteAttemptList,\r
-        sizeof (IfrNvData->DeleteAttemptList)\r
-        );\r
-      Status = IScsiConfigDisplayDeleteAttempts (IfrNvData);\r
-      break;\r
+      IScsiConfigUpdateAttempt ();\r
 \r
-    case KEY_SAVE_DELETE_ATTEMPT:\r
-      //\r
-      // Delete the Attempt Order from NVR\r
-      //\r
-      Status = IScsiConfigDeleteAttempts (IfrNvData);\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_APPLY;\r
+      break;\r
+      \r
+    case KEY_SAVE_ATTEMPT_CONFIG:\r
+      Status = IScsiConvertIfrNvDataToAttemptConfigData (IfrNvData, Private->Current);\r
       if (EFI_ERROR (Status)) {\r
         break;\r
       }\r
 \r
-      IScsiConfigUpdateAttempt ();\r
-      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_SUBMIT;\r
-      break;\r
-\r
-    case KEY_IGNORE_DELETE_ATTEMPT:\r
-      CopyMem (\r
-        IfrNvData->DeleteAttemptList,\r
-        OldIfrNvData.DeleteAttemptList,\r
-        sizeof (IfrNvData->DeleteAttemptList)\r
-        );\r
-      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_SUBMIT;\r
-      break;\r
-\r
-    case KEY_ORDER_ATTEMPT_CONFIG:\r
-      //\r
-      // Order the attempt according to user input.\r
-      //\r
-      CopyMem (\r
-        OldIfrNvData.DynamicOrderedList,\r
-        IfrNvData->DynamicOrderedList,\r
-        sizeof (IfrNvData->DynamicOrderedList)\r
-        );\r
-      IScsiConfigDisplayOrderAttempts ();\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_APPLY;\r
       break;\r
 \r
     case KEY_SAVE_ORDER_CHANGES:\r
@@ -2151,7 +2227,7 @@ IScsiFormCallback (
       }\r
 \r
       IScsiConfigUpdateAttempt ();\r
-      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_SUBMIT;\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_SUBMIT_EXIT;\r
       break;\r
 \r
     case KEY_IGNORE_ORDER_CHANGES:\r
@@ -2160,26 +2236,29 @@ IScsiFormCallback (
         OldIfrNvData.DynamicOrderedList,\r
         sizeof (IfrNvData->DynamicOrderedList)\r
         );\r
-      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_SUBMIT;\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_DISCARD_EXIT;\r
       break;\r
 \r
-    case KEY_ATTEMPT_NAME:\r
-      if (StrLen (IfrNvData->AttemptName) > ATTEMPT_NAME_SIZE) {\r
-        CopyMem (AttemptName, IfrNvData->AttemptName, ATTEMPT_NAME_SIZE * sizeof (CHAR16));\r
-        CopyMem (&AttemptName[ATTEMPT_NAME_SIZE], L"...", 4 * sizeof (CHAR16));\r
-      } else {\r
-        CopyMem (\r
-          AttemptName,\r
-          IfrNvData->AttemptName,\r
-          (StrLen (IfrNvData->AttemptName) + 1) * sizeof (CHAR16)\r
-          );\r
+    case KEY_SAVE_DELETE_ATTEMPT:\r
+      //\r
+      // Delete the Attempt Order from NVR\r
+      //\r
+      Status = IScsiConfigDeleteAttempts (IfrNvData);\r
+      if (EFI_ERROR (Status)) {\r
+        break;\r
       }\r
 \r
-      UnicodeStrToAsciiStr (IfrNvData->AttemptName, Private->Current->AttemptName);\r
-\r
       IScsiConfigUpdateAttempt ();\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_SUBMIT_EXIT;\r
+      break;\r
 \r
-      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_SUBMIT;\r
+    case KEY_IGNORE_DELETE_ATTEMPT:\r
+      CopyMem (\r
+        IfrNvData->DeleteAttemptList,\r
+        OldIfrNvData.DeleteAttemptList,\r
+        sizeof (IfrNvData->DeleteAttemptList)\r
+        );\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_DISCARD_EXIT;\r
       break;\r
 \r
     case KEY_IP_MODE:\r
@@ -2351,38 +2430,23 @@ IScsiFormCallback (
 \r
       break;\r
 \r
-    case KEY_SAVE_ATTEMPT_CONFIG:\r
-      Status = IScsiConvertIfrNvDataToAttemptConfigData (IfrNvData, Private->Current);\r
-      if (EFI_ERROR (Status)) {\r
-        break;\r
-      }\r
-\r
-      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_SUBMIT;\r
-      break;\r
-\r
     default:\r
-      Status = IScsiConfigProcessDefault (QuestionId, IfrNvData);\r
       break;\r
     }\r
+  }\r
 \r
-    if (!EFI_ERROR (Status)) {\r
-      //\r
-      // Pass changed uncommitted data back to Form Browser.\r
-      //\r
-      BufferSize = sizeof (ISCSI_CONFIG_IFR_NVDATA);\r
-      HiiSetBrowserData (NULL, NULL, BufferSize, (UINT8 *) IfrNvData, NULL);\r
-    }\r
-\r
-    FreePool (IfrNvData);\r
-    FreePool (IScsiName);\r
-\r
-    return Status;\r
+  if (!EFI_ERROR (Status)) {\r
+    //\r
+    // Pass changed uncommitted data back to Form Browser.\r
+    //\r
+    BufferSize = sizeof (ISCSI_CONFIG_IFR_NVDATA);\r
+    HiiSetBrowserData (NULL, NULL, BufferSize, (UINT8 *) IfrNvData, NULL);\r
   }\r
 \r
-  //\r
-  // All other action return unsupported.\r
-  //\r
-  return EFI_UNSUPPORTED;\r
+  FreePool (IfrNvData);\r
+  FreePool (IScsiName);\r
+\r
+  return Status;\r
 }\r
 \r
 \r
@@ -2432,7 +2496,7 @@ IScsiConfigFormInit (
   // Publish our HII data.\r
   //\r
   CallbackInfo->RegisteredHandle = HiiAddPackages (\r
-                                     &mVendorGuid,\r
+                                     &gIScsiConfigGuid,\r
                                      CallbackInfo->DriverHandle,\r
                                      IScsiDxeStrings,\r
                                      IScsiConfigVfrBin,\r
@@ -2496,6 +2560,13 @@ IScsiConfigFormUnload (
 \r
   ASSERT (mPrivate->NicCount == 0);\r
 \r
+  //\r
+  // Free attempt is created but not saved to system.\r
+  //\r
+  if (mPrivate->NewAttempt != NULL) {\r
+    FreePool (mPrivate->NewAttempt);\r
+  }\r
+\r
   FreePool (mPrivate);\r
   mPrivate = NULL;\r
 \r