]> git.proxmox.com Git - mirror_edk2.git/commitdiff
Add additional delay in DHCP6 InfoRequest interface to wait for link local address...
authorsfu5 <sfu5@6f19259b-4bc3-4df7-8a09-765794883524>
Wed, 22 Aug 2012 08:01:19 +0000 (08:01 +0000)
committersfu5 <sfu5@6f19259b-4bc3-4df7-8a09-765794883524>
Wed, 22 Aug 2012 08:01:19 +0000 (08:01 +0000)
Signed-off-by: Fu Siyuan <siyuan.fu@intel.com>
Reviewed-by: Ye Ting <ting.ye@intel.com>
Reviewed-by: qianouyang <qian.ouyang@intel.com>
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@13664 6f19259b-4bc3-4df7-8a09-765794883524

NetworkPkg/Dhcp6Dxe/Dhcp6Driver.c
NetworkPkg/Dhcp6Dxe/Dhcp6Dxe.inf
NetworkPkg/Dhcp6Dxe/Dhcp6Impl.c
NetworkPkg/Dhcp6Dxe/Dhcp6Impl.h
NetworkPkg/Dhcp6Dxe/Dhcp6Io.c
NetworkPkg/Dhcp6Dxe/Dhcp6Io.h
NetworkPkg/Dhcp6Dxe/Dhcp6Utility.c
NetworkPkg/Dhcp6Dxe/Dhcp6Utility.h

index 54ef2e2783d8c6cd630bd16c9405d540b9ce49cc..b789f2a478194d0ec3907a9f080e2fcf60921ec1 100644 (file)
@@ -2,7 +2,7 @@
   Driver Binding functions and Service Binding functions\r
   implementationfor for Dhcp6 Driver.\r
 \r
