X-Git-Url: https://gerrit.fd.io/r/gitweb?a=blobdiff_plain;f=src%2Fplugins%2Favf%2Fdevice.c;h=def8a799ecb743a7272b35e1de50d7a244cf3ffd;hb=ffe9a5489;hp=c6bf2df4443678b0cb05bfc822e42741a168833a;hpb=bb7991a037a23eb966aee2d6f8069353c6a64c94;p=vpp.git diff --git a/src/plugins/avf/device.c b/src/plugins/avf/device.c index c6bf2df4443..def8a799ecb 100644 --- a/src/plugins/avf/device.c +++ b/src/plugins/avf/device.c @@ -20,11 +20,12 @@ #include #include #include +#include #include #define AVF_MBOX_LEN 64 -#define AVF_MBOX_BUF_SZ 512 +#define AVF_MBOX_BUF_SZ 4096 #define AVF_RXQ_SZ 512 #define AVF_TXQ_SZ 512 #define AVF_ITR_INT 250 @@ -484,7 +485,7 @@ retry: goto done; } - if (d->flags & AVF_AQ_F_BUF) + if (out_len && d->flags & AVF_AQ_F_BUF) { void *buf = ad->arq_bufs + ad->arq_next_slot * AVF_MBOX_BUF_SZ; clib_memcpy_fast (out, buf, out_len); @@ -555,10 +556,11 @@ avf_op_get_vf_resources (vlib_main_t * vm, avf_device_t * ad, virtchnl_vf_resource_t * res) { clib_error_t *err = 0; - u32 bitmap = (VIRTCHNL_VF_OFFLOAD_L2 | VIRTCHNL_VF_OFFLOAD_RSS_PF | - VIRTCHNL_VF_OFFLOAD_WB_ON_ITR | VIRTCHNL_VF_OFFLOAD_VLAN | - VIRTCHNL_VF_OFFLOAD_RX_POLLING | - VIRTCHNL_VF_CAP_ADV_LINK_SPEED); + u32 bitmap = + (VIRTCHNL_VF_OFFLOAD_L2 | VIRTCHNL_VF_OFFLOAD_RSS_PF | + VIRTCHNL_VF_OFFLOAD_WB_ON_ITR | VIRTCHNL_VF_OFFLOAD_VLAN | + VIRTCHNL_VF_OFFLOAD_RX_POLLING | VIRTCHNL_VF_CAP_ADV_LINK_SPEED | + VIRTCHNL_VF_OFFLOAD_FDIR_PF | VIRTCHNL_VF_OFFLOAD_ADV_RSS_PF); avf_log_debug (ad, "get_vf_reqources: bitmap 0x%x", bitmap); err = avf_send_to_pf (vm, ad, VIRTCHNL_OP_GET_VF_RESOURCES, &bitmap, @@ -1175,6 +1177,20 @@ error: vlib_log_err (avf_log.class, "%U", format_clib_error, ad->error); } +clib_error_t * +avf_op_program_flow (vlib_main_t *vm, avf_device_t *ad, int is_create, + u8 *rule, u32 rule_len, u8 *program_status, + u32 status_len) +{ + avf_log_debug (ad, "avf_op_program_flow: vsi_id %u is_create %u", ad->vsi_id, + is_create); + + return avf_send_to_pf (vm, ad, + is_create ? VIRTCHNL_OP_ADD_FDIR_FILTER : + VIRTCHNL_OP_DEL_FDIR_FILTER, + rule, rule_len, program_status, status_len); +} + static void avf_process_handle_request (vlib_main_t * vm, avf_process_req_t * req) { @@ -1185,6 +1201,10 @@ avf_process_handle_request (vlib_main_t * vm, avf_process_req_t * req) req->is_add); else if (req->type == AVF_PROCESS_REQ_CONFIG_PROMISC_MDDE) req->error = avf_op_config_promisc_mode (vm, ad, req->is_enable); + else if (req->type == AVF_PROCESS_REQ_PROGRAM_FLOW) + req->error = + avf_op_program_flow (vm, ad, req->is_add, req->rule, req->rule_len, + req->program_status, req->status_len); else clib_panic ("BUG: unknown avf proceess request type"); @@ -1307,10 +1327,10 @@ avf_process (vlib_main_t * vm, vlib_node_runtime_t * rt, vlib_frame_t * f) * during suspend */ vec_reset_length (dev_pointers); /* *INDENT-OFF* */ - pool_foreach_index (i, am->devices, + pool_foreach_index (i, am->devices) { vec_add1 (dev_pointers, avf_get_device (i)); - }); + } vec_foreach_index (i, dev_pointers) { @@ -1373,6 +1393,7 @@ avf_irq_n_handler (vlib_main_t * vm, vlib_pci_dev_handle_t h, u16 line) vnet_main_t *vnm = vnet_get_main (); uword pd = vlib_pci_get_private_data (vm, h); avf_device_t *ad = avf_get_device (pd); + avf_rxq_t *rxq = vec_elt_at_index (ad->rxqs, line - 1); if (ad->flags & AVF_DEVICE_F_ELOG) { @@ -1396,8 +1417,8 @@ avf_irq_n_handler (vlib_main_t * vm, vlib_pci_dev_handle_t h, u16 line) line--; - if (ad->flags & AVF_DEVICE_F_RX_INT && ad->rxqs[line].int_mode) - vnet_device_input_set_interrupt_pending (vnm, ad->hw_if_index, line); + if (ad->flags & AVF_DEVICE_F_RX_INT && rxq->int_mode) + vnet_hw_if_rx_queue_set_int_pending (vnm, rxq->queue_index); avf_irq_n_set_state (ad, line, AVF_IRQ_STATE_ENABLED); } @@ -1415,7 +1436,6 @@ avf_delete_if (vlib_main_t * vm, avf_device_t * ad, int with_barrier) if (with_barrier) vlib_worker_thread_barrier_sync (vm); vnet_hw_interface_set_flags (vnm, ad->hw_if_index, 0); - vnet_hw_interface_unassign_rx_thread (vnm, ad->hw_if_index, 0); ethernet_delete_interface (vnm, ad->hw_if_index); if (with_barrier) vlib_worker_thread_barrier_release (vm); @@ -1519,7 +1539,7 @@ avf_create_if (vlib_main_t * vm, avf_create_if_args_t * args) return; /* *INDENT-OFF* */ - pool_foreach (adp, am->devices, ({ + pool_foreach (adp, am->devices) { if ((*adp)->pci_addr.as_u32 == args->addr.as_u32) { args->rv = VNET_API_ERROR_ADDRESS_IN_USE; @@ -1528,7 +1548,7 @@ avf_create_if (vlib_main_t * vm, avf_create_if_args_t * args) &args->addr, "pci address in use"); return; } - })); + } /* *INDENT-ON* */ pool_get (am->devices, adp); @@ -1648,10 +1668,9 @@ avf_create_if (vlib_main_t * vm, avf_create_if_args_t * args) /* Indicate ability to support L3 DMAC filtering and * initialize interface to L3 non-promisc mode */ vnet_hw_interface_t *hi = vnet_get_hw_interface (vnm, ad->hw_if_index); - hi->flags |= - VNET_HW_INTERFACE_FLAG_SUPPORTS_MAC_FILTER | - VNET_HW_INTERFACE_FLAG_SUPPORTS_TX_L4_CKSUM_OFFLOAD | - VNET_HW_INTERFACE_FLAG_SUPPORTS_GSO; + hi->caps |= VNET_HW_INTERFACE_CAP_SUPPORTS_MAC_FILTER | + VNET_HW_INTERFACE_CAP_SUPPORTS_L4_TX_CKSUM | + VNET_HW_INTERFACE_CAP_SUPPORTS_TCP_GSO; ethernet_set_flags (vnm, ad->hw_if_index, ETHERNET_INTERFACE_FLAG_DEFAULT_L3); @@ -1659,12 +1678,23 @@ avf_create_if (vlib_main_t * vm, avf_create_if_args_t * args) args->sw_if_index = ad->sw_if_index = sw->sw_if_index; vnet_hw_interface_t *hw = vnet_get_hw_interface (vnm, ad->hw_if_index); - hw->flags |= VNET_HW_INTERFACE_FLAG_SUPPORTS_INT_MODE; - vnet_hw_interface_set_input_node (vnm, ad->hw_if_index, - avf_input_node.index); + hw->caps |= VNET_HW_INTERFACE_CAP_SUPPORTS_INT_MODE; + vnet_hw_if_set_input_node (vnm, ad->hw_if_index, avf_input_node.index); for (i = 0; i < ad->n_rx_queues; i++) - vnet_hw_interface_assign_rx_thread (vnm, ad->hw_if_index, i, ~0); + { + u32 qi, fi; + qi = vnet_hw_if_register_rx_queue (vnm, ad->hw_if_index, i, + VNET_HW_IF_RXQ_THREAD_ANY); + + if (ad->flags & AVF_DEVICE_F_RX_INT) + { + fi = vlib_pci_get_msix_file_index (vm, ad->pci_dev_handle, i + 1); + vnet_hw_if_set_rx_queue_file_index (vnm, qi, fi); + } + ad->rxqs[i].queue_index = qi; + } + vnet_hw_if_update_runtime_data (vnm, ad->hw_if_index); if (pool_elts (am->devices) == 1) vlib_process_signal_event (vm, avf_process_node.index, @@ -1782,9 +1812,26 @@ avf_clear_hw_interface_counters (u32 instance) &ad->eth_stats, sizeof (ad->eth_stats)); } -/* *INDENT-OFF* */ -VNET_DEVICE_CLASS (avf_device_class,) = +clib_error_t * +avf_program_flow (u32 dev_instance, int is_add, u8 *rule, u32 rule_len, + u8 *program_status, u32 status_len) { + vlib_main_t *vm = vlib_get_main (); + avf_process_req_t req; + + req.dev_instance = dev_instance; + req.type = AVF_PROCESS_REQ_PROGRAM_FLOW; + req.is_add = is_add; + req.rule = rule; + req.rule_len = rule_len; + req.program_status = program_status; + req.status_len = status_len; + + return avf_process_request (vm, &req); +} + +/* *INDENT-OFF* */ +VNET_DEVICE_CLASS (avf_device_class, ) = { .name = "Adaptive Virtual Function (AVF) interface", .clear_counters = avf_clear_hw_interface_counters, .format_device = format_avf_device, @@ -1795,6 +1842,7 @@ VNET_DEVICE_CLASS (avf_device_class,) = .mac_addr_add_del_function = avf_add_del_mac_address, .tx_function_n_errors = AVF_TX_N_ERROR, .tx_function_error_strings = avf_tx_func_error_strings, + .flow_ops_function = avf_flow_ops_fn, }; /* *INDENT-ON* */