Multiple changes for June release
[samplevnf.git] / VNFs / DPPD-PROX / commands.c
index 93acc62..50d04d2 100644 (file)
@@ -18,6 +18,9 @@
 #include <rte_table_hash.h>
 #include <rte_version.h>
 #include <rte_malloc.h>
+#if RTE_VERSION >= RTE_VERSION_NUM(18,5,0,0)
+#include <rte_eal_memconfig.h>
+#endif
 
 #include "prox_malloc.h"
 #include "display.h"
@@ -84,9 +87,14 @@ static void warn_inactive_cores(uint32_t *cores, int count, const char *prefix)
 static inline int wait_command_handled(struct lcore_cfg *lconf)
 {
        uint64_t t1 = rte_rdtsc(), t2;
+       int max_time = 5;
+
+       if (lconf->msg.type == LCONF_MSG_STOP)
+               max_time = 30;
+
        while (lconf_is_req(lconf)) {
                t2 = rte_rdtsc();
-               if (t2 - t1 > 5 * rte_get_tsc_hz()) {
+               if (t2 - t1 > max_time * rte_get_tsc_hz()) {
                        // Failed to handle command ...
                        for (uint8_t task_id = 0; task_id < lconf->n_tasks_all; ++task_id) {
                                struct task_args *targs = &lconf->targs[task_id];
@@ -101,10 +109,22 @@ static inline int wait_command_handled(struct lcore_cfg *lconf)
        }
        return 0;
 }
+
+static inline void start_l3(struct task_args *targ)
+{
+       if (!task_is_master(targ)) {
+               if ((targ->nb_txrings != 0) || (targ->nb_txports != 0)) {
+                       if (targ->flags & TASK_ARG_L3)
+                               task_start_l3(targ->tbase, targ);
+               }
+       }
+}
+
 void start_cores(uint32_t *cores, int count, int task_id)
 {
        int n_started_cores = 0;
        uint32_t started_cores[RTE_MAX_LCORE];
+       struct task_args *targ;
 
        warn_inactive_cores(cores, count, "Can't start core");
 
@@ -112,7 +132,15 @@ void start_cores(uint32_t *cores, int count, int task_id)
                struct lcore_cfg *lconf = &lcore_cfg[cores[i]];
 
                if (lconf->n_tasks_run != lconf->n_tasks_all) {
-
+                       if (task_id == -1) {
+                               for (uint8_t tid = 0; tid < lconf->n_tasks_all; ++tid) {
+                                       targ = &lconf->targs[tid];
+                                       start_l3(targ);
+                               }
+                       } else {
+                               targ = &lconf->targs[task_id];
+                               start_l3(targ);
+                       }
                        lconf->msg.type = LCONF_MSG_START;
                        lconf->msg.task_id = task_id;
                        lconf_set_req(lconf);
@@ -234,8 +262,96 @@ void cmd_mem_stats(void)
        }
 }
 
+static void get_hp_sz_string(char *sz_str, uint64_t hp_sz)
+{
+       switch (hp_sz >> 20) {
+       case 0:
+               strcpy(sz_str, " 0 ");
+               break;
+       case 2:
+               strcpy(sz_str, "2MB");
+               break;
+       case 1024:
+               strcpy(sz_str, "1GB");
+               break;
+       default:
+               strcpy(sz_str, "??");
+       }
+}
+
+#if RTE_VERSION >= RTE_VERSION_NUM(18,5,0,0)
+// Print all segments, 1 by 1
+// Unused for now, keep for reference
+static int print_all_segments(const struct rte_memseg_list *memseg_list, const struct rte_memseg *memseg, void *arg)
+{
+       struct rte_mem_config *mcfg = rte_eal_get_configuration()->mem_config;
+       int memseg_list_idx, memseg_idx;
+       int n = (*(int *)arg)++;
+
+       memseg_list_idx = memseg_list - mcfg->memsegs;
+       if ((memseg_list_idx < 0) || (memseg_list_idx >= RTE_MAX_MEMSEG_LISTS)) {
+               plog_err("Invalid memseg_list_idx = %d; memseg_list = %p, mcfg->memsegs = %p\n", memseg_list_idx, memseg_list, mcfg->memsegs);
+               return -1;
+       }
+       memseg_idx = rte_fbarray_find_idx(&memseg_list->memseg_arr, memseg);
+       if (memseg_idx < 0) {
+               plog_err("Invalid memseg_idx = %d; memseg_list = %p, memseg = %p\n", memseg_idx, memseg_list, memseg);
+               return -1;
+       }
+
+       char sz_str[5];
+       get_hp_sz_string(sz_str, memseg->hugepage_sz);
+       plog_info("Segment %u (sock %d): [%i-%i] [%#lx-%#lx] at %p using %zu pages of %s\n",
+               n,
+               memseg->socket_id,
+               memseg_list_idx,
+               memseg_idx,
+               memseg->iova,
+               memseg->iova+memseg->len,
+               memseg->addr,
+               memseg->len/memseg->hugepage_sz, sz_str);
+
+        return 0;
+}
+
+// Print memory segments
+// Contiguous segments are shown as 1 big segment
+static int print_segments(const struct rte_memseg_list *memseg_list, const struct rte_memseg *memseg, size_t len, void *arg)
+{
+       struct rte_mem_config *mcfg = rte_eal_get_configuration()->mem_config;
+       int memseg_list_idx, memseg_idx;
+       static int n = 0;
+
+       memseg_list_idx = memseg_list - mcfg->memsegs;
+       if ((memseg_list_idx < 0) || (memseg_list_idx >= RTE_MAX_MEMSEG_LISTS)) {
+               plog_err("Invalid memseg_list_idx = %d; memseg_list = %p, mcfg->memsegs = %p\n", memseg_list_idx, memseg_list, mcfg->memsegs);
+               return -1;
+       }
+       memseg_idx = rte_fbarray_find_idx(&memseg_list->memseg_arr, memseg);
+       if (memseg_idx < 0) {
+               plog_err("Invalid memseg_idx = %d; memseg_list = %p, memseg = %p\n", memseg_idx, memseg_list, memseg);
+               return -1;
+       }
+
+       char sz_str[5];
+       get_hp_sz_string(sz_str, memseg->hugepage_sz);
+       plog_info("Segment %u (sock %d): [%i-%i] [%#lx-%#lx] at %p using %zu pages of %s\n",
+               n++,
+               memseg->socket_id,
+               memseg_list_idx,
+               memseg_idx,
+               memseg->iova,
+               memseg->iova+len,
+               memseg->addr,
+               memseg->hugepage_sz?len/memseg->hugepage_sz:0, sz_str);
+
+        return 0;
+}
+
+#endif
 void cmd_mem_layout(void)
 {
+#if RTE_VERSION < RTE_VERSION_NUM(18,5,0,0)
        const struct rte_memseg* memseg = rte_eal_get_physmem_layout();
 
        plog_info("Memory layout:\n");
@@ -243,17 +359,8 @@ void cmd_mem_layout(void)
                if (memseg[i].addr == NULL)
                        break;
 
-               const char *sz_str;
-               switch (memseg[i].hugepage_sz >> 20) {
-               case 2:
-                       sz_str = "2MB";
-                       break;
-               case 1024:
-                       sz_str = "1GB";
-                       break;
-               default:
-                       sz_str = "??";
-               }
+               char sz_str[5];
+               get_hp_sz_string(sz_str, memseg[i].hugepage_sz);
 
                plog_info("Segment %u: [%#lx-%#lx] at %p using %zu pages of %s\n",
                          i,
@@ -262,6 +369,11 @@ void cmd_mem_layout(void)
                          memseg[i].addr,
                          memseg[i].len/memseg[i].hugepage_sz, sz_str);
        }
+#else
+       int segment_number = 0;
+       //rte_memseg_walk(print_all_segments, &segment_number);
+       rte_memseg_contig_walk(print_segments, &segment_number);
+#endif
 }
 
 void cmd_dump(uint8_t lcore_id, uint8_t task_id, uint32_t nb_packets, struct input *input, int rx, int tx)
@@ -733,6 +845,7 @@ void cmd_portinfo(int port_id, char *dst, size_t max_len)
        dst += snprintf(dst, end - dst, "\tDriver: %s\n", port_cfg->driver_name);
        dst += snprintf(dst, end - dst, "\tMac address: "MAC_BYTES_FMT"\n", MAC_BYTES(port_cfg->eth_addr.addr_bytes));
        dst += snprintf(dst, end - dst, "\tLink speed: %u Mbps\n", port_cfg->link_speed);
+       dst += snprintf(dst, end - dst, "\tLink max speed: %u Mbps\n", port_cfg->max_link_speed);
        dst += snprintf(dst, end - dst, "\tLink status: %s\n", port_cfg->link_up? "up" : "down");
        dst += snprintf(dst, end - dst, "\tSocket: %u\n", port_cfg->socket);
        dst += snprintf(dst, end - dst, "\tPCI address: %s\n", port_cfg->pci_addr);