summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorXavier Simonart <xavier.simonart@intel.com>2018-12-13 12:52:02 +0100
committerXavier Simonart <xavier.simonart@intel.com>2019-01-28 12:14:20 +0100
commitfd72a6505e18c66a31843708bb69a41739b97a84 (patch)
tree299d281a1d229282560588250a888d30ea6bb61b
parent8bffdf8c09100f8a923c37bd9be39a13cbc49862 (diff)
Add support for configurable arp timers in L3 mode
L3 mode supports two timers: - arp_update_time, defaulted to 1 second, which makes PROX to send arp request every second for active flows - arp_timeout, previously defaulted to 30 seconds, which makes PROX consider a MAC address as invalid if no arp_reply was received within those 30 seconds. Those timers values were hardcoded. They can now be configured through the configuration file (within the core section), using resp. "arp update time" and "arp timeout" keywords. Unit is milli seconds. The default becomes respectively 1 second and 2 weeks. Change-Id: I35e46e97df32ca44c2cdfae85a20ee015de5d6e1 Signed-off-by: Xavier Simonart <xavier.simonart@intel.com>
-rw-r--r--VNFs/DPPD-PROX/packet_utils.c23
-rw-r--r--VNFs/DPPD-PROX/packet_utils.h4
-rw-r--r--VNFs/DPPD-PROX/prox_args.c4
-rw-r--r--VNFs/DPPD-PROX/task_init.h2
4 files changed, 26 insertions, 7 deletions
diff --git a/VNFs/DPPD-PROX/packet_utils.c b/VNFs/DPPD-PROX/packet_utils.c
index e93f430c..6c3da0ec 100644
--- a/VNFs/DPPD-PROX/packet_utils.c
+++ b/VNFs/DPPD-PROX/packet_utils.c
@@ -89,7 +89,7 @@ int write_dst_mac(struct task_base *tbase, struct rte_mbuf *mbuf, uint32_t *ip_d
return SEND_MBUF;
} else if (tsc > l3->gw.arp_update_time) {
// long time since we have sent an arp, send arp
- l3->gw.arp_update_time = tsc + hz;
+ l3->gw.arp_update_time = tsc + l3->arp_update_time * hz / 1000;
*ip_dst = l3->gw.ip;
if ((l3->flags & FLAG_DST_MAC_KNOWN) && (tsc < l3->gw.arp_timeout)){
// MAC is valid in the table => send also the mbuf
@@ -120,7 +120,7 @@ int write_dst_mac(struct task_base *tbase, struct rte_mbuf *mbuf, uint32_t *ip_d
return SEND_MBUF;
} else if (tsc > l3->optimized_arp_table[idx].arp_update_time) {
// ARP not sent since a long time, send ARP
- l3->optimized_arp_table[idx].arp_update_time = tsc + hz;
+ l3->optimized_arp_table[idx].arp_update_time = tsc + l3->arp_update_time * hz / 1000;
if (tsc < l3->optimized_arp_table[idx].arp_timeout) {
// MAC still valid => also send mbuf
memcpy(mac, &l3->optimized_arp_table[idx].mac, sizeof(struct ether_addr));
@@ -137,7 +137,7 @@ int write_dst_mac(struct task_base *tbase, struct rte_mbuf *mbuf, uint32_t *ip_d
}
// IP address not found in table
l3->optimized_arp_table[l3->n_pkts].ip = *ip_dst;
- l3->optimized_arp_table[l3->n_pkts].arp_update_time = tsc + hz;
+ l3->optimized_arp_table[l3->n_pkts].arp_update_time = tsc + l3->arp_update_time * hz / 1000;
l3->n_pkts++;
if (l3->n_pkts < 4) {
@@ -171,7 +171,7 @@ int write_dst_mac(struct task_base *tbase, struct rte_mbuf *mbuf, uint32_t *ip_d
return DROP_MBUF;
} else {
l3->arp_table[ret].ip = *ip_dst;
- l3->arp_table[ret].arp_update_time = tsc + hz;
+ l3->arp_table[ret].arp_update_time = tsc + l3->arp_update_time * hz / 1000;
}
return SEND_ARP;
} else {
@@ -182,6 +182,7 @@ int write_dst_mac(struct task_base *tbase, struct rte_mbuf *mbuf, uint32_t *ip_d
return SEND_MBUF;
} else if (tsc > l3->arp_table[ret].arp_update_time) {
// ARP not sent since a long time, send ARP
+ l3->arp_table[ret].arp_update_time = tsc + l3->arp_update_time * hz / 1000;
l3->arp_table[ret].arp_update_time = tsc + hz;
if (tsc < l3->arp_table[ret].arp_timeout) {
// MAC still valid => send also MBUF
@@ -229,6 +230,14 @@ void task_init_l3(struct task_base *tbase, struct task_args *targ)
tbase->l3.core_id = targ->lconf->id;
tbase->l3.task_id = targ->id;
tbase->l3.tmaster = targ->tmaster;
+ if (tbase->l3.arp_timeout != 0)
+ tbase->l3.arp_timeout = targ->arp_timeout;
+ else
+ tbase->l3.arp_timeout = DEFAULT_ARP_TIMEOUT;
+ if (tbase->l3.arp_update_time != 0)
+ tbase->l3.arp_update_time = targ->arp_update_time;
+ else
+ tbase->l3.arp_update_time = DEFAULT_ARP_UPDATE_TIME;
}
void task_start_l3(struct task_base *tbase, struct task_args *targ)
@@ -299,7 +308,7 @@ void handle_ctrl_plane_pkts(struct task_base *tbase, struct rte_mbuf **mbufs, ui
// MAC address of the gateway
memcpy(&l3->gw.mac, &hdr->arp.data.sha, 6);
l3->flags |= FLAG_DST_MAC_KNOWN;
- l3->gw.arp_timeout = tsc + 30 * hz;
+ l3->gw.arp_timeout = tsc + l3->arp_timeout * hz / 1000;
} else if (l3->n_pkts < 4) {
// Few packets tracked - should be faster to loop through them thean using a hash table
for (idx = 0; idx < l3->n_pkts; idx++) {
@@ -310,7 +319,7 @@ void handle_ctrl_plane_pkts(struct task_base *tbase, struct rte_mbuf **mbufs, ui
if (idx < l3->n_pkts) {
// IP not found; this is a reply while we never asked for the request!
memcpy(&l3->optimized_arp_table[idx].mac, &(hdr->arp.data.sha), sizeof(struct ether_addr));
- l3->optimized_arp_table[idx].arp_timeout = tsc + 30 * hz;
+ l3->optimized_arp_table[idx].arp_timeout = tsc + l3->arp_timeout * hz / 1000;
}
} else {
int ret = rte_hash_add_key(l3->ip_hash, (const void *)&ip);
@@ -318,7 +327,7 @@ void handle_ctrl_plane_pkts(struct task_base *tbase, struct rte_mbuf **mbufs, ui
plogx_info("Unable add ip %d.%d.%d.%d in mac_hash\n", IP4(ip));
} else {
memcpy(&l3->arp_table[ret].mac, &(hdr->arp.data.sha), sizeof(struct ether_addr));
- l3->arp_table[ret].arp_timeout = tsc + 30 * hz;
+ l3->arp_table[ret].arp_timeout = tsc + l3->arp_timeout * hz / 1000;
}
}
tx_drop(mbufs[j]);
diff --git a/VNFs/DPPD-PROX/packet_utils.h b/VNFs/DPPD-PROX/packet_utils.h
index 74a3f60e..cb4dc913 100644
--- a/VNFs/DPPD-PROX/packet_utils.h
+++ b/VNFs/DPPD-PROX/packet_utils.h
@@ -33,6 +33,8 @@ enum {
SEND_ARP,
DROP_MBUF
};
+#define DEFAULT_ARP_TIMEOUT (1000 * 3600 * 24 * 15) // ~15 days = disabled by default
+#define DEFAULT_ARP_UPDATE_TIME (1000) // 1 second
struct task_base;
struct task_args;
@@ -50,6 +52,8 @@ struct l3_base {
uint8_t reachable_port_id;
uint8_t core_id;
uint8_t task_id;
+ uint32_t arp_timeout;
+ uint32_t arp_update_time;
struct arp_table gw;
struct arp_table optimized_arp_table[4];
struct rte_hash *ip_hash;
diff --git a/VNFs/DPPD-PROX/prox_args.c b/VNFs/DPPD-PROX/prox_args.c
index 59c514fc..d77eab1a 100644
--- a/VNFs/DPPD-PROX/prox_args.c
+++ b/VNFs/DPPD-PROX/prox_args.c
@@ -1362,6 +1362,10 @@ static int get_core_cfg(unsigned sindex, char *str, void *data)
if (STR_EQ(str, "local ipv6")) { /* source IPv6 address to be used for packets */
return parse_ip6(&targ->local_ipv6, pkey);
}
+ if (STR_EQ(str, "arp timeout"))
+ return parse_int(&targ->arp_timeout, pkey);
+ if (STR_EQ(str, "arp update time"))
+ return parse_int(&targ->arp_update_time, pkey);
if (STR_EQ(str, "number of packets"))
return parse_int(&targ->n_pkts, pkey);
if (STR_EQ(str, "pipes")) {
diff --git a/VNFs/DPPD-PROX/task_init.h b/VNFs/DPPD-PROX/task_init.h
index 5186826a..91a0d7eb 100644
--- a/VNFs/DPPD-PROX/task_init.h
+++ b/VNFs/DPPD-PROX/task_init.h
@@ -127,6 +127,8 @@ struct task_args {
uint32_t gateway_ipv4;
uint32_t local_ipv4;
uint32_t remote_ipv4;
+ uint32_t arp_timeout;
+ uint32_t arp_update_time;
struct ipv6_addr local_ipv6; /* For IPv6 Tunnel, it's the local tunnel endpoint address */
struct rte_ring *rx_rings[MAX_RINGS_PER_TASK];
struct rte_ring *tx_rings[MAX_RINGS_PER_TASK];