Simplify cores_task_are_valid()
[samplevnf.git] / VNFs / DPPD-PROX / cmd_parser.c
index 9568847..927abc2 100644 (file)
@@ -51,6 +51,7 @@
 #include "stats_latency.h"
 #include "handle_cgnat.h"
 #include "handle_impair.h"
+#include "rx_pkt.h"
 
 static int core_task_is_valid(int lcore_id, int task_id)
 {
@@ -75,19 +76,8 @@ static int cores_task_are_valid(unsigned int *lcores, int task_id, unsigned int
        unsigned int lcore_id;
        for (unsigned int i = 0; i < nb_cores; i++) {
                lcore_id = lcores[i];
-               if (lcore_id >= RTE_MAX_LCORE) {
-                       plog_err("Invalid core id %u (lcore ID above %d)\n", lcore_id, RTE_MAX_LCORE);
+               if (core_task_is_valid(lcore_id, task_id) == 0)
                        return 0;
-               }
-               else if (!prox_core_active(lcore_id, 0)) {
-                       plog_err("Invalid core id %u (lcore is not active)\n", lcore_id);
-                       return 0;
-               }
-               else if (task_id >= lcore_cfg[lcore_id].n_tasks_all) {
-                       plog_err("Invalid task id (valid task IDs for core %u are below %u)\n",
-                               lcore_id, lcore_cfg[lcore_id].n_tasks_all);
-                       return 0;
-               }
        }
        return 1;
 }
@@ -235,6 +225,22 @@ static int parse_cmd_dump_rx(const char *str, struct input *input)
 
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
+                       if (lcores[i] > RTE_MAX_LCORE) {
+                               plog_warn("core_id too high, maximum allowed is: %u\n", RTE_MAX_LCORE);
+                               return -1;
+                       } else if (task_id >= lcore_cfg[lcores[i]].n_tasks_all) {
+                               plog_warn("task_id too high, should be in [0, %u]\n", lcore_cfg[lcores[i]].n_tasks_all - 1);
+                               return -1;
+                       } else {
+                               struct lcore_cfg *lconf = &lcore_cfg[lcores[i]];
+                               struct task_base *tbase = lconf->tasks_all[task_id];
+                               int prev_count = tbase->aux->rx_prev_count;
+                               if (((prev_count) && (tbase->aux->rx_pkt_prev[prev_count - 1] == rx_pkt_dummy))
+                                       || (tbase->rx_pkt == rx_pkt_dummy)) {
+                                       plog_warn("Unable to dump_rx as rx_pkt_dummy\n");
+                                       return -1;
+                               }
+                       }
                        cmd_dump(lcores[i], task_id, nb_packets, input, 1, 0);
                }
        }
@@ -308,18 +314,25 @@ static int parse_cmd_rate(const char *str, struct input *input)
        return 0;
 }
 
-int task_is_mode(uint32_t lcore_id, uint32_t task_id, const char *mode, const char *sub_mode)
+int task_is_mode_and_submode(uint32_t lcore_id, uint32_t task_id, const char *mode, const char *sub_mode)
+{
+       struct task_args *targs = &lcore_cfg[lcore_id].targs[task_id];
+
+       return !strcmp(targs->task_init->mode_str, mode) && !strcmp(targs->sub_mode_str, sub_mode);
+}
+
+int task_is_mode(uint32_t lcore_id, uint32_t task_id, const char *mode)
 {
        struct task_init *t = lcore_cfg[lcore_id].targs[task_id].task_init;
 
-       return !strcmp(t->mode_str, mode) && !strcmp(t->sub_mode_str, sub_mode);
+       return !strcmp(t->mode_str, mode);
 }
 
 int task_is_sub_mode(uint32_t lcore_id, uint32_t task_id, const char *sub_mode)
 {
-       struct task_init *t = lcore_cfg[lcore_id].targs[task_id].task_init;
+       struct task_args *targs = &lcore_cfg[lcore_id].targs[task_id];
 
-       return !strcmp(t->sub_mode_str, sub_mode);
+       return !strcmp(targs->sub_mode_str, sub_mode);
 }
 
 static void log_pkt_count(uint32_t count, uint32_t lcore_id, uint32_t task_id)
