{
int rv;
- /*
- * DAW-FIXME: The DPDK VMXNET3 driver does not currently support
- * multi-buffer packets. Max out at 1518 bytes for now.
- *
- * If/when the driver gets fixed, then this should be
- * removed.
- */
- if ((xd->pmd == VNET_DPDK_PMD_VMXNET3) &&
- (hi->max_packet_bytes > 1518))
- {
- hi->max_packet_bytes = 1518;
-
- vlib_cli_output (vlib_get_main(),
- "VMXNET3 driver does not support jumbo frames "
- "yet -- setting mtu to 1518!");
- }
-
xd->port_conf.rxmode.max_rx_pkt_len = hi->max_packet_bytes;
if (xd->admin_up)
xd->af_packet_port_id = af_packet_port_id++;
break;
+ case VNET_DPDK_PMD_BOND:
+ xd->port_type = VNET_DPDK_PORT_TYPE_ETH_BOND;
+ break;
+
default:
xd->port_type = VNET_DPDK_PORT_TYPE_UNKNOWN;
}
return 0;
}
-/*
- * Tell the vlib physical memory allocator that we've handled
- * the initialization. We don't actually do so until
- * vlib_main(...) callls the dpdk config function.
- */
-int vlib_app_physmem_init (vlib_main_t * vm, physmem_main_t * pm,
- int physmem_required)
-{
- return 1;
-}
-
static clib_error_t *
write_sys_fs (char * file_name, char * fmt, ...)
{
_vec_len (path) = 0;
path = format (path, "/sys/bus/pci/drivers/%s/new_id%c", driver_name, 0);
error = write_sys_fs ((char *) path, "%s %s", pci_vid, pci_did);
- if (error)
- continue;
_vec_len (path) = 0;
path = format (path, "/sys/bus/pci/drivers/%s/bind%c", driver_name, 0);
return error;
}
-static uword
-unformat_socket_mem (unformat_input_t * input, va_list * va)
-{
- uword ** r = va_arg (* va, uword **);
- int i = 0;
- u32 mem;
-
- while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
- {
- if (unformat (input, ","))
- hash_set (*r, i, 1024);
- else if (unformat (input, "%u,", &mem))
- hash_set (*r, i, mem);
- else if (unformat (input, "%u", &mem))
- hash_set (*r, i, mem);
- else
- {
- unformat_put_input (input);
- goto done;
- }
- i++;
- }
-
-done:
- return 1;
-}
-
static u32
get_node_free_hugepages_num (u32 node, u32 page_size)
{
u32 pages_avail;
pages_avail = get_node_free_hugepages_num(c, 1048576);
- if (!(pages_avail >= pages_num_1g))
+ if (!pages_avail || !(pages_avail >= pages_num_1g))
use_1g = 0;
pages_avail = get_node_free_hugepages_num(c, 2048);
- if (!(pages_avail >= pages_num_2m))
+ if (!pages_avail || !(pages_avail >= pages_num_2m))
use_2m = 0;
}
}
if (ret < 0)
return clib_error_return (0, "rte_eal_init returned %d", ret);
+ /* Dump the physical memory layout prior to creating the mbuf_pool */
+ fprintf(stdout, "DPDK physical memory layout:\n");
+ rte_dump_physmem_layout(stdout);
+
/* main thread 1st */
- error = vlib_buffer_pool_create(vm, dm->num_mbufs, MBUF_SIZE, rte_socket_id());
+ error = vlib_buffer_pool_create(vm, dm->num_mbufs, rte_socket_id());
if (error)
return error;
for (i = 0; i < RTE_MAX_LCORE; i++)
{
- error = vlib_buffer_pool_create(vm, dm->num_mbufs, MBUF_SIZE,
+ error = vlib_buffer_pool_create(vm, dm->num_mbufs,
rte_lcore_to_socket_id(i));
if (error)
return error;
vlib_frame_t * f)
{
clib_error_t * error;
+ vnet_main_t * vnm = vnet_get_main();
dpdk_main_t * dm = &dpdk_main;
+ ethernet_main_t * em = ðernet_main;
dpdk_device_t * xd;
vlib_thread_main_t * tm = vlib_get_thread_main();
void *vu_state;
dpdk_update_link_state (xd, now);
}
+{ // Setup MACs for bond interfaces and their links which was initialized in
+ // dpdk_port_setup() but needs to be done again here to take effect.
+ int nports = rte_eth_dev_count();
+ if (nports > 0) {
+ for (i = 0; i < nports; i++) {
+ struct rte_eth_dev_info dev_info;
+ rte_eth_dev_info_get(i, &dev_info);
+ if (!dev_info.driver_name)
+ dev_info.driver_name = dev_info.pci_dev->driver->name;
+ ASSERT(dev_info.driver_name);
+ if (strncmp(dev_info.driver_name, "rte_bond_pmd", 12) == 0) {
+ u8 addr[6];
+ u8 slink[16];
+ int nlink = rte_eth_bond_slaves_get(i, slink, 16);
+ if (nlink > 0) {
+ vnet_hw_interface_t * hi;
+ ethernet_interface_t * ei;
+ /* Get MAC of 1st slave link */
+ rte_eth_macaddr_get(slink[0], (struct ether_addr *)addr);
+ /* Set MAC of bounded interface to that of 1st slave link */
+ rte_eth_bond_mac_address_set(i, (struct ether_addr *)addr);
+ /* Populate MAC of bonded interface in VPP hw tables */
+ hi = vnet_get_hw_interface (
+ vnm, dm->devices[i].vlib_hw_if_index);
+ ei = pool_elt_at_index (em->interfaces, hi->hw_instance);
+ memcpy (hi->hw_address, addr, 6);
+ memcpy (ei->address, addr, 6);
+ /* Add MAC to other slave links */
+ while (nlink > 1) {
+ nlink--;
+ rte_eth_dev_mac_addr_add(
+ slink[nlink], (struct ether_addr *)addr, 0);
+ }
+ }
+ }
+ }
+ }
+}
+
while (1)
{
- vlib_process_wait_for_event_or_clock (vm, 5.0);
+ /*
+ * check each time through the loop in case intervals are changed
+ */
+ f64 min_wait = dm->link_state_poll_interval < dm->stat_poll_interval ?
+ dm->link_state_poll_interval : dm->stat_poll_interval;
+
+ vlib_process_wait_for_event_or_clock (vm, min_wait);
if (dpdk_get_admin_up_down_in_progress())
/* skip the poll if an admin up down is in progress (on any interface) */
vec_foreach (xd, dm->devices)
{
f64 now = vlib_time_now (vm);
- if ((now - xd->time_last_stats_update) >= DPDK_STATS_POLL_INTERVAL)
+ if ((now - xd->time_last_stats_update) >= dm->stat_poll_interval)
dpdk_update_counters (xd, now);
- if ((now - xd->time_last_link_update) >= DPDK_LINK_POLL_INTERVAL)
+ if ((now - xd->time_last_link_update) >= dm->link_state_poll_interval)
dpdk_update_link_state (xd, now);
if (xd->dev_type == VNET_DPDK_DEV_VHOST_USER)
.process_log2_n_stack_bytes = 17,
};
+int dpdk_set_stat_poll_interval (f64 interval)
+{
+ if (interval < DPDK_MIN_STATS_POLL_INTERVAL)
+ return (VNET_API_ERROR_INVALID_VALUE);
+
+ dpdk_main.stat_poll_interval = interval;
+
+ return 0;
+}
+
+int dpdk_set_link_state_poll_interval (f64 interval)
+{
+ if (interval < DPDK_MIN_LINK_POLL_INTERVAL)
+ return (VNET_API_ERROR_INVALID_VALUE);
+
+ dpdk_main.link_state_poll_interval = interval;
+
+ return 0;
+}
+
clib_error_t *
dpdk_init (vlib_main_t * vm)
{
_(rte_cxgbe_driver)
#endif
+#ifdef RTE_LIBRTE_PMD_BOND
+ _(bond_drv)
+#endif
+
#undef _
/*
| IP_BUFFER_L4_CHECKSUM_COMPUTED
| IP_BUFFER_L4_CHECKSUM_CORRECT);
+ dm->stat_poll_interval = DPDK_STATS_POLL_INTERVAL;
+ dm->link_state_poll_interval = DPDK_LINK_POLL_INTERVAL;
+
/* init CLI */
if ((error = vlib_call_init_function (vm, dpdk_cli_init)))
return error;