if (adapter->xdp_prog) {
e_warn(probe, "SRIOV is not supported with XDP\n"); return -EINVAL;
}
/* Enable VMDq flag so device will be set in VM mode */
adapter->flags |= IXGBE_FLAG_SRIOV_ENABLED |
IXGBE_FLAG_VMDQ_ENABLED;
/* Allocate memory for per VF control structures */
adapter->vfinfo = kcalloc(num_vfs, sizeof(struct vf_data_storage),
GFP_KERNEL); if (!adapter->vfinfo) return -ENOMEM;
/* Disable RSC when in SR-IOV mode */
adapter->flags2 &= ~(IXGBE_FLAG2_RSC_CAPABLE |
IXGBE_FLAG2_RSC_ENABLED);
for (i = 0; i < num_vfs; i++) { /* enable spoof checking for all VFs */
adapter->vfinfo[i].spoofchk_enabled = true;
adapter->vfinfo[i].link_enable = true;
/* We support VF RSS querying only for 82599 and x540 * devices at the moment. These devices share RSS * indirection table and RSS hash key with PF therefore * we want to disable the querying by default.
*/
adapter->vfinfo[i].rss_query_enabled = false;
/* Untrust all VFs */
adapter->vfinfo[i].trusted = false;
/* set the default xcast mode */
adapter->vfinfo[i].xcast_mode = IXGBEVF_XCAST_MODE_NONE;
}
e_info(probe, "SR-IOV enabled with %d VFs\n", num_vfs); return 0;
}
/** * ixgbe_get_vfs - Find and take references to all vf devices * @adapter: Pointer to adapter struct
*/ staticvoid ixgbe_get_vfs(struct ixgbe_adapter *adapter)
{ struct pci_dev *pdev = adapter->pdev;
u16 vendor = pdev->vendor; struct pci_dev *vfdev; int vf = 0;
u16 vf_id; int pos;
vfdev = pci_get_device(vendor, vf_id, NULL); for (; vfdev; vfdev = pci_get_device(vendor, vf_id, vfdev)) { if (!vfdev->is_virtfn) continue; if (vfdev->physfn != pdev) continue; if (vf >= adapter->num_vfs) continue;
pci_dev_get(vfdev);
adapter->vfinfo[vf].vfdev = vfdev;
++vf;
}
}
/* Note this function is called when the user wants to enable SR-IOV * VFs using the now deprecated module parameter
*/ void ixgbe_enable_sriov(struct ixgbe_adapter *adapter, unsignedint max_vfs)
{ int pre_existing_vfs = 0; unsignedint num_vfs;
pre_existing_vfs = pci_num_vf(adapter->pdev); if (!pre_existing_vfs && !max_vfs) return;
/* If there are pre-existing VFs then we have to force * use of that many - over ride any module parameter value. * This may result from the user unloading the PF driver * while VFs were assigned to guest VMs or because the VFs * have been created via the new PCI SR-IOV sysfs interface.
*/ if (pre_existing_vfs) {
num_vfs = pre_existing_vfs;
dev_warn(&adapter->pdev->dev, "Virtual Functions already enabled for this device - Please reload all VF drivers to avoid spoofed packet errors\n");
} else { int err; /* * The 82599 supports up to 64 VFs per physical function * but this implementation limits allocation to 63 so that * basic networking resources are still available to the * physical function. If the user requests greater than * 63 VFs then it is an error - reset to default of zero.
*/
num_vfs = min_t(unsignedint, max_vfs, IXGBE_MAX_VFS_DRV_LIMIT);
err = pci_enable_sriov(adapter->pdev, num_vfs); if (err) {
e_err(probe, "Failed to enable PCI sriov: %d\n", err); return;
}
}
if (!__ixgbe_enable_sriov(adapter, num_vfs)) {
ixgbe_get_vfs(adapter); return;
}
/* If we have gotten to this point then there is no memory available * to manage the VF devices - print message and bail.
*/
e_err(probe, "Unable to allocate memory for VF Data Storage - " "SRIOV disabled\n");
ixgbe_disable_sriov(adapter);
}
spin_lock_irqsave(&adapter->vfs_lock, flags); /* set num VFs to 0 to prevent access to vfinfo */
adapter->num_vfs = 0;
spin_unlock_irqrestore(&adapter->vfs_lock, flags);
/* put the reference to all of the vf devices */ for (vf = 0; vf < num_vfs; ++vf) { struct pci_dev *vfdev = adapter->vfinfo[vf].vfdev;
if (!vfdev) continue;
adapter->vfinfo[vf].vfdev = NULL;
pci_dev_put(vfdev);
}
/* free VF control structures */
kfree(adapter->vfinfo);
adapter->vfinfo = NULL;
/* free macvlan list */
kfree(adapter->mv_list);
adapter->mv_list = NULL;
/* if SR-IOV is already disabled then there is nothing to do */ if (!(adapter->flags & IXGBE_FLAG_SRIOV_ENABLED)) return 0;
if (hw->mac.ops.disable_mdd)
hw->mac.ops.disable_mdd(hw);
#ifdef CONFIG_PCI_IOV /* * If our VFs are assigned we cannot shut down SR-IOV * without causing issues, so just leave the hardware * available but disabled
*/ if (pci_vfs_assigned(adapter->pdev)) {
e_dev_warn("Unloading driver while VFs are assigned - VFs will not be deallocated\n"); return -EPERM;
} /* disable iov and allow time for transactions to clear */
pci_disable_sriov(adapter->pdev); #endif
/* Disable VMDq flag so device will be set in VM mode */ if (bitmap_weight(adapter->fwd_bitmask, adapter->num_rx_pools) == 1) {
adapter->flags &= ~IXGBE_FLAG_VMDQ_ENABLED;
adapter->flags &= ~IXGBE_FLAG_SRIOV_ENABLED;
rss = min_t(int, ixgbe_max_rss_indices(adapter),
num_online_cpus());
} else {
rss = min_t(int, IXGBE_MAX_L2A_QUEUES, num_online_cpus());
}
/* While the SR-IOV capability structure reports total VFs to be 64, * we limit the actual number allocated as below based on two factors. * Num_TCs MAX_VFs * 1 63 * <=4 31 * >4 15 * First, we reserve some transmit/receive resources for the PF. * Second, VMDQ also uses the same pools that SR-IOV does. We need to * account for this, so that we don't accidentally allocate more VFs * than we have available pools. The PCI bus driver already checks for * other values out of range.
*/
num_tc = adapter->hw_tcs;
num_rx_pools = bitmap_weight(adapter->fwd_bitmask,
adapter->num_rx_pools);
limit = (num_tc > 4) ? IXGBE_MAX_VFS_8TC :
(num_tc > 1) ? IXGBE_MAX_VFS_4TC : IXGBE_MAX_VFS_1TC;
if (num_vfs > (limit - num_rx_pools)) {
e_dev_err("Currently configured with %d TCs, and %d offloaded macvlans. Creating more than %d VFs is not allowed\n",
num_tc, num_rx_pools - 1, limit - num_rx_pools); return -EPERM;
}
err = __ixgbe_enable_sriov(adapter, num_vfs); if (err) return err;
for (i = 0; i < num_vfs; i++)
ixgbe_vf_configuration(dev, (i | 0x10000000));
/* reset before enabling SRIOV to avoid mailbox issues */
ixgbe_sriov_reinit(adapter);
err = pci_enable_sriov(dev, num_vfs); if (err) {
e_dev_warn("Failed to enable PCI sriov: %d\n", err); return err;
}
ixgbe_get_vfs(adapter);
/* Only reinit if no error and state changed */ #ifdef CONFIG_PCI_IOV if (!err && (current_flags != adapter->flags ||
prev_num_vf != pci_num_vf(dev)))
ixgbe_sriov_reinit(adapter); #endif
return err;
}
int ixgbe_pci_sriov_configure(struct pci_dev *dev, int num_vfs)
{ if (num_vfs == 0) return ixgbe_pci_sriov_disable(dev); else return ixgbe_pci_sriov_enable(dev, num_vfs);
}
/* only so many hash values supported */
entries = min(entries, IXGBE_MAX_VF_MC_ENTRIES);
/* * salt away the number of multi cast addresses assigned * to this VF for later use to restore when the PF multi cast * list changes
*/
vfinfo->num_vf_mc_hashes = entries;
/* * VFs are limited to using the MTA hash table for their multicast * addresses
*/ for (i = 0; i < entries; i++) {
vfinfo->vf_mc_hashes[i] = hash_list[i];
}
/* Restore any VF macvlans */
ixgbe_full_sync_mac_table(adapter);
} #endif
staticint ixgbe_set_vf_vlan(struct ixgbe_adapter *adapter, int add, int vid,
u32 vf)
{ struct ixgbe_hw *hw = &adapter->hw; int err;
/* If VLAN overlaps with one the PF is currently monitoring make * sure that we are able to allocate a VLVF entry. This may be * redundant but it guarantees PF will maintain visibility to * the VLAN.
*/ if (add && test_bit(vid, adapter->active_vlans)) {
err = hw->mac.ops.set_vfta(hw, vid, VMDQ_P(0), true, false); if (err) return err;
}
/* If we failed to add the VF VLAN or we are removing the VF VLAN * we may need to drop the PF pool bit in order to allow us to free * up the VLVF resources.
*/ if (test_bit(vid, adapter->active_vlans) ||
(adapter->flags2 & IXGBE_FLAG2_VLAN_PROMISC))
ixgbe_update_pf_promisc_vlvf(adapter, vid);
if (max_frame < ETH_MIN_MTU || max_frame > IXGBE_MAX_JUMBO_FRAME_SIZE) {
e_err(drv, "VF max_frame %d out of range\n", max_frame); return -EINVAL;
}
/* * For 82599EB we have to keep all PFs and VFs operating with * the same max_frame value in order to avoid sending an oversize * frame to a VF. In order to guarantee this is handled correctly * for all cases we have several special exceptions to take into * account before we can enable the VF for receive
*/ if (adapter->hw.mac.type == ixgbe_mac_82599EB) { struct net_device *dev = adapter->netdev; int pf_max_frame = dev->mtu + ETH_HLEN;
u32 reg_offset, vf_shift, vfre; int err = 0;
#ifdef CONFIG_FCOE if (dev->fcoe_mtu)
pf_max_frame = max_t(int, pf_max_frame,
IXGBE_FCOE_JUMBO_FRAME_SIZE);
#endif/* CONFIG_FCOE */ switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_11: case ixgbe_mbox_api_12: case ixgbe_mbox_api_13: case ixgbe_mbox_api_14: case ixgbe_mbox_api_16: case ixgbe_mbox_api_17: /* Version 1.1 supports jumbo frames on VFs if PF has * jumbo frames enabled which means legacy VFs are * disabled
*/ if (pf_max_frame > ETH_FRAME_LEN) break;
fallthrough; default: /* If the PF or VF are running w/ jumbo frames enabled * we need to shut down the VF Rx path as we cannot * support jumbo frames on legacy VFs
*/ if ((pf_max_frame > ETH_FRAME_LEN) ||
(max_frame > (ETH_FRAME_LEN + ETH_FCS_LEN)))
err = -EINVAL; break;
}
/* * If index was zero then we were asked to clear the uc list * for the VF. We're done.
*/ if (!index) return 0;
list_for_each_entry(entry, &adapter->vf_mvs.l, l) { if (entry->free) {
found = true; break;
}
}
/* * If we traversed the entire list and didn't find a free entry * then we're out of space on the RAR table. It's also possible * for the &adapter->vf_mvs.l list to be empty because the original * memory allocation for the list failed, which is not fatal but does * mean we can't support VF requests for MACVLAN because we couldn't * allocate memory for the list management required.
*/ if (!found) return -ENOSPC;
for (i = vf * q_per_pool; i < ((vf + 1) * q_per_pool); i++) {
u32 reg;
/* flush previous write */
IXGBE_WRITE_FLUSH(hw);
/* indicate to hardware that we want to set drop enable */
reg = IXGBE_QDE_WRITE | qde;
reg |= i << IXGBE_QDE_IDX_SHIFT;
IXGBE_WRITE_REG(hw, IXGBE_QDE, reg);
}
}
/** * ixgbe_set_vf_rx_tx - Set VF rx tx * @adapter: Pointer to adapter struct * @vf: VF identifier * * Set or reset correct transmit and receive for vf
**/ staticvoid ixgbe_set_vf_rx_tx(struct ixgbe_adapter *adapter, int vf)
{
u32 reg_cur_tx, reg_cur_rx, reg_req_tx, reg_req_rx; struct ixgbe_hw *hw = &adapter->hw;
u32 reg_offset, vf_shift;
/* The 82599 cannot support a mix of jumbo and non-jumbo PF/VFs. * For more info take a look at ixgbe_set_vf_lpe
*/ if (adapter->hw.mac.type == ixgbe_mac_82599EB) { struct net_device *dev = adapter->netdev; int pf_max_frame = dev->mtu + ETH_HLEN;
e_info(probe, "VF Reset msg received from vf %d\n", vf);
/* reset the filters for the device */
ixgbe_vf_reset_event(adapter, vf);
ixgbe_vf_clear_mbx(adapter, vf);
/* set vf mac address */ if (!is_zero_ether_addr(vf_mac))
ixgbe_set_vf_mac(adapter, vf, vf_mac);
vf_shift = vf % 32;
reg_offset = vf / 32;
/* force drop enable for all VF Rx queues */
reg = IXGBE_QDE_ENABLE; if (adapter->vfinfo[vf].pf_vlan)
reg |= IXGBE_QDE_HIDE_VLAN;
ixgbe_write_qde(adapter, vf, reg);
ixgbe_set_vf_rx_tx(adapter, vf);
/* enable VF mailbox for further messages */
adapter->vfinfo[vf].clear_to_send = true;
/* Enable counting of spoofed packets in the SSVPC register */
reg = IXGBE_READ_REG(hw, IXGBE_VMECM(reg_offset));
reg |= BIT(vf_shift);
IXGBE_WRITE_REG(hw, IXGBE_VMECM(reg_offset), reg);
/* * Reset the VFs TDWBAL and TDWBAH registers * which are not cleared by an FLR
*/ for (i = 0; i < q_per_pool; i++) {
IXGBE_WRITE_REG(hw, IXGBE_PVFTDWBAHn(q_per_pool, vf, i), 0);
IXGBE_WRITE_REG(hw, IXGBE_PVFTDWBALn(q_per_pool, vf, i), 0);
}
/* reply to reset with ack and vf mac address */
msgbuf[0] = IXGBE_VF_RESET; if (!is_zero_ether_addr(vf_mac) && adapter->vfinfo[vf].pf_set_mac) {
msgbuf[0] |= IXGBE_VT_MSGTYPE_ACK;
memcpy(addr, vf_mac, ETH_ALEN);
} else {
msgbuf[0] |= IXGBE_VT_MSGTYPE_NACK;
}
/* * Piggyback the multicast filter type so VF can compute the * correct vectors
*/
msgbuf[3] = hw->mac.mc_filter_type;
ixgbe_write_mbx(hw, msgbuf, IXGBE_VF_PERMADDR_MSG_LEN, vf);
if (!is_valid_ether_addr(new_mac)) {
e_warn(drv, "VF %d attempted to set invalid mac\n", vf); return -1;
}
if (adapter->vfinfo[vf].pf_set_mac && !adapter->vfinfo[vf].trusted &&
!ether_addr_equal(adapter->vfinfo[vf].vf_mac_addresses, new_mac)) {
e_warn(drv, "VF %d attempted to override administratively set MAC address\n" "Reload the VF driver to resume operations\n",
vf); return -1;
}
staticint ixgbe_set_vf_macvlan_msg(struct ixgbe_adapter *adapter,
u32 *msgbuf, u32 vf)
{
u8 *new_mac = ((u8 *)(&msgbuf[1])); int index = FIELD_GET(IXGBE_VT_MSGINFO_MASK, msgbuf[0]); int err;
if (adapter->vfinfo[vf].pf_set_mac && !adapter->vfinfo[vf].trusted &&
index > 0) {
e_warn(drv, "VF %d requested MACVLAN filter but is administratively denied\n",
vf); return -1;
}
/* An non-zero index indicates the VF is setting a filter */ if (index) { if (!is_valid_ether_addr(new_mac)) {
e_warn(drv, "VF %d attempted to set invalid mac\n", vf); return -1;
}
/* * If the VF is allowed to set MAC filters then turn off * anti-spoofing to avoid false positives.
*/ if (adapter->vfinfo[vf].spoofchk_enabled) { struct ixgbe_hw *hw = &adapter->hw;
err = ixgbe_set_vf_macvlan(adapter, vf, index, new_mac); if (err == -ENOSPC)
e_warn(drv, "VF %d has requested a MACVLAN filter but there is no space for it\n",
vf);
return err < 0;
}
staticint ixgbe_negotiate_vf_api(struct ixgbe_adapter *adapter,
u32 *msgbuf, u32 vf)
{ int api = msgbuf[1];
switch (api) { case ixgbe_mbox_api_10: case ixgbe_mbox_api_11: case ixgbe_mbox_api_12: case ixgbe_mbox_api_13: case ixgbe_mbox_api_14: case ixgbe_mbox_api_16: case ixgbe_mbox_api_17:
adapter->vfinfo[vf].vf_api = api; return 0; default: break;
}
e_dbg(drv, "VF %d requested unsupported api version %u\n", vf, api);
/* verify the PF is supporting the correct APIs */ switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_20: case ixgbe_mbox_api_11: case ixgbe_mbox_api_12: case ixgbe_mbox_api_13: case ixgbe_mbox_api_14: case ixgbe_mbox_api_16: case ixgbe_mbox_api_17: break; default: return -1;
}
/* only allow 1 Tx queue for bandwidth limiting */
msgbuf[IXGBE_VF_TX_QUEUES] = __ALIGN_MASK(1, ~vmdq->mask);
msgbuf[IXGBE_VF_RX_QUEUES] = __ALIGN_MASK(1, ~vmdq->mask);
/* if TCs > 1 determine which TC belongs to default user priority */ if (num_tcs > 1)
default_tc = netdev_get_prio_tc_map(dev, adapter->default_up);
/* notify VF of need for VLAN tag stripping, and correct queue */ if (num_tcs)
msgbuf[IXGBE_VF_TRANS_VLAN] = num_tcs; elseif (adapter->vfinfo[vf].pf_vlan || adapter->vfinfo[vf].pf_qos)
msgbuf[IXGBE_VF_TRANS_VLAN] = 1; else
msgbuf[IXGBE_VF_TRANS_VLAN] = 0;
/* notify VF of default queue */
msgbuf[IXGBE_VF_DEF_QUEUE] = default_tc;
/* Check if operation is permitted */ if (!adapter->vfinfo[vf].rss_query_enabled) return -EPERM;
/* verify the PF is supporting the correct API */ switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_17: case ixgbe_mbox_api_16: case ixgbe_mbox_api_14: case ixgbe_mbox_api_13: case ixgbe_mbox_api_12: break; default: return -EOPNOTSUPP;
}
/* This mailbox command is supported (required) only for 82599 and x540 * VFs which support up to 4 RSS queues. Therefore we will compress the * RETA by saving only 2 bits from each entry. This way we will be able * to transfer the whole RETA in a single mailbox operation.
*/ for (i = 0; i < reta_size / 16; i++) {
out_buf[i] = 0; for (j = 0; j < 16; j++)
out_buf[i] |= (u32)(reta[16 * i + j] & 0x3) << (2 * j);
}
/* Check if the operation is permitted */ if (!adapter->vfinfo[vf].rss_query_enabled) return -EPERM;
/* verify the PF is supporting the correct API */ switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_17: case ixgbe_mbox_api_16: case ixgbe_mbox_api_14: case ixgbe_mbox_api_13: case ixgbe_mbox_api_12: break; default: return -EOPNOTSUPP;
}
/* verify the PF is supporting the correct APIs */ switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_12: /* promisc introduced in 1.3 version */ if (xcast_mode == IXGBEVF_XCAST_MODE_PROMISC) return -EOPNOTSUPP;
fallthrough; case ixgbe_mbox_api_13: case ixgbe_mbox_api_14: case ixgbe_mbox_api_16: case ixgbe_mbox_api_17: break; default: return -EOPNOTSUPP;
}
/* verify the PF is supporting the correct API */ switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_12: case ixgbe_mbox_api_13: case ixgbe_mbox_api_14: case ixgbe_mbox_api_16: case ixgbe_mbox_api_17: break; default: return -EOPNOTSUPP;
}
*link_state = adapter->vfinfo[vf].link_enable;
return 0;
}
/** * ixgbe_send_vf_link_status - send link status data to VF * @adapter: pointer to adapter struct * @msgbuf: pointer to message buffers * @vf: VF identifier * * Reply for IXGBE_VF_GET_PF_LINK_STATE mbox command sending link status data. * * Return: 0 on success or -EOPNOTSUPP when operation is not supported.
*/ staticint ixgbe_send_vf_link_status(struct ixgbe_adapter *adapter,
u32 *msgbuf, u32 vf)
{ struct ixgbe_hw *hw = &adapter->hw;
switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_16: case ixgbe_mbox_api_17: if (hw->mac.type != ixgbe_mac_e610) return -EOPNOTSUPP; break; default: return -EOPNOTSUPP;
} /* Simply provide stored values as watchdog & link status events take * care of its freshness.
*/
msgbuf[1] = adapter->link_speed;
msgbuf[2] = adapter->link_up;
return 0;
}
/** * ixgbe_negotiate_vf_features - negotiate supported features with VF driver * @adapter: pointer to adapter struct * @msgbuf: pointer to message buffers * @vf: VF identifier * * Return: 0 on success or -EOPNOTSUPP when operation is not supported.
*/ staticint ixgbe_negotiate_vf_features(struct ixgbe_adapter *adapter,
u32 *msgbuf, u32 vf)
{
u32 features = msgbuf[1];
switch (adapter->vfinfo[vf].vf_api) { case ixgbe_mbox_api_17: break; default: return -EOPNOTSUPP;
}
features &= IXGBE_SUPPORTED_FEATURES;
msgbuf[1] = features;
if (retval) {
pr_err("Error receiving message from VF\n"); return retval;
}
/* this is a message we already processed, do nothing */ if (msgbuf[0] & (IXGBE_VT_MSGTYPE_ACK | IXGBE_VT_MSGTYPE_NACK)) return 0;
/* flush the ack before we write any messages back */
IXGBE_WRITE_FLUSH(hw);
if (msgbuf[0] == IXGBE_VF_RESET) return ixgbe_vf_reset_msg(adapter, vf);
/* * until the vf completes a virtual function reset it should not be * allowed to start any configuration.
*/ if (!adapter->vfinfo[vf].clear_to_send) {
msgbuf[0] |= IXGBE_VT_MSGTYPE_NACK;
ixgbe_write_mbx(hw, msgbuf, 1, vf); return 0;
}
switch ((msgbuf[0] & 0xFFFF)) { case IXGBE_VF_SET_MAC_ADDR:
retval = ixgbe_set_vf_mac_addr(adapter, msgbuf, vf); break; case IXGBE_VF_SET_MULTICAST:
retval = ixgbe_set_vf_multicasts(adapter, msgbuf, vf); break; case IXGBE_VF_SET_VLAN:
retval = ixgbe_set_vf_vlan_msg(adapter, msgbuf, vf); break; case IXGBE_VF_SET_LPE:
retval = ixgbe_set_vf_lpe(adapter, msgbuf[1], vf); break; case IXGBE_VF_SET_MACVLAN:
retval = ixgbe_set_vf_macvlan_msg(adapter, msgbuf, vf); break; case IXGBE_VF_API_NEGOTIATE:
retval = ixgbe_negotiate_vf_api(adapter, msgbuf, vf); break; case IXGBE_VF_GET_QUEUES:
retval = ixgbe_get_vf_queues(adapter, msgbuf, vf); break; case IXGBE_VF_GET_RETA:
retval = ixgbe_get_vf_reta(adapter, msgbuf, vf); break; case IXGBE_VF_GET_RSS_KEY:
retval = ixgbe_get_vf_rss_key(adapter, msgbuf, vf); break; case IXGBE_VF_UPDATE_XCAST_MODE:
retval = ixgbe_update_vf_xcast_mode(adapter, msgbuf, vf); break; case IXGBE_VF_GET_LINK_STATE:
retval = ixgbe_get_vf_link_state(adapter, msgbuf, vf); break; case IXGBE_VF_IPSEC_ADD:
retval = ixgbe_ipsec_vf_add_sa(adapter, msgbuf, vf); break; case IXGBE_VF_IPSEC_DEL:
retval = ixgbe_ipsec_vf_del_sa(adapter, msgbuf, vf); break; case IXGBE_VF_GET_PF_LINK_STATE:
retval = ixgbe_send_vf_link_status(adapter, msgbuf, vf); break; case IXGBE_VF_FEATURES_NEGOTIATE:
retval = ixgbe_negotiate_vf_features(adapter, msgbuf, vf); break; default:
e_err(drv, "Unhandled Msg %8.8x\n", msgbuf[0]);
retval = -EIO; break;
}
/* notify the VF of the results of what it sent us */ if (retval)
msgbuf[0] |= IXGBE_VT_MSGTYPE_NACK; else
msgbuf[0] |= IXGBE_VT_MSGTYPE_ACK;
/* if device isn't clear to send it shouldn't be reading either */ if (!adapter->vfinfo[vf].clear_to_send)
ixgbe_write_mbx(hw, &msg, 1, vf);
}
/** * ixgbe_check_mdd_event - check for MDD event on all VFs * @adapter: pointer to ixgbe adapter * * Return: true if there is a VF on which MDD event occurred, false otherwise.
*/ bool ixgbe_check_mdd_event(struct ixgbe_adapter *adapter)
{ struct ixgbe_hw *hw = &adapter->hw;
DECLARE_BITMAP(vf_bitmap, 64); bool ret = false; int i;
if (!hw->mac.ops.handle_mdd) returnfalse;
/* Did we have a malicious event */
bitmap_zero(vf_bitmap, 64);
hw->mac.ops.handle_mdd(hw, vf_bitmap);
/* Log any blocked queues and release lock */
for_each_set_bit(i, vf_bitmap, 64) {
dev_warn(&adapter->pdev->dev, "Malicious event on VF %d tx:%x rx:%x\n", i,
IXGBE_READ_REG(hw, IXGBE_LVMMC_TX),
IXGBE_READ_REG(hw, IXGBE_LVMMC_RX));
if (hw->mac.ops.restore_mdd_vf) {
u32 ping;
hw->mac.ops.restore_mdd_vf(hw, i);
/* get the VF to rebuild its queues */
adapter->vfinfo[i].clear_to_send = 0;
ping = IXGBE_PF_CONTROL_MSG |
IXGBE_VT_MSGTYPE_CTS;
ixgbe_write_mbx(hw, &ping, 1, i);
}
for (i = 0 ; i < adapter->num_vfs; i++) {
ping = IXGBE_PF_CONTROL_MSG; if (adapter->vfinfo[i].clear_to_send)
ping |= IXGBE_VT_MSGTYPE_CTS;
ixgbe_write_mbx(hw, &ping, 1, i);
}
}
/** * ixgbe_set_all_vfs - update vfs queues * @adapter: Pointer to adapter struct * * Update setting transmit and receive queues for all vfs
**/ void ixgbe_set_all_vfs(struct ixgbe_adapter *adapter)
{ int i;
for (i = 0 ; i < adapter->num_vfs; i++)
ixgbe_set_vf_link_state(adapter, i,
adapter->vfinfo[i].link_state);
}
int ixgbe_ndo_set_vf_mac(struct net_device *netdev, int vf, u8 *mac)
{ struct ixgbe_adapter *adapter = ixgbe_from_netdev(netdev); int retval;
if (vf >= adapter->num_vfs) return -EINVAL;
if (is_valid_ether_addr(mac)) {
dev_info(&adapter->pdev->dev, "setting MAC %pM on VF %d\n",
mac, vf);
dev_info(&adapter->pdev->dev, "Reload the VF driver to make this change effective.");
if (test_bit(__IXGBE_DOWN, &adapter->state)) {
dev_warn(&adapter->pdev->dev, "The VF MAC address has been set, but the PF device is not up.\n");
dev_warn(&adapter->pdev->dev, "Bring the PF device up before attempting to use the VF device.\n");
}
} else {
dev_warn(&adapter->pdev->dev, "The VF MAC address was NOT set due to invalid or duplicate MAC address.\n");
}
} elseif (is_zero_ether_addr(mac)) { unsignedchar *vf_mac_addr =
adapter->vfinfo[vf].vf_mac_addresses;
/* nothing to do */ if (is_zero_ether_addr(vf_mac_addr)) return 0;
dev_info(&adapter->pdev->dev, "removing MAC on VF %d\n", vf);
retval = ixgbe_del_mac_filter(adapter, vf_mac_addr, vf); if (retval >= 0) {
adapter->vfinfo[vf].pf_set_mac = false;
memcpy(vf_mac_addr, mac, ETH_ALEN);
} else {
dev_warn(&adapter->pdev->dev, "Could NOT remove the VF MAC address.\n");
}
} else {
retval = -EINVAL;
}
return retval;
}
staticint ixgbe_enable_port_vlan(struct ixgbe_adapter *adapter, int vf,
u16 vlan, u8 qos)
{ struct ixgbe_hw *hw = &adapter->hw; int err;
err = ixgbe_set_vf_vlan(adapter, true, vlan, vf); if (err) goto out;
/* enable hide vlan on X550 */ if (hw->mac.type >= ixgbe_mac_X550)
ixgbe_write_qde(adapter, vf, IXGBE_QDE_ENABLE |
IXGBE_QDE_HIDE_VLAN);
adapter->vfinfo[vf].pf_vlan = vlan;
adapter->vfinfo[vf].pf_qos = qos;
dev_info(&adapter->pdev->dev, "Setting VLAN %d, QOS 0x%x on VF %d\n", vlan, qos, vf); if (test_bit(__IXGBE_DOWN, &adapter->state)) {
dev_warn(&adapter->pdev->dev, "The VF VLAN has been set, but the PF device is not up.\n");
dev_warn(&adapter->pdev->dev, "Bring the PF device up before attempting to use the VF device.\n");
}
out: return err;
}
staticint ixgbe_disable_port_vlan(struct ixgbe_adapter *adapter, int vf)
{ struct ixgbe_hw *hw = &adapter->hw; int err;
int ixgbe_ndo_set_vf_vlan(struct net_device *netdev, int vf, u16 vlan,
u8 qos, __be16 vlan_proto)
{ int err = 0; struct ixgbe_adapter *adapter = ixgbe_from_netdev(netdev);
if ((vf >= adapter->num_vfs) || (vlan > 4095) || (qos > 7)) return -EINVAL; if (vlan_proto != htons(ETH_P_8021Q)) return -EPROTONOSUPPORT; if (vlan || qos) { /* Check if there is already a port VLAN set, if so * we have to delete the old one first before we * can set the new one. The usage model had * previously assumed the user would delete the * old port VLAN before setting a new one but this * is not necessarily the case.
*/ if (adapter->vfinfo[vf].pf_vlan)
err = ixgbe_disable_port_vlan(adapter, vf); if (err) goto out;
err = ixgbe_enable_port_vlan(adapter, vf, vlan, qos);
} else {
err = ixgbe_disable_port_vlan(adapter, vf);
}
out: return err;
}
int ixgbe_link_mbps(struct ixgbe_adapter *adapter)
{ switch (adapter->link_speed) { case IXGBE_LINK_SPEED_100_FULL: return 100; case IXGBE_LINK_SPEED_1GB_FULL: return 1000; case IXGBE_LINK_SPEED_10GB_FULL: return 10000; default: return 0;
}
}
if (tx_rate) { /* start with base link speed value */
bcnrc_val = adapter->vf_rate_link_speed;
/* Calculate the rate factor values to set */
bcnrc_val <<= IXGBE_RTTBCNRC_RF_INT_SHIFT;
bcnrc_val /= tx_rate;
/* clear everything but the rate factor */
bcnrc_val &= IXGBE_RTTBCNRC_RF_INT_MASK |
IXGBE_RTTBCNRC_RF_DEC_MASK;
/* enable the rate scheduler */
bcnrc_val |= IXGBE_RTTBCNRC_RS_ENA;
}
/* * Set global transmit compensation time to the MMW_SIZE in RTTBCNRM * register. Typically MMW_SIZE=0x014 if 9728-byte jumbo is supported * and 0x004 otherwise.
*/ switch (hw->mac.type) { case ixgbe_mac_82599EB:
IXGBE_WRITE_REG(hw, IXGBE_RTTBCNRM, 0x4); break; case ixgbe_mac_X540:
IXGBE_WRITE_REG(hw, IXGBE_RTTBCNRM, 0x14); break; default: break;
}
/* determine how many queues per pool based on VMDq mask */
queues_per_pool = __ALIGN_MASK(1, ~vmdq->mask);
/* write value for all Tx queues belonging to VF */ for (queue = 0; queue < queues_per_pool; queue++) { unsignedint reg_idx = (vf * queues_per_pool) + queue;
void ixgbe_check_vf_rate_limit(struct ixgbe_adapter *adapter)
{ int i;
/* VF Tx rate limit was not set */ if (!adapter->vf_rate_link_speed) return;
if (ixgbe_link_mbps(adapter) != adapter->vf_rate_link_speed) {
adapter->vf_rate_link_speed = 0;
dev_info(&adapter->pdev->dev, "Link speed has been changed. VF Transmit rate is disabled\n");
}
for (i = 0; i < adapter->num_vfs; i++) { if (!adapter->vf_rate_link_speed)
adapter->vfinfo[i].tx_rate = 0;
ixgbe_set_vf_rate_limit(adapter, i);
}
}
int ixgbe_ndo_set_vf_bw(struct net_device *netdev, int vf, int min_tx_rate, int max_tx_rate)
{ struct ixgbe_adapter *adapter = ixgbe_from_netdev(netdev); int link_speed;
/* verify VF is active */ if (vf >= adapter->num_vfs) return -EINVAL;
/* verify link is up */ if (!adapter->link_up) return -EINVAL;
/* verify we are linked at 10Gbps */
link_speed = ixgbe_link_mbps(adapter); if (link_speed != 10000) return -EINVAL;
if (min_tx_rate) return -EINVAL;
/* rate limit cannot be less than 10Mbs or greater than link speed */ if (max_tx_rate && ((max_tx_rate <= 10) || (max_tx_rate > link_speed))) return -EINVAL;
/* store values */
adapter->vf_rate_link_speed = link_speed;
adapter->vfinfo[vf].tx_rate = max_tx_rate;
/* Ensure LLDP and FC is set for Ethertype Antispoofing if we will be * calling set_ethertype_anti_spoofing for each VF in loop below
*/ if (hw->mac.ops.set_ethertype_anti_spoofing) {
IXGBE_WRITE_REG(hw, IXGBE_ETQF(IXGBE_ETQF_FILTER_LLDP),
(IXGBE_ETQF_FILTER_EN |
IXGBE_ETQF_TX_ANTISPOOF |
ETH_P_LLDP));
/** * ixgbe_set_vf_link_state - Set link state * @adapter: Pointer to adapter struct * @vf: VF identifier * @state: required link state * * Set a link force state on/off a single vf
**/ void ixgbe_set_vf_link_state(struct ixgbe_adapter *adapter, int vf, int state)
{
adapter->vfinfo[vf].link_state = state;
switch (state) { case IFLA_VF_LINK_STATE_AUTO: if (test_bit(__IXGBE_DOWN, &adapter->state))
adapter->vfinfo[vf].link_enable = false; else
adapter->vfinfo[vf].link_enable = true; break; case IFLA_VF_LINK_STATE_ENABLE:
adapter->vfinfo[vf].link_enable = true; break; case IFLA_VF_LINK_STATE_DISABLE:
adapter->vfinfo[vf].link_enable = false; break;
}
/** * ixgbe_ndo_set_vf_link_state - Set link state * @netdev: network interface device structure * @vf: VF identifier * @state: required link state * * Set the link state of a specified VF, regardless of physical link state
**/ int ixgbe_ndo_set_vf_link_state(struct net_device *netdev, int vf, int state)
{ struct ixgbe_adapter *adapter = ixgbe_from_netdev(netdev); int ret = 0;
if (vf < 0 || vf >= adapter->num_vfs) {
dev_err(&adapter->pdev->dev, "NDO set VF link - invalid VF identifier %d\n", vf); return -EINVAL;
}
switch (state) { case IFLA_VF_LINK_STATE_ENABLE:
dev_info(&adapter->pdev->dev, "NDO set VF %d link state %d - not supported\n",
vf, state); break; case IFLA_VF_LINK_STATE_DISABLE:
dev_info(&adapter->pdev->dev, "NDO set VF %d link state disable\n", vf);
ixgbe_set_vf_link_state(adapter, vf, state); break; case IFLA_VF_LINK_STATE_AUTO:
dev_info(&adapter->pdev->dev, "NDO set VF %d link state auto\n", vf);
ixgbe_set_vf_link_state(adapter, vf, state); break; default:
dev_err(&adapter->pdev->dev, "NDO set VF %d - invalid link state %d\n", vf, state);
ret = -EINVAL;
}
return ret;
}
int ixgbe_ndo_set_vf_rss_query_en(struct net_device *netdev, int vf, bool setting)
{ struct ixgbe_adapter *adapter = ixgbe_from_netdev(netdev);
/* This operation is currently supported only for 82599 and x540 * devices.
*/ if (adapter->hw.mac.type < ixgbe_mac_82599EB ||
adapter->hw.mac.type >= ixgbe_mac_X550) return -EOPNOTSUPP;
if (vf >= adapter->num_vfs) return -EINVAL;
adapter->vfinfo[vf].rss_query_enabled = setting;
return 0;
}
int ixgbe_ndo_set_vf_trust(struct net_device *netdev, int vf, bool setting)
{ struct ixgbe_adapter *adapter = ixgbe_from_netdev(netdev);
if (vf >= adapter->num_vfs) return -EINVAL;
/* nothing to do */ if (adapter->vfinfo[vf].trusted == setting) return 0;
adapter->vfinfo[vf].trusted = setting;
/* reset VF to reconfigure features */
adapter->vfinfo[vf].clear_to_send = false;
ixgbe_ping_vf(adapter, vf);
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.