Fix: unnecesary uio binding for Mellanox NIC
[vpp.git] / src / plugins / dpdk / device / init.c
index 17e7761..acf712f 100755 (executable)
 #include <vppinfra/error.h>
 #include <vppinfra/format.h>
 #include <vppinfra/bitmap.h>
+#include <vppinfra/linux/sysfs.h>
+#include <vlib/unix/unix.h>
 
 #include <vnet/ethernet/ethernet.h>
 #include <dpdk/device/dpdk.h>
-#include <vlib/unix/physmem.h>
 #include <vlib/pci/pci.h>
 
 #include <stdio.h>
@@ -37,8 +38,6 @@ dpdk_main_t dpdk_main;
 
 #define LINK_STATE_ELOGS       0
 
-#define DEFAULT_HUGE_DIR (VPP_RUN_DIR "/hugepages")
-
 /* Port configuration, mildly modified Intel app values */
 
 static struct rte_eth_conf port_conf_template = {
@@ -196,8 +195,8 @@ dpdk_lib_init (dpdk_main_t * dm)
                                         "dpdk rx");
 
   if (dm->conf->enable_tcp_udp_checksum)
-    dm->buffer_flags_template &= ~(IP_BUFFER_L4_CHECKSUM_CORRECT
-                                  | IP_BUFFER_L4_CHECKSUM_COMPUTED);
+    dm->buffer_flags_template &= ~(VNET_BUFFER_F_L4_CHECKSUM_CORRECT
+                                  | VNET_BUFFER_F_L4_CHECKSUM_COMPUTED);
 
   /* vlib_buffer_t template */
   vec_validate_aligned (dm->buffer_templates, tm->n_vlib_mains - 1,
@@ -351,6 +350,11 @@ dpdk_lib_init (dpdk_main_t * dm)
            case VNET_DPDK_PMD_IGB:
            case VNET_DPDK_PMD_IXGBE:
            case VNET_DPDK_PMD_I40E:
+             xd->port_type = port_type_from_speed_capa (&dev_info);
+             xd->flags |= DPDK_DEVICE_FLAG_TX_OFFLOAD |
+               DPDK_DEVICE_FLAG_INTEL_PHDR_CKSUM;
+
+             break;
            case VNET_DPDK_PMD_CXGBE:
            case VNET_DPDK_PMD_MLX4:
            case VNET_DPDK_PMD_MLX5:
@@ -367,6 +371,7 @@ dpdk_lib_init (dpdk_main_t * dm)
 
            case VNET_DPDK_PMD_THUNDERX:
              xd->port_type = VNET_DPDK_PORT_TYPE_ETH_VF;
+             xd->port_conf.rxmode.hw_strip_crc = 1;
              break;
 
            case VNET_DPDK_PMD_DPAA2:
@@ -415,6 +420,10 @@ dpdk_lib_init (dpdk_main_t * dm)
              xd->port_type = VNET_DPDK_PORT_TYPE_VIRTIO_USER;
              break;
 
+           case VNET_DPDK_PMD_VHOST_ETHER:
+             xd->port_type = VNET_DPDK_PORT_TYPE_VHOST_ETHER;
+             break;
+
            default:
              xd->port_type = VNET_DPDK_PORT_TYPE_UNKNOWN;
            }
@@ -575,6 +584,9 @@ dpdk_lib_init (dpdk_main_t * dm)
 
       hi = vnet_get_hw_interface (dm->vnet_main, xd->hw_if_index);
 
+      if (xd->flags & DPDK_DEVICE_FLAG_TX_OFFLOAD)
+       hi->flags |= VNET_HW_INTERFACE_FLAG_SUPPORTS_TX_L4_CKSUM_OFFLOAD;
+
       dpdk_device_setup (xd);
 
       if (vec_len (xd->errors))
@@ -678,6 +690,11 @@ dpdk_bind_devices_to_uio (dpdk_config_main_t * conf)
     /* Chelsio T4/T5 */
     else if (d->vendor_id == 0x1425 && (d->device_id & 0xe000) == 0x4000)
       ;