-  Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2009 - 2012, 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
@@ -132,6 +132,7 @@ Dhcp6CreateService (
   )\r
 {\r
   DHCP6_SERVICE             *Dhcp6Srv;\r
+  EFI_STATUS                Status;\r
 \r
   *Service = NULL;\r
   Dhcp6Srv = AllocateZeroPool (sizeof (DHCP6_SERVICE));\r
@@ -165,6 +166,19 @@ Dhcp6CreateService (
     sizeof (EFI_SERVICE_BINDING_PROTOCOL)\r
     );\r
 \r
+  //\r
+  // Locate Ip6->Ip6Config and store it for get IP6 Duplicate Address Detection transmits.\r
+  //\r
+  Status = gBS->HandleProtocol (\r
+                  Controller,\r
+                  &gEfiIp6ConfigProtocolGuid,\r
+                  (VOID **) &Dhcp6Srv->Ip6Cfg\r
+                  );\r
+  if (EFI_ERROR (Status)) {\r
+    FreePool (Dhcp6Srv);\r
+    return Status;\r
+  }\r
+\r
   //\r
   // Generate client Duid: If SMBIOS system UUID is located, generate DUID in DUID-UUID format.\r
   // Otherwise, in DUID-LLT format.\r
index f10b07ac3c1ae9048fedfe5452580699ab526638..7c84397431a4580b42413f0288b496f9171edadd 100644 (file)
@@ -1,7 +1,7 @@
 ## @file\r
 #  Component description file for Dhcp6 module.\r
 #\r
-#  Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>\r
+#  Copyright (c) 2009 - 2012, 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
@@ -66,4 +66,4 @@
   gEfiUdp6ProtocolGuid\r
   gEfiDhcp6ServiceBindingProtocolGuid\r
   gEfiDhcp6ProtocolGuid\r
-\r
+  gEfiIp6ConfigProtocolGuid\r
index 4bed614d2baeb47bf05711a9de5e40eabcb07093..2c2b9f9f0e7b5219050c1b43fa983c6990497ff2 100644 (file)
@@ -608,11 +608,12 @@ EfiDhcp6InfoRequest (
   )\r
 {\r
   EFI_STATUS                   Status;\r
-  EFI_TPL                      OldTpl;\r
   DHCP6_INSTANCE               *Instance;\r
   DHCP6_SERVICE                *Service;\r
-  DHCP6_INF_CB                 *InfCb;\r
   UINTN                        Index;\r
+  EFI_EVENT                    Timer;\r
+  EFI_STATUS                   TimerStatus;\r
+  UINTN                        GetMappingTimeOut;\r
 \r
   if (This == NULL || OptionRequest == NULL || Retransmission == NULL || ReplyCallback == NULL) {\r
     return EFI_INVALID_PARAMETER;\r
@@ -637,57 +638,63 @@ EfiDhcp6InfoRequest (
   Instance = DHCP6_INSTANCE_FROM_THIS (This);\r
   Service  = Instance->Service;\r
 \r
-  OldTpl           = gBS->RaiseTPL (TPL_CALLBACK);\r
-  Instance->UdpSts = EFI_ALREADY_STARTED;\r
-\r
-  //\r
-  // Create and initialize the control block for the info-request.\r
-  //\r
-  InfCb = AllocateZeroPool (sizeof(DHCP6_INF_CB));\r
-\r
-  if (InfCb == NULL) {\r
-    gBS->RestoreTPL (OldTpl);\r
-    return EFI_OUT_OF_RESOURCES;\r
-  }\r
-\r
-  InfCb->ReplyCallback   = ReplyCallback;\r
-  InfCb->CallbackContext = CallbackContext;\r
-  InfCb->TimeoutEvent    = TimeoutEvent;\r
-\r
-  InsertTailList (&Instance->InfList, &InfCb->Link);\r
-\r
-  //\r
-  // Send the info-request message to start exchange process.\r
-  //\r
-  Status = Dhcp6SendInfoRequestMsg (\r
+  Status = Dhcp6StartInfoRequest (\r
              Instance,\r
-             InfCb,\r
              SendClientId,\r
              OptionRequest,\r
              OptionCount,\r
              OptionList,\r
-             Retransmission\r
+             Retransmission,\r
+             TimeoutEvent,\r
+             ReplyCallback,\r
+             CallbackContext\r
              );\r
+  if (Status == EFI_NO_MAPPING) {\r
+    //\r
+    // The link local address is not ready, wait for some time and restart\r
+    // the DHCP6 information request process.\r
+    //\r
+    Status = Dhcp6GetMappingTimeOut(Service->Ip6Cfg, &GetMappingTimeOut);\r
+    if (EFI_ERROR(Status)) {\r
+      return Status;\r
+    }\r
 \r
-  if (EFI_ERROR (Status)) {\r
-    goto ON_ERROR;\r
-  }\r
+    Status = gBS->CreateEvent (EVT_TIMER, TPL_CALLBACK, NULL, NULL, &Timer);\r
+    if (EFI_ERROR (Status)) {\r
+      return Status;\r
+    }\r
 \r
-  //\r
-  // Register receive callback for the stateless exchange process.\r
-  //\r
-  Status = UdpIoRecvDatagram(\r
-             Service->UdpIo,\r
-             Dhcp6ReceivePacket,\r
-             Service,\r
-             0\r
-             );\r
+    //\r
+    // Start the timer, wait for link local address DAD to finish.\r
+    //\r
+    Status = gBS->SetTimer (Timer, TimerRelative, GetMappingTimeOut);\r
+    if (EFI_ERROR (Status)) {\r
+      gBS->CloseEvent (Timer);\r
+      return Status;\r
+    }\r
 \r
-  if (EFI_ERROR (Status) && (Status != EFI_ALREADY_STARTED)) {\r
-    goto ON_ERROR;\r
+    do {  \r
+      TimerStatus = gBS->CheckEvent (Timer);\r
+      if (!EFI_ERROR (TimerStatus)) {\r
+        Status = Dhcp6StartInfoRequest (\r
+                   Instance,\r
+                   SendClientId,\r
+                   OptionRequest,\r
+                   OptionCount,\r
+                   OptionList,\r
+                   Retransmission,\r
+                   TimeoutEvent,\r
+                   ReplyCallback,\r
+                   CallbackContext\r
+                   );\r
+      }\r
+    } while (TimerStatus == EFI_NOT_READY);\r
+    \r
+    gBS->CloseEvent (Timer);\r
+  }\r
+  if (EFI_ERROR (Status)) {\r
+    return Status;\r
   }\r
-\r
-  gBS->RestoreTPL (OldTpl);\r
 \r
   //\r
   // Poll udp out of the net tpl if synchoronus call.\r
@@ -701,14 +708,6 @@ EfiDhcp6InfoRequest (
   }\r
 \r
   return EFI_SUCCESS;\r
-\r
-ON_ERROR:\r
-\r
-  RemoveEntryList (&InfCb->Link);\r
-  FreePool (InfCb);\r
-  gBS->RestoreTPL (OldTpl);\r
-\r
-  return Status;\r
 }\r
 \r
 \r
index dda0cf37d56943b1babdeda2b33eb16b6ac63749..0e206cd504ece25dfdd8631af05bf21afb745588 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Dhcp6 internal data structure and definition declaration.\r
 \r
-  Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2009 - 2012, 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
@@ -21,6 +21,7 @@
 \r
 #include <Protocol/Dhcp6.h>\r
 #include <Protocol/Udp6.h>\r
+#include <Protocol/Ip6Config.h>\r
 #include <Protocol/ServiceBinding.h>\r
 #include <Protocol/DriverBinding.h>\r
 \r
@@ -259,6 +260,7 @@ struct _DHCP6_SERVICE {
   EFI_HANDLE                    Image;\r
   EFI_SERVICE_BINDING_PROTOCOL  ServiceBinding;\r
   EFI_SIMPLE_NETWORK_PROTOCOL   *Snp;\r
+  EFI_IP6_CONFIG_PROTOCOL       *Ip6Cfg;\r
   EFI_DHCP6_DUID                *ClientId;\r
   UDP_IO                        *UdpIo;\r
   UINT32                        Xid;\r
index 7320642eddf9b4498bbbe7207e9f43a507297393..656fd8390844fb9947cb3f7d127c35fb44fe9cef 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Dhcp6 internal functions implementation.\r
 \r
-  Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2009 - 2012, 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
@@ -1626,6 +1626,106 @@ Dhcp6SendRenewRebindMsg (
   return Dhcp6EnqueueRetry (Instance, Packet, Elapsed, NULL);\r
 }\r
 \r
+/**\r
+  Start the information request process.\r
+\r
+  @param[in]  Instance          The pointer to the Dhcp6 instance.\r
+  @param[in]  SendClientId      If TRUE, the client identifier option will be included in\r
+                                information request message. Otherwise, the client identifier\r
+                                option will not be included.\r
+  @param[in]  OptionRequest     The pointer to the option request option.\r
+  @param[in]  OptionCount       The number options in the OptionList.\r
+  @param[in]  OptionList        The array pointers to the appended options.\r
+  @param[in]  Retransmission    The pointer to the retransmission control.\r
+  @param[in]  TimeoutEvent      The event of timeout.\r
+  @param[in]  ReplyCallback     The callback function when the reply was received.\r
+  @param[in]  CallbackContext   The pointer to the parameter passed to the callback.\r
+\r
+  @retval EFI_SUCCESS           Start the info-request process successfully.\r
+  @retval EFI_OUT_OF_RESOURCES  Required system resources could not be allocated.\r
+  @retval EFI_NO_MAPPING        No source address is available for use.\r
+  @retval Others                Failed to start the info-request process.\r
+\r
+**/\r
+EFI_STATUS\r
+Dhcp6StartInfoRequest (\r
+  IN DHCP6_INSTANCE            *Instance,\r
+  IN BOOLEAN                   SendClientId,\r
+  IN EFI_DHCP6_PACKET_OPTION   *OptionRequest,\r
+  IN UINT32                    OptionCount,\r
+  IN EFI_DHCP6_PACKET_OPTION   *OptionList[]    OPTIONAL,\r
+  IN EFI_DHCP6_RETRANSMISSION  *Retransmission,\r
+  IN EFI_EVENT                 TimeoutEvent     OPTIONAL,\r
+  IN EFI_DHCP6_INFO_CALLBACK   ReplyCallback,\r
+  IN VOID                      *CallbackContext OPTIONAL\r
+  )\r
+{\r
+  EFI_STATUS                   Status;\r
+  DHCP6_INF_CB                 *InfCb;\r
+  DHCP6_SERVICE                *Service;\r
+  EFI_TPL                      OldTpl;\r
+\r
+  Service  = Instance->Service;\r
+\r
+  OldTpl = gBS->RaiseTPL (TPL_CALLBACK);\r
+  Instance->UdpSts = EFI_ALREADY_STARTED;\r
+  //\r
+  // Create and initialize the control block for the info-request.\r
+  //\r
+  InfCb = AllocateZeroPool (sizeof(DHCP6_INF_CB));\r
+\r
+  if (InfCb == NULL) {\r
+    gBS->RestoreTPL (OldTpl);\r
+    return EFI_OUT_OF_RESOURCES;\r
+  }\r
+\r
+  InfCb->ReplyCallback   = ReplyCallback;\r
+  InfCb->CallbackContext = CallbackContext;\r
+  InfCb->TimeoutEvent    = TimeoutEvent;\r
+\r
+  InsertTailList (&Instance->InfList, &InfCb->Link);\r
+\r
+  //\r
+  // Send the info-request message to start exchange process.\r
+  //\r
+  Status = Dhcp6SendInfoRequestMsg (\r
+             Instance,\r
+             InfCb,\r
+             SendClientId,\r
+             OptionRequest,\r
+             OptionCount,\r
+             OptionList,\r
+             Retransmission\r
+             );\r
+\r
+  if (EFI_ERROR (Status)) {\r
+    goto ON_ERROR;\r
+  }\r
+\r
+  //\r
+  // Register receive callback for the stateless exchange process.\r
+  //\r
+  Status = UdpIoRecvDatagram(\r
+             Service->UdpIo,\r
+             Dhcp6ReceivePacket,\r
+             Service,\r
+             0\r
+             );\r
+\r
+  if (EFI_ERROR (Status) && (Status != EFI_ALREADY_STARTED)) {\r
+    goto ON_ERROR;\r
+  }\r
+  \r
+  gBS->RestoreTPL (OldTpl);\r
+  return EFI_SUCCESS;\r
+  \r
+ON_ERROR:\r
+  gBS->RestoreTPL (OldTpl); \r
+  RemoveEntryList (&InfCb->Link);\r
+  FreePool (InfCb);\r
+\r
+  return Status;\r
+}\r
 \r
 /**\r
   Create the information request message and send it.\r
index 31459c96d32aa8d860e69f5b215440064bc0c693..b0b12a79fe8efc60016f9523e321ee9f4c16d28c 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Dhcp6 internal functions declaration.\r
 \r
-  Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2009 - 2012, 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
@@ -129,6 +129,40 @@ Dhcp6SendReleaseMsg (
   IN EFI_DHCP6_IA              *RelIa\r
   );\r
 \r
+/**\r
+  Start the information request process.\r
+\r
+  @param[in]  Instance          The pointer to the Dhcp6 instance.\r
+  @param[in]  SendClientId      If TRUE, the client identifier option will be included in\r
+                                information request message. Otherwise, the client identifier\r
+                                option will not be included.\r
+  @param[in]  OptionRequest     The pointer to the option request option.\r
+  @param[in]  OptionCount       The number options in the OptionList.\r
+  @param[in]  OptionList        The array pointers to the appended options.\r
+  @param[in]  Retransmission    The pointer to the retransmission control.\r
+  @param[in]  TimeoutEvent      The event of timeout.\r
+  @param[in]  ReplyCallback     The callback function when the reply was received.\r
+  @param[in]  CallbackContext   The pointer to the parameter passed to the callback.\r
+\r
+  @retval EFI_SUCCESS           Start the info-request process successfully.\r
+  @retval EFI_OUT_OF_RESOURCES  Required system resources could not be allocated.\r
+  @retval EFI_NO_MAPPING        No source address is available for use.\r
+  @retval Others                Failed to start the info-request process.\r
+\r
+**/\r
+EFI_STATUS\r
+Dhcp6StartInfoRequest (\r
+  IN DHCP6_INSTANCE            *Instance,\r
+  IN BOOLEAN                   SendClientId,\r
+  IN EFI_DHCP6_PACKET_OPTION   *OptionRequest,\r
+  IN UINT32                    OptionCount,\r
+  IN EFI_DHCP6_PACKET_OPTION   *OptionList[]    OPTIONAL,\r
+  IN EFI_DHCP6_RETRANSMISSION  *Retransmission,\r
+  IN EFI_EVENT                 TimeoutEvent     OPTIONAL,\r
+  IN EFI_DHCP6_INFO_CALLBACK   ReplyCallback,\r
+  IN VOID                      *CallbackContext OPTIONAL\r
+  );\r
+\r
 /**\r
   Create the information request message and send it.\r
 \r
index 6bf96a19966d33cd7a6d203d006e2eed0ccfa092..4c32028680d078dede26e225b73e24b3dd110425 100644 (file)
@@ -1189,3 +1189,42 @@ Dhcp6AppendCacheIa (
     Instance->IaCb.Ia  = NewIa;\r
   }\r
 }\r
+\r
+/**\r
+  Calculate the Dhcp6 get mapping timeout by adding additinal delay to the IP6 DAD transmits count.\r
+\r
+  @param[in]   Ip6Cfg              The pointer to Ip6 config protocol.\r
+  @param[out]  TimeOut             The time out value in 100ns units.\r
+\r
+  @retval   EFI_INVALID_PARAMETER  Input parameters are invalid.\r
+  @retval   EFI_SUCCESS            Calculate the time out value successfully.\r
+**/\r
+EFI_STATUS\r
+Dhcp6GetMappingTimeOut (\r
+  IN  EFI_IP6_CONFIG_PROTOCOL       *Ip6Cfg,\r
+  OUT UINTN                         *TimeOut\r
+  ) \r
+{\r
+  EFI_STATUS            Status;\r
+  UINTN                 DataSize;\r
+  EFI_IP6_CONFIG_DUP_ADDR_DETECT_TRANSMITS    DadXmits;\r
+\r
+  if (Ip6Cfg == NULL || TimeOut == NULL) {\r
+    return EFI_INVALID_PARAMETER;\r
+  }\r
+\r
+  DataSize = sizeof (EFI_IP6_CONFIG_DUP_ADDR_DETECT_TRANSMITS);\r
+  Status = Ip6Cfg->GetData (\r
+                     Ip6Cfg,\r
+                     Ip6ConfigDataTypeDupAddrDetectTransmits,\r
+                     &DataSize,\r
+                     &DadXmits\r
+                     );\r
+  if (EFI_ERROR (Status)) {\r
+    return Status;\r
+  }\r
+  \r
+  *TimeOut = TICKS_PER_SECOND * DadXmits.DupAddrDetectTransmits + DHCP6_DAD_ADDITIONAL_DELAY;\r
+  \r
+  return EFI_SUCCESS;\r
+}\r
index 61bb9f324e9a04156f15c7b3fa863e5738d258ff..2a44d0068fda1a41d13614b8b8bae664f1987937 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Dhcp6 support functions declaration.\r
 \r
-  Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2009 - 2012, 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
@@ -17,7 +17,8 @@
 #define __EFI_DHCP6_UTILITY_H__\r
 \r
 \r
-#define  DHCP6_10_BIT_MASK     0x3ff\r
+#define  DHCP6_10_BIT_MASK             0x3ff\r
+#define  DHCP6_DAD_ADDITIONAL_DELAY    30000000 // 3 seconds\r
 \r
 /**\r
   Generate client Duid in the format of Duid-llt.\r
@@ -337,4 +338,18 @@ Dhcp6AppendCacheIa (
   IN DHCP6_INSTANCE           *Instance\r
   );\r
 \r
+/**\r
+  Calculate the Dhcp6 get mapping timeout by adding additinal delay to the IP6 DAD transmits count.\r
+\r
+  @param[in]   Ip6Cfg              The pointer to Ip6 config protocol.\r
+  @param[out]  TimeOut             The time out value in 100ns units.\r
+\r
+  @retval   EFI_INVALID_PARAMETER  Input parameters are invalid.\r
+  @retval   EFI_SUCCESS            Calculate the time out value successfully.\r
+**/\r
+EFI_STATUS\r
+Dhcp6GetMappingTimeOut (\r
+  IN  EFI_IP6_CONFIG_PROTOCOL       *Ip6Cfg,\r
+  OUT UINTN                         *TimeOut\r
+  );\r
 #endif\r