@@ -346,7 +359,7 @@ static int parse_cmd_count(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       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 {
@@ -375,11 +388,12 @@ static int parse_cmd_set_probability(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if (!task_is_mode(lcore_id, task_id, "impair", "")) {
+                       if ((!task_is_mode_and_submode(lcore_id, task_id, "impair", "")) && (!task_is_mode_and_submode(lcore_id, task_id, "impair", "l3"))){
                                plog_err("Core %u task %u is not impairing packets\n", lcore_id, task_id);
+                       } else {
+                               struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
+                               task_impair_set_proba(tbase, probability);
                        }
-                       struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
-                       task_impair_set_proba(tbase, probability);
                }
        }
        return 0;
@@ -399,11 +413,12 @@ static int parse_cmd_delay_us(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if (!task_is_mode(lcore_id, task_id, "impair", "")) {
+                       if ((!task_is_mode_and_submode(lcore_id, task_id, "impair", "")) && (!task_is_mode_and_submode(lcore_id, task_id, "impair", "l3"))){
                                plog_err("Core %u task %u is not impairing packets\n", lcore_id, task_id);
+                       } else {
+                               struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
+                               task_impair_set_delay_us(tbase, delay_us, 0);
                        }
-                       struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
-                       task_impair_set_delay_us(tbase, delay_us, 0);
                }
        }
        return 0;
@@ -423,11 +438,12 @@ static int parse_cmd_random_delay_us(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if (!task_is_mode(lcore_id, task_id, "impair", "")) {
+                       if ((!task_is_mode_and_submode(lcore_id, task_id, "impair", "")) && (!task_is_mode_and_submode(lcore_id, task_id, "impair", "l3"))){
                                plog_err("Core %u task %u is not impairing packets\n", lcore_id, task_id);
+                       } else {
+                               struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
+                               task_impair_set_delay_us(tbase, 0, delay_us);
                        }
-                       struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
-                       task_impair_set_delay_us(tbase, 0, delay_us);
                }
        }
        return 0;
@@ -484,13 +500,12 @@ static int parse_cmd_pkt_size(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       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 {
+                               struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
+                               task_gen_set_pkt_size(tbase, pkt_size); /* error printed within function */
                        }
-                       struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
-
-                       if (task_gen_set_pkt_size(tbase, pkt_size) != 0)
-                               return -1;
                }
        }
        return 0;
@@ -516,11 +531,11 @@ static int parse_cmd_speed(const char *str, struct input *input)
 
        for (i = 0; i < nb_cores; i++) {
                lcore_id = lcores[i];
-               if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+               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];
@@ -550,11 +565,11 @@ static int parse_cmd_speed_byte(const char *str, struct input *input)
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
 
-                       if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       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];
@@ -576,7 +591,7 @@ static int parse_cmd_reset_randoms_all(const char *str, struct input *input)
        unsigned task_id, lcore_id = -1;
        while (prox_core_next(&lcore_id, 0) == 0) {
                for (task_id = 0; task_id < lcore_cfg[lcore_id].n_tasks_all; task_id++) {
-                       if ((task_is_mode(lcore_id, task_id, "gen", "")) || (task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       if ((task_is_mode_and_submode(lcore_id, task_id, "gen", "")) || (task_is_mode_and_submode(lcore_id, task_id, "gen", "l3"))) {
                                struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
                                uint32_t n_rands = task_gen_get_n_randoms(tbase);
 
@@ -597,7 +612,7 @@ static int parse_cmd_reset_values_all(const char *str, struct input *input)
        unsigned task_id, lcore_id = -1;
        while (prox_core_next(&lcore_id, 0) == 0) {
                for (task_id = 0; task_id < lcore_cfg[lcore_id].n_tasks_all; task_id++) {
-                       if ((task_is_mode(lcore_id, task_id, "gen", "")) || (task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       if ((task_is_mode_and_submode(lcore_id, task_id, "gen", "")) || (task_is_mode_and_submode(lcore_id, task_id, "gen", "l3"))) {
                                struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
 
                                plog_info("Resetting values on core %d task %d\n", lcore_id, task_id);
@@ -618,7 +633,7 @@ static int parse_cmd_reset_values(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       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 {
@@ -649,7 +664,7 @@ static int parse_cmd_set_value(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       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 (offset > ETHER_MAX_LEN) {
@@ -690,7 +705,7 @@ static int parse_cmd_set_random(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
+                       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 (offset > ETHER_MAX_LEN) {
@@ -832,14 +847,15 @@ static int parse_cmd_gateway_ip(const char *str, struct input *input)
        }
        for (i = 0; i < nb_cores; i++) {
                lcore_id = lcores[i];
-               if ((!task_is_mode(lcore_id, task_id, "gen", "")) && (!task_is_mode(lcore_id, task_id, "gen", "l3"))) {
-                       plog_err("Core %u task %u is not generating packets\n", lcore_id, task_id);
+
+               if (!task_is_sub_mode(lcore_id, task_id, "l3")) {
+                       plog_err("Core %u task %u is not in l3 mode\n", lcore_id, task_id);
                }
                else {
                        uint32_t gateway_ip = ((ip[3] & 0xFF) << 24) | ((ip[2] & 0xFF) << 16) | ((ip[1] & 0xFF) << 8) | ((ip[0] & 0xFF) << 0);
                        struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
                        plog_info("Setting gateway ip to %s\n", str);
-                       task_gen_set_gateway_ip(tbase, gateway_ip);
+                       task_set_gateway_ip(tbase, gateway_ip);
                }
        }
        return 0;
@@ -860,12 +876,16 @@ static int parse_cmd_local_ip(const char *str, struct input *input)
        }
        for (i = 0; i < nb_cores; i++) {
                lcore_id = lcores[i];
-               if (!task_is_mode(lcore_id, task_id, "arp", "local")) {
-                       plog_err("Core %u task %u is not in arp mode\n", lcore_id, task_id);
-               }
-               else {
-                       uint32_t local_ip = ((ip[3] & 0xFF) << 24) | ((ip[2] & 0xFF) << 16) | ((ip[1] & 0xFF) << 8) | ((ip[0] & 0xFF) << 0);
-                       struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
+               struct task_base *tbase = lcore_cfg[lcore_id].tasks_all[task_id];
+               uint32_t local_ip = ((ip[3] & 0xFF) << 24) | ((ip[2] & 0xFF) << 16) | ((ip[1] & 0xFF) << 8) | ((ip[0] & 0xFF) << 0);
+               if (!task_is_mode_and_submode(lcore_id, task_id, "arp", "local")) {
+                       if (!task_is_sub_mode(lcore_id, task_id, "l3")) {
+                               plog_err("Core %u task %u is not in l3 mode\n", lcore_id, task_id);
+                       } else {
+                               plog_info("Setting local ip to %s\n", str);
+                               task_set_local_ip(tbase, local_ip);
+                       }
+               } else {
                        plog_info("Setting local ip to %s\n", str);
                        task_arp_set_local_ip(tbase, local_ip);
                }
@@ -1551,6 +1571,49 @@ static int parse_cmd_port_stats(const char *str, struct input *input)
        return 0;
 }
 
+static int parse_cmd_multi_port_stats(const char *str, struct input *input)
+{
+       uint32_t ports[PROX_MAX_PORTS];
+       int nb_ports = parse_list_set(ports, str, PROX_MAX_PORTS);
+       if (nb_ports <= 0) {
+               return -1;
+       }
+
+       char buf[PROX_MAX_PORTS * (11+5*21) + 1], *pbuf = buf;
+       int left = sizeof(buf);
+       for (int i = 0; i < nb_ports; ++i) {
+               struct get_port_stats s;
+               if (stats_port(ports[i], &s)) {
+                       plog_err("Invalid port %u\n", ports[i]);
+                       return 0;
+               }
+
+               int len = snprintf(pbuf, left,
+                               "%u,"
+                               "%"PRIu64",%"PRIu64","
+                               "%"PRIu64",%"PRIu64","
+                               "%"PRIu64";",
+                               //TODO: adjust buf size above when adding fields
+                               ports[i],
+                               s.rx_tot, s.tx_tot,
+                               s.no_mbufs_tot, s.ierrors_tot + s.imissed_tot,
+                               s.last_tsc);
+               if ((len < 0) || (len >= left)) {
+                       plog_err("Cannot print stats for port %u\n", ports[i]);
+                       return 0;
+               }
+               pbuf += len;
+               left -= len;
+       }
+       pbuf--;
+       *pbuf = '\n';
+
+       plog_info("%s", buf);
+       if (input->reply)
+               input->reply(input, buf, sizeof(buf) - left);
+       return 0;
+}
+
 static int parse_cmd_core_stats(const char *str, struct input *input)
 {
        unsigned lcores[RTE_MAX_LCORE], lcore_id, task_id, nb_cores;
@@ -1582,6 +1645,39 @@ static int parse_cmd_core_stats(const char *str, struct input *input)
        return 0;
 }
 
+static int parse_cmd_dp_core_stats(const char *str, struct input *input)
+{
+       unsigned lcores[RTE_MAX_LCORE], lcore_id, task_id, nb_cores;
+
+       if (parse_core_task(str, lcores, &task_id, &nb_cores))
+               return -1;
+
+       if (cores_task_are_valid(lcores, task_id, nb_cores)) {
+               for (unsigned int i = 0; i < nb_cores; i++) {
+                       lcore_id = lcores[i];
+                       uint64_t tot_rx = stats_core_task_tot_rx(lcore_id, task_id);
+                       uint64_t tot_tx = stats_core_task_tot_tx(lcore_id, task_id);
+                       uint64_t tot_rx_non_dp = stats_core_task_tot_rx_non_dp(lcore_id, task_id);
+                       uint64_t tot_tx_non_dp = stats_core_task_tot_tx_non_dp(lcore_id, task_id);
+                       uint64_t tot_drop = stats_core_task_tot_drop(lcore_id, task_id);
+                       uint64_t last_tsc = stats_core_task_last_tsc(lcore_id, task_id);
+
+                       if (input->reply) {
+                               char buf[128];
+                               snprintf(buf, sizeof(buf),
+                                       "%"PRIu64",%"PRIu64",%"PRIu64",%"PRIu64",%"PRIu64",%"PRIu64",%"PRIu64"\n",
+                                       tot_rx, tot_tx, tot_rx_non_dp, tot_tx_non_dp, tot_drop, last_tsc, rte_get_tsc_hz());
+                               input->reply(input, buf, strlen(buf));
+                       }
+                       else {
+                               plog_info("RX: %"PRIu64", TX: %"PRIu64", RX_NON_DP:  %"PRIu64", TX_NON_DP: %"PRIu64", DROP: %"PRIu64"\n",
+                                       tot_rx, tot_tx, tot_rx_non_dp, tot_tx_non_dp, tot_drop);
+                       }
+               }
+       }
+       return 0;
+}
+
 static int parse_cmd_lat_stats(const char *str, struct input *input)
 {
        unsigned lcores[RTE_MAX_LCORE], lcore_id, task_id, nb_cores;
@@ -1592,7 +1688,7 @@ static int parse_cmd_lat_stats(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if (!task_is_mode(lcore_id, task_id, "lat", "")) {
+                       if (!task_is_mode(lcore_id, task_id, "lat")) {
                                plog_err("Core %u task %u is not measuring latency\n", lcore_id, task_id);
                        }
                        else {
@@ -1633,6 +1729,28 @@ static int parse_cmd_lat_stats(const char *str, struct input *input)
        return 0;
 }
 
+static int parse_cmd_show_irq_buckets(const char *str, struct input *input)
+{
+       char buf[4096] = {0};
+       unsigned int i, c;
+       unsigned lcores[RTE_MAX_LCORE], lcore_id, task_id, nb_cores;
+
+       if (parse_core_task(str, lcores, &task_id, &nb_cores))
+               return -1;
+
+       if (cores_task_are_valid(lcores, task_id, nb_cores)) {
+               for (c = 0; c < nb_cores; c++) {
+                       lcore_id = lcores[c];
+                       get_irq_buckets_by_core_task(buf, lcore_id, task_id);
+                       plog_info("%s", buf);
+                       if (input->reply)
+                               input->reply(input, buf, strlen(buf));
+                       buf[0] = 0;
+               }
+       }
+       return 0;
+}
+
 static int parse_cmd_irq(const char *str, struct input *input)
 {
        unsigned int i, c;
@@ -1644,7 +1762,7 @@ static int parse_cmd_irq(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (c = 0; c < nb_cores; c++) {
                        lcore_id = lcores[c];
-                       if (!task_is_mode(lcore_id, task_id, "irq", "")) {
+                       if (!task_is_mode(lcore_id, task_id, "irq")) {
                                plog_err("Core %u task %u is not in irq mode\n", lcore_id, task_id);
                        } else {
                                struct task_irq *task_irq = (struct task_irq *)(lcore_cfg[lcore_id].tasks_all[task_id]);
@@ -1692,7 +1810,7 @@ static int parse_cmd_lat_packets(const char *str, struct input *input)
        if (cores_task_are_valid(lcores, task_id, nb_cores)) {
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
-                       if (!task_is_mode(lcore_id, task_id, "lat", "")) {
+                       if (!task_is_mode(lcore_id, task_id, "lat")) {
                                plog_err("Core %u task %u is not measuring latency\n", lcore_id, task_id);
                        }
                        else {
@@ -1714,7 +1832,7 @@ static int parse_cmd_cgnat_public_hash(const char *str, struct input *input)
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
 
-                       if (!task_is_mode(lcore_id, task_id, "cgnat", "")) {
+                       if (!task_is_mode(lcore_id, task_id, "cgnat")) {
                                plog_err("Core %u task %u is not cgnat\n", lcore_id, task_id);
                        }
                        else {
@@ -1738,7 +1856,7 @@ static int parse_cmd_cgnat_private_hash(const char *str, struct input *input)
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
 
-                       if (!task_is_mode(lcore_id, task_id, "cgnat", "")) {
+                       if (!task_is_mode(lcore_id, task_id, "cgnat")) {
                                plog_err("Core %u task %u is not cgnat\n", lcore_id, task_id);
                        }
                        else {
@@ -1766,7 +1884,7 @@ static int parse_cmd_accuracy(const char *str, struct input *input)
                for (unsigned int i = 0; i < nb_cores; i++) {
                        lcore_id = lcores[i];
 
-                       if (!task_is_mode(lcore_id, task_id, "lat", "")) {
+                       if (!task_is_mode(lcore_id, task_id, "lat")) {
                                plog_err("Core %u task %u is not measuring latency\n", lcore_id, task_id);
                        }
                        else {
@@ -1875,10 +1993,13 @@ static struct cmd_str cmd_strings[] = {
        {"tot imissed tot", "", "Print total number of imissed since reset", parse_cmd_tot_imissed_tot},
        {"lat stats", "<core id> <task id>", "Print min,max,avg latency as measured during last sampling interval", parse_cmd_lat_stats},
        {"irq stats", "<core id> <task id>", "Print irq related infos", parse_cmd_irq},
+       {"show irq buckets", "<core id> <task id>", "Print irq buckets", parse_cmd_show_irq_buckets},
        {"lat packets", "<core id> <task id>", "Print the latency for each of the last set of packets", parse_cmd_lat_packets},
        {"accuracy limit", "<core id> <task id> <nsec>", "Only consider latency of packets that were measured with an error no more than <nsec>", parse_cmd_accuracy},
        {"core stats", "<core id> <task id>", "Print rx/tx/drop for task <task id> running on core <core id>", parse_cmd_core_stats},
+       {"dp core stats", "<core id> <task id>", "Print rx/tx/non_dp_rx/non_dp_tx/drop for task <task id> running on core <core id>", parse_cmd_dp_core_stats},
        {"port_stats", "<port id>", "Print rate for no_mbufs, ierrors + imissed, rx_bytes, tx_bytes, rx_pkts, tx_pkts; totals for RX, TX, no_mbufs, ierrors + imissed for port <port id>", parse_cmd_port_stats},
+       {"multi port stats", "<port list>", "Get stats for multiple ports, semi-colon separated: port id, total for rx_pkts, tx_pkts, no_mbufs, ierrors + imissed, last_tsc", parse_cmd_multi_port_stats},
        {"read reg", "", "Read register", parse_cmd_read_reg},
        {"write reg", "", "Read register", parse_cmd_write_reg},
        {"set vlan offload", "", "Set Vlan offload", parse_cmd_set_vlan_offload},
@@ -1897,7 +2018,7 @@ static struct cmd_str cmd_strings[] = {
        {"port down", "<port id>", "Set the port down", parse_cmd_port_down},
        {"port link state", "<port id>", "Get link state (up or down) for port", parse_cmd_port_link_state},
        {"port xstats", "<port id>", "Get extra statistics for the port", parse_cmd_xstats},
-       {"stats", "<stats_path>", "Get stats as sepcified by <stats_path>. A comma-separated list of <stats_path> can be supplied", parse_cmd_stats},
+       {"stats", "<stats_path>", "Get stats as specified by <stats_path>. A comma-separated list of <stats_path> can be supplied", parse_cmd_stats},
        {"cgnat dump public hash", "<core id> <task id>", "Dump cgnat public hash table", parse_cmd_cgnat_public_hash},
        {"cgnat dump private hash", "<core id> <task id>", "Dump cgnat private hash table", parse_cmd_cgnat_private_hash},
        {"delay_us", "<core_id> <task_id> <delay_us>", "Set the delay in usec for the impair mode to <delay_us>", parse_cmd_delay_us},