]> git.proxmox.com Git - mirror_edk2.git/blobdiff - NetworkPkg/Dhcp6Dxe/Dhcp6Io.c
NetworkPkg: Replace BSD License with BSD+Patent License
[mirror_edk2.git] / NetworkPkg / Dhcp6Dxe / Dhcp6Io.c
index 962d9387cab741edac548f3d509723e876a63797..4f8393cb36ce93d87a035c2c37113db0a8ec4db1 100644 (file)
@@ -1,15 +1,10 @@
 /** @file\r
   Dhcp6 internal functions implementation.\r
 \r
-  Copyright (c) 2009 - 2012, Intel Corporation. All rights reserved.<BR>\r
+  (C) Copyright 2014 Hewlett-Packard Development Company, L.P.<BR>\r
+  Copyright (c) 2009 - 2018, 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 of the BSD License\r
-  which accompanies this distribution.  The full text of the license may be found at\r
-  http://opensource.org/licenses/bsd-license.php.\r
-\r
-  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
-  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+  SPDX-License-Identifier: BSD-2-Clause-Patent\r
 \r
 **/\r
 \r
@@ -363,6 +358,32 @@ Dhcp6CleanupRetry (
   }\r
 }\r
 \r
+/**\r
+  Check whether the TxCb is still a valid control block in the instance's retry list.\r
+\r
+  @param[in]  Instance       The pointer to DHCP6_INSTANCE.\r
+  @param[in]  TxCb           The control block for a transmitted message.\r
+\r
+  @retval   TRUE      The control block is in Instance's retry list.\r
+  @retval   FALSE     The control block is NOT in Instance's retry list.\r
+\r
+**/\r
+BOOLEAN\r
+Dhcp6IsValidTxCb (\r
+  IN  DHCP6_INSTANCE          *Instance,\r
+  IN  DHCP6_TX_CB             *TxCb\r
+  )\r
+{\r
+  LIST_ENTRY                *Entry;\r
+\r
+  NET_LIST_FOR_EACH (Entry, &Instance->TxList) {\r
+    if (TxCb == NET_LIST_USER_STRUCT (Entry, DHCP6_TX_CB, Link)) {\r
+      return TRUE;\r
+    }\r
+  }\r
+\r
+  return FALSE;\r
+}\r
 \r
 /**\r
   Clean up the session of the instance stateful exchange.\r
@@ -518,7 +539,6 @@ Dhcp6UpdateIaInfo (
   )\r
 {\r
   EFI_STATUS                  Status;\r
-  EFI_DHCP6_STATE             State;\r
   UINT8                       *Option;\r
   UINT8                       *IaInnerOpt;\r
   UINT16                      IaInnerLen;\r
@@ -539,7 +559,6 @@ Dhcp6UpdateIaInfo (
   //\r
   // See details in the section-18.1.8 of rfc-3315.\r
   //\r
-  State  = Dhcp6Init;\r
   Option = Dhcp6SeekIaOption (\r
              Packet->Dhcp6.Option,\r
              Packet->Length - sizeof (EFI_DHCP6_HEADER),\r
@@ -1742,12 +1761,12 @@ Dhcp6StartInfoRequest (
   if (EFI_ERROR (Status) && (Status != EFI_ALREADY_STARTED)) {\r
     goto ON_ERROR;\r
   }\r
-  \r
+\r
   gBS->RestoreTPL (OldTpl);\r
   return EFI_SUCCESS;\r
-  \r
+\r
 ON_ERROR:\r
-  gBS->RestoreTPL (OldTpl); \r
+  gBS->RestoreTPL (OldTpl);\r
   RemoveEntryList (&InfCb->Link);\r
   FreePool (InfCb);\r
 \r
@@ -1871,7 +1890,7 @@ Dhcp6SendInfoRequestMsg (
   //\r
   Packet->Length += (UINT32) (Cursor - Packet->Dhcp6.Option);\r
   ASSERT (Packet->Size > Packet->Length + 8);\r
-  \r
+\r
   //\r
   // Clear initial time for current transaction.\r
   //\r
@@ -2207,15 +2226,15 @@ Dhcp6HandleReplyMsg (
       }\r
     } else if (Status == EFI_NOT_FOUND) {\r
       //\r
-      // Refer to RFC3315 Chapter 18.1.8, for each IA in the original Renew or Rebind message, \r
+      // Refer to RFC3315 Chapter 18.1.8, for each IA in the original Renew or Rebind message,\r
       // the client sends a Renew or Rebind if the IA is not in the Reply message.\r
       // Return EFI_SUCCESS so we can continue to restart the Renew/Rebind process.\r
       //\r
       return EFI_SUCCESS;\r
     }\r
-    \r
+\r
     goto ON_EXIT;\r
-    \r
+\r
   } else if (Option != NULL) {\r
     //\r
     // Any error status code option is found.\r
@@ -2264,7 +2283,7 @@ Dhcp6HandleReplyMsg (
     case Dhcp6StsNoBinding:\r
       if (Instance->IaCb.Ia->State == Dhcp6Renewing || Instance->IaCb.Ia->State == Dhcp6Rebinding) {\r
         //\r
-        // Refer to RFC3315 Chapter 18.1.8, for each IA in the original Renew or Rebind message, the client \r
+        // Refer to RFC3315 Chapter 18.1.8, for each IA in the original Renew or Rebind message, the client\r
         // sends a Request message if the IA contained a Status Code option with the NoBinding status.\r
         //\r
         Status = Dhcp6SendRequestMsg(Instance);\r
@@ -2283,7 +2302,7 @@ Dhcp6HandleReplyMsg (
   }\r
 \r
   return EFI_SUCCESS;\r
-  \r
+\r
 ON_EXIT:\r
 \r
   if (!EFI_ERROR(Status)) {\r
@@ -2293,7 +2312,7 @@ ON_EXIT:
                FALSE\r
                );\r
   }\r
-  \r
+\r
   return Status;\r
 }\r
 \r
@@ -2402,14 +2421,12 @@ Dhcp6HandleAdvertiseMsg (
 {\r
   EFI_STATUS                  Status;\r
   UINT8                       *Option;\r
-  UINT16                      StsCode;\r
   BOOLEAN                     Timeout;\r
 \r
   ASSERT(Instance->Config);\r
   ASSERT(Instance->IaCb.Ia);\r
 \r
   Timeout = FALSE;\r
-  StsCode = Dhcp6StsSuccess;\r
 \r
   //\r
   // If the client does receives a valid reply message that includes a rapid\r
@@ -2789,6 +2806,7 @@ Dhcp6ReceivePacket (
   LIST_ENTRY                *Next1;\r
   LIST_ENTRY                *Entry2;\r
   LIST_ENTRY                *Next2;\r
+  EFI_STATUS                Status;\r
 \r
   ASSERT (Udp6Wrap != NULL);\r
   ASSERT (Context != NULL);\r
@@ -2803,6 +2821,10 @@ Dhcp6ReceivePacket (
     return ;\r
   }\r
 \r
+  if (Udp6Wrap->TotalSize < sizeof (EFI_DHCP6_HEADER)) {\r
+    goto ON_CONTINUE;\r
+  }\r
+\r
   //\r
   // Copy the net buffer received from upd6 to a Dhcp6 packet.\r
   //\r
@@ -2868,6 +2890,21 @@ Dhcp6ReceivePacket (
 \r
 ON_CONTINUE:\r
 \r
+  if (!IsDispatched) {\r
+    Status = UdpIoRecvDatagram (\r
+             Service->UdpIo,\r
+             Dhcp6ReceivePacket,\r
+             Service,\r
+             0\r
+             );\r
+    if (EFI_ERROR (Status)) {\r
+      NET_LIST_FOR_EACH_SAFE (Entry1, Next1, &Service->Child) {\r
+        Instance = NET_LIST_USER_STRUCT (Entry1, DHCP6_INSTANCE, Link);\r
+        Dhcp6CleanupRetry (Instance, DHCP6_PACKET_ALL);\r
+      }\r
+    }\r
+  }\r
+\r
   NetbufFree (Udp6Wrap);\r
 \r
   if (Packet != NULL) {\r
@@ -2981,7 +3018,9 @@ Dhcp6OnTimerTick (
           // Select the advertisement received before.\r
           //\r
           Status = Dhcp6SelectAdvertiseMsg (Instance, Instance->AdSelect);\r
-          if (EFI_ERROR (Status)) {\r
+          if (Status == EFI_ABORTED) {\r
+            goto ON_CLOSE;\r
+          } else if (EFI_ERROR (Status)) {\r
             TxCb->RetryCnt++;\r
           }\r
           return;\r
@@ -2997,6 +3036,7 @@ Dhcp6OnTimerTick (
       // Check whether overflow the max retry count limit for this packet\r
       //\r
       if (TxCb->RetryCtl.Mrc != 0 && TxCb->RetryCtl.Mrc < TxCb->RetryCnt) {\r
+        Status = EFI_NO_RESPONSE;\r
         goto ON_CLOSE;\r
       }\r
 \r
@@ -3004,6 +3044,7 @@ Dhcp6OnTimerTick (
       // Check whether overflow the max retry duration for this packet\r
       //\r
       if (TxCb->RetryCtl.Mrd != 0 && TxCb->RetryCtl.Mrd <= TxCb->RetryLos) {\r
+        Status = EFI_NO_RESPONSE;\r
         goto ON_CLOSE;\r
       }\r
 \r
@@ -3093,9 +3134,11 @@ Dhcp6OnTimerTick (
 \r
  ON_CLOSE:\r
 \r
-  if (TxCb->TxPacket->Dhcp6.Header.MessageType == Dhcp6MsgInfoRequest ||\r
+  if (Dhcp6IsValidTxCb (Instance, TxCb) &&\r
+      TxCb->TxPacket != NULL &&\r
+      (TxCb->TxPacket->Dhcp6.Header.MessageType == Dhcp6MsgInfoRequest ||\r
       TxCb->TxPacket->Dhcp6.Header.MessageType == Dhcp6MsgRenew       ||\r
-      TxCb->TxPacket->Dhcp6.Header.MessageType == Dhcp6MsgConfirm\r
+      TxCb->TxPacket->Dhcp6.Header.MessageType == Dhcp6MsgConfirm)\r
       ) {\r
     //\r
     // The failure of renew/Confirm will still switch to the bound state.\r
@@ -3120,6 +3163,6 @@ Dhcp6OnTimerTick (
     //\r
     // The failure of the others will terminate current state machine if timeout.\r
     //\r
-    Dhcp6CleanupSession (Instance, EFI_NO_RESPONSE);\r
+    Dhcp6CleanupSession (Instance, Status);\r
   }\r
 }\r