aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/plugins/vmxnet3/README.md2
-rw-r--r--src/plugins/vmxnet3/cli.c5
-rw-r--r--src/plugins/vmxnet3/format.c1
-rw-r--r--src/plugins/vmxnet3/output.c9
-rw-r--r--src/plugins/vmxnet3/vmxnet3.c55
-rw-r--r--src/plugins/vmxnet3/vmxnet3.h2
6 files changed, 66 insertions, 8 deletions
diff --git a/src/plugins/vmxnet3/README.md b/src/plugins/vmxnet3/README.md
index a49671325c9..4f03c1575f9 100644
--- a/src/plugins/vmxnet3/README.md
+++ b/src/plugins/vmxnet3/README.md
@@ -34,7 +34,7 @@ echo Y | sudo tee /sys/module/vfio/parameters/enable_unsafe_noiommu_mode
3. Bind interface to vfio-pci
```
-dpdk-devbind.py --bind vfio-pci 0b:00.0
+sudo dpdk-devbind.py --bind vfio-pci 0b:00.0
```
### Interface Creation
diff --git a/src/plugins/vmxnet3/cli.c b/src/plugins/vmxnet3/cli.c
index 3a7e5d9ee65..1e4ac4a76f5 100644
--- a/src/plugins/vmxnet3/cli.c
+++ b/src/plugins/vmxnet3/cli.c
@@ -206,8 +206,9 @@ show_vmxnet3 (vlib_main_t * vm, u32 * hw_if_indices, u8 show_descr)
{
hi = vnet_get_hw_interface (vnm, hw_if_indices[i]);
vd = vec_elt_at_index (vmxm->devices, hi->dev_instance);
- vlib_cli_output (vm, "Interface: %s (ifindex %d)",
- hi->name, hw_if_indices[i]);
+ vlib_cli_output (vm, "Interface: %U (ifindex %d)",
+ format_vnet_hw_if_index_name, vnm, hw_if_indices[i],
+ hw_if_indices[i]);
vlib_cli_output (vm, " Version: %u", vd->version);
vlib_cli_output (vm, " PCI Address: %U", format_vlib_pci_addr,
&vd->pci_addr);
diff --git a/src/plugins/vmxnet3/format.c b/src/plugins/vmxnet3/format.c
index 8ee812ecc06..56904652a79 100644
--- a/src/plugins/vmxnet3/format.c
+++ b/src/plugins/vmxnet3/format.c
@@ -62,6 +62,7 @@ format_vmxnet3_device (u8 * s, va_list * args)
vmxnet3_txq_t *txq = vec_elt_at_index (vd->txqs, 0);
s = format (s, "flags: %U", format_vmxnet3_device_flags, vd);
+ s = format (s, "\n%Uspeed %u", format_white_space, indent, vd->link_speed);
s = format (s, "\n%Urx queues %u, rx desc %u, tx queues %u, tx desc %u",
format_white_space, indent,
vd->num_rx_queues, rxq->size, vd->num_tx_queues, txq->size);
diff --git a/src/plugins/vmxnet3/output.c b/src/plugins/vmxnet3/output.c
index 2ca1cc9f107..32b77dec259 100644
--- a/src/plugins/vmxnet3/output.c
+++ b/src/plugins/vmxnet3/output.c
@@ -115,8 +115,15 @@ VNET_DEVICE_CLASS_TX_FN (vmxnet3_device_class) (vlib_main_t * vm,
u16 qid = thread_index;
u16 n_retry = 5;
- txq = vec_elt_at_index (vd->txqs, qid % vd->num_tx_queues);
+ if (PREDICT_FALSE (!(vd->flags & VMXNET3_DEVICE_F_LINK_UP)))
+ {
+ vlib_buffer_free (vm, buffers, n_left);
+ vlib_error_count (vm, node->node_index, VMXNET3_TX_ERROR_LINK_DOWN,
+ n_left);
+ return (0);
+ }
+ txq = vec_elt_at_index (vd->txqs, qid % vd->num_tx_queues);
clib_spinlock_lock_if_init (&txq->lock);
retry:
diff --git a/src/plugins/vmxnet3/vmxnet3.c b/src/plugins/vmxnet3/vmxnet3.c
index 74e600304a7..2ff6d7969d2 100644
--- a/src/plugins/vmxnet3/vmxnet3.c
+++ b/src/plugins/vmxnet3/vmxnet3.c
@@ -185,6 +185,7 @@ vmxnet3_provision_driver_shared (vlib_main_t * vm, vmxnet3_device_t * vd)
shared->misc.num_tx_queues = vd->num_tx_queues;
shared->misc.num_rx_queues = vd->num_rx_queues;
shared->interrupt.num_intrs = vd->num_intrs;
+ shared->interrupt.event_intr_index = 1;
shared->interrupt.control = VMXNET3_IC_DISABLE_ALL;
shared->rx_filter.mode = VMXNET3_RXMODE_UCAST | VMXNET3_RXMODE_BCAST |
VMXNET3_RXMODE_ALL_MULTI;
@@ -309,7 +310,7 @@ vmxnet3_device_init (vlib_main_t * vm, vmxnet3_device_t * vd,
vd->num_tx_queues = 1;
vd->num_rx_queues = 1;
- vd->num_intrs = 1;
+ vd->num_intrs = 2;
/* Quiesce the device */
vmxnet3_reg_write (vd, 1, VMXNET3_REG_CMD, VMXNET3_CMD_QUIESCE_DEV);
@@ -351,6 +352,18 @@ vmxnet3_device_init (vlib_main_t * vm, vmxnet3_device_t * vd,
return error;
}
+ vmxnet3_reg_write (vd, 1, VMXNET3_REG_CMD, VMXNET3_CMD_GET_LINK);
+ ret = vmxnet3_reg_read (vd, 1, VMXNET3_REG_CMD);
+ if (ret & 1)
+ {
+ vd->flags |= VMXNET3_DEVICE_F_LINK_UP;
+ vd->link_speed = ret >> 16;
+ }
+ else
+ {
+ vd->flags &= ~VMXNET3_DEVICE_F_LINK_UP;
+ }
+
/* Get the mac address */
ret = vmxnet3_reg_read (vd, 1, VMXNET3_REG_MACL);
clib_memcpy (vd->mac_addr, &ret, 4);
@@ -413,7 +426,7 @@ vmxnet3_device_init (vlib_main_t * vm, vmxnet3_device_t * vd,
}
static void
-vmxnet3_irq_handler (vlib_pci_dev_handle_t h, u16 line)
+vmxnet3_irq_0_handler (vlib_pci_dev_handle_t h, u16 line)
{
vnet_main_t *vnm = vnet_get_main ();
vmxnet3_main_t *vmxm = &vmxnet3_main;
@@ -425,6 +438,31 @@ vmxnet3_irq_handler (vlib_pci_dev_handle_t h, u16 line)
vnet_device_input_set_interrupt_pending (vnm, vd->hw_if_index, qid);
}
+static void
+vmxnet3_irq_1_handler (vlib_pci_dev_handle_t h, u16 line)
+{
+ vnet_main_t *vnm = vnet_get_main ();
+ vmxnet3_main_t *vmxm = &vmxnet3_main;
+ uword pd = vlib_pci_get_private_data (h);
+ vmxnet3_device_t *vd = pool_elt_at_index (vmxm->devices, pd);
+ u32 ret;
+
+ vmxnet3_reg_write (vd, 1, VMXNET3_REG_CMD, VMXNET3_CMD_GET_LINK);
+ ret = vmxnet3_reg_read (vd, 1, VMXNET3_REG_CMD);
+ if (ret & 1)
+ {
+ vd->flags |= VMXNET3_DEVICE_F_LINK_UP;
+ vd->link_speed = ret >> 16;
+ vnet_hw_interface_set_flags (vnm, vd->hw_if_index,
+ VNET_HW_INTERFACE_FLAG_LINK_UP);
+ }
+ else
+ {
+ vd->flags &= ~VMXNET3_DEVICE_F_LINK_UP;
+ vnet_hw_interface_set_flags (vnm, vd->hw_if_index, 0);
+ }
+}
+
static u8
vmxnet3_queue_size_valid (u16 qsz)
{
@@ -504,10 +542,14 @@ vmxnet3_create_if (vlib_main_t * vm, vmxnet3_create_if_args_t * args)
goto error;
if ((error = vlib_pci_register_msix_handler (h, 0, 1,
- &vmxnet3_irq_handler)))
+ &vmxnet3_irq_0_handler)))
goto error;
- if ((error = vlib_pci_enable_msix_irq (h, 0, 1)))
+ if ((error = vlib_pci_register_msix_handler (h, 1, 1,
+ &vmxnet3_irq_1_handler)))
+ goto error;
+
+ if ((error = vlib_pci_enable_msix_irq (h, 0, 2)))
goto error;
if ((error = vlib_pci_intr_enable (h)))
@@ -533,6 +575,11 @@ vmxnet3_create_if (vlib_main_t * vm, vmxnet3_create_if_args_t * args)
vnet_hw_interface_set_input_node (vnm, vd->hw_if_index,
vmxnet3_input_node.index);
vnet_hw_interface_assign_rx_thread (vnm, vd->hw_if_index, 0, ~0);
+ if (vd->flags & VMXNET3_DEVICE_F_LINK_UP)
+ vnet_hw_interface_set_flags (vnm, vd->hw_if_index,
+ VNET_HW_INTERFACE_FLAG_LINK_UP);
+ else
+ vnet_hw_interface_set_flags (vnm, vd->hw_if_index, 0);
return;
error:
diff --git a/src/plugins/vmxnet3/vmxnet3.h b/src/plugins/vmxnet3/vmxnet3.h
index 666dec77b38..f3868a88ae3 100644
--- a/src/plugins/vmxnet3/vmxnet3.h
+++ b/src/plugins/vmxnet3/vmxnet3.h
@@ -18,6 +18,7 @@
#define foreach_vmxnet3_tx_func_error \
_(ERROR_PACKETS, "error packets") \
+ _(LINK_DOWN, "link down") \
_(NO_FREE_SLOTS, "no free tx slots")
typedef enum
@@ -472,6 +473,7 @@ typedef struct
vmxnet3_dma *dma;
+ u32 link_speed;
} vmxnet3_device_t;
typedef struct