#define ETH_I40E_FLOATING_VEB_LIST_ARG "floating_veb_list"
#define ETH_I40E_SUPPORT_MULTI_DRIVER "support-multi-driver"
#define ETH_I40E_QUEUE_NUM_PER_VF_ARG "queue-num-per-vf"
+#define ETH_I40E_USE_LATEST_VEC "use-latest-supported-vec"
#define I40E_CLEAR_PXE_WAIT_MS 200
uint64_t *stat);
static void i40e_pf_config_irq0(struct i40e_hw *hw, bool no_queue);
static void i40e_dev_interrupt_handler(void *param);
+static void i40e_dev_alarm_handler(void *param);
static int i40e_res_pool_init(struct i40e_res_pool_info *pool,
uint32_t base, uint32_t num);
static void i40e_res_pool_destroy(struct i40e_res_pool_info *pool);
struct i40e_ethertype_filter *filter);
static int i40e_tunnel_filter_convert(
- struct i40e_aqc_add_rm_cloud_filt_elem_ext *cld_filter,
+ struct i40e_aqc_cloud_filters_element_bb *cld_filter,
struct i40e_tunnel_filter *tunnel_filter);
static int i40e_sw_tunnel_filter_insert(struct i40e_pf *pf,
struct i40e_tunnel_filter *tunnel_filter);
ETH_I40E_FLOATING_VEB_LIST_ARG,
ETH_I40E_SUPPORT_MULTI_DRIVER,
ETH_I40E_QUEUE_NUM_PER_VF_ARG,
+ ETH_I40E_USE_LATEST_VEC,
NULL};
static const struct rte_pci_id pci_id_i40e_map[] = {
return i40e_aq_debug_write_register(hw, reg_addr, reg_val, cmd_details);
}
+static int
+i40e_parse_latest_vec_handler(__rte_unused const char *key,
+ const char *value,
+ void *opaque)
+{
+ struct i40e_adapter *ad;
+ int use_latest_vec;
+
+ ad = (struct i40e_adapter *)opaque;
+
+ use_latest_vec = atoi(value);
+
+ if (use_latest_vec != 0 && use_latest_vec != 1)
+ PMD_DRV_LOG(WARNING, "Value should be 0 or 1, set it as 1!");
+
+ ad->use_latest_vec = (uint8_t)use_latest_vec;
+
+ return 0;
+}
+
+static int
+i40e_use_latest_vec(struct rte_eth_dev *dev)
+{
+ struct i40e_adapter *ad =
+ I40E_DEV_PRIVATE_TO_ADAPTER(dev->data->dev_private);
+ struct rte_kvargs *kvlist;
+ int kvargs_count;
+
+ ad->use_latest_vec = false;
+
+ if (!dev->device->devargs)
+ return 0;
+
+ kvlist = rte_kvargs_parse(dev->device->devargs->args, valid_keys);
+ if (!kvlist)
+ return -EINVAL;
+
+ kvargs_count = rte_kvargs_count(kvlist, ETH_I40E_USE_LATEST_VEC);
+ if (!kvargs_count) {
+ rte_kvargs_free(kvlist);
+ return 0;
+ }
+
+ if (kvargs_count > 1)
+ PMD_DRV_LOG(WARNING, "More than one argument \"%s\" and only "
+ "the first invalid or last valid one is used !",
+ ETH_I40E_USE_LATEST_VEC);
+
+ if (rte_kvargs_process(kvlist, ETH_I40E_USE_LATEST_VEC,
+ i40e_parse_latest_vec_handler, ad) < 0) {
+ rte_kvargs_free(kvlist);
+ return -EINVAL;
+ }
+
+ rte_kvargs_free(kvlist);
+ return 0;
+}
+
+#define I40E_ALARM_INTERVAL 50000 /* us */
+
static int
eth_i40e_dev_init(struct rte_eth_dev *dev, void *init_params __rte_unused)
{
/* Check if need to support multi-driver */
i40e_support_multi_driver(dev);
+ /* Check if users want the latest supported vec path */
+ i40e_use_latest_vec(dev);
/* Make sure all is clean before doing PF reset */
i40e_clear_hw(hw);
- /* Initialize the hardware */
- i40e_hw_init(dev);
-
/* Reset here to make sure all is clean for each PF */
ret = i40e_pf_reset(hw);
if (ret) {
return ret;
}
+ /* Initialize the parameters for adminq */
+ i40e_init_adminq_parameter(hw);
+ ret = i40e_init_adminq(hw);
+ if (ret != I40E_SUCCESS) {
+ PMD_INIT_LOG(ERR, "Failed to init adminq: %d", ret);
+ return -EIO;
+ }
+ PMD_INIT_LOG(INFO, "FW %d.%d API %d.%d NVM %02d.%02d.%02d eetrack %04x",
+ hw->aq.fw_maj_ver, hw->aq.fw_min_ver,
+ hw->aq.api_maj_ver, hw->aq.api_min_ver,
+ ((hw->nvm.version >> 12) & 0xf),
+ ((hw->nvm.version >> 4) & 0xff),
+ (hw->nvm.version & 0xf), hw->nvm.eetrack);
+
+ /* Initialize the hardware */
+ i40e_hw_init(dev);
+
i40e_config_automask(pf);
i40e_set_default_pctype_table(dev);
/* Initialize the input set for filters (hash and fd) to default value */
i40e_filter_input_set_init(pf);
- /* Initialize the parameters for adminq */
- i40e_init_adminq_parameter(hw);
- ret = i40e_init_adminq(hw);
- if (ret != I40E_SUCCESS) {
- PMD_INIT_LOG(ERR, "Failed to init adminq: %d", ret);
- return -EIO;
- }
- PMD_INIT_LOG(INFO, "FW %d.%d API %d.%d NVM %02d.%02d.%02d eetrack %04x",
- hw->aq.fw_maj_ver, hw->aq.fw_min_ver,
- hw->aq.api_maj_ver, hw->aq.api_min_ver,
- ((hw->nvm.version >> 12) & 0xf),
- ((hw->nvm.version >> 4) & 0xff),
- (hw->nvm.version & 0xf), hw->nvm.eetrack);
-
/* initialise the L3_MAP register */
if (!pf->support_multi_driver) {
ret = i40e_aq_debug_write_global_register(hw,
i40e_dev_link_update(dev, 0);
}
- /* enable uio intr after callback register */
- rte_intr_enable(intr_handle);
+ if (dev->data->dev_conf.intr_conf.rxq == 0) {
+ rte_eal_alarm_set(I40E_ALARM_INTERVAL,
+ i40e_dev_alarm_handler, dev);
+ } else {
+ /* enable uio intr after callback register */
+ rte_intr_enable(intr_handle);
+ }
i40e_filter_restore(pf);
if (hw->adapter_stopped == 1)
return;
+
+ if (dev->data->dev_conf.intr_conf.rxq == 0) {
+ rte_eal_alarm_cancel(i40e_dev_alarm_handler, dev);
+ rte_intr_enable(intr_handle);
+ }
+
/* Disable all queues */
i40e_dev_switch_queues(pf, FALSE);
DEV_RX_OFFLOAD_UDP_CKSUM |
DEV_RX_OFFLOAD_TCP_CKSUM |
DEV_RX_OFFLOAD_OUTER_IPV4_CKSUM |
- DEV_RX_OFFLOAD_CRC_STRIP |
DEV_RX_OFFLOAD_KEEP_CRC |
+ DEV_RX_OFFLOAD_SCATTER |
DEV_RX_OFFLOAD_VLAN_EXTEND |
DEV_RX_OFFLOAD_VLAN_FILTER |
DEV_RX_OFFLOAD_JUMBO_FRAME;
if (vlan_type == ETH_VLAN_TYPE_OUTER)
hw->second_tag = rte_cpu_to_le_16(tpid);
}
- ret = i40e_aq_set_switch_config(hw, 0, 0, NULL);
+ ret = i40e_aq_set_switch_config(hw, 0, 0, 0, NULL);
if (ret != I40E_SUCCESS) {
PMD_DRV_LOG(ERR,
"Set switch config failed aq_err: %d",
rte_intr_enable(dev->intr_handle);
}
+static void
+i40e_dev_alarm_handler(void *param)
+{
+ struct rte_eth_dev *dev = (struct rte_eth_dev *)param;
+ struct i40e_hw *hw = I40E_DEV_PRIVATE_TO_HW(dev->data->dev_private);
+ uint32_t icr0;
+
+ /* Disable interrupt */
+ i40e_pf_disable_irq0(hw);
+
+ /* read out interrupt causes */
+ icr0 = I40E_READ_REG(hw, I40E_PFINT_ICR0);
+
+ /* No interrupt event indicated */
+ if (!(icr0 & I40E_PFINT_ICR0_INTEVENT_MASK))
+ goto done;
+ if (icr0 & I40E_PFINT_ICR0_ECC_ERR_MASK)
+ PMD_DRV_LOG(ERR, "ICR0: unrecoverable ECC error");
+ if (icr0 & I40E_PFINT_ICR0_MAL_DETECT_MASK)
+ PMD_DRV_LOG(ERR, "ICR0: malicious programming detected");
+ if (icr0 & I40E_PFINT_ICR0_GRST_MASK)
+ PMD_DRV_LOG(INFO, "ICR0: global reset requested");
+ if (icr0 & I40E_PFINT_ICR0_PCI_EXCEPTION_MASK)
+ PMD_DRV_LOG(INFO, "ICR0: PCI exception activated");
+ if (icr0 & I40E_PFINT_ICR0_STORM_DETECT_MASK)
+ PMD_DRV_LOG(INFO, "ICR0: a change in the storm control state");
+ if (icr0 & I40E_PFINT_ICR0_HMC_ERR_MASK)
+ PMD_DRV_LOG(ERR, "ICR0: HMC error");
+ if (icr0 & I40E_PFINT_ICR0_PE_CRITERR_MASK)
+ PMD_DRV_LOG(ERR, "ICR0: protocol engine critical error");
+
+ if (icr0 & I40E_PFINT_ICR0_VFLR_MASK) {
+ PMD_DRV_LOG(INFO, "ICR0: VF reset detected");
+ i40e_dev_handle_vfr_event(dev);
+ }
+ if (icr0 & I40E_PFINT_ICR0_ADMINQ_MASK) {
+ PMD_DRV_LOG(INFO, "ICR0: adminq event");
+ i40e_dev_handle_aq_msg(dev);
+ }
+
+done:
+ /* Enable interrupt */
+ i40e_pf_enable_irq0(hw);
+ rte_eal_alarm_set(I40E_ALARM_INTERVAL,
+ i40e_dev_alarm_handler, dev);
+}
+
int
i40e_add_macvlan_filters(struct i40e_vsi *vsi,
struct i40e_macvlan_filter *filter,
/* Convert tunnel filter structure */
static int
i40e_tunnel_filter_convert(
- struct i40e_aqc_add_rm_cloud_filt_elem_ext *cld_filter,
+ struct i40e_aqc_cloud_filters_element_bb *cld_filter,
struct i40e_tunnel_filter *tunnel_filter)
{
ether_addr_copy((struct ether_addr *)&cld_filter->element.outer_mac,
int val, ret = 0;
struct i40e_hw *hw = I40E_PF_TO_HW(pf);
struct i40e_vsi *vsi = pf->main_vsi;
- struct i40e_aqc_add_rm_cloud_filt_elem_ext *cld_filter;
- struct i40e_aqc_add_rm_cloud_filt_elem_ext *pfilter;
+ struct i40e_aqc_cloud_filters_element_bb *cld_filter;
+ struct i40e_aqc_cloud_filters_element_bb *pfilter;
struct i40e_tunnel_rule *tunnel_rule = &pf->tunnel;
struct i40e_tunnel_filter *tunnel, *node;
struct i40e_tunnel_filter check_filter; /* Check if filter exists */
if (ret < 0)
rte_free(tunnel);
} else {
- ret = i40e_aq_remove_cloud_filters(hw, vsi->seid,
+ ret = i40e_aq_rem_cloud_filters(hw, vsi->seid,
&cld_filter->element, 1);
if (ret < 0) {
PMD_DRV_LOG(ERR, "Failed to delete a tunnel filter.");
struct i40e_pf_vf *vf = NULL;
struct i40e_hw *hw = I40E_PF_TO_HW(pf);
struct i40e_vsi *vsi;
- struct i40e_aqc_add_rm_cloud_filt_elem_ext *cld_filter;
- struct i40e_aqc_add_rm_cloud_filt_elem_ext *pfilter;
+ struct i40e_aqc_cloud_filters_element_bb *cld_filter;
+ struct i40e_aqc_cloud_filters_element_bb *pfilter;
struct i40e_tunnel_rule *tunnel_rule = &pf->tunnel;
struct i40e_tunnel_filter *tunnel, *node;
struct i40e_tunnel_filter check_filter; /* Check if filter exists */
if (add) {
if (big_buffer)
- ret = i40e_aq_add_cloud_filters_big_buffer(hw,
+ ret = i40e_aq_add_cloud_filters_bb(hw,
vsi->seid, cld_filter, 1);
else
ret = i40e_aq_add_cloud_filters(hw,
rte_free(tunnel);
} else {
if (big_buffer)
- ret = i40e_aq_remove_cloud_filters_big_buffer(
+ ret = i40e_aq_rem_cloud_filters_bb(
hw, vsi->seid, cld_filter, 1);
else
- ret = i40e_aq_remove_cloud_filters(hw, vsi->seid,
- &cld_filter->element, 1);
+ ret = i40e_aq_rem_cloud_filters(hw, vsi->seid,
+ &cld_filter->element, 1);
if (ret < 0) {
PMD_DRV_LOG(ERR, "Failed to delete a tunnel filter.");
rte_free(cld_filter);
* LLDP MIB change event.
*/
if (sw_dcb == TRUE) {
+ /* When using NVM 6.01 or later, the RX data path does
+ * not hang if the FW LLDP is stopped.
+ */
+ if (((hw->nvm.version >> 12) & 0xf) >= 6 &&
+ ((hw->nvm.version >> 4) & 0xff) >= 1) {
+ ret = i40e_aq_stop_lldp(hw, TRUE, NULL);
+ if (ret != I40E_SUCCESS)
+ PMD_INIT_LOG(DEBUG, "Failed to stop lldp");
+ }
+
ret = i40e_init_dcb(hw);
/* If lldp agent is stopped, the return value from
* i40e_init_dcb we expect is failure with I40E_AQ_RC_EPERM
struct i40e_tunnel_filter_list
*tunnel_list = &pf->tunnel.tunnel_list;
struct i40e_tunnel_filter *f;
- struct i40e_aqc_add_rm_cloud_filt_elem_ext cld_filter;
+ struct i40e_aqc_cloud_filters_element_bb cld_filter;
bool big_buffer = 0;
TAILQ_FOREACH(f, tunnel_list, rules) {
big_buffer = 1;
if (big_buffer)
- i40e_aq_add_cloud_filters_big_buffer(hw,
- vsi->seid, &cld_filter, 1);
+ i40e_aq_add_cloud_filters_bb(hw,
+ vsi->seid, &cld_filter, 1);
else
i40e_aq_add_cloud_filters(hw, vsi->seid,
&cld_filter.element, 1);
ETH_I40E_FLOATING_VEB_ARG "=1"
ETH_I40E_FLOATING_VEB_LIST_ARG "=<string>"
ETH_I40E_QUEUE_NUM_PER_VF_ARG "=1|2|4|8|16"
- ETH_I40E_SUPPORT_MULTI_DRIVER "=1");
+ ETH_I40E_SUPPORT_MULTI_DRIVER "=1"
+ ETH_I40E_USE_LATEST_VEC "=0|1");