提交 df905cea 编写于 作者: D David S. Miller

Merge branch 'sfc-next'

Shradha Shah says:

====================
sfc: ndo_get_phys_port_id, vadaptor stats and PF unload when Vf's assigned to guest

This is the third and last instalment of SRIOV for EF10 patches.

This patch set includes implementation of ndo_get_phys_port_id
and changes to the MAC statistics code in order to support
vadaptor statistics.

It also includes code to deal with PF unload when Vf's are still
assigned to the guest.

The first couple of patches create sysfs files for physical port
and link control flags which are particularly useful when we have
enabled a large number of VF's.

These patches have been tested with and without CONFIG_SFC_SRIOV.
The creation and content of the sysfs files has been tested.
The statistics are tested using ethtool for monitoring.
====================
Signed-off-by: NDavid S. Miller <davem@davemloft.net>
此差异已折叠。
......@@ -165,6 +165,11 @@ static void efx_ef10_sriov_free_vf_vports(struct efx_nic *efx)
for (i = 0; i < efx->vf_count; i++) {
struct ef10_vf *vf = nic_data->vf + i;
/* If VF is assigned, do not free the vport */
if (vf->pci_dev &&
vf->pci_dev->dev_flags & PCI_DEV_FLAGS_ASSIGNED)
continue;
if (vf->vport_assigned) {
efx_ef10_evb_port_assign(efx, EVB_PORT_ID_NULL, i);
vf->vport_assigned = 0;
......@@ -380,7 +385,9 @@ void efx_ef10_vswitching_remove_pf(struct efx_nic *efx)
efx_ef10_vport_free(efx, nic_data->vport_id);
nic_data->vport_id = EVB_PORT_ID_ASSIGNED;
efx_ef10_vswitch_free(efx, nic_data->vport_id);
/* Only free the vswitch if no VFs are assigned */
if (!pci_vfs_assigned(efx->pci_dev))
efx_ef10_vswitch_free(efx, nic_data->vport_id);
}
void efx_ef10_vswitching_remove_vf(struct efx_nic *efx)
......@@ -413,11 +420,22 @@ static int efx_ef10_pci_sriov_enable(struct efx_nic *efx, int num_vfs)
return rc;
}
static int efx_ef10_pci_sriov_disable(struct efx_nic *efx)
static int efx_ef10_pci_sriov_disable(struct efx_nic *efx, bool force)
{
struct pci_dev *dev = efx->pci_dev;
unsigned int vfs_assigned = 0;
vfs_assigned = pci_vfs_assigned(dev);
if (vfs_assigned && !force) {
netif_info(efx, drv, efx->net_dev, "VFs are assigned to guests; "
"please detach them before disabling SR-IOV\n");
return -EBUSY;
}
if (!vfs_assigned)
pci_disable_sriov(dev);
pci_disable_sriov(dev);
efx_ef10_sriov_free_vf_vswitching(efx);
efx->vf_count = 0;
return 0;
......@@ -426,7 +444,7 @@ static int efx_ef10_pci_sriov_disable(struct efx_nic *efx)
int efx_ef10_sriov_configure(struct efx_nic *efx, int num_vfs)
{
if (num_vfs == 0)
return efx_ef10_pci_sriov_disable(efx);
return efx_ef10_pci_sriov_disable(efx, false);
else
return efx_ef10_pci_sriov_enable(efx, num_vfs);
}
......@@ -439,12 +457,25 @@ int efx_ef10_sriov_init(struct efx_nic *efx)
void efx_ef10_sriov_fini(struct efx_nic *efx)
{
struct efx_ef10_nic_data *nic_data = efx->nic_data;
unsigned int i;
int rc;
if (!nic_data->vf)
if (!nic_data->vf) {
/* Remove any un-assigned orphaned VFs */
if (pci_num_vf(efx->pci_dev) && !pci_vfs_assigned(efx->pci_dev))
pci_disable_sriov(efx->pci_dev);
return;
}
/* Remove any VFs in the host */
for (i = 0; i < efx->vf_count; ++i) {
struct efx_nic *vf_efx = nic_data->vf[i].efx;
if (vf_efx)
vf_efx->pci_dev->driver->remove(vf_efx->pci_dev);
}
rc = efx_ef10_pci_sriov_disable(efx);
rc = efx_ef10_pci_sriov_disable(efx, true);
if (rc)
netif_dbg(efx, drv, efx->net_dev,
"Disabling SRIOV was not successful rc=%d\n", rc);
......@@ -736,3 +767,17 @@ int efx_ef10_sriov_get_vf_config(struct efx_nic *efx, int vf_i,
return 0;
}
int efx_ef10_sriov_get_phys_port_id(struct efx_nic *efx,
struct netdev_phys_item_id *ppid)
{
struct efx_ef10_nic_data *nic_data = efx->nic_data;
if (!is_valid_ether_addr(nic_data->port_id))
return -EOPNOTSUPP;
ppid->id_len = ETH_ALEN;
memcpy(ppid->id, nic_data->port_id, ppid->id_len);
return 0;
}
......@@ -15,6 +15,7 @@
/**
* struct ef10_vf - PF's store of VF data
* @efx: efx_nic struct for the current VF
* @pci_dev: the pci_dev struct for the VF, retained while the VF is assigned
* @vport_id: vport ID for the VF
* @vport_assigned: record whether the vport is currently assigned to the VF
* @mac: MAC address for the VF, zero when address is removed from the vport
......@@ -22,6 +23,7 @@
*/
struct ef10_vf {
struct efx_nic *efx;
struct pci_dev *pci_dev;
unsigned int vport_id;
unsigned int vport_assigned;
u8 mac[ETH_ALEN];
......@@ -54,6 +56,9 @@ int efx_ef10_sriov_get_vf_config(struct efx_nic *efx, int vf_i,
int efx_ef10_sriov_set_vf_link_state(struct efx_nic *efx, int vf_i,
int link_state);
int efx_ef10_sriov_get_phys_port_id(struct efx_nic *efx,
struct netdev_phys_item_id *ppid);
int efx_ef10_vswitching_probe_pf(struct efx_nic *efx);
int efx_ef10_vswitching_probe_vf(struct efx_nic *efx);
int efx_ef10_vswitching_restore_pf(struct efx_nic *efx);
......
......@@ -1298,7 +1298,9 @@ static void efx_fini_io(struct efx_nic *efx)
efx->membase_phys = 0;
}
pci_disable_device(efx->pci_dev);
/* Don't disable bus-mastering if VFs are assigned */
if (!pci_vfs_assigned(efx->pci_dev))
pci_disable_device(efx->pci_dev);
}
void efx_set_default_rx_indir_table(struct efx_nic *efx)
......@@ -2282,6 +2284,7 @@ static const struct net_device_ops efx_netdev_ops = {
.ndo_set_vf_spoofchk = efx_sriov_set_vf_spoofchk,
.ndo_get_vf_config = efx_sriov_get_vf_config,
.ndo_set_vf_link_state = efx_sriov_set_vf_link_state,
.ndo_get_phys_port_id = efx_sriov_get_phys_port_id,
#endif
#ifdef CONFIG_NET_POLL_CONTROLLER
.ndo_poll_controller = efx_netpoll,
......@@ -2901,7 +2904,8 @@ static void efx_pci_remove_main(struct efx_nic *efx)
}
/* Final NIC shutdown
* This is called only at module unload (or hotplug removal).
* This is called only at module unload (or hotplug removal). A PF can call
* this on its VFs to ensure they are unbound first.
*/
static void efx_pci_remove(struct pci_dev *pci_dev)
{
......
......@@ -2755,7 +2755,7 @@
#define MC_CMD_0x2e_PRIVILEGE_CTG SRIOV_CTG_GENERAL
/* MC_CMD_MAC_STATS_IN msgrequest */
#define MC_CMD_MAC_STATS_IN_LEN 16
#define MC_CMD_MAC_STATS_IN_LEN 20
/* ??? */
#define MC_CMD_MAC_STATS_IN_DMA_ADDR_OFST 0
#define MC_CMD_MAC_STATS_IN_DMA_ADDR_LEN 8
......@@ -2777,6 +2777,8 @@
#define MC_CMD_MAC_STATS_IN_PERIOD_MS_LBN 16
#define MC_CMD_MAC_STATS_IN_PERIOD_MS_WIDTH 16
#define MC_CMD_MAC_STATS_IN_DMA_LEN_OFST 12
/* port id so vadapter stats can be provided */
#define MC_CMD_MAC_STATS_IN_PORT_ID_OFST 16
/* MC_CMD_MAC_STATS_OUT_DMA msgresponse */
#define MC_CMD_MAC_STATS_OUT_DMA_LEN 0
......@@ -2891,11 +2893,31 @@
/* enum: RXDP counter: Number of times an emergency descriptor fetch was
* performed. Valid for EF10 with PM_AND_RXDP_COUNTERS capability only.
*/
#define MC_CMD_MAC_RXDP_EMERGENCY_FETCH_CONDITIONS 0x47
#define MC_CMD_MAC_RXDP_HLB_FETCH_CONDITIONS 0x47
/* enum: RXDP counter: Number of times the DPCPU waited for an existing
* descriptor fetch. Valid for EF10 with PM_AND_RXDP_COUNTERS capability only.
*/
#define MC_CMD_MAC_RXDP_EMERGENCY_WAIT_CONDITIONS 0x48
#define MC_CMD_MAC_RXDP_HLB_WAIT_CONDITIONS 0x48
#define MC_CMD_MAC_VADAPTER_RX_DMABUF_START 0x4c /* enum */
#define MC_CMD_MAC_VADAPTER_RX_UNICAST_PACKETS 0x4c /* enum */
#define MC_CMD_MAC_VADAPTER_RX_UNICAST_BYTES 0x4d /* enum */
#define MC_CMD_MAC_VADAPTER_RX_MULTICAST_PACKETS 0x4e /* enum */
#define MC_CMD_MAC_VADAPTER_RX_MULTICAST_BYTES 0x4f /* enum */
#define MC_CMD_MAC_VADAPTER_RX_BROADCAST_PACKETS 0x50 /* enum */
#define MC_CMD_MAC_VADAPTER_RX_BROADCAST_BYTES 0x51 /* enum */
#define MC_CMD_MAC_VADAPTER_RX_BAD_PACKETS 0x52 /* enum */
#define MC_CMD_MAC_VADAPTER_RX_BAD_BYTES 0x53 /* enum */
#define MC_CMD_MAC_VADAPTER_RX_OVERFLOW 0x54 /* enum */
#define MC_CMD_MAC_VADAPTER_TX_DMABUF_START 0x57 /* enum */
#define MC_CMD_MAC_VADAPTER_TX_UNICAST_PACKETS 0x57 /* enum */
#define MC_CMD_MAC_VADAPTER_TX_UNICAST_BYTES 0x58 /* enum */
#define MC_CMD_MAC_VADAPTER_TX_MULTICAST_PACKETS 0x59 /* enum */
#define MC_CMD_MAC_VADAPTER_TX_MULTICAST_BYTES 0x5a /* enum */
#define MC_CMD_MAC_VADAPTER_TX_BROADCAST_PACKETS 0x5b /* enum */
#define MC_CMD_MAC_VADAPTER_TX_BROADCAST_BYTES 0x5c /* enum */
#define MC_CMD_MAC_VADAPTER_TX_BAD_PACKETS 0x5d /* enum */
#define MC_CMD_MAC_VADAPTER_TX_BAD_BYTES 0x5e /* enum */
#define MC_CMD_MAC_VADAPTER_TX_OVERFLOW 0x5f /* enum */
/* enum: Start of GMAC stats buffer space, for Siena only. */
#define MC_CMD_GMAC_DMABUF_START 0x40
/* enum: End of GMAC stats buffer space, for Siena only. */
......@@ -5578,6 +5600,8 @@
#define MC_CMD_GET_CAPABILITIES_OUT_MCAST_FILTER_CHAINING_WIDTH 1
#define MC_CMD_GET_CAPABILITIES_OUT_PM_AND_RXDP_COUNTERS_LBN 27
#define MC_CMD_GET_CAPABILITIES_OUT_PM_AND_RXDP_COUNTERS_WIDTH 1
#define MC_CMD_GET_CAPABILITIES_OUT_EVB_LBN 30
#define MC_CMD_GET_CAPABILITIES_OUT_EVB_WIDTH 1
/* RxDPCPU firmware id. */
#define MC_CMD_GET_CAPABILITIES_OUT_RX_DPCPU_FW_ID_OFST 4
#define MC_CMD_GET_CAPABILITIES_OUT_RX_DPCPU_FW_ID_LEN 2
......
......@@ -924,6 +924,7 @@ enum efx_stats_action {
static int efx_mcdi_mac_stats(struct efx_nic *efx,
enum efx_stats_action action, int clear)
{
struct efx_ef10_nic_data *nic_data = efx->nic_data;
MCDI_DECLARE_BUF(inbuf, MC_CMD_MAC_STATS_IN_LEN);
int rc;
int change = action == EFX_STATS_PULL ? 0 : 1;
......@@ -945,9 +946,14 @@ static int efx_mcdi_mac_stats(struct efx_nic *efx,
MAC_STATS_IN_PERIODIC_NOEVENT, 1,
MAC_STATS_IN_PERIOD_MS, period);
MCDI_SET_DWORD(inbuf, MAC_STATS_IN_DMA_LEN, dma_len);
rc = efx_mcdi_rpc(efx, MC_CMD_MAC_STATS, inbuf, sizeof(inbuf),
NULL, 0, NULL);
MCDI_SET_DWORD(inbuf, MAC_STATS_IN_PORT_ID, nic_data->vport_id);
rc = efx_mcdi_rpc_quiet(efx, MC_CMD_MAC_STATS, inbuf, sizeof(inbuf),
NULL, 0, NULL);
/* Expect ENOENT if DMA queues have not been set up */
if (rc && (rc != -ENOENT || atomic_read(&efx->active_queues)))
efx_mcdi_display_error(efx, MC_CMD_MAC_STATS, sizeof(inbuf),
NULL, 0, rc);
return rc;
}
......
......@@ -1350,6 +1350,8 @@ struct efx_nic_type {
struct ifla_vf_info *ivi);
int (*sriov_set_vf_link_state)(struct efx_nic *efx, int vf_i,
int link_state);
int (*sriov_get_phys_port_id)(struct efx_nic *efx,
struct netdev_phys_item_id *ppid);
int (*vswitching_probe)(struct efx_nic *efx);
int (*vswitching_restore)(struct efx_nic *efx);
void (*vswitching_remove)(struct efx_nic *efx);
......
......@@ -407,59 +407,77 @@ struct siena_nic_data {
};
enum {
EF10_STAT_tx_bytes = GENERIC_STAT_COUNT,
EF10_STAT_tx_packets,
EF10_STAT_tx_pause,
EF10_STAT_tx_control,
EF10_STAT_tx_unicast,
EF10_STAT_tx_multicast,
EF10_STAT_tx_broadcast,
EF10_STAT_tx_lt64,
EF10_STAT_tx_64,
EF10_STAT_tx_65_to_127,
EF10_STAT_tx_128_to_255,
EF10_STAT_tx_256_to_511,
EF10_STAT_tx_512_to_1023,
EF10_STAT_tx_1024_to_15xx,
EF10_STAT_tx_15xx_to_jumbo,
EF10_STAT_rx_bytes,
EF10_STAT_rx_bytes_minus_good_bytes,
EF10_STAT_rx_good_bytes,
EF10_STAT_rx_bad_bytes,
EF10_STAT_rx_packets,
EF10_STAT_rx_good,
EF10_STAT_rx_bad,
EF10_STAT_rx_pause,
EF10_STAT_rx_control,
EF10_STAT_port_tx_bytes = GENERIC_STAT_COUNT,
EF10_STAT_port_tx_packets,
EF10_STAT_port_tx_pause,
EF10_STAT_port_tx_control,
EF10_STAT_port_tx_unicast,
EF10_STAT_port_tx_multicast,
EF10_STAT_port_tx_broadcast,
EF10_STAT_port_tx_lt64,
EF10_STAT_port_tx_64,
EF10_STAT_port_tx_65_to_127,
EF10_STAT_port_tx_128_to_255,
EF10_STAT_port_tx_256_to_511,
EF10_STAT_port_tx_512_to_1023,
EF10_STAT_port_tx_1024_to_15xx,
EF10_STAT_port_tx_15xx_to_jumbo,
EF10_STAT_port_rx_bytes,
EF10_STAT_port_rx_bytes_minus_good_bytes,
EF10_STAT_port_rx_good_bytes,
EF10_STAT_port_rx_bad_bytes,
EF10_STAT_port_rx_packets,
EF10_STAT_port_rx_good,
EF10_STAT_port_rx_bad,
EF10_STAT_port_rx_pause,
EF10_STAT_port_rx_control,
EF10_STAT_port_rx_unicast,
EF10_STAT_port_rx_multicast,
EF10_STAT_port_rx_broadcast,
EF10_STAT_port_rx_lt64,
EF10_STAT_port_rx_64,
EF10_STAT_port_rx_65_to_127,
EF10_STAT_port_rx_128_to_255,
EF10_STAT_port_rx_256_to_511,
EF10_STAT_port_rx_512_to_1023,
EF10_STAT_port_rx_1024_to_15xx,
EF10_STAT_port_rx_15xx_to_jumbo,
EF10_STAT_port_rx_gtjumbo,
EF10_STAT_port_rx_bad_gtjumbo,
EF10_STAT_port_rx_overflow,
EF10_STAT_port_rx_align_error,
EF10_STAT_port_rx_length_error,
EF10_STAT_port_rx_nodesc_drops,
EF10_STAT_port_rx_pm_trunc_bb_overflow,
EF10_STAT_port_rx_pm_discard_bb_overflow,
EF10_STAT_port_rx_pm_trunc_vfifo_full,
EF10_STAT_port_rx_pm_discard_vfifo_full,
EF10_STAT_port_rx_pm_trunc_qbb,
EF10_STAT_port_rx_pm_discard_qbb,
EF10_STAT_port_rx_pm_discard_mapping,
EF10_STAT_port_rx_dp_q_disabled_packets,
EF10_STAT_port_rx_dp_di_dropped_packets,
EF10_STAT_port_rx_dp_streaming_packets,
EF10_STAT_port_rx_dp_hlb_fetch,
EF10_STAT_port_rx_dp_hlb_wait,
EF10_STAT_rx_unicast,
EF10_STAT_rx_unicast_bytes,
EF10_STAT_rx_multicast,
EF10_STAT_rx_multicast_bytes,
EF10_STAT_rx_broadcast,
EF10_STAT_rx_lt64,
EF10_STAT_rx_64,
EF10_STAT_rx_65_to_127,
EF10_STAT_rx_128_to_255,
EF10_STAT_rx_256_to_511,
EF10_STAT_rx_512_to_1023,
EF10_STAT_rx_1024_to_15xx,
EF10_STAT_rx_15xx_to_jumbo,
EF10_STAT_rx_gtjumbo,
EF10_STAT_rx_bad_gtjumbo,
EF10_STAT_rx_broadcast_bytes,
EF10_STAT_rx_bad,
EF10_STAT_rx_bad_bytes,
EF10_STAT_rx_overflow,
EF10_STAT_rx_align_error,
EF10_STAT_rx_length_error,
EF10_STAT_rx_nodesc_drops,
EF10_STAT_rx_pm_trunc_bb_overflow,
EF10_STAT_rx_pm_discard_bb_overflow,
EF10_STAT_rx_pm_trunc_vfifo_full,
EF10_STAT_rx_pm_discard_vfifo_full,
EF10_STAT_rx_pm_trunc_qbb,
EF10_STAT_rx_pm_discard_qbb,
EF10_STAT_rx_pm_discard_mapping,
EF10_STAT_rx_dp_q_disabled_packets,
EF10_STAT_rx_dp_di_dropped_packets,
EF10_STAT_rx_dp_streaming_packets,
EF10_STAT_rx_dp_hlb_fetch,
EF10_STAT_rx_dp_hlb_wait,
EF10_STAT_tx_unicast,
EF10_STAT_tx_unicast_bytes,
EF10_STAT_tx_multicast,
EF10_STAT_tx_multicast_bytes,
EF10_STAT_tx_broadcast,
EF10_STAT_tx_broadcast_bytes,
EF10_STAT_tx_bad,
EF10_STAT_tx_bad_bytes,
EF10_STAT_tx_overflow,
EF10_STAT_COUNT
};
......@@ -524,6 +542,7 @@ struct efx_ef10_nic_data {
unsigned int vport_id;
bool must_probe_vswitching;
unsigned int pf_index;
u8 port_id[ETH_ALEN];
#ifdef CONFIG_SFC_SRIOV
unsigned int vf_index;
struct ef10_vf *vf;
......
......@@ -70,3 +70,14 @@ int efx_sriov_set_vf_link_state(struct net_device *net_dev, int vf_i,
else
return -EOPNOTSUPP;
}
int efx_sriov_get_phys_port_id(struct net_device *net_dev,
struct netdev_phys_item_id *ppid)
{
struct efx_nic *efx = netdev_priv(net_dev);
if (efx->type->sriov_get_phys_port_id)
return efx->type->sriov_get_phys_port_id(efx, ppid);
else
return -EOPNOTSUPP;
}
......@@ -23,6 +23,8 @@ int efx_sriov_get_vf_config(struct net_device *net_dev, int vf_i,
struct ifla_vf_info *ivi);
int efx_sriov_set_vf_link_state(struct net_device *net_dev, int vf_i,
int link_state);
int efx_sriov_get_phys_port_id(struct net_device *net_dev,
struct netdev_phys_item_id *ppid);
#endif /* CONFIG_SFC_SRIOV */
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册