summaryrefslogtreecommitdiffstats
path: root/src/vnet/dhcp
diff options
context:
space:
mode:
authorDave Barach <dave@barachs.net>2019-11-08 20:20:17 -0500
committerAndrew Yourtchenko <ayourtch@gmail.com>2020-08-07 21:45:43 +0000
commit47214ee1e0a6043d9b2a0fa2b7a204787218b906 (patch)
treeedbacac26114794b40f3f5c0bef07c25259df4dc /src/vnet/dhcp
parent201fa41eb568d677d3f57401356fbeaba30ca0b5 (diff)
dhcp: fix dhcpv6 client and dhcpv6 prefix delegation
Keep trying even if the interface in question is not "admin-up, link-up." In real life, it's normal for link autonegotiation to take a good fraction of a second. The driver layer takes care of packets sent to an interface which can't transmit at the moment. Renew address leases at the preferred renewal time, not at the expiration time. Type: fix Signed-off-by: Dave Barach <dave@barachs.net> Change-Id: I68ec1c52cc1f4a8aa256185820748b845e92f7c1 (cherry picked from commit 20b962d3e494513ab28854936cc8bbc32891686b)
Diffstat (limited to 'src/vnet/dhcp')
-rw-r--r--src/vnet/dhcp/dhcp6_ia_na_client_cp.c12
-rw-r--r--src/vnet/dhcp/dhcp6_ia_na_client_dp.c14
-rw-r--r--src/vnet/dhcp/dhcp6_pd_client_dp.c30
3 files changed, 19 insertions, 37 deletions
diff --git a/src/vnet/dhcp/dhcp6_ia_na_client_cp.c b/src/vnet/dhcp/dhcp6_ia_na_client_cp.c
index ad0ca8e3e93..c5e4d0ce1da 100644
--- a/src/vnet/dhcp/dhcp6_ia_na_client_cp.c
+++ b/src/vnet/dhcp/dhcp6_ia_na_client_cp.c
@@ -317,7 +317,11 @@ dhcp6_reply_event_handler (vl_api_dhcp6_reply_event_t * mp)
{
address_info->preferred_lt = preferred_time;
address_info->valid_lt = valid_time;
- address_info->due_time = current_time + valid_time;
+ address_info->due_time = current_time;
+ /* Renew the lease at the preferred time, if non-zero */
+ address_info->due_time += (preferred_time > 0) ?
+ preferred_time : valid_time;
+
if (address_info->due_time > rm->max_valid_due_time)
rm->max_valid_due_time = address_info->due_time;
continue;
@@ -331,7 +335,11 @@ dhcp6_reply_event_handler (vl_api_dhcp6_reply_event_t * mp)
address_info->address = *address;
address_info->preferred_lt = preferred_time;
address_info->valid_lt = valid_time;
- address_info->due_time = current_time + valid_time;
+ address_info->due_time = current_time;
+ /* Renew the lease at the preferred time, if non-zero */
+ address_info->due_time += (preferred_time > 0) ?
+ preferred_time : valid_time;
+
if (address_info->due_time > rm->max_valid_due_time)
rm->max_valid_due_time = address_info->due_time;
rm->client_state_by_sw_if_index[sw_if_index].address_count++;
diff --git a/src/vnet/dhcp/dhcp6_ia_na_client_dp.c b/src/vnet/dhcp/dhcp6_ia_na_client_dp.c
index 4b4bee77837..2903a040250 100644
--- a/src/vnet/dhcp/dhcp6_ia_na_client_dp.c
+++ b/src/vnet/dhcp/dhcp6_ia_na_client_dp.c
@@ -103,8 +103,6 @@ create_buffer_for_client_message (vlib_main_t * vm, u32 sw_if_index,
u32 type)
{
dhcp6_client_common_main_t *ccm = &dhcp6_client_common_main;
- vnet_main_t *vnm = vnet_get_main ();
-
vlib_buffer_t *b;
u32 bi;
ip6_header_t *ip;
@@ -116,18 +114,6 @@ create_buffer_for_client_message (vlib_main_t * vm, u32 sw_if_index,
u32 n_addresses;
u32 i;
- vnet_hw_interface_t *hw = vnet_get_sup_hw_interface (vnm, sw_if_index);
- vnet_sw_interface_t *sup_sw = vnet_get_sup_sw_interface (vnm, sw_if_index);
- vnet_sw_interface_t *sw = vnet_get_sw_interface (vnm, sw_if_index);
-
- /* Interface(s) down? */
- if ((hw->flags & VNET_HW_INTERFACE_FLAG_LINK_UP) == 0)
- return NULL;
- if ((sup_sw->flags & VNET_SW_INTERFACE_FLAG_ADMIN_UP) == 0)
- return NULL;
- if ((sw->flags & VNET_SW_INTERFACE_FLAG_ADMIN_UP) == 0)
- return NULL;
-
/* Get a link-local address */
src_addr = ip6_neighbor_get_link_local_address (sw_if_index);
diff --git a/src/vnet/dhcp/dhcp6_pd_client_dp.c b/src/vnet/dhcp/dhcp6_pd_client_dp.c
index 90ac3028107..a7be073568e 100644
--- a/src/vnet/dhcp/dhcp6_pd_client_dp.c
+++ b/src/vnet/dhcp/dhcp6_pd_client_dp.c
@@ -104,8 +104,6 @@ create_buffer_for_client_message (vlib_main_t * vm,
* client_state, u32 type)
{
dhcp6_client_common_main_t *ccm = &dhcp6_client_common_main;
- vnet_main_t *vnm = vnet_get_main ();
-
vlib_buffer_t *b;
u32 bi;
ip6_header_t *ip;
@@ -117,17 +115,10 @@ create_buffer_for_client_message (vlib_main_t * vm,
u32 n_prefixes;
u32 i;
- vnet_hw_interface_t *hw = vnet_get_sup_hw_interface (vnm, sw_if_index);
- vnet_sw_interface_t *sup_sw = vnet_get_sup_sw_interface (vnm, sw_if_index);
- vnet_sw_interface_t *sw = vnet_get_sw_interface (vnm, sw_if_index);
-
- /* Interface(s) down? */
- if ((hw->flags & VNET_HW_INTERFACE_FLAG_LINK_UP) == 0)
- return NULL;
- if ((sup_sw->flags & VNET_SW_INTERFACE_FLAG_ADMIN_UP) == 0)
- return NULL;
- if ((sw->flags & VNET_SW_INTERFACE_FLAG_ADMIN_UP) == 0)
- return NULL;
+ /*
+ * Note: do NOT psychoanalyze link-state here.
+ * If the interface is down, let the driver turf the packet.
+ */
/* Get a link-local address */
src_addr = ip6_neighbor_get_link_local_address (sw_if_index);
@@ -320,10 +311,10 @@ check_pd_send_client_message (vlib_main_t * vm,
else
{
client_state->sleep_interval =
- (2 + random_f64_from_to (-0.1, 0.1)) * client_state->sleep_interval;
+ (2.0 + random_f64_from_to (-0.1, 0.1)) * client_state->sleep_interval;
if (client_state->sleep_interval > params->mrt)
client_state->sleep_interval =
- (1 + random_f64_from_to (-0.1, 0.1)) * params->mrt;
+ (1.0 + random_f64_from_to (-0.1, 0.1)) * params->mrt;
client_state->due_time = current_time + client_state->sleep_interval;
@@ -426,12 +417,9 @@ dhcp6_pd_send_client_message (vlib_main_t * vm, u32 sw_if_index, u8 stop,
client_state->buffer =
create_buffer_for_client_message (vm, sw_if_index, client_state,
params->msg_type);
- if (!client_state->buffer)
- client_state->keep_sending_client_message = 0;
- else
- vlib_process_signal_event (vm,
- send_dhcp6_pd_client_message_process_node.index,
- 1, 0);
+ if (client_state->buffer)
+ vlib_process_signal_event
+ (vm, send_dhcp6_pd_client_message_process_node.index, 1, 0);
}
}