Commit b3c8e0de authored by David S. Miller's avatar David S. Miller

Merge branch '40GbE' of git://git.kernel.org/pub/scm/linux/kernel/git/tnguy/net-queue

Tony Nguyen says:

====================
Intel Wired LAN Driver Updates 2022-01-04

This series contains updates to i40e and iavf drivers.

Mateusz adjusts displaying of failed VF MAC message when the failure is
expected as well as modifying an NVM info message to not confuse the user
for i40e.

Di Zhu fixes a use-after-free issue MAC filters for i40e.

Jedrzej fixes an issue with misreporting of Rx and Tx queues during
reinitialization for i40e.

Karen correct checking of channel queue configuration to occur against
active queues for iavf.
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents 1d5a4742 b712941c
...@@ -99,6 +99,24 @@ MODULE_LICENSE("GPL v2"); ...@@ -99,6 +99,24 @@ MODULE_LICENSE("GPL v2");
static struct workqueue_struct *i40e_wq; static struct workqueue_struct *i40e_wq;
static void netdev_hw_addr_refcnt(struct i40e_mac_filter *f,
struct net_device *netdev, int delta)
{
struct netdev_hw_addr *ha;
if (!f || !netdev)
return;
netdev_for_each_mc_addr(ha, netdev) {
if (ether_addr_equal(ha->addr, f->macaddr)) {
ha->refcount += delta;
if (ha->refcount <= 0)
ha->refcount = 1;
break;
}
}
}
/** /**
* i40e_allocate_dma_mem_d - OS specific memory alloc for shared code * i40e_allocate_dma_mem_d - OS specific memory alloc for shared code
* @hw: pointer to the HW structure * @hw: pointer to the HW structure
...@@ -2036,6 +2054,7 @@ static void i40e_undo_add_filter_entries(struct i40e_vsi *vsi, ...@@ -2036,6 +2054,7 @@ static void i40e_undo_add_filter_entries(struct i40e_vsi *vsi,
hlist_for_each_entry_safe(new, h, from, hlist) { hlist_for_each_entry_safe(new, h, from, hlist) {
/* We can simply free the wrapper structure */ /* We can simply free the wrapper structure */
hlist_del(&new->hlist); hlist_del(&new->hlist);
netdev_hw_addr_refcnt(new->f, vsi->netdev, -1);
kfree(new); kfree(new);
} }
} }
...@@ -2383,6 +2402,10 @@ int i40e_sync_vsi_filters(struct i40e_vsi *vsi) ...@@ -2383,6 +2402,10 @@ int i40e_sync_vsi_filters(struct i40e_vsi *vsi)
&tmp_add_list, &tmp_add_list,
&tmp_del_list, &tmp_del_list,
vlan_filters); vlan_filters);
hlist_for_each_entry(new, &tmp_add_list, hlist)
netdev_hw_addr_refcnt(new->f, vsi->netdev, 1);
if (retval) if (retval)
goto err_no_memory_locked; goto err_no_memory_locked;
...@@ -2515,6 +2538,7 @@ int i40e_sync_vsi_filters(struct i40e_vsi *vsi) ...@@ -2515,6 +2538,7 @@ int i40e_sync_vsi_filters(struct i40e_vsi *vsi)
if (new->f->state == I40E_FILTER_NEW) if (new->f->state == I40E_FILTER_NEW)
new->f->state = new->state; new->f->state = new->state;
hlist_del(&new->hlist); hlist_del(&new->hlist);
netdev_hw_addr_refcnt(new->f, vsi->netdev, -1);
kfree(new); kfree(new);
} }
spin_unlock_bh(&vsi->mac_filter_hash_lock); spin_unlock_bh(&vsi->mac_filter_hash_lock);
...@@ -8716,6 +8740,27 @@ int i40e_open(struct net_device *netdev) ...@@ -8716,6 +8740,27 @@ int i40e_open(struct net_device *netdev)
return 0; return 0;
} }
/**
* i40e_netif_set_realnum_tx_rx_queues - Update number of tx/rx queues
* @vsi: vsi structure
*
* This updates netdev's number of tx/rx queues
*
* Returns status of setting tx/rx queues
**/
static int i40e_netif_set_realnum_tx_rx_queues(struct i40e_vsi *vsi)
{
int ret;
ret = netif_set_real_num_rx_queues(vsi->netdev,
vsi->num_queue_pairs);
if (ret)
return ret;
return netif_set_real_num_tx_queues(vsi->netdev,
vsi->num_queue_pairs);
}
/** /**
* i40e_vsi_open - * i40e_vsi_open -
* @vsi: the VSI to open * @vsi: the VSI to open
...@@ -8752,13 +8797,7 @@ int i40e_vsi_open(struct i40e_vsi *vsi) ...@@ -8752,13 +8797,7 @@ int i40e_vsi_open(struct i40e_vsi *vsi)
goto err_setup_rx; goto err_setup_rx;
/* Notify the stack of the actual queue counts. */ /* Notify the stack of the actual queue counts. */
err = netif_set_real_num_tx_queues(vsi->netdev, err = i40e_netif_set_realnum_tx_rx_queues(vsi);
vsi->num_queue_pairs);
if (err)
goto err_set_queues;
err = netif_set_real_num_rx_queues(vsi->netdev,
vsi->num_queue_pairs);
if (err) if (err)
goto err_set_queues; goto err_set_queues;
...@@ -14149,6 +14188,9 @@ struct i40e_vsi *i40e_vsi_setup(struct i40e_pf *pf, u8 type, ...@@ -14149,6 +14188,9 @@ struct i40e_vsi *i40e_vsi_setup(struct i40e_pf *pf, u8 type,
case I40E_VSI_MAIN: case I40E_VSI_MAIN:
case I40E_VSI_VMDQ2: case I40E_VSI_VMDQ2:
ret = i40e_config_netdev(vsi); ret = i40e_config_netdev(vsi);
if (ret)
goto err_netdev;
ret = i40e_netif_set_realnum_tx_rx_queues(vsi);
if (ret) if (ret)
goto err_netdev; goto err_netdev;
ret = register_netdev(vsi->netdev); ret = register_netdev(vsi->netdev);
...@@ -15451,8 +15493,8 @@ static int i40e_probe(struct pci_dev *pdev, const struct pci_device_id *ent) ...@@ -15451,8 +15493,8 @@ static int i40e_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
if (hw->aq.api_maj_ver == I40E_FW_API_VERSION_MAJOR && if (hw->aq.api_maj_ver == I40E_FW_API_VERSION_MAJOR &&
hw->aq.api_min_ver > I40E_FW_MINOR_VERSION(hw)) hw->aq.api_min_ver > I40E_FW_MINOR_VERSION(hw))
dev_info(&pdev->dev, dev_dbg(&pdev->dev,
"The driver for the device detected a newer version of the NVM image v%u.%u than expected v%u.%u. Please install the most recent version of the network driver.\n", "The driver for the device detected a newer version of the NVM image v%u.%u than v%u.%u.\n",
hw->aq.api_maj_ver, hw->aq.api_maj_ver,
hw->aq.api_min_ver, hw->aq.api_min_ver,
I40E_FW_API_VERSION_MAJOR, I40E_FW_API_VERSION_MAJOR,
......
...@@ -1877,17 +1877,19 @@ int i40e_pci_sriov_configure(struct pci_dev *pdev, int num_vfs) ...@@ -1877,17 +1877,19 @@ int i40e_pci_sriov_configure(struct pci_dev *pdev, int num_vfs)
/***********************virtual channel routines******************/ /***********************virtual channel routines******************/
/** /**
* i40e_vc_send_msg_to_vf * i40e_vc_send_msg_to_vf_ex
* @vf: pointer to the VF info * @vf: pointer to the VF info
* @v_opcode: virtual channel opcode * @v_opcode: virtual channel opcode
* @v_retval: virtual channel return value * @v_retval: virtual channel return value
* @msg: pointer to the msg buffer * @msg: pointer to the msg buffer
* @msglen: msg length * @msglen: msg length
* @is_quiet: true for not printing unsuccessful return values, false otherwise
* *
* send msg to VF * send msg to VF
**/ **/
static int i40e_vc_send_msg_to_vf(struct i40e_vf *vf, u32 v_opcode, static int i40e_vc_send_msg_to_vf_ex(struct i40e_vf *vf, u32 v_opcode,
u32 v_retval, u8 *msg, u16 msglen) u32 v_retval, u8 *msg, u16 msglen,
bool is_quiet)
{ {
struct i40e_pf *pf; struct i40e_pf *pf;
struct i40e_hw *hw; struct i40e_hw *hw;
...@@ -1903,7 +1905,7 @@ static int i40e_vc_send_msg_to_vf(struct i40e_vf *vf, u32 v_opcode, ...@@ -1903,7 +1905,7 @@ static int i40e_vc_send_msg_to_vf(struct i40e_vf *vf, u32 v_opcode,
abs_vf_id = vf->vf_id + hw->func_caps.vf_base_id; abs_vf_id = vf->vf_id + hw->func_caps.vf_base_id;
/* single place to detect unsuccessful return values */ /* single place to detect unsuccessful return values */
if (v_retval) { if (v_retval && !is_quiet) {
vf->num_invalid_msgs++; vf->num_invalid_msgs++;
dev_info(&pf->pdev->dev, "VF %d failed opcode %d, retval: %d\n", dev_info(&pf->pdev->dev, "VF %d failed opcode %d, retval: %d\n",
vf->vf_id, v_opcode, v_retval); vf->vf_id, v_opcode, v_retval);
...@@ -1933,6 +1935,23 @@ static int i40e_vc_send_msg_to_vf(struct i40e_vf *vf, u32 v_opcode, ...@@ -1933,6 +1935,23 @@ static int i40e_vc_send_msg_to_vf(struct i40e_vf *vf, u32 v_opcode,
return 0; return 0;
} }
/**
* i40e_vc_send_msg_to_vf
* @vf: pointer to the VF info
* @v_opcode: virtual channel opcode
* @v_retval: virtual channel return value
* @msg: pointer to the msg buffer
* @msglen: msg length
*
* send msg to VF
**/
static int i40e_vc_send_msg_to_vf(struct i40e_vf *vf, u32 v_opcode,
u32 v_retval, u8 *msg, u16 msglen)
{
return i40e_vc_send_msg_to_vf_ex(vf, v_opcode, v_retval,
msg, msglen, false);
}
/** /**
* i40e_vc_send_resp_to_vf * i40e_vc_send_resp_to_vf
* @vf: pointer to the VF info * @vf: pointer to the VF info
...@@ -2695,6 +2714,7 @@ static int i40e_vc_get_stats_msg(struct i40e_vf *vf, u8 *msg) ...@@ -2695,6 +2714,7 @@ static int i40e_vc_get_stats_msg(struct i40e_vf *vf, u8 *msg)
* i40e_check_vf_permission * i40e_check_vf_permission
* @vf: pointer to the VF info * @vf: pointer to the VF info
* @al: MAC address list from virtchnl * @al: MAC address list from virtchnl
* @is_quiet: set true for printing msg without opcode info, false otherwise
* *
* Check that the given list of MAC addresses is allowed. Will return -EPERM * Check that the given list of MAC addresses is allowed. Will return -EPERM
* if any address in the list is not valid. Checks the following conditions: * if any address in the list is not valid. Checks the following conditions:
...@@ -2709,13 +2729,15 @@ static int i40e_vc_get_stats_msg(struct i40e_vf *vf, u8 *msg) ...@@ -2709,13 +2729,15 @@ static int i40e_vc_get_stats_msg(struct i40e_vf *vf, u8 *msg)
* addresses might not be accurate. * addresses might not be accurate.
**/ **/
static inline int i40e_check_vf_permission(struct i40e_vf *vf, static inline int i40e_check_vf_permission(struct i40e_vf *vf,
struct virtchnl_ether_addr_list *al) struct virtchnl_ether_addr_list *al,
bool *is_quiet)
{ {
struct i40e_pf *pf = vf->pf; struct i40e_pf *pf = vf->pf;
struct i40e_vsi *vsi = pf->vsi[vf->lan_vsi_idx]; struct i40e_vsi *vsi = pf->vsi[vf->lan_vsi_idx];
int mac2add_cnt = 0; int mac2add_cnt = 0;
int i; int i;
*is_quiet = false;
for (i = 0; i < al->num_elements; i++) { for (i = 0; i < al->num_elements; i++) {
struct i40e_mac_filter *f; struct i40e_mac_filter *f;
u8 *addr = al->list[i].addr; u8 *addr = al->list[i].addr;
...@@ -2739,6 +2761,7 @@ static inline int i40e_check_vf_permission(struct i40e_vf *vf, ...@@ -2739,6 +2761,7 @@ static inline int i40e_check_vf_permission(struct i40e_vf *vf,
!ether_addr_equal(addr, vf->default_lan_addr.addr)) { !ether_addr_equal(addr, vf->default_lan_addr.addr)) {
dev_err(&pf->pdev->dev, dev_err(&pf->pdev->dev,
"VF attempting to override administratively set MAC address, bring down and up the VF interface to resume normal operation\n"); "VF attempting to override administratively set MAC address, bring down and up the VF interface to resume normal operation\n");
*is_quiet = true;
return -EPERM; return -EPERM;
} }
...@@ -2775,6 +2798,7 @@ static int i40e_vc_add_mac_addr_msg(struct i40e_vf *vf, u8 *msg) ...@@ -2775,6 +2798,7 @@ static int i40e_vc_add_mac_addr_msg(struct i40e_vf *vf, u8 *msg)
(struct virtchnl_ether_addr_list *)msg; (struct virtchnl_ether_addr_list *)msg;
struct i40e_pf *pf = vf->pf; struct i40e_pf *pf = vf->pf;
struct i40e_vsi *vsi = NULL; struct i40e_vsi *vsi = NULL;
bool is_quiet = false;
i40e_status ret = 0; i40e_status ret = 0;
int i; int i;
...@@ -2791,7 +2815,7 @@ static int i40e_vc_add_mac_addr_msg(struct i40e_vf *vf, u8 *msg) ...@@ -2791,7 +2815,7 @@ static int i40e_vc_add_mac_addr_msg(struct i40e_vf *vf, u8 *msg)
*/ */
spin_lock_bh(&vsi->mac_filter_hash_lock); spin_lock_bh(&vsi->mac_filter_hash_lock);
ret = i40e_check_vf_permission(vf, al); ret = i40e_check_vf_permission(vf, al, &is_quiet);
if (ret) { if (ret) {
spin_unlock_bh(&vsi->mac_filter_hash_lock); spin_unlock_bh(&vsi->mac_filter_hash_lock);
goto error_param; goto error_param;
...@@ -2829,8 +2853,8 @@ static int i40e_vc_add_mac_addr_msg(struct i40e_vf *vf, u8 *msg) ...@@ -2829,8 +2853,8 @@ static int i40e_vc_add_mac_addr_msg(struct i40e_vf *vf, u8 *msg)
error_param: error_param:
/* send the response to the VF */ /* send the response to the VF */
return i40e_vc_send_resp_to_vf(vf, VIRTCHNL_OP_ADD_ETH_ADDR, return i40e_vc_send_msg_to_vf_ex(vf, VIRTCHNL_OP_ADD_ETH_ADDR,
ret); ret, NULL, 0, is_quiet);
} }
/** /**
......
...@@ -2708,8 +2708,11 @@ static int iavf_validate_ch_config(struct iavf_adapter *adapter, ...@@ -2708,8 +2708,11 @@ static int iavf_validate_ch_config(struct iavf_adapter *adapter,
total_max_rate += tx_rate; total_max_rate += tx_rate;
num_qps += mqprio_qopt->qopt.count[i]; num_qps += mqprio_qopt->qopt.count[i];
} }
if (num_qps > IAVF_MAX_REQ_QUEUES) if (num_qps > adapter->num_active_queues) {
dev_err(&adapter->pdev->dev,
"Cannot support requested number of queues\n");
return -EINVAL; return -EINVAL;
}
ret = iavf_validate_tx_bandwidth(adapter, total_max_rate); ret = iavf_validate_tx_bandwidth(adapter, total_max_rate);
return ret; return ret;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment