summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--VNFs/DPPD-PROX/cmd_parser.c8
-rw-r--r--VNFs/DPPD-PROX/handle_gen.c19
-rw-r--r--VNFs/DPPD-PROX/handle_lat.c32
3 files changed, 48 insertions, 11 deletions
diff --git a/VNFs/DPPD-PROX/cmd_parser.c b/VNFs/DPPD-PROX/cmd_parser.c
index 09ea9653..f88ee942 100644
--- a/VNFs/DPPD-PROX/cmd_parser.c
+++ b/VNFs/DPPD-PROX/cmd_parser.c
@@ -545,8 +545,8 @@ static int parse_cmd_speed(const char *str, struct input *input)
if ((!task_is_mode_and_submode(lcore_id, task_id, "gen", "")) && (!task_is_mode_and_submode(lcore_id, task_id, "gen", "l3"))) {
plog_err("Core %u task %u is not generating packets\n", lcore_id, task_id);
}
- else if (speed > 400.0f || speed < 0.0f) {
- plog_err("Speed out of range (must be betweeen 0%% and 100%%)\n");
+ else if (speed > 1000.0f || speed < 0.0f) { // Up to 100 Gbps
+ plog_err("Speed out of range (must be betweeen 0%% and 1000%%)\n");
}
else {
struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
@@ -579,8 +579,8 @@ static int parse_cmd_speed_byte(const char *str, struct input *input)
if ((!task_is_mode_and_submode(lcore_id, task_id, "gen", "")) && (!task_is_mode_and_submode(lcore_id, task_id, "gen", "l3"))) {
plog_err("Core %u task %u is not generating packets\n", lcore_id, task_id);
}
- else if (bps > 1250000000) {
- plog_err("Speed out of range (must be <= 1250000000)\n");
+ else if (bps > 12500000000) { // Up to 100Gbps
+ plog_err("Speed out of range (must be <= 12500000000)\n");
}
else {
struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
diff --git a/VNFs/DPPD-PROX/handle_gen.c b/VNFs/DPPD-PROX/handle_gen.c
index c48b4c13..0f70ee6b 100644
--- a/VNFs/DPPD-PROX/handle_gen.c
+++ b/VNFs/DPPD-PROX/handle_gen.c
@@ -122,6 +122,7 @@ struct task_gen {
struct ether_addr src_mac;
uint8_t flags;
uint8_t cksum_offload;
+ struct prox_port_cfg *port;
} __rte_cache_aligned;
static inline uint8_t ipv4_get_hdr_len(struct ipv4_hdr *ip)
@@ -1144,6 +1145,12 @@ static void start(struct task_base *tbase)
if (tbase->l3.tmaster) {
register_all_ip_to_ctrl_plane(task);
}
+ if (task->port) {
+ // task->port->link->speed reports the link speed in Mbps e.g. 40k for a 40 Gbps NIC
+ // task->link_speed reported link speed in Bytes per sec.
+ task->link_speed = task->port->link_speed * 125000L;
+ plog_info("\tGenerating at %ld Mbps\n", 8 * task->link_speed / 1000000);
+ }
/* TODO
Handle the case when two tasks transmit to the same port
and one of them is stopped. In that case ARP (requests or replies)
@@ -1190,9 +1197,16 @@ static void init_task_gen(struct task_base *tbase, struct task_args *targ)
task->sig = targ->sig;
task->new_rate_bps = targ->rate_bps;
+ /*
+ * For tokens, use 10 Gbps as base rate
+ * Scripts can then use speed command, with speed=100 as 10 Gbps and speed=400 as 40 Gbps
+ * Script can query prox "port info" command to find out the port link speed to know
+ * at which rate to start. Note that virtio running on OVS returns 10 Gbps, so a script has
+ * probably also to check the driver (as returned by the same "port info" command.
+ */
struct token_time_cfg tt_cfg = token_time_cfg_create(1250000000, rte_get_tsc_hz(), -1);
-
token_time_init(&task->token_time, &tt_cfg);
+
init_task_gen_seeds(task);
task->min_bulk_size = targ->min_bulk_size;
@@ -1211,8 +1225,6 @@ static void init_task_gen(struct task_base *tbase, struct task_args *targ)
task->generator_id = targ->generator_id;
task->link_speed = UINT64_MAX;
- if (targ->nb_txrings == 0 && targ->nb_txports == 1)
- task->link_speed = 1250000000;
if (!strcmp(targ->pcap_file, "")) {
plog_info("\tUsing inline definition of a packet\n");
@@ -1237,6 +1249,7 @@ static void init_task_gen(struct task_base *tbase, struct task_args *targ)
struct prox_port_cfg *port = find_reachable_port(targ);
if (port) {
task->cksum_offload = port->capabilities.tx_offload_cksum;
+ task->port = port;
}
}
diff --git a/VNFs/DPPD-PROX/handle_lat.c b/VNFs/DPPD-PROX/handle_lat.c
index 95ebcc73..b50f9504 100644
--- a/VNFs/DPPD-PROX/handle_lat.c
+++ b/VNFs/DPPD-PROX/handle_lat.c
@@ -32,6 +32,7 @@
#include "quit.h"
#include "eld.h"
#include "prox_shared.h"
+#include "prox_port_cfg.h"
#define DEFAULT_BUCKET_SIZE 10
@@ -105,8 +106,10 @@ struct task_lat {
uint32_t generator_count;
struct early_loss_detect *eld;
struct rx_pkt_meta_data *rx_pkt_meta;
+ uint64_t link_speed;
FILE *fp_rx;
FILE *fp_tx;
+ struct prox_port_cfg *port;
};
static uint32_t abs_diff(uint32_t a, uint32_t b)
@@ -375,9 +378,9 @@ static uint32_t task_lat_early_loss_detect(struct task_lat *task, struct unique_
return early_loss_detect_add(eld, packet_index);
}
-static uint64_t tsc_extrapolate_backward(uint64_t tsc_from, uint64_t bytes, uint64_t tsc_minimum)
+static uint64_t tsc_extrapolate_backward(uint64_t link_speed, uint64_t tsc_from, uint64_t bytes, uint64_t tsc_minimum)
{
- uint64_t tsc = tsc_from - rte_get_tsc_hz()*bytes/1250000000;
+ uint64_t tsc = tsc_from - (rte_get_tsc_hz()*bytes)/link_speed;
if (likely(tsc > tsc_minimum))
return tsc;
else
@@ -495,7 +498,7 @@ static int handle_lat_bulk(struct task_base *tbase, struct rte_mbuf **mbufs, uin
bytes_total_in_bulk += mbuf_wire_size(mbufs[flipped]);
}
- pkt_rx_time = tsc_extrapolate_backward(rx_tsc, task->rx_pkt_meta[0].bytes_after_in_bulk, task->last_pkts_tsc) >> LATENCY_ACCURACY;
+ pkt_rx_time = tsc_extrapolate_backward(task->link_speed, rx_tsc, task->rx_pkt_meta[0].bytes_after_in_bulk, task->last_pkts_tsc) >> LATENCY_ACCURACY;
if ((uint32_t)((task->begin >> LATENCY_ACCURACY)) > pkt_rx_time) {
// Extrapolation went up to BEFORE begin => packets were stuck in the NIC but we were not seeing them
rx_time_err = pkt_rx_time - (uint32_t)(task->last_pkts_tsc >> LATENCY_ACCURACY);
@@ -510,7 +513,7 @@ static int handle_lat_bulk(struct task_base *tbase, struct rte_mbuf **mbufs, uin
struct rx_pkt_meta_data *rx_pkt_meta = &task->rx_pkt_meta[j];
uint8_t *hdr = rx_pkt_meta->hdr;
- pkt_rx_time = tsc_extrapolate_backward(rx_tsc, rx_pkt_meta->bytes_after_in_bulk, task->last_pkts_tsc) >> LATENCY_ACCURACY;
+ pkt_rx_time = tsc_extrapolate_backward(task->link_speed, rx_tsc, rx_pkt_meta->bytes_after_in_bulk, task->last_pkts_tsc) >> LATENCY_ACCURACY;
pkt_tx_time = rx_pkt_meta->pkt_tx_time;
if (task->unique_id_pos) {
@@ -604,6 +607,18 @@ void task_lat_set_accuracy_limit(struct task_lat *task, uint32_t accuracy_limit_
task->limit = nsec_to_tsc(accuracy_limit_nsec);
}
+static void lat_start(struct task_base *tbase)
+{
+ struct task_lat *task = (struct task_lat *)tbase;
+
+ if (task->port) {
+ // task->port->link->speed reports the link speed in Mbps e.g. 40k for a 40 Gbps NIC
+ // task->link_speed reported link speed in Bytes per sec.
+ task->link_speed = task->port->link_speed * 125000L;
+ plog_info("\tReceiving at %ld Mbps\n", 8 * task->link_speed / 1000000);
+ }
+}
+
static void init_task_lat(struct task_base *tbase, struct task_args *targ)
{
struct task_lat *task = (struct task_lat *)tbase;
@@ -636,12 +651,21 @@ static void init_task_lat(struct task_base *tbase, struct task_args *targ)
task_lat_set_accuracy_limit(task, targ->accuracy_limit_nsec);
task->rx_pkt_meta = prox_zmalloc(MAX_RX_PKT_ALL * sizeof(*task->rx_pkt_meta), socket_id);
PROX_PANIC(task->rx_pkt_meta == NULL, "unable to allocate memory to store RX packet meta data");
+
+ task->link_speed = UINT64_MAX;
+ if (targ->nb_rxports) {
+ // task->port structure is only used while starting handle_lat to get the link_speed.
+ // link_speed can not be quiried at init as the port has not been initialized yet.
+ struct prox_port_cfg *port = &prox_port_cfg[targ->rx_port_queue[0].port];
+ task->port = port;
+ }
}
static struct task_init task_init_lat = {
.mode_str = "lat",
.init = init_task_lat,
.handle = handle_lat_bulk,
+ .start = lat_start,
.stop = lat_stop,
.flag_features = TASK_FEATURE_TSC_RX | TASK_FEATURE_RX_ALL | TASK_FEATURE_ZERO_RX | TASK_FEATURE_NEVER_DISCARDS,
.size = sizeof(struct task_lat)