mirror of
https://github.com/lwip-tcpip/lwip.git
synced 2024-10-05 22:29:49 +00:00
The DHCP client should enter the REBOOTING state when connecting to a
new network. If DHCP has bound to an address, it must be verified after netif_set_link_up.
This commit is contained in:
parent
d83fc6893b
commit
103ba9b0fc
@ -100,6 +100,8 @@
|
|||||||
#define DHCP_MAX_MSG_LEN(netif) (netif->mtu)
|
#define DHCP_MAX_MSG_LEN(netif) (netif->mtu)
|
||||||
#define DHCP_MAX_MSG_LEN_MIN_REQUIRED 576
|
#define DHCP_MAX_MSG_LEN_MIN_REQUIRED 576
|
||||||
|
|
||||||
|
#define REBOOT_TRIES 2
|
||||||
|
|
||||||
/* DHCP client state machine functions */
|
/* DHCP client state machine functions */
|
||||||
static void dhcp_handle_ack(struct netif *netif);
|
static void dhcp_handle_ack(struct netif *netif);
|
||||||
static void dhcp_handle_nak(struct netif *netif);
|
static void dhcp_handle_nak(struct netif *netif);
|
||||||
@ -113,6 +115,7 @@ static void dhcp_bind(struct netif *netif);
|
|||||||
static err_t dhcp_decline(struct netif *netif);
|
static err_t dhcp_decline(struct netif *netif);
|
||||||
#endif /* DHCP_DOES_ARP_CHECK */
|
#endif /* DHCP_DOES_ARP_CHECK */
|
||||||
static err_t dhcp_rebind(struct netif *netif);
|
static err_t dhcp_rebind(struct netif *netif);
|
||||||
|
static err_t dhcp_reboot(struct netif *netif);
|
||||||
static void dhcp_set_state(struct dhcp *dhcp, u8_t new_state);
|
static void dhcp_set_state(struct dhcp *dhcp, u8_t new_state);
|
||||||
|
|
||||||
/* receive, unfold, parse and free incoming messages */
|
/* receive, unfold, parse and free incoming messages */
|
||||||
@ -421,6 +424,12 @@ dhcp_timeout(struct netif *netif)
|
|||||||
dhcp_release(netif);
|
dhcp_release(netif);
|
||||||
dhcp_discover(netif);
|
dhcp_discover(netif);
|
||||||
}
|
}
|
||||||
|
} else if (dhcp->state == DHCP_REBOOTING) {
|
||||||
|
if (dhcp->tries < REBOOT_TRIES) {
|
||||||
|
dhcp_reboot(netif);
|
||||||
|
} else {
|
||||||
|
dhcp_discover(netif);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -705,6 +714,36 @@ dhcp_inform(struct netif *netif)
|
|||||||
netif->dhcp = old_dhcp;
|
netif->dhcp = old_dhcp;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Handle a possible change in the network configuration.
|
||||||
|
*
|
||||||
|
* This enters the REBOOTING state to verify that the currently bound
|
||||||
|
* address is still valid.
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
dhcp_network_changed(struct netif *netif)
|
||||||
|
{
|
||||||
|
struct dhcp *dhcp = netif->dhcp;
|
||||||
|
if (!dhcp)
|
||||||
|
return;
|
||||||
|
switch (dhcp->state) {
|
||||||
|
case DHCP_REBINDING:
|
||||||
|
case DHCP_RENEWING:
|
||||||
|
case DHCP_BOUND:
|
||||||
|
case DHCP_REBOOTING:
|
||||||
|
netif_set_down(netif);
|
||||||
|
dhcp->tries = 0;
|
||||||
|
dhcp_reboot(netif);
|
||||||
|
break;
|
||||||
|
case DHCP_OFF:
|
||||||
|
/* stay off */
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
dhcp->tries = 0;
|
||||||
|
dhcp_discover(netif);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#if DHCP_DOES_ARP_CHECK
|
#if DHCP_DOES_ARP_CHECK
|
||||||
/**
|
/**
|
||||||
* Match an ARP reply with the offered IP address.
|
* Match an ARP reply with the offered IP address.
|
||||||
@ -1054,6 +1093,53 @@ dhcp_rebind(struct netif *netif)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Enter REBOOTING state to verify an existing lease
|
||||||
|
*
|
||||||
|
* @param netif network interface which must reboot
|
||||||
|
*/
|
||||||
|
static err_t
|
||||||
|
dhcp_reboot(struct netif *netif)
|
||||||
|
{
|
||||||
|
struct dhcp *dhcp = netif->dhcp;
|
||||||
|
err_t result;
|
||||||
|
u16_t msecs;
|
||||||
|
LWIP_DEBUGF(DHCP_DEBUG | LWIP_DBG_TRACE | LWIP_DBG_STATE, ("dhcp_reboot()\n"));
|
||||||
|
dhcp_set_state(dhcp, DHCP_REBOOTING);
|
||||||
|
|
||||||
|
/* create and initialize the DHCP message header */
|
||||||
|
result = dhcp_create_request(netif);
|
||||||
|
if (result == ERR_OK) {
|
||||||
|
|
||||||
|
dhcp_option(dhcp, DHCP_OPTION_MESSAGE_TYPE, DHCP_OPTION_MESSAGE_TYPE_LEN);
|
||||||
|
dhcp_option_byte(dhcp, DHCP_REQUEST);
|
||||||
|
|
||||||
|
dhcp_option(dhcp, DHCP_OPTION_MAX_MSG_SIZE, DHCP_OPTION_MAX_MSG_SIZE_LEN);
|
||||||
|
dhcp_option_short(dhcp, 576);
|
||||||
|
|
||||||
|
dhcp_option(dhcp, DHCP_OPTION_REQUESTED_IP, 4);
|
||||||
|
dhcp_option_long(dhcp, ntohl(dhcp->offered_ip_addr.addr));
|
||||||
|
|
||||||
|
dhcp_option_trailer(dhcp);
|
||||||
|
|
||||||
|
pbuf_realloc(dhcp->p_out, sizeof(struct dhcp_msg) - DHCP_OPTIONS_LEN + dhcp->options_out_len);
|
||||||
|
|
||||||
|
/* broadcast to server */
|
||||||
|
udp_connect(dhcp->pcb, IP_ADDR_ANY, DHCP_SERVER_PORT);
|
||||||
|
udp_sendto_if(dhcp->pcb, dhcp->p_out, IP_ADDR_BROADCAST, DHCP_SERVER_PORT, netif);
|
||||||
|
dhcp_delete_request(netif);
|
||||||
|
LWIP_DEBUGF(DHCP_DEBUG | LWIP_DBG_TRACE | LWIP_DBG_STATE, ("dhcp_reboot: REBOOTING\n"));
|
||||||
|
} else {
|
||||||
|
LWIP_DEBUGF(DHCP_DEBUG | LWIP_DBG_TRACE | 2, ("dhcp_reboot: could not allocate DHCP request\n"));
|
||||||
|
}
|
||||||
|
dhcp->tries++;
|
||||||
|
msecs = dhcp->tries < 10 ? dhcp->tries * 1000 : 10 * 1000;
|
||||||
|
dhcp->request_timeout = (msecs + DHCP_FINE_TIMER_MSECS - 1) / DHCP_FINE_TIMER_MSECS;
|
||||||
|
LWIP_DEBUGF(DHCP_DEBUG | LWIP_DBG_TRACE | LWIP_DBG_STATE, ("dhcp_reboot(): set request timeout %"U16_F" msecs\n", msecs));
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Release a DHCP lease.
|
* Release a DHCP lease.
|
||||||
*
|
*
|
||||||
|
@ -55,6 +55,9 @@
|
|||||||
#if LWIP_AUTOIP
|
#if LWIP_AUTOIP
|
||||||
#include "lwip/autoip.h"
|
#include "lwip/autoip.h"
|
||||||
#endif /* LWIP_AUTOIP */
|
#endif /* LWIP_AUTOIP */
|
||||||
|
#if LWIP_DHCP
|
||||||
|
#include "lwip/dhcp.h"
|
||||||
|
#endif /* LWIP_DHCP */
|
||||||
|
|
||||||
#if LWIP_NETIF_STATUS_CALLBACK
|
#if LWIP_NETIF_STATUS_CALLBACK
|
||||||
#define NETIF_STATUS_CALLBACK(n) { if (n->status_callback) (n->status_callback)(n); }
|
#define NETIF_STATUS_CALLBACK(n) { if (n->status_callback) (n->status_callback)(n); }
|
||||||
@ -410,7 +413,13 @@ void netif_set_up(struct netif *netif)
|
|||||||
etharp_gratuitous(netif);
|
etharp_gratuitous(netif);
|
||||||
}
|
}
|
||||||
#endif /* LWIP_ARP */
|
#endif /* LWIP_ARP */
|
||||||
|
|
||||||
|
#if LWIP_IGMP
|
||||||
|
/* resend IGMP memberships */
|
||||||
|
if (netif->flags & NETIF_FLAG_IGMP) {
|
||||||
|
igmp_report_groups( netif);
|
||||||
|
}
|
||||||
|
#endif /* LWIP_IGMP */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -463,6 +472,12 @@ void netif_set_link_up(struct netif *netif )
|
|||||||
{
|
{
|
||||||
netif->flags |= NETIF_FLAG_LINK_UP;
|
netif->flags |= NETIF_FLAG_LINK_UP;
|
||||||
|
|
||||||
|
#if LWIP_DHCP
|
||||||
|
if (netif->dhcp) {
|
||||||
|
dhcp_network_changed(netif);
|
||||||
|
}
|
||||||
|
#endif /* LWIP_DHCP */
|
||||||
|
|
||||||
#if LWIP_AUTOIP
|
#if LWIP_AUTOIP
|
||||||
if (netif->autoip) {
|
if (netif->autoip) {
|
||||||
autoip_network_changed(netif);
|
autoip_network_changed(netif);
|
||||||
|
@ -124,6 +124,8 @@ err_t dhcp_release(struct netif *netif);
|
|||||||
void dhcp_stop(struct netif *netif);
|
void dhcp_stop(struct netif *netif);
|
||||||
/** inform server of our manual IP address */
|
/** inform server of our manual IP address */
|
||||||
void dhcp_inform(struct netif *netif);
|
void dhcp_inform(struct netif *netif);
|
||||||
|
/** Handle a possible change in the network configuration */
|
||||||
|
void dhcp_network_changed(struct netif *netif);
|
||||||
|
|
||||||
/** if enabled, check whether the offered IP address is not in use, using ARP */
|
/** if enabled, check whether the offered IP address is not in use, using ARP */
|
||||||
#if DHCP_DOES_ARP_CHECK
|
#if DHCP_DOES_ARP_CHECK
|
||||||
|
Loading…
Reference in New Issue
Block a user