ixgbevf: Add range checking for setting MTU
Currently when setting the VF's MTU, the PF can return a NACK but this isn't passed on to the VF. Propagate the results from the PF to the VF so errors can be reported. In ixgbevf_change_mtu, return an error and reject the change. For ixgbevf_configure_rx, log the error for debugging purposes since the function is buried in a series of Rx config routines that are void. Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com> Signed-off-by: Emil Tantilov <emil.s.tantilov@intel.com> Tested-by: Andrew Bowers <andrewx.bowers@intel.com> Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
This commit is contained in:
parent
6e469ed03e
commit
6a11e52b69
|
@ -1802,16 +1802,19 @@ static void ixgbevf_configure_rx_ring(struct ixgbevf_adapter *adapter,
|
|||
**/
|
||||
static void ixgbevf_configure_rx(struct ixgbevf_adapter *adapter)
|
||||
{
|
||||
int i;
|
||||
struct ixgbe_hw *hw = &adapter->hw;
|
||||
struct net_device *netdev = adapter->netdev;
|
||||
int i, ret;
|
||||
|
||||
ixgbevf_setup_psrtype(adapter);
|
||||
if (hw->mac.type >= ixgbe_mac_X550_vf)
|
||||
ixgbevf_setup_vfmrqc(adapter);
|
||||
|
||||
/* notify the PF of our intent to use this size of frame */
|
||||
hw->mac.ops.set_rlpml(hw, netdev->mtu + ETH_HLEN + ETH_FCS_LEN);
|
||||
ret = hw->mac.ops.set_rlpml(hw, netdev->mtu + ETH_HLEN + ETH_FCS_LEN);
|
||||
if (ret)
|
||||
dev_err(&adapter->pdev->dev,
|
||||
"Failed to set MTU at %d\n", netdev->mtu);
|
||||
|
||||
/* Setup the HW Rx Head and Tail Descriptor Pointers and
|
||||
* the Base and Length of the Rx Descriptor Ring
|
||||
|
@ -3737,6 +3740,7 @@ static int ixgbevf_change_mtu(struct net_device *netdev, int new_mtu)
|
|||
struct ixgbe_hw *hw = &adapter->hw;
|
||||
int max_frame = new_mtu + ETH_HLEN + ETH_FCS_LEN;
|
||||
int max_possible_frame = MAXIMUM_ETHERNET_VLAN_SIZE;
|
||||
int ret;
|
||||
|
||||
switch (adapter->hw.api_version) {
|
||||
case ixgbe_mbox_api_11:
|
||||
|
@ -3753,14 +3757,17 @@ static int ixgbevf_change_mtu(struct net_device *netdev, int new_mtu)
|
|||
if ((new_mtu < 68) || (max_frame > max_possible_frame))
|
||||
return -EINVAL;
|
||||
|
||||
/* notify the PF of our intent to use this size of frame */
|
||||
ret = hw->mac.ops.set_rlpml(hw, max_frame);
|
||||
if (ret)
|
||||
return -EINVAL;
|
||||
|
||||
hw_dbg(hw, "changing MTU from %d to %d\n",
|
||||
netdev->mtu, new_mtu);
|
||||
|
||||
/* must set new MTU before calling down or up */
|
||||
netdev->mtu = new_mtu;
|
||||
|
||||
/* notify the PF of our intent to use this size of frame */
|
||||
hw->mac.ops.set_rlpml(hw, max_frame);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -33,6 +33,18 @@
|
|||
*/
|
||||
#define IXGBE_HV_RESET_OFFSET 0x201
|
||||
|
||||
static inline s32 ixgbevf_write_msg_read_ack(struct ixgbe_hw *hw, u32 *msg,
|
||||
u32 *retmsg, u16 size)
|
||||
{
|
||||
struct ixgbe_mbx_info *mbx = &hw->mbx;
|
||||
s32 retval = mbx->ops.write_posted(hw, msg, size);
|
||||
|
||||
if (retval)
|
||||
return retval;
|
||||
|
||||
return mbx->ops.read_posted(hw, retmsg, size);
|
||||
}
|
||||
|
||||
/**
|
||||
* ixgbevf_start_hw_vf - Prepare hardware for Tx/Rx
|
||||
* @hw: pointer to hardware structure
|
||||
|
@ -470,17 +482,6 @@ static s32 ixgbevf_hv_set_rar_vf(struct ixgbe_hw *hw, u32 index, u8 *addr,
|
|||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
static void ixgbevf_write_msg_read_ack(struct ixgbe_hw *hw,
|
||||
u32 *msg, u16 size)
|
||||
{
|
||||
struct ixgbe_mbx_info *mbx = &hw->mbx;
|
||||
u32 retmsg[IXGBE_VFMAILBOX_SIZE];
|
||||
s32 retval = mbx->ops.write_posted(hw, msg, size);
|
||||
|
||||
if (!retval)
|
||||
mbx->ops.read_posted(hw, retmsg, size);
|
||||
}
|
||||
|
||||
/**
|
||||
* ixgbevf_update_mc_addr_list_vf - Update Multicast addresses
|
||||
* @hw: pointer to the HW structure
|
||||
|
@ -521,7 +522,7 @@ static s32 ixgbevf_update_mc_addr_list_vf(struct ixgbe_hw *hw,
|
|||
vector_list[i++] = ixgbevf_mta_vector(hw, ha->addr);
|
||||
}
|
||||
|
||||
ixgbevf_write_msg_read_ack(hw, msgbuf, IXGBE_VFMAILBOX_SIZE);
|
||||
ixgbevf_write_msg_read_ack(hw, msgbuf, msgbuf, IXGBE_VFMAILBOX_SIZE);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -799,13 +800,22 @@ out:
|
|||
* @hw: pointer to the HW structure
|
||||
* @max_size: value to assign to max frame size
|
||||
**/
|
||||
static void ixgbevf_set_rlpml_vf(struct ixgbe_hw *hw, u16 max_size)
|
||||
static s32 ixgbevf_set_rlpml_vf(struct ixgbe_hw *hw, u16 max_size)
|
||||
{
|
||||
u32 msgbuf[2];
|
||||
s32 ret_val;
|
||||
|
||||
msgbuf[0] = IXGBE_VF_SET_LPE;
|
||||
msgbuf[1] = max_size;
|
||||
ixgbevf_write_msg_read_ack(hw, msgbuf, 2);
|
||||
|
||||
ret_val = ixgbevf_write_msg_read_ack(hw, msgbuf, msgbuf, 2);
|
||||
if (ret_val)
|
||||
return ret_val;
|
||||
if ((msgbuf[0] & IXGBE_VF_SET_LPE) &&
|
||||
(msgbuf[0] & IXGBE_VT_MSGTYPE_NACK))
|
||||
return IXGBE_ERR_MBX;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -814,7 +824,7 @@ static void ixgbevf_set_rlpml_vf(struct ixgbe_hw *hw, u16 max_size)
|
|||
* @max_size: value to assign to max frame size
|
||||
* Hyper-V variant.
|
||||
**/
|
||||
static void ixgbevf_hv_set_rlpml_vf(struct ixgbe_hw *hw, u16 max_size)
|
||||
static s32 ixgbevf_hv_set_rlpml_vf(struct ixgbe_hw *hw, u16 max_size)
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
|
@ -825,6 +835,8 @@ static void ixgbevf_hv_set_rlpml_vf(struct ixgbe_hw *hw, u16 max_size)
|
|||
/* CRC == 4 */
|
||||
reg |= ((max_size + 4) | IXGBE_RXDCTL_RLPML_EN);
|
||||
IXGBE_WRITE_REG(hw, IXGBE_VFRXDCTL(0), reg);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -69,7 +69,7 @@ struct ixgbe_mac_operations {
|
|||
s32 (*disable_mc)(struct ixgbe_hw *);
|
||||
s32 (*clear_vfta)(struct ixgbe_hw *);
|
||||
s32 (*set_vfta)(struct ixgbe_hw *, u32, u32, bool);
|
||||
void (*set_rlpml)(struct ixgbe_hw *, u16);
|
||||
s32 (*set_rlpml)(struct ixgbe_hw *, u16);
|
||||
};
|
||||
|
||||
enum ixgbe_mac_type {
|
||||
|
|
Loading…
Reference in New Issue