+    /* Mellanox  */
+    else if (d->vendor_id == 0x15b3 && d->device_id >= 0x1013 && d->device_id <= 0x101a)
+      {
+        continue;
+      }
     else
       {
         clib_warning ("Unsupported PCI device 0x%04x:0x%04x found "
@@ -826,6 +843,10 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
   u8 huge_dir = 0;
   u8 file_prefix = 0;
   u8 *socket_mem = 0;
+  u8 *huge_dir_path = 0;
+
+  huge_dir_path =
+    format (0, "%s/hugepages%c", vlib_unix_get_runtime_dir (), 0);
 
   conf->device_config_index_by_pci_addr = hash_create (0, sizeof (uword));
   log_level = RTE_LOG_NOTICE;
@@ -971,7 +992,7 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
       u8 less_than_1g = 1;
       int rv;
 
-      umount (DEFAULT_HUGE_DIR);
+      umount ((char *) huge_dir_path);
 
       /* Process "socket-mem" parameter value */
       if (vec_len (socket_mem))
@@ -1015,21 +1036,28 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
       clib_bitmap_foreach (c, tm->cpu_socket_bitmap, (
         {
          int pages_avail, page_size, mem;
+         clib_error_t  *e = 0;
 
          vec_validate(mem_by_socket, c);
          mem = mem_by_socket[c];
 
          page_size = 1024;
-         pages_avail = vlib_sysfs_get_free_hugepages(c, page_size * 1024);
+         e = clib_sysfs_get_free_hugepages(c, page_size * 1024, &pages_avail);
 
-         if (pages_avail < 0 || page_size * pages_avail < mem)
+         if (e != 0 || pages_avail < 0 || page_size * pages_avail < mem)
            use_1g = 0;
 
+         if (e)
+          clib_error_free (e);
+
          page_size = 2;
-         pages_avail = vlib_sysfs_get_free_hugepages(c, page_size * 1024);
+         e = clib_sysfs_get_free_hugepages(c, page_size * 1024, &pages_avail);
 
-         if (pages_avail < 0 || page_size * pages_avail < mem)
+         if (e != 0 || pages_avail < 0 || page_size * pages_avail < mem)
            use_2m = 0;
+
+         if (e)
+          clib_error_free (e);
       }));
       /* *INDENT-ON* */
 
@@ -1048,27 +1076,20 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
 
       vec_free (mem_by_socket);
 
-      /* Make sure VPP_RUN_DIR exists */
-      error = unix_make_vpp_run_dir ();
+      error = vlib_unix_recursive_mkdir ((char *) huge_dir_path);
       if (error)
-       goto done;
-
-      rv = mkdir (DEFAULT_HUGE_DIR, 0755);
-      if (rv && errno != EEXIST)
        {
-         error = clib_error_return (0, "mkdir '%s' failed errno %d",
-                                    DEFAULT_HUGE_DIR, errno);
          goto done;
        }
 
       if (use_1g && !(less_than_1g && use_2m))
        {
-         rv =
-           mount ("none", DEFAULT_HUGE_DIR, "hugetlbfs", 0, "pagesize=1G");
+         rv = mount ("none", (char *) huge_dir_path, "hugetlbfs", 0,
+                     "pagesize=1G");
        }
       else if (use_2m)
        {
-         rv = mount ("none", DEFAULT_HUGE_DIR, "hugetlbfs", 0, NULL);
+         rv = mount ("none", (char *) huge_dir_path, "hugetlbfs", 0, NULL);
        }
       else
        {
@@ -1083,7 +1104,7 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
 
       tmp = format (0, "--huge-dir%c", 0);
       vec_add1 (conf->eal_init_args, tmp);
-      tmp = format (0, "%s%c", DEFAULT_HUGE_DIR, 0);
+      tmp = format (0, "%s%c", huge_dir_path, 0);
       vec_add1 (conf->eal_init_args, tmp);
       if (!file_prefix)
        {
@@ -1182,11 +1203,7 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
 
   /* Set up DPDK eal and packet mbuf pool early. */
 
-#if RTE_VERSION >= RTE_VERSION_NUM(17, 5, 0, 0)
   rte_log_set_global_level (log_level);
-#else
-  rte_set_log_level (log_level);
-#endif
 
   vm = vlib_get_main ();
 
@@ -1195,12 +1212,15 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
     conf->eal_init_args_str = format (conf->eal_init_args_str, "%s ",
                                      conf->eal_init_args[i]);
 
+  clib_warning ("EAL init args: %s", conf->eal_init_args_str);
   ret =
     rte_eal_init (vec_len (conf->eal_init_args),
                  (char **) conf->eal_init_args);
 
   /* lazy umount hugepages */
-  umount2 (DEFAULT_HUGE_DIR, MNT_DETACH);
+  umount2 ((char *) huge_dir_path, MNT_DETACH);
+  rmdir ((char *) huge_dir_path);
+  vec_free (huge_dir_path);
 
   if (ret < 0)
     return clib_error_return (0, "rte_eal_init returned %d", ret);
@@ -1210,13 +1230,13 @@ dpdk_config (vlib_main_t * vm, unformat_input_t * input)
   rte_dump_physmem_layout (stdout);
 
   /* main thread 1st */
-  error = vlib_buffer_pool_create (vm, conf->num_mbufs, rte_socket_id ());
+  error = dpdk_buffer_pool_create (vm, conf->num_mbufs, rte_socket_id ());
   if (error)
     return error;
 
   for (i = 0; i < RTE_MAX_LCORE; i++)
     {
-      error = vlib_buffer_pool_create (vm, conf->num_mbufs,
+      error = dpdk_buffer_pool_create (vm, conf->num_mbufs,
                                       rte_lcore_to_socket_id (i));
       if (error)
        return error;
@@ -1544,7 +1564,8 @@ dpdk_init (vlib_main_t * vm)
   /* Default vlib_buffer_t flags, DISABLES tcp/udp checksumming... */
   dm->buffer_flags_template =
     (VLIB_BUFFER_TOTAL_LENGTH_VALID | VLIB_BUFFER_EXT_HDR_VALID
-     | IP_BUFFER_L4_CHECKSUM_COMPUTED | IP_BUFFER_L4_CHECKSUM_CORRECT);
+     | VNET_BUFFER_F_L4_CHECKSUM_COMPUTED |
+     VNET_BUFFER_F_L4_CHECKSUM_CORRECT);
 
   dm->stat_poll_interval = DPDK_STATS_POLL_INTERVAL;
   dm->link_state_poll_interval = DPDK_LINK_POLL_INTERVAL;