/** @file\r
+ This file implement the EFI_DHCP4_PROTOCOL interface.\r
+\r
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>\r
+SPDX-License-Identifier: BSD-2-Clause-Patent\r
\r
-Copyright (c) 2006 - 2008, Intel Corporation\r
-All rights reserved. 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
\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
\r
-Module Name:\r
+#include "Dhcp4Impl.h"\r
\r
- Dhcp4Impl.c\r
+/**\r
+ Returns the current operating mode and cached data packet for the EFI DHCPv4 Protocol driver.\r
\r
-Abstract:\r
+ The GetModeData() function returns the current operating mode and cached data\r
+ packet for the EFI DHCPv4 Protocol driver.\r
\r
- This file implement the EFI_DHCP4_PROTOCOL interface.\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[out] Dhcp4ModeData Pointer to storage for the EFI_DHCP4_MODE_DATA structure.\r
\r
+ @retval EFI_SUCCESS The mode data was returned.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
\r
**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4GetModeData (\r
+ IN EFI_DHCP4_PROTOCOL *This,\r
+ OUT EFI_DHCP4_MODE_DATA *Dhcp4ModeData\r
+ );\r
\r
+/**\r
+ Initializes, changes, or resets the operational settings for the EFI DHCPv4 Protocol driver.\r
+\r
+ The Configure() function is used to initialize, change, or reset the operational\r
+ settings of the EFI DHCPv4 Protocol driver for the communication device on which\r
+ the EFI DHCPv4 Service Binding Protocol is installed. This function can be\r
+ successfully called only if both of the following are true:\r
+ * This instance of the EFI DHCPv4 Protocol driver is in the Dhcp4Stopped, Dhcp4Init,\r
+ Dhcp4InitReboot, or Dhcp4Bound states.\r
+ * No other EFI DHCPv4 Protocol driver instance that is controlled by this EFI\r
+ DHCPv4 Service Binding Protocol driver instance has configured this EFI DHCPv4\r
+ Protocol driver.\r
+ When this driver is in the Dhcp4Stopped state, it can transfer into one of the\r
+ following two possible initial states:\r
+ * Dhcp4Init\r
+ * Dhcp4InitReboot\r
+ The driver can transfer into these states by calling Configure() with a non-NULL\r
+ Dhcp4CfgData. The driver will transfer into the appropriate state based on the\r
+ supplied client network address in the ClientAddress parameter and DHCP options\r
+ in the OptionList parameter as described in RFC 2131.\r
+ When Configure() is called successfully while Dhcp4CfgData is set to NULL, the\r
+ default configuring data will be reset in the EFI DHCPv4 Protocol driver and\r
+ the state of the EFI DHCPv4 Protocol driver will not be changed. If one instance\r
+ wants to make it possible for another instance to configure the EFI DHCPv4 Protocol\r
+ driver, it must call this function with Dhcp4CfgData set to NULL.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] Dhcp4CfgData Pointer to the EFI_DHCP4_CONFIG_DATA.\r
+\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the Dhcp4Init or\r
+ Dhcp4InitReboot state, if the original state of this driver\r
+ was Dhcp4Stopped and the value of Dhcp4CfgData was\r
+ not NULL. Otherwise, the state was left unchanged.\r
+ @retval EFI_ACCESS_DENIED This instance of the EFI DHCPv4 Protocol driver was not in the\r
+ Dhcp4Stopped, Dhcp4Init, Dhcp4InitReboot, or Dhcp4Bound state;\r
+ Or onother instance of this EFI DHCPv4 Protocol driver is already\r
+ in a valid configured state.\r
+ @retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
+ @retval EFI_OUT_OF_RESOURCES Required system resources could not be allocated.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
\r
-#include "Dhcp4Impl.h"\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4Configure (\r
+ IN EFI_DHCP4_PROTOCOL *This,\r
+ IN EFI_DHCP4_CONFIG_DATA *Dhcp4CfgData OPTIONAL\r
+ );\r
+\r
+/**\r
+ Starts the DHCP configuration process.\r
+\r
+ The Start() function starts the DHCP configuration process. This function can\r
+ be called only when the EFI DHCPv4 Protocol driver is in the Dhcp4Init or\r
+ Dhcp4InitReboot state.\r
+ If the DHCP process completes successfully, the state of the EFI DHCPv4 Protocol\r
+ driver will be transferred through Dhcp4Selecting and Dhcp4Requesting to the\r
+ Dhcp4Bound state. The CompletionEvent will then be signaled if it is not NULL.\r
+ If the process aborts, either by the user or by some unexpected network error,\r
+ the state is restored to the Dhcp4Init state. The Start() function can be called\r
+ again to restart the process.\r
+ Refer to RFC 2131 for precise state transitions during this process. At the\r
+ time when each event occurs in this process, the callback function that was set\r
+ by EFI_DHCP4_PROTOCOL.Configure() will be called and the user can take this\r
+ opportunity to control the process.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] CompletionEvent If not NULL, indicates the event that will be signaled when the\r
+ EFI DHCPv4 Protocol driver is transferred into the\r
+ Dhcp4Bound state or when the DHCP process is aborted.\r
+ EFI_DHCP4_PROTOCOL.GetModeData() can be called to\r
+ check the completion status. If NULL,\r
+ EFI_DHCP4_PROTOCOL.Start() will wait until the driver\r
+ is transferred into the Dhcp4Bound state or the process fails.\r
+\r
+ @retval EFI_SUCCESS The DHCP configuration process has started, or it has completed\r
+ when CompletionEvent is NULL.\r
+ @retval EFI_NOT_STARTED The EFI DHCPv4 Protocol driver is in the Dhcp4Stopped\r
+ state. EFI_DHCP4_PROTOCOL. Configure() needs to be called.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
+ @retval EFI_OUT_OF_RESOURCES Required system resources could not be allocated.\r
+ @retval EFI_TIMEOUT The DHCP configuration process failed because no response was\r
+ received from the server within the specified timeout value.\r
+ @retval EFI_ABORTED The user aborted the DHCP process.\r
+ @retval EFI_ALREADY_STARTED Some other EFI DHCPv4 Protocol instance already started the\r
+ DHCP process.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4Start (\r
+ IN EFI_DHCP4_PROTOCOL *This,\r
+ IN EFI_EVENT CompletionEvent OPTIONAL\r
+ );\r
+\r
+/**\r
+ Extends the lease time by sending a request packet.\r
+\r
+ The RenewRebind() function is used to manually extend the lease time when the\r
+ EFI DHCPv4 Protocol driver is in the Dhcp4Bound state and the lease time has\r
+ not expired yet. This function will send a request packet to the previously\r
+ found server (or to any server when RebindRequest is TRUE) and transfer the\r
+ state into the Dhcp4Renewing state (or Dhcp4Rebinding when RebindingRequest is\r
+ TRUE). When a response is received, the state is returned to Dhcp4Bound.\r
+ If no response is received before the try count is exceeded (the RequestTryCount\r
+ field that is specified in EFI_DHCP4_CONFIG_DATA) but before the lease time that\r
+ was issued by the previous server expires, the driver will return to the Dhcp4Bound\r
+ state and the previous configuration is restored. The outgoing and incoming packets\r
+ can be captured by the EFI_DHCP4_CALLBACK function.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] RebindRequest If TRUE, this function broadcasts the request packets and enters\r
+ the Dhcp4Rebinding state. Otherwise, it sends a unicast\r
+ request packet and enters the Dhcp4Renewing state.\r
+ @param[in] CompletionEvent If not NULL, this event is signaled when the renew/rebind phase\r
+ completes or some error occurs.\r
+ EFI_DHCP4_PROTOCOL.GetModeData() can be called to\r
+ check the completion status. If NULL,\r
+ EFI_DHCP4_PROTOCOL.RenewRebind() will busy-wait\r
+ until the DHCP process finishes.\r
+\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the\r
+ Dhcp4Renewing state or is back to the Dhcp4Bound state.\r
+ @retval EFI_NOT_STARTED The EFI DHCPv4 Protocol driver is in the Dhcp4Stopped\r
+ state. EFI_DHCP4_PROTOCOL.Configure() needs to\r
+ be called.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
+ @retval EFI_TIMEOUT There was no response from the server when the try count was\r
+ exceeded.\r
+ @retval EFI_ACCESS_DENIED The driver is not in the Dhcp4Bound state.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4RenewRebind (\r
+ IN EFI_DHCP4_PROTOCOL *This,\r
+ IN BOOLEAN RebindRequest,\r
+ IN EFI_EVENT CompletionEvent OPTIONAL\r
+ );\r
+\r
+/**\r
+ Releases the current address configuration.\r
+\r
+ The Release() function releases the current configured IP address by doing either\r
+ of the following:\r
+ * Sending a DHCPRELEASE packet when the EFI DHCPv4 Protocol driver is in the\r
+ Dhcp4Bound state\r
+ * Setting the previously assigned IP address that was provided with the\r
+ EFI_DHCP4_PROTOCOL.Configure() function to 0.0.0.0 when the driver is in\r
+ Dhcp4InitReboot state\r
+ After a successful call to this function, the EFI DHCPv4 Protocol driver returns\r
+ to the Dhcp4Init state and any subsequent incoming packets will be discarded silently.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the Dhcp4Init phase.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
+ @retval EFI_ACCESS_DENIED The EFI DHCPv4 Protocol driver is not Dhcp4InitReboot state.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4Release (\r
+ IN EFI_DHCP4_PROTOCOL *This\r
+ );\r
+\r
+/**\r
+ Stops the current address configuration.\r
+\r
+ The Stop() function is used to stop the DHCP configuration process. After this\r
+ function is called successfully, the EFI DHCPv4 Protocol driver is transferred\r
+ into the Dhcp4Stopped state. EFI_DHCP4_PROTOCOL.Configure() needs to be called\r
+ before DHCP configuration process can be started again. This function can be\r
+ called when the EFI DHCPv4 Protocol driver is in any state.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the Dhcp4Stopped phase.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4Stop (\r
+ IN EFI_DHCP4_PROTOCOL *This\r
+ );\r
\r
+/**\r
+ Builds a DHCP packet, given the options to be appended or deleted or replaced.\r
+\r
+ The Build() function is used to assemble a new packet from the original packet\r
+ by replacing or deleting existing options or appending new options. This function\r
+ does not change any state of the EFI DHCPv4 Protocol driver and can be used at\r
+ any time.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] SeedPacket Initial packet to be used as a base for building new packet.\r
+ @param[in] DeleteCount Number of opcodes in the DeleteList.\r
+ @param[in] DeleteList List of opcodes to be deleted from the seed packet.\r
+ Ignored if DeleteCount is zero.\r
+ @param[in] AppendCount Number of entries in the OptionList.\r
+ @param[in] AppendList Pointer to a DHCP option list to be appended to SeedPacket.\r
+ If SeedPacket also contains options in this list, they are\r
+ replaced by new options (except pad option). Ignored if\r
+ AppendCount is zero. Type EFI_DHCP4_PACKET_OPTION\r
+ @param[out] NewPacket Pointer to storage for the pointer to the new allocated packet.\r
+ Use the EFI Boot Service FreePool() on the resulting pointer\r
+ when done with the packet.\r
+\r
+ @retval EFI_SUCCESS The new packet was built.\r
+ @retval EFI_OUT_OF_RESOURCES Storage for the new packet could not be allocated.\r
+ @retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4Build (\r
+ IN EFI_DHCP4_PROTOCOL *This,\r
+ IN EFI_DHCP4_PACKET *SeedPacket,\r
+ IN UINT32 DeleteCount,\r
+ IN UINT8 *DeleteList OPTIONAL,\r
+ IN UINT32 AppendCount,\r
+ IN EFI_DHCP4_PACKET_OPTION *AppendList[] OPTIONAL,\r
+ OUT EFI_DHCP4_PACKET **NewPacket\r
+ );\r
\r
/**\r
- Get the current operation parameter and lease for the network interface.\r
+ Transmits a DHCP formatted packet and optionally waits for responses.\r
\r
- @param This The DHCP protocol instance\r
- @param Dhcp4ModeData The variable to save the DHCP mode data.\r
+ The TransmitReceive() function is used to transmit a DHCP packet and optionally\r
+ wait for the response from servers. This function does not change the state of\r
+ the EFI DHCPv4 Protocol driver and thus can be used at any time.\r
\r
- @retval EFI_INVALID_PARAMETER The parameter is invalid\r
- @retval EFI_SUCCESS The Dhcp4ModeData is updated with the current\r
- operation parameter.\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] Token Pointer to the EFI_DHCP4_TRANSMIT_RECEIVE_TOKEN structure.\r
+\r
+ @retval EFI_SUCCESS The packet was successfully queued for transmission.\r
+ @retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
+ @retval EFI_NOT_READY The previous call to this function has not finished yet. Try to call\r
+ this function after collection process completes.\r
+ @retval EFI_NO_MAPPING The default station address is not available yet.\r
+ @retval EFI_OUT_OF_RESOURCES Required system resources could not be allocated.\r
+ @retval Others Some other unexpected error occurred.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4TransmitReceive (\r
+ IN EFI_DHCP4_PROTOCOL *This,\r
+ IN EFI_DHCP4_TRANSMIT_RECEIVE_TOKEN *Token\r
+ );\r
+\r
+/**\r
+ Parses the packed DHCP option data.\r
+\r
+ The Parse() function is used to retrieve the option list from a DHCP packet.\r
+ If *OptionCount isn't zero, and there is enough space for all the DHCP options\r
+ in the Packet, each element of PacketOptionList is set to point to somewhere in\r
+ the Packet->Dhcp4.Option where a new DHCP option begins. If RFC3396 is supported,\r
+ the caller should reassemble the parsed DHCP options to get the finial result.\r
+ If *OptionCount is zero or there isn't enough space for all of them, the number\r
+ of DHCP options in the Packet is returned in OptionCount.\r
+\r
+ @param This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param Packet Pointer to packet to be parsed.\r
+ @param OptionCount On input, the number of entries in the PacketOptionList.\r
+ On output, the number of entries that were written into the\r
+ PacketOptionList.\r
+ @param PacketOptionList List of packet option entries to be filled in. End option or pad\r
+ options are not included.\r
+\r
+ @retval EFI_SUCCESS The packet was successfully parsed.\r
+ @retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
+ @retval EFI_BUFFER_TOO_SMALL One or more of the following conditions is TRUE:\r
+ 1) *OptionCount is smaller than the number of options that\r
+ were found in the Packet.\r
+ 2) PacketOptionList is NULL.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+EfiDhcp4Parse (\r
+ IN EFI_DHCP4_PROTOCOL *This,\r
+ IN EFI_DHCP4_PACKET *Packet,\r
+ IN OUT UINT32 *OptionCount,\r
+ OUT EFI_DHCP4_PACKET_OPTION *PacketOptionList[] OPTIONAL\r
+ );\r
+\r
+EFI_DHCP4_PROTOCOL mDhcp4ProtocolTemplate = {\r
+ EfiDhcp4GetModeData,\r
+ EfiDhcp4Configure,\r
+ EfiDhcp4Start,\r
+ EfiDhcp4RenewRebind,\r
+ EfiDhcp4Release,\r
+ EfiDhcp4Stop,\r
+ EfiDhcp4Build,\r
+ EfiDhcp4TransmitReceive,\r
+ EfiDhcp4Parse\r
+};\r
+\r
+/**\r
+ Returns the current operating mode and cached data packet for the EFI DHCPv4 Protocol driver.\r
+\r
+ The GetModeData() function returns the current operating mode and cached data\r
+ packet for the EFI DHCPv4 Protocol driver.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[out] Dhcp4ModeData Pointer to storage for the EFI_DHCP4_MODE_DATA structure.\r
+\r
+ @retval EFI_SUCCESS The mode data was returned.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
\r
**/\r
EFI_STATUS\r
// Caller can use GetModeData to retrieve current DHCP states\r
// no matter whether it is the active child or not.\r
//\r
- Dhcp4ModeData->State = (EFI_DHCP4_STATE) DhcpSb->DhcpState;\r
+ Dhcp4ModeData->State = (EFI_DHCP4_STATE) DhcpSb->DhcpState;\r
CopyMem (&Dhcp4ModeData->ConfigData, &DhcpSb->ActiveConfig, sizeof (Dhcp4ModeData->ConfigData));\r
CopyMem (&Dhcp4ModeData->ClientMacAddress, &DhcpSb->Mac, sizeof (Dhcp4ModeData->ClientMacAddress));\r
\r
if (Para != NULL) {\r
Ip = HTONL (Para->Router);\r
CopyMem (&Dhcp4ModeData->RouterAddress, &Ip, sizeof (EFI_IPv4_ADDRESS));\r
- Dhcp4ModeData->LeaseTime = Para->Lease;\r
+ Dhcp4ModeData->LeaseTime = Para->Lease;\r
} else {\r
ZeroMem (&Dhcp4ModeData->RouterAddress, sizeof (EFI_IPv4_ADDRESS));\r
- Dhcp4ModeData->LeaseTime = 0xffffffff;\r
+ Dhcp4ModeData->LeaseTime = 0xffffffff;\r
}\r
\r
Dhcp4ModeData->ReplyPacket = DhcpSb->Selected;\r
\r
@param Config The DHCP configure data\r
\r
- @return None\r
-\r
**/\r
VOID\r
DhcpCleanConfigure (\r
- IN EFI_DHCP4_CONFIG_DATA *Config\r
+ IN OUT EFI_DHCP4_CONFIG_DATA *Config\r
)\r
{\r
UINT32 Index;\r
\r
if (Config->DiscoverTimeout != NULL) {\r
- gBS->FreePool (Config->DiscoverTimeout);\r
+ FreePool (Config->DiscoverTimeout);\r
}\r
\r
if (Config->RequestTimeout != NULL) {\r
- gBS->FreePool (Config->RequestTimeout);\r
+ FreePool (Config->RequestTimeout);\r
}\r
\r
if (Config->OptionList != NULL) {\r
for (Index = 0; Index < Config->OptionCount; Index++) {\r
if (Config->OptionList[Index] != NULL) {\r
- gBS->FreePool (Config->OptionList[Index]);\r
+ FreePool (Config->OptionList[Index]);\r
}\r
}\r
\r
- gBS->FreePool (Config->OptionList);\r
+ FreePool (Config->OptionList);\r
}\r
\r
ZeroMem (Config, sizeof (EFI_DHCP4_CONFIG_DATA));\r
Allocate memory for configure parameter such as timeout value for Dst,\r
then copy the configure parameter from Src to Dst.\r
\r
- @param Dst The destination DHCP configure data.\r
- @param Src The source DHCP configure data.\r
+ @param[out] Dst The destination DHCP configure data.\r
+ @param[in] Src The source DHCP configure data.\r
\r
@retval EFI_OUT_OF_RESOURCES Failed to allocate memory.\r
@retval EFI_SUCCESS The configure is copied.\r
**/\r
EFI_STATUS\r
DhcpCopyConfigure (\r
- IN EFI_DHCP4_CONFIG_DATA *Dst,\r
- IN EFI_DHCP4_CONFIG_DATA *Src\r
+ OUT EFI_DHCP4_CONFIG_DATA *Dst,\r
+ IN EFI_DHCP4_CONFIG_DATA *Src\r
)\r
{\r
EFI_DHCP4_PACKET_OPTION **DstOptions;\r
EFI_DHCP4_PACKET_OPTION **SrcOptions;\r
- INTN Len;\r
+ UINTN Len;\r
UINT32 Index;\r
\r
CopyMem (Dst, Src, sizeof (*Dst));\r
\r
@param DhcpSb The DHCP service instance.\r
\r
- @return None\r
-\r
**/\r
VOID\r
DhcpYieldControl (\r
DhcpSb->ActiveChild = NULL;\r
\r
if (Config->DiscoverTimeout != NULL) {\r
- gBS->FreePool (Config->DiscoverTimeout);\r
+ FreePool (Config->DiscoverTimeout);\r
\r
Config->DiscoverTryCount = 0;\r
Config->DiscoverTimeout = NULL;\r
}\r
\r
if (Config->RequestTimeout != NULL) {\r
- gBS->FreePool (Config->RequestTimeout);\r
+ FreePool (Config->RequestTimeout);\r
\r
Config->RequestTryCount = 0;\r
Config->RequestTimeout = NULL;\r
\r
\r
/**\r
- Configure the DHCP protocol instance and its underlying DHCP service\r
- for operation. If Dhcp4CfgData is NULL and the child is currently\r
- controlling the DHCP service, release the control.\r
-\r
- @param This The DHCP protocol instance\r
- @param Dhcp4CfgData The DHCP configure data.\r
-\r
- @retval EFI_INVALID_PARAMETER The parameters are invalid.\r
- @retval EFI_ACCESS_DENIED The service isn't in one of configurable states,\r
- or there is already an active child.\r
- @retval EFI_OUT_OF_RESOURCE Failed to allocate some resources.\r
- @retval EFI_SUCCESS The child is configured.\r
+ Initializes, changes, or resets the operational settings for the EFI DHCPv4 Protocol driver.\r
+\r
+ The Configure() function is used to initialize, change, or reset the operational\r
+ settings of the EFI DHCPv4 Protocol driver for the communication device on which\r
+ the EFI DHCPv4 Service Binding Protocol is installed. This function can be\r
+ successfully called only if both of the following are true:\r
+ * This instance of the EFI DHCPv4 Protocol driver is in the Dhcp4Stopped, Dhcp4Init,\r
+ Dhcp4InitReboot, or Dhcp4Bound states.\r
+ * No other EFI DHCPv4 Protocol driver instance that is controlled by this EFI\r
+ DHCPv4 Service Binding Protocol driver instance has configured this EFI DHCPv4\r
+ Protocol driver.\r
+ When this driver is in the Dhcp4Stopped state, it can transfer into one of the\r
+ following two possible initial states:\r
+ * Dhcp4Init\r
+ * Dhcp4InitReboot\r
+ The driver can transfer into these states by calling Configure() with a non-NULL\r
+ Dhcp4CfgData. The driver will transfer into the appropriate state based on the\r
+ supplied client network address in the ClientAddress parameter and DHCP options\r
+ in the OptionList parameter as described in RFC 2131.\r
+ When Configure() is called successfully while Dhcp4CfgData is set to NULL, the\r
+ default configuring data will be reset in the EFI DHCPv4 Protocol driver and\r
+ the state of the EFI DHCPv4 Protocol driver will not be changed. If one instance\r
+ wants to make it possible for another instance to configure the EFI DHCPv4 Protocol\r
+ driver, it must call this function with Dhcp4CfgData set to NULL.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] Dhcp4CfgData Pointer to the EFI_DHCP4_CONFIG_DATA.\r
+\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the Dhcp4Init or\r
+ Dhcp4InitReboot state, if the original state of this driver\r
+ was Dhcp4Stopped and the value of Dhcp4CfgData was\r
+ not NULL. Otherwise, the state was left unchanged.\r
+ @retval EFI_ACCESS_DENIED This instance of the EFI DHCPv4 Protocol driver was not in the\r
+ Dhcp4Stopped, Dhcp4Init, Dhcp4InitReboot, or Dhcp4Bound state;\r
+ Or onother instance of this EFI DHCPv4 Protocol driver is already\r
+ in a valid configured state.\r
+ @retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
+ @retval EFI_OUT_OF_RESOURCES Required system resources could not be allocated.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
\r
**/\r
EFI_STATUS\r
}\r
\r
if (Dhcp4CfgData != NULL) {\r
- if (Dhcp4CfgData->DiscoverTryCount && (Dhcp4CfgData->DiscoverTimeout == NULL)) {\r
+ if ((Dhcp4CfgData->DiscoverTryCount != 0) && (Dhcp4CfgData->DiscoverTimeout == NULL)) {\r
return EFI_INVALID_PARAMETER;\r
}\r
\r
- if (Dhcp4CfgData->RequestTryCount && (Dhcp4CfgData->RequestTimeout == NULL)) {\r
+ if ((Dhcp4CfgData->RequestTryCount != 0) && (Dhcp4CfgData->RequestTimeout == NULL)) {\r
return EFI_INVALID_PARAMETER;\r
}\r
\r
- if (Dhcp4CfgData->OptionCount && (Dhcp4CfgData->OptionList == NULL)) {\r
+ if ((Dhcp4CfgData->OptionCount != 0) && (Dhcp4CfgData->OptionList == NULL)) {\r
return EFI_INVALID_PARAMETER;\r
}\r
\r
CopyMem (&Ip, &Dhcp4CfgData->ClientAddress, sizeof (IP4_ADDR));\r
-\r
- if ((Ip != 0) && !Ip4IsUnicast (NTOHL (Ip), 0)) {\r
-\r
+ if (IP4_IS_LOCAL_BROADCAST(NTOHL (Ip))) {\r
return EFI_INVALID_PARAMETER;\r
}\r
}\r
\r
\r
/**\r
- Start the DHCP process.\r
-\r
- @param This The DHCP protocol instance\r
- @param CompletionEvent The event to signal is address is acquired.\r
-\r
- @retval EFI_INVALID_PARAMETER The parameters are invalid.\r
- @retval EFI_NOT_STARTED The protocol hasn't been configured.\r
- @retval EFI_ALREADY_STARTED The DHCP process has already been started.\r
- @retval EFI_SUCCESS The DHCP process is started.\r
+ Starts the DHCP configuration process.\r
+\r
+ The Start() function starts the DHCP configuration process. This function can\r
+ be called only when the EFI DHCPv4 Protocol driver is in the Dhcp4Init or\r
+ Dhcp4InitReboot state.\r
+ If the DHCP process completes successfully, the state of the EFI DHCPv4 Protocol\r
+ driver will be transferred through Dhcp4Selecting and Dhcp4Requesting to the\r
+ Dhcp4Bound state. The CompletionEvent will then be signaled if it is not NULL.\r
+ If the process aborts, either by the user or by some unexpected network error,\r
+ the state is restored to the Dhcp4Init state. The Start() function can be called\r
+ again to restart the process.\r
+ Refer to RFC 2131 for precise state transitions during this process. At the\r
+ time when each event occurs in this process, the callback function that was set\r
+ by EFI_DHCP4_PROTOCOL.Configure() will be called and the user can take this\r
+ opportunity to control the process.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] CompletionEvent If not NULL, indicates the event that will be signaled when the\r
+ EFI DHCPv4 Protocol driver is transferred into the\r
+ Dhcp4Bound state or when the DHCP process is aborted.\r
+ EFI_DHCP4_PROTOCOL.GetModeData() can be called to\r
+ check the completion status. If NULL,\r
+ EFI_DHCP4_PROTOCOL.Start() will wait until the driver\r
+ is transferred into the Dhcp4Bound state or the process fails.\r
+\r
+ @retval EFI_SUCCESS The DHCP configuration process has started, or it has completed\r
+ when CompletionEvent is NULL.\r
+ @retval EFI_NOT_STARTED The EFI DHCPv4 Protocol driver is in the Dhcp4Stopped\r
+ state. EFI_DHCP4_PROTOCOL. Configure() needs to be called.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
+ @retval EFI_OUT_OF_RESOURCES Required system resources could not be allocated.\r
+ @retval EFI_TIMEOUT The DHCP configuration process failed because no response was\r
+ received from the server within the specified timeout value.\r
+ @retval EFI_ABORTED The user aborted the DHCP process.\r
+ @retval EFI_ALREADY_STARTED Some other EFI DHCPv4 Protocol instance already started the\r
+ DHCP process.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
+ @retval EFI_NO_MEDIA There was a media error.\r
\r
**/\r
EFI_STATUS\r
DHCP_SERVICE *DhcpSb;\r
EFI_STATUS Status;\r
EFI_TPL OldTpl;\r
+ EFI_STATUS MediaStatus;\r
\r
//\r
// First validate the parameters\r
goto ON_ERROR;\r
}\r
\r
- DhcpSb->IoStatus = EFI_ALREADY_STARTED;\r
-\r
- if (EFI_ERROR (Status = DhcpInitRequest (DhcpSb))) {\r
+ //\r
+ // Check Media Satus.\r
+ //\r
+ MediaStatus = EFI_SUCCESS;\r
+ NetLibDetectMediaWaitTimeout (DhcpSb->Controller, DHCP_CHECK_MEDIA_WAITING_TIME, &MediaStatus);\r
+ if (MediaStatus != EFI_SUCCESS) {\r
+ Status = EFI_NO_MEDIA;\r
goto ON_ERROR;\r
}\r
\r
- //\r
- // Start/Restart the receiving.\r
- //\r
- Status = UdpIoRecvDatagram (DhcpSb->UdpIo, DhcpInput, DhcpSb, 0);\r
+ DhcpSb->IoStatus = EFI_ALREADY_STARTED;\r
\r
- if (EFI_ERROR (Status) && (Status != EFI_ALREADY_STARTED)) {\r
+ if (EFI_ERROR (Status = DhcpInitRequest (DhcpSb))) {\r
goto ON_ERROR;\r
}\r
\r
+\r
Instance->CompletionEvent = CompletionEvent;\r
\r
//\r
\r
if (CompletionEvent == NULL) {\r
while (DhcpSb->IoStatus == EFI_ALREADY_STARTED) {\r
- DhcpSb->UdpIo->Udp->Poll (DhcpSb->UdpIo->Udp);\r
+ DhcpSb->UdpIo->Protocol.Udp4->Poll (DhcpSb->UdpIo->Protocol.Udp4);\r
}\r
\r
return DhcpSb->IoStatus;\r
\r
\r
/**\r
- Request an extra manual renew/rebind.\r
-\r
- @param This The DHCP protocol instance\r
- @param RebindRequest TRUE if request a rebind, otherwise renew it\r
- @param CompletionEvent Event to signal when complete\r
-\r
- @retval EFI_INVALID_PARAMETER The parameters are invalid\r
- @retval EFI_NOT_STARTED The DHCP protocol hasn't been started.\r
- @retval EFI_ACCESS_DENIED The DHCP protocol isn't in Bound state.\r
- @retval EFI_SUCCESS The DHCP is renewed/rebound.\r
+ Extends the lease time by sending a request packet.\r
+\r
+ The RenewRebind() function is used to manually extend the lease time when the\r
+ EFI DHCPv4 Protocol driver is in the Dhcp4Bound state and the lease time has\r
+ not expired yet. This function will send a request packet to the previously\r
+ found server (or to any server when RebindRequest is TRUE) and transfer the\r
+ state into the Dhcp4Renewing state (or Dhcp4Rebinding when RebindingRequest is\r
+ TRUE). When a response is received, the state is returned to Dhcp4Bound.\r
+ If no response is received before the try count is exceeded (the RequestTryCount\r
+ field that is specified in EFI_DHCP4_CONFIG_DATA) but before the lease time that\r
+ was issued by the previous server expires, the driver will return to the Dhcp4Bound\r
+ state and the previous configuration is restored. The outgoing and incoming packets\r
+ can be captured by the EFI_DHCP4_CALLBACK function.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] RebindRequest If TRUE, this function broadcasts the request packets and enters\r
+ the Dhcp4Rebinding state. Otherwise, it sends a unicast\r
+ request packet and enters the Dhcp4Renewing state.\r
+ @param[in] CompletionEvent If not NULL, this event is signaled when the renew/rebind phase\r
+ completes or some error occurs.\r
+ EFI_DHCP4_PROTOCOL.GetModeData() can be called to\r
+ check the completion status. If NULL,\r
+ EFI_DHCP4_PROTOCOL.RenewRebind() will busy-wait\r
+ until the DHCP process finishes.\r
+\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the\r
+ Dhcp4Renewing state or is back to the Dhcp4Bound state.\r
+ @retval EFI_NOT_STARTED The EFI DHCPv4 Protocol driver is in the Dhcp4Stopped\r
+ state. EFI_DHCP4_PROTOCOL.Configure() needs to\r
+ be called.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
+ @retval EFI_TIMEOUT There was no response from the server when the try count was\r
+ exceeded.\r
+ @retval EFI_ACCESS_DENIED The driver is not in the Dhcp4Bound state.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
\r
**/\r
EFI_STATUS\r
\r
if (DhcpSb->DhcpState == Dhcp4Stopped) {\r
Status = EFI_NOT_STARTED;\r
- goto ON_ERROR;\r
+ goto ON_EXIT;\r
}\r
\r
if (DhcpSb->DhcpState != Dhcp4Bound) {\r
Status = EFI_ACCESS_DENIED;\r
- goto ON_ERROR;\r
+ goto ON_EXIT;\r
}\r
\r
if (DHCP_IS_BOOTP (DhcpSb->Para)) {\r
- return EFI_SUCCESS;\r
+ Status = EFI_SUCCESS;\r
+ goto ON_EXIT;\r
}\r
\r
//\r
DhcpSetState (DhcpSb, Dhcp4Rebinding, FALSE);\r
}\r
\r
+ //\r
+ // Clear initial time to make sure that elapsed-time\r
+ // is set to 0 for first REQUEST in renewal process.\r
+ //\r
+ Instance->ElaspedTime = 0;\r
+\r
Status = DhcpSendMessage (\r
DhcpSb,\r
DhcpSb->Selected,\r
\r
if (EFI_ERROR (Status)) {\r
DhcpSetState (DhcpSb, Dhcp4Bound, FALSE);\r
- goto ON_ERROR;\r
+ goto ON_EXIT;\r
}\r
\r
DhcpSb->ExtraRefresh = TRUE;\r
\r
if (CompletionEvent == NULL) {\r
while (DhcpSb->IoStatus == EFI_ALREADY_STARTED) {\r
- DhcpSb->UdpIo->Udp->Poll (DhcpSb->UdpIo->Udp);\r
+ DhcpSb->UdpIo->Protocol.Udp4->Poll (DhcpSb->UdpIo->Protocol.Udp4);\r
+\r
}\r
\r
return DhcpSb->IoStatus;\r
\r
return EFI_SUCCESS;\r
\r
-ON_ERROR:\r
+ON_EXIT:\r
gBS->RestoreTPL (OldTpl);\r
return Status;\r
}\r
\r
\r
/**\r
- Release the current acquired lease.\r
+ Releases the current address configuration.\r
+\r
+ The Release() function releases the current configured IP address by doing either\r
+ of the following:\r
+ * Sending a DHCPRELEASE packet when the EFI DHCPv4 Protocol driver is in the\r
+ Dhcp4Bound state\r
+ * Setting the previously assigned IP address that was provided with the\r
+ EFI_DHCP4_PROTOCOL.Configure() function to 0.0.0.0 when the driver is in\r
+ Dhcp4InitReboot state\r
+ After a successful call to this function, the EFI DHCPv4 Protocol driver returns\r
+ to the Dhcp4Init state and any subsequent incoming packets will be discarded silently.\r
\r
- @param This The DHCP protocol instance\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
\r
- @retval EFI_INVALID_PARAMETER The parameter is invalid\r
- @retval EFI_DEVICE_ERROR Failed to transmit the DHCP release packet\r
- @retval EFI_ACCESS_DENIED The DHCP service isn't in one of the connected\r
- state.\r
- @retval EFI_SUCCESS The lease is released.\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the Dhcp4Init phase.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
+ @retval EFI_ACCESS_DENIED The EFI DHCPv4 Protocol driver is not Dhcp4InitReboot state.\r
+ @retval EFI_DEVICE_ERROR An unexpected system or network error occurred.\r
\r
**/\r
EFI_STATUS\r
\r
\r
/**\r
- Stop the current DHCP process. After this, other DHCP child\r
- can gain control of the service, configure and use it.\r
+ Stops the current address configuration.\r
\r
- @param This The DHCP protocol instance\r
+ The Stop() function is used to stop the DHCP configuration process. After this\r
+ function is called successfully, the EFI DHCPv4 Protocol driver is transferred\r
+ into the Dhcp4Stopped state. EFI_DHCP4_PROTOCOL.Configure() needs to be called\r
+ before DHCP configuration process can be started again. This function can be\r
+ called when the EFI DHCPv4 Protocol driver is in any state.\r
\r
- @retval EFI_INVALID_PARAMETER The parameter is invalid.\r
- @retval EFI_SUCCESS The DHCP process is stopped.\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+\r
+ @retval EFI_SUCCESS The EFI DHCPv4 Protocol driver is now in the Dhcp4Stopped phase.\r
+ @retval EFI_INVALID_PARAMETER This is NULL.\r
\r
**/\r
EFI_STATUS\r
\r
\r
/**\r
- Build a new DHCP packet from the seed packet. Options may be deleted or\r
- appended. The caller should free the NewPacket when finished using it.\r
-\r
- @param This The DHCP protocol instance.\r
- @param SeedPacket The seed packet to start with\r
- @param DeleteCount The number of options to delete\r
- @param DeleteList The options to delete from the packet\r
- @param AppendCount The number of options to append\r
- @param AppendList The options to append to the packet\r
- @param NewPacket The new packet, allocated and built by this\r
- function.\r
-\r
- @retval EFI_INVALID_PARAMETER The parameters are invalid.\r
- @retval EFI_OUT_OF_RESOURCES Failed to allocate memory\r
- @retval EFI_SUCCESS The packet is build.\r
+ Builds a DHCP packet, given the options to be appended or deleted or replaced.\r
+\r
+ The Build() function is used to assemble a new packet from the original packet\r
+ by replacing or deleting existing options or appending new options. This function\r
+ does not change any state of the EFI DHCPv4 Protocol driver and can be used at\r
+ any time.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] SeedPacket Initial packet to be used as a base for building new packet.\r
+ @param[in] DeleteCount Number of opcodes in the DeleteList.\r
+ @param[in] DeleteList List of opcodes to be deleted from the seed packet.\r
+ Ignored if DeleteCount is zero.\r
+ @param[in] AppendCount Number of entries in the OptionList.\r
+ @param[in] AppendList Pointer to a DHCP option list to be appended to SeedPacket.\r
+ If SeedPacket also contains options in this list, they are\r
+ replaced by new options (except pad option). Ignored if\r
+ AppendCount is zero. Type EFI_DHCP4_PACKET_OPTION\r
+ @param[out] NewPacket Pointer to storage for the pointer to the new allocated packet.\r
+ Use the EFI Boot Service FreePool() on the resulting pointer\r
+ when done with the packet.\r
+\r
+ @retval EFI_SUCCESS The new packet was built.\r
+ @retval EFI_OUT_OF_RESOURCES Storage for the new packet could not be allocated.\r
+ @retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
\r
**/\r
EFI_STATUS\r
);\r
}\r
\r
+/**\r
+ Callback by UdpIoCreatePort() when creating UdpIo for this Dhcp4 instance.\r
+\r
+ @param[in] UdpIo The UdpIo being created.\r
+ @param[in] Context Dhcp4 instance.\r
+\r
+ @retval EFI_SUCCESS UdpIo is configured successfully.\r
+ @retval EFI_INVALID_PARAMETER Class E IP address is not supported or other parameters\r
+ are not valid.\r
+ @retval other Other error occurs.\r
+**/\r
EFI_STATUS\r
+EFIAPI\r
Dhcp4InstanceConfigUdpIo (\r
- IN UDP_IO_PORT *UdpIo,\r
+ IN UDP_IO *UdpIo,\r
IN VOID *Context\r
)\r
{\r
DHCP_SERVICE *DhcpSb;\r
EFI_DHCP4_TRANSMIT_RECEIVE_TOKEN *Token;\r
EFI_UDP4_CONFIG_DATA UdpConfigData;\r
+ IP4_ADDR ClientAddr;\r
IP4_ADDR Ip;\r
+ INTN Class;\r
+ IP4_ADDR SubnetMask;\r
\r
Instance = (DHCP_PROTOCOL *) Context;\r
DhcpSb = Instance->Service;\r
UdpConfigData.TimeToLive = 64;\r
UdpConfigData.DoNotFragment = TRUE;\r
\r
- Ip = HTONL (DhcpSb->ClientAddr);\r
+ ClientAddr = EFI_NTOHL (Token->Packet->Dhcp4.Header.ClientAddr);\r
+ Ip = HTONL (ClientAddr);\r
CopyMem (&UdpConfigData.StationAddress, &Ip, sizeof (EFI_IPv4_ADDRESS));\r
\r
- Ip = HTONL (DhcpSb->Netmask);\r
+ if (DhcpSb->Netmask == 0) {\r
+ //\r
+ // The Dhcp4.TransmitReceive() API should be able to used at any time according to\r
+ // UEFI spec, while in classless addressing network, the netmask must be explicitly\r
+ // provided together with the station address.\r
+ // If the DHCP instance haven't be configured with a valid netmask, we could only\r
+ // compute it according to the classful addressing rule.\r
+ //\r
+ Class = NetGetIpClass (ClientAddr);\r
+ //\r
+ // Class E IP address is not supported here!\r
+ //\r
+ ASSERT (Class < IP4_ADDR_CLASSE);\r
+ if (Class >= IP4_ADDR_CLASSE) {\r
+ return EFI_INVALID_PARAMETER;\r
+ }\r
+\r
+ SubnetMask = gIp4AllMasks[Class << 3];\r
+ } else {\r
+ SubnetMask = DhcpSb->Netmask;\r
+ }\r
+\r
+ Ip = HTONL (SubnetMask);\r
CopyMem (&UdpConfigData.SubnetMask, &Ip, sizeof (EFI_IPv4_ADDRESS));\r
\r
if ((Token->ListenPointCount == 0) || (Token->ListenPoints[0].ListenPort == 0)) {\r
UdpConfigData.StationPort = Token->ListenPoints[0].ListenPort;\r
}\r
\r
- return UdpIo->Udp->Configure (UdpIo->Udp, &UdpConfigData);\r
+ return UdpIo->Protocol.Udp4->Configure (UdpIo->Protocol.Udp4, &UdpConfigData);\r
}\r
\r
+/**\r
+ Create UdpIo for this Dhcp4 instance.\r
+\r
+ @param Instance The Dhcp4 instance.\r
+\r
+ @retval EFI_SUCCESS UdpIo is created successfully.\r
+ @retval EFI_OUT_OF_RESOURCES Fails to create UdpIo because of limited\r
+ resources or configuration failure.\r
+**/\r
EFI_STATUS\r
Dhcp4InstanceCreateUdpIo (\r
- IN DHCP_PROTOCOL *Instance\r
+ IN OUT DHCP_PROTOCOL *Instance\r
)\r
{\r
DHCP_SERVICE *DhcpSb;\r
+ EFI_STATUS Status;\r
+ VOID *Udp4;\r
\r
ASSERT (Instance->Token != NULL);\r
\r
DhcpSb = Instance->Service;\r
- Instance->UdpIo = UdpIoCreatePort (DhcpSb->Controller, DhcpSb->Image, Dhcp4InstanceConfigUdpIo, Instance);\r
+ Instance->UdpIo = UdpIoCreateIo (\r
+ DhcpSb->Controller,\r
+ DhcpSb->Image,\r
+ Dhcp4InstanceConfigUdpIo,\r
+ UDP_IO_UDP4_VERSION,\r
+ Instance\r
+ );\r
if (Instance->UdpIo == NULL) {\r
return EFI_OUT_OF_RESOURCES;\r
} else {\r
- return EFI_SUCCESS;\r
+ Status = gBS->OpenProtocol (\r
+ Instance->UdpIo->UdpHandle,\r
+ &gEfiUdp4ProtocolGuid,\r
+ (VOID **) &Udp4,\r
+ Instance->Service->Image,\r
+ Instance->Handle,\r
+ EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER\r
+ );\r
+ if (EFI_ERROR (Status)) {\r
+ UdpIoFreeIo (Instance->UdpIo);\r
+ Instance->UdpIo = NULL;\r
+ }\r
+ return Status;\r
}\r
}\r
\r
+/**\r
+ Callback of Dhcp packet. Does nothing.\r
+\r
+ @param Arg The context.\r
+\r
+**/\r
VOID\r
+EFIAPI\r
DhcpDummyExtFree (\r
IN VOID *Arg\r
)\r
-/*++\r
-\r
-Routine Description:\r
-\r
- Release the packet.\r
-\r
-Arguments:\r
-\r
- Arg - The packet to release\r
+{\r
+}\r
\r
-Returns:\r
+/**\r
+ Callback of UdpIoRecvDatagram() that handles a Dhcp4 packet.\r
\r
- None\r
+ Only BOOTP responses will be handled that correspond to the Xid of the request\r
+ sent out. The packet will be queued to the response queue.\r
\r
---*/\r
-{\r
-}\r
+ @param UdpPacket The Dhcp4 packet.\r
+ @param EndPoint Udp4 address pair.\r
+ @param IoStatus Status of the input.\r
+ @param Context Extra info for the input.\r
\r
+**/\r
VOID\r
+EFIAPI\r
PxeDhcpInput (\r
NET_BUF *UdpPacket,\r
- UDP_POINTS *Points,\r
+ UDP_END_POINT *EndPoint,\r
EFI_STATUS IoStatus,\r
VOID *Context\r
)\r
{\r
DHCP_PROTOCOL *Instance;\r
- DHCP_SERVICE *DhcpSb;\r
EFI_DHCP4_HEADER *Head;\r
NET_BUF *Wrap;\r
EFI_DHCP4_PACKET *Packet;\r
Wrap = NULL;\r
Instance = (DHCP_PROTOCOL *) Context;\r
Token = Instance->Token;\r
- DhcpSb = Instance->Service;\r
\r
//\r
- // Don't restart receive if error occurs or DHCP is destoried.\r
+ // Don't restart receive if error occurs or DHCP is destroyed.\r
//\r
if (EFI_ERROR (IoStatus)) {\r
return ;\r
//\r
Len = NET_ROUNDUP (sizeof (EFI_DHCP4_PACKET) + UdpPacket->TotalSize - sizeof (EFI_DHCP4_HEADER), 4);\r
Wrap = NetbufAlloc (Len);\r
-\r
if (Wrap == NULL) {\r
goto RESTART;\r
}\r
\r
Packet = (EFI_DHCP4_PACKET *) NetbufAllocSpace (Wrap, Len, NET_BUF_TAIL);\r
+ ASSERT (Packet != NULL);\r
+\r
Packet->Size = Len;\r
Head = &Packet->Dhcp4.Header;\r
Packet->Length = NetbufCopy (UdpPacket, 0, UdpPacket->TotalSize, (UINT8 *) Head);\r
//\r
if ((Head->OpCode != BOOTP_REPLY) ||\r
(Head->Xid != Token->Packet->Dhcp4.Header.Xid) ||\r
- (CompareMem (DhcpSb->ClientAddressSendOut, Head->ClientHwAddr, Head->HwAddrLen) != 0)) {\r
+ (CompareMem (&Token->Packet->Dhcp4.Header.ClientHwAddr[0], Head->ClientHwAddr, Head->HwAddrLen) != 0)) {\r
goto RESTART;\r
}\r
\r
}\r
}\r
\r
+/**\r
+ Complete a Dhcp4 transaction and signal the upper layer.\r
+\r
+ @param Instance Dhcp4 instance.\r
+\r
+**/\r
VOID\r
PxeDhcpDone (\r
IN DHCP_PROTOCOL *Instance\r
}\r
\r
//\r
- // Copy the recieved DHCP responses.\r
+ // Copy the received DHCP responses.\r
//\r
NetbufQueCopy (&Instance->ResponseQueue, 0, Instance->ResponseQueue.BufSize, (UINT8 *) Token->ResponseList);\r
Token->Status = EFI_SUCCESS;\r
\r
SIGNAL_USER:\r
//\r
- // Clean the resources dedicated for this transmit receive transaction.\r
+ // Clean up the resources dedicated for this transmit receive transaction.\r
//\r
NetbufQueFlush (&Instance->ResponseQueue);\r
- UdpIoCleanPort (Instance->UdpIo);\r
- UdpIoFreePort (Instance->UdpIo);\r
+ UdpIoCleanIo (Instance->UdpIo);\r
+ gBS->CloseProtocol (\r
+ Instance->UdpIo->UdpHandle,\r
+ &gEfiUdp4ProtocolGuid,\r
+ Instance->Service->Image,\r
+ Instance->Handle\r
+ );\r
+ UdpIoFreeIo (Instance->UdpIo);\r
Instance->UdpIo = NULL;\r
Instance->Token = NULL;\r
\r
/**\r
Transmits a DHCP formatted packet and optionally waits for responses.\r
\r
- @param This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
- @param Token Pointer to the EFI_DHCP4_TRANSMIT_RECEIVE_TOKEN structure.\r
+ The TransmitReceive() function is used to transmit a DHCP packet and optionally\r
+ wait for the response from servers. This function does not change the state of\r
+ the EFI DHCPv4 Protocol driver and thus can be used at any time.\r
+\r
+ @param[in] This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param[in] Token Pointer to the EFI_DHCP4_TRANSMIT_RECEIVE_TOKEN structure.\r
\r
@retval EFI_SUCCESS The packet was successfully queued for transmission.\r
@retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
EFI_STATUS Status;\r
NET_FRAGMENT Frag;\r
NET_BUF *Wrap;\r
- UDP_POINTS EndPoint;\r
+ UDP_END_POINT EndPoint;\r
IP4_ADDR Ip;\r
DHCP_SERVICE *DhcpSb;\r
- IP4_ADDR Gateway;\r
- IP4_ADDR SubnetMask;\r
+ EFI_IP_ADDRESS Gateway;\r
+ IP4_ADDR ClientAddr;\r
\r
if ((This == NULL) || (Token == NULL) || (Token->Packet == NULL)) {\r
return EFI_INVALID_PARAMETER;\r
return EFI_NOT_READY;\r
}\r
\r
- if ((Token->Packet->Dhcp4.Magik != DHCP_OPTION_MAGIC) ||\r
- (NTOHL (Token->Packet->Dhcp4.Header.Xid) == Instance->Service->Xid) ||\r
- (Token->TimeoutValue == 0) ||\r
- ((Token->ListenPointCount != 0) && (Token->ListenPoints == NULL)) ||\r
- EFI_ERROR (DhcpValidateOptions (Token->Packet, NULL)) ||\r
- EFI_IP4_EQUAL (&Token->RemoteAddress, &mZeroIp4Addr)) {\r
+ if ((Token->Packet->Dhcp4.Magik != DHCP_OPTION_MAGIC) ||\r
+ (NTOHL (Token->Packet->Dhcp4.Header.Xid) == Instance->Service->Xid) ||\r
+ (Token->TimeoutValue == 0) ||\r
+ ((Token->ListenPointCount != 0) && (Token->ListenPoints == NULL)) ||\r
+ EFI_ERROR (DhcpValidateOptions (Token->Packet, NULL)) ||\r
+ EFI_IP4_EQUAL (&Token->RemoteAddress, &mZeroIp4Addr)\r
+ ) {\r
//\r
- // The DHCP packet isn't well-formed, the Transaction ID is already used\r
- // , the timeout value is zero, the ListenPoint is invalid,\r
- // or the RemoteAddress is zero.\r
+ // The DHCP packet isn't well-formed, the Transaction ID is already used,\r
+ // the timeout value is zero, the ListenPoint is invalid, or the\r
+ // RemoteAddress is zero.\r
//\r
return EFI_INVALID_PARAMETER;\r
}\r
\r
- if (DhcpSb->ClientAddr == 0) {\r
+ ClientAddr = EFI_NTOHL (Token->Packet->Dhcp4.Header.ClientAddr);\r
\r
+ if (ClientAddr == 0) {\r
return EFI_NO_MAPPING;\r
}\r
\r
//\r
// Save the Client Address is sent out\r
//\r
- CopyMem (&DhcpSb->ClientAddressSendOut[0], &Token->Packet->Dhcp4.Header.ClientHwAddr[0], Token->Packet->Dhcp4.Header.HwAddrLen);\r
+ CopyMem (\r
+ &DhcpSb->ClientAddressSendOut[0],\r
+ &Token->Packet->Dhcp4.Header.ClientHwAddr[0],\r
+ Token->Packet->Dhcp4.Header.HwAddrLen\r
+ );\r
\r
//\r
// Wrap the DHCP packet into a net buffer.\r
}\r
\r
//\r
- // Set the local address and local port.\r
+ // Set the local address and local port to ZERO.\r
//\r
- EndPoint.LocalAddr = 0;\r
- EndPoint.LocalPort = 0;\r
+ ZeroMem (&EndPoint, sizeof (UDP_END_POINT));\r
\r
//\r
// Set the destination address and destination port.\r
//\r
CopyMem (&Ip, &Token->RemoteAddress, sizeof (EFI_IPv4_ADDRESS));\r
- EndPoint.RemoteAddr = NTOHL (Ip);\r
+ EndPoint.RemoteAddr.Addr[0] = NTOHL (Ip);\r
\r
if (Token->RemotePort == 0) {\r
EndPoint.RemotePort = DHCP_SERVER_PORT;\r
//\r
// Get the gateway.\r
//\r
- SubnetMask = DhcpSb->Netmask;\r
- Gateway = 0;\r
- if (!IP4_NET_EQUAL (DhcpSb->ClientAddr, EndPoint.RemoteAddr, SubnetMask)) {\r
- CopyMem (&Gateway, &Token->GatewayAddress, sizeof (EFI_IPv4_ADDRESS));\r
- Gateway = NTOHL (Gateway);\r
+ ZeroMem (&Gateway, sizeof (Gateway));\r
+ if (!IP4_NET_EQUAL (ClientAddr, EndPoint.RemoteAddr.Addr[0], DhcpSb->Netmask)) {\r
+ CopyMem (&Gateway.v4, &Token->GatewayAddress, sizeof (EFI_IPv4_ADDRESS));\r
+ Gateway.Addr[0] = NTOHL (Gateway.Addr[0]);\r
}\r
\r
//\r
// Transmit the DHCP packet.\r
//\r
- Status = UdpIoSendDatagram (Instance->UdpIo, Wrap, &EndPoint, Gateway, DhcpOnPacketSent, NULL);\r
+ Status = UdpIoSendDatagram (Instance->UdpIo, Wrap, &EndPoint, &Gateway, DhcpOnPacketSent, NULL);\r
if (EFI_ERROR (Status)) {\r
NetbufFree (Wrap);\r
goto ON_ERROR;\r
ON_ERROR:\r
\r
if (EFI_ERROR (Status) && (Instance->UdpIo != NULL)) {\r
- UdpIoCleanPort (Instance->UdpIo);\r
- UdpIoFreePort (Instance->UdpIo);\r
+ UdpIoCleanIo (Instance->UdpIo);\r
+ gBS->CloseProtocol (\r
+ Instance->UdpIo->UdpHandle,\r
+ &gEfiUdp4ProtocolGuid,\r
+ Instance->Service->Image,\r
+ Instance->Handle\r
+ );\r
+ UdpIoFreeIo (Instance->UdpIo);\r
Instance->UdpIo = NULL;\r
Instance->Token = NULL;\r
}\r
// Keep polling until timeout if no error happens and the CompletionEvent\r
// is NULL.\r
//\r
- while (Instance->Timeout != 0) {\r
- Instance->UdpIo->Udp->Poll (Instance->UdpIo->Udp);\r
+ while (TRUE) {\r
+ OldTpl = gBS->RaiseTPL (TPL_CALLBACK);\r
+ //\r
+ // Raise TPL to protect the UDPIO in instance, in case that DhcpOnTimerTick\r
+ // free it when timeout.\r
+ //\r
+ if (Instance->Timeout > 0) {\r
+ Instance->UdpIo->Protocol.Udp4->Poll (Instance->UdpIo->Protocol.Udp4);\r
+ gBS->RestoreTPL (OldTpl);\r
+ } else {\r
+ gBS->RestoreTPL (OldTpl);\r
+ break;\r
+ }\r
}\r
}\r
\r
EFI_DHCP4_PACKET_OPTION array in the DHCP_PARSE_CONTEXT to point\r
the individual DHCP option in the packet.\r
\r
- @param Tag The DHCP option type\r
- @param Len length of the DHCP option data\r
- @param Data The DHCP option data\r
- @param Context The context, to pass several parameters in.\r
+ @param[in] Tag The DHCP option type\r
+ @param[in] Len Length of the DHCP option data\r
+ @param[in] Data The DHCP option data\r
+ @param[in] Context The context, to pass several parameters in.\r
\r
@retval EFI_SUCCESS It always returns EFI_SUCCESS\r
\r
\r
if (Parse->Index <= Parse->OptionCount) {\r
//\r
- // Use _CR to get the memory position of EFI_DHCP4_PACKET_OPTION for\r
+ // Use BASE_CR to get the memory position of EFI_DHCP4_PACKET_OPTION for\r
// the EFI_DHCP4_PACKET_OPTION->Data because DhcpIterateOptions only\r
// pass in the point to option data.\r
//\r
- Parse->Option[Parse->Index - 1] = _CR (Data, EFI_DHCP4_PACKET_OPTION, Data);\r
+ Parse->Option[Parse->Index - 1] = BASE_CR (Data, EFI_DHCP4_PACKET_OPTION, Data);\r
}\r
\r
return EFI_SUCCESS;\r
\r
\r
/**\r
- Parse the DHCP options in the Packet into the PacketOptionList.\r
- User should allocate this array of EFI_DHCP4_PACKET_OPTION points.\r
-\r
- @param This The DHCP protocol instance\r
- @param Packet The DHCP packet to parse\r
- @param OptionCount On input, the size of the PacketOptionList; On\r
- output, the actual number of options processed.\r
- @param PacketOptionList The array of EFI_DHCP4_PACKET_OPTION points\r
-\r
- @retval EFI_INVALID_PARAMETER The parameters are invalid.\r
- @retval EFI_BUFFER_TOO_SMALL A bigger array of points is needed.\r
- @retval EFI_SUCCESS The options are parsed.\r
+ Parses the packed DHCP option data.\r
+\r
+ The Parse() function is used to retrieve the option list from a DHCP packet.\r
+ If *OptionCount isn't zero, and there is enough space for all the DHCP options\r
+ in the Packet, each element of PacketOptionList is set to point to somewhere in\r
+ the Packet->Dhcp4.Option where a new DHCP option begins. If RFC3396 is supported,\r
+ the caller should reassemble the parsed DHCP options to get the finial result.\r
+ If *OptionCount is zero or there isn't enough space for all of them, the number\r
+ of DHCP options in the Packet is returned in OptionCount.\r
+\r
+ @param This Pointer to the EFI_DHCP4_PROTOCOL instance.\r
+ @param Packet Pointer to packet to be parsed.\r
+ @param OptionCount On input, the number of entries in the PacketOptionList.\r
+ On output, the number of entries that were written into the\r
+ PacketOptionList.\r
+ @param PacketOptionList List of packet option entries to be filled in. End option or pad\r
+ options are not included.\r
+\r
+ @retval EFI_SUCCESS The packet was successfully parsed.\r
+ @retval EFI_INVALID_PARAMETER Some parameter is NULL.\r
+ @retval EFI_BUFFER_TOO_SMALL One or more of the following conditions is TRUE:\r
+ 1) *OptionCount is smaller than the number of options that\r
+ were found in the Packet.\r
+ 2) PacketOptionList is NULL.\r
\r
**/\r
EFI_STATUS\r
return EFI_SUCCESS;\r
}\r
\r
-EFI_DHCP4_PROTOCOL mDhcp4ProtocolTemplate = {\r
- EfiDhcp4GetModeData,\r
- EfiDhcp4Configure,\r
- EfiDhcp4Start,\r
- EfiDhcp4RenewRebind,\r
- EfiDhcp4Release,\r
- EfiDhcp4Stop,\r
- EfiDhcp4Build,\r
- EfiDhcp4TransmitReceive,\r
- EfiDhcp4Parse\r
-};\r
+/**\r
+ Set the elapsed time based on the given instance and the pointer to the\r
+ elapsed time option.\r
\r
+ @param[in] Elapsed The pointer to the position to append.\r
+ @param[in] Instance The pointer to the Dhcp4 instance.\r
+**/\r
+VOID\r
+SetElapsedTime (\r
+ IN UINT16 *Elapsed,\r
+ IN DHCP_PROTOCOL *Instance\r
+ )\r
+{\r
+ WriteUnaligned16 (Elapsed, HTONS(Instance->ElaspedTime));\r
+}\r