Merge branch 'sfc-remove-nic_data-usage-in-common-code'
Edward Cree says: ==================== sfc: remove nic_data usage in common code efx->nic_data should only be used from NIC-specific code (i.e. nic_type functions and things they call), in files like ef10[_sriov].c and siena.c. This series refactors several nic_data usages from common code (mainly in mcdi_filters.c) into nic_type functions, in preparation for the upcoming ef100 driver which will use those functions but have its own struct layout for efx->nic_data distinct from ef10's. After this series, one nic_data usage (in ptp.c) remains; it wasn't clear to me how to fix it, and ef100 devices don't yet have PTP support (so the initial ef100 driver will not call that code). ==================== Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
commit
9b1b31d5d4
@ -553,7 +553,7 @@ static int efx_ef10_probe(struct efx_nic *efx)
|
||||
|
||||
efx->rss_context.context_id = EFX_MCDI_RSS_CONTEXT_INVALID;
|
||||
|
||||
nic_data->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
efx->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
|
||||
/* In case we're recovering from a crash (kexec), we want to
|
||||
* cancel any outstanding request by the previous user of this
|
||||
@ -1281,13 +1281,13 @@ static int efx_ef10_init_nic(struct efx_nic *efx)
|
||||
nic_data->must_check_datapath_caps = false;
|
||||
}
|
||||
|
||||
if (nic_data->must_realloc_vis) {
|
||||
if (efx->must_realloc_vis) {
|
||||
/* We cannot let the number of VIs change now */
|
||||
rc = efx_ef10_alloc_vis(efx, nic_data->n_allocated_vis,
|
||||
nic_data->n_allocated_vis);
|
||||
if (rc)
|
||||
return rc;
|
||||
nic_data->must_realloc_vis = false;
|
||||
efx->must_realloc_vis = false;
|
||||
}
|
||||
|
||||
if (nic_data->must_restore_piobufs && nic_data->n_piobufs) {
|
||||
@ -1326,16 +1326,15 @@ static void efx_ef10_table_reset_mc_allocations(struct efx_nic *efx)
|
||||
#endif
|
||||
|
||||
/* All our allocations have been reset */
|
||||
nic_data->must_realloc_vis = true;
|
||||
nic_data->must_restore_rss_contexts = true;
|
||||
nic_data->must_restore_filters = true;
|
||||
efx->must_realloc_vis = true;
|
||||
efx_mcdi_filter_table_reset_mc_allocations(efx);
|
||||
nic_data->must_restore_piobufs = true;
|
||||
efx_ef10_forget_old_piobufs(efx);
|
||||
efx->rss_context.context_id = EFX_MCDI_RSS_CONTEXT_INVALID;
|
||||
|
||||
/* Driver-created vswitches and vports must be re-created */
|
||||
nic_data->must_probe_vswitching = true;
|
||||
nic_data->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
efx->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
#ifdef CONFIG_SFC_SRIOV
|
||||
if (nic_data->vf)
|
||||
for (i = 0; i < efx->vf_count; i++)
|
||||
@ -2389,6 +2388,86 @@ static void efx_ef10_tx_write(struct efx_tx_queue *tx_queue)
|
||||
}
|
||||
}
|
||||
|
||||
static int efx_ef10_probe_multicast_chaining(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
unsigned int enabled, implemented;
|
||||
bool want_workaround_26807;
|
||||
int rc;
|
||||
|
||||
rc = efx_mcdi_get_workarounds(efx, &implemented, &enabled);
|
||||
if (rc == -ENOSYS) {
|
||||
/* GET_WORKAROUNDS was implemented before this workaround,
|
||||
* thus it must be unavailable in this firmware.
|
||||
*/
|
||||
nic_data->workaround_26807 = false;
|
||||
return 0;
|
||||
}
|
||||
if (rc)
|
||||
return rc;
|
||||
want_workaround_26807 =
|
||||
implemented & MC_CMD_GET_WORKAROUNDS_OUT_BUG26807;
|
||||
nic_data->workaround_26807 =
|
||||
!!(enabled & MC_CMD_GET_WORKAROUNDS_OUT_BUG26807);
|
||||
|
||||
if (want_workaround_26807 && !nic_data->workaround_26807) {
|
||||
unsigned int flags;
|
||||
|
||||
rc = efx_mcdi_set_workaround(efx,
|
||||
MC_CMD_WORKAROUND_BUG26807,
|
||||
true, &flags);
|
||||
if (!rc) {
|
||||
if (flags &
|
||||
1 << MC_CMD_WORKAROUND_EXT_OUT_FLR_DONE_LBN) {
|
||||
netif_info(efx, drv, efx->net_dev,
|
||||
"other functions on NIC have been reset\n");
|
||||
|
||||
/* With MCFW v4.6.x and earlier, the
|
||||
* boot count will have incremented,
|
||||
* so re-read the warm_boot_count
|
||||
* value now to ensure this function
|
||||
* doesn't think it has changed next
|
||||
* time it checks.
|
||||
*/
|
||||
rc = efx_ef10_get_warm_boot_count(efx);
|
||||
if (rc >= 0) {
|
||||
nic_data->warm_boot_count = rc;
|
||||
rc = 0;
|
||||
}
|
||||
}
|
||||
nic_data->workaround_26807 = true;
|
||||
} else if (rc == -EPERM) {
|
||||
rc = 0;
|
||||
}
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
static int efx_ef10_filter_table_probe(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
int rc = efx_ef10_probe_multicast_chaining(efx);
|
||||
struct efx_mcdi_filter_vlan *vlan;
|
||||
|
||||
if (rc)
|
||||
return rc;
|
||||
rc = efx_mcdi_filter_table_probe(efx, nic_data->workaround_26807);
|
||||
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
list_for_each_entry(vlan, &nic_data->vlan_list, list) {
|
||||
rc = efx_mcdi_filter_add_vlan(efx, vlan->vid);
|
||||
if (rc)
|
||||
goto fail_add_vlan;
|
||||
}
|
||||
return 0;
|
||||
|
||||
fail_add_vlan:
|
||||
efx_mcdi_filter_table_remove(efx);
|
||||
return rc;
|
||||
}
|
||||
|
||||
/* This creates an entry in the RX descriptor queue */
|
||||
static inline void
|
||||
efx_ef10_build_rx_desc(struct efx_rx_queue *rx_queue, unsigned int index)
|
||||
@ -2464,75 +2543,14 @@ static int efx_ef10_ev_init(struct efx_channel *channel)
|
||||
{
|
||||
struct efx_nic *efx = channel->efx;
|
||||
struct efx_ef10_nic_data *nic_data;
|
||||
unsigned int enabled, implemented;
|
||||
bool use_v2, cut_thru;
|
||||
int rc;
|
||||
|
||||
nic_data = efx->nic_data;
|
||||
use_v2 = nic_data->datapath_caps2 &
|
||||
1 << MC_CMD_GET_CAPABILITIES_V2_OUT_INIT_EVQ_V2_LBN;
|
||||
cut_thru = !(nic_data->datapath_caps &
|
||||
1 << MC_CMD_GET_CAPABILITIES_OUT_RX_BATCHING_LBN);
|
||||
rc = efx_mcdi_ev_init(channel, cut_thru, use_v2);
|
||||
|
||||
/* IRQ return is ignored */
|
||||
if (channel->channel || rc)
|
||||
return rc;
|
||||
|
||||
/* Successfully created event queue on channel 0 */
|
||||
rc = efx_mcdi_get_workarounds(efx, &implemented, &enabled);
|
||||
if (rc == -ENOSYS) {
|
||||
/* GET_WORKAROUNDS was implemented before this workaround,
|
||||
* thus it must be unavailable in this firmware.
|
||||
*/
|
||||
nic_data->workaround_26807 = false;
|
||||
rc = 0;
|
||||
} else if (rc) {
|
||||
goto fail;
|
||||
} else {
|
||||
nic_data->workaround_26807 =
|
||||
!!(enabled & MC_CMD_GET_WORKAROUNDS_OUT_BUG26807);
|
||||
|
||||
if (implemented & MC_CMD_GET_WORKAROUNDS_OUT_BUG26807 &&
|
||||
!nic_data->workaround_26807) {
|
||||
unsigned int flags;
|
||||
|
||||
rc = efx_mcdi_set_workaround(efx,
|
||||
MC_CMD_WORKAROUND_BUG26807,
|
||||
true, &flags);
|
||||
|
||||
if (!rc) {
|
||||
if (flags &
|
||||
1 << MC_CMD_WORKAROUND_EXT_OUT_FLR_DONE_LBN) {
|
||||
netif_info(efx, drv, efx->net_dev,
|
||||
"other functions on NIC have been reset\n");
|
||||
|
||||
/* With MCFW v4.6.x and earlier, the
|
||||
* boot count will have incremented,
|
||||
* so re-read the warm_boot_count
|
||||
* value now to ensure this function
|
||||
* doesn't think it has changed next
|
||||
* time it checks.
|
||||
*/
|
||||
rc = efx_ef10_get_warm_boot_count(efx);
|
||||
if (rc >= 0) {
|
||||
nic_data->warm_boot_count = rc;
|
||||
rc = 0;
|
||||
}
|
||||
}
|
||||
nic_data->workaround_26807 = true;
|
||||
} else if (rc == -EPERM) {
|
||||
rc = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!rc)
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
efx_mcdi_ev_fini(channel);
|
||||
return rc;
|
||||
return efx_mcdi_ev_init(channel, cut_thru, use_v2);
|
||||
}
|
||||
|
||||
static void efx_ef10_handle_rx_wrong_queue(struct efx_rx_queue *rx_queue,
|
||||
@ -3100,16 +3118,15 @@ void efx_ef10_handle_drain_event(struct efx_nic *efx)
|
||||
|
||||
static int efx_ef10_fini_dmaq(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
struct efx_channel *channel;
|
||||
struct efx_tx_queue *tx_queue;
|
||||
struct efx_rx_queue *rx_queue;
|
||||
struct efx_channel *channel;
|
||||
int pending;
|
||||
|
||||
/* If the MC has just rebooted, the TX/RX queues will have already been
|
||||
* torn down, but efx->active_queues needs to be set to zero.
|
||||
*/
|
||||
if (nic_data->must_realloc_vis) {
|
||||
if (efx->must_realloc_vis) {
|
||||
atomic_set(&efx->active_queues, 0);
|
||||
return 0;
|
||||
}
|
||||
@ -3158,22 +3175,22 @@ static int efx_ef10_vport_set_mac_address(struct efx_nic *efx)
|
||||
efx_mcdi_filter_table_remove(efx);
|
||||
up_write(&efx->filter_sem);
|
||||
|
||||
rc = efx_ef10_vadaptor_free(efx, nic_data->vport_id);
|
||||
rc = efx_ef10_vadaptor_free(efx, efx->vport_id);
|
||||
if (rc)
|
||||
goto restore_filters;
|
||||
|
||||
ether_addr_copy(mac_old, nic_data->vport_mac);
|
||||
rc = efx_ef10_vport_del_mac(efx, nic_data->vport_id,
|
||||
rc = efx_ef10_vport_del_mac(efx, efx->vport_id,
|
||||
nic_data->vport_mac);
|
||||
if (rc)
|
||||
goto restore_vadaptor;
|
||||
|
||||
rc = efx_ef10_vport_add_mac(efx, nic_data->vport_id,
|
||||
rc = efx_ef10_vport_add_mac(efx, efx->vport_id,
|
||||
efx->net_dev->dev_addr);
|
||||
if (!rc) {
|
||||
ether_addr_copy(nic_data->vport_mac, efx->net_dev->dev_addr);
|
||||
} else {
|
||||
rc2 = efx_ef10_vport_add_mac(efx, nic_data->vport_id, mac_old);
|
||||
rc2 = efx_ef10_vport_add_mac(efx, efx->vport_id, mac_old);
|
||||
if (rc2) {
|
||||
/* Failed to add original MAC, so clear vport_mac */
|
||||
eth_zero_addr(nic_data->vport_mac);
|
||||
@ -3182,12 +3199,12 @@ static int efx_ef10_vport_set_mac_address(struct efx_nic *efx)
|
||||
}
|
||||
|
||||
restore_vadaptor:
|
||||
rc2 = efx_ef10_vadaptor_alloc(efx, nic_data->vport_id);
|
||||
rc2 = efx_ef10_vadaptor_alloc(efx, efx->vport_id);
|
||||
if (rc2)
|
||||
goto reset_nic;
|
||||
restore_filters:
|
||||
down_write(&efx->filter_sem);
|
||||
rc2 = efx_mcdi_filter_table_probe(efx);
|
||||
rc2 = efx_ef10_filter_table_probe(efx);
|
||||
up_write(&efx->filter_sem);
|
||||
if (rc2)
|
||||
goto reset_nic;
|
||||
@ -3225,11 +3242,11 @@ static int efx_ef10_set_mac_address(struct efx_nic *efx)
|
||||
ether_addr_copy(MCDI_PTR(inbuf, VADAPTOR_SET_MAC_IN_MACADDR),
|
||||
efx->net_dev->dev_addr);
|
||||
MCDI_SET_DWORD(inbuf, VADAPTOR_SET_MAC_IN_UPSTREAM_PORT_ID,
|
||||
nic_data->vport_id);
|
||||
efx->vport_id);
|
||||
rc = efx_mcdi_rpc_quiet(efx, MC_CMD_VADAPTOR_SET_MAC, inbuf,
|
||||
sizeof(inbuf), NULL, 0, NULL);
|
||||
|
||||
efx_mcdi_filter_table_probe(efx);
|
||||
efx_ef10_filter_table_probe(efx);
|
||||
up_write(&efx->filter_sem);
|
||||
mutex_unlock(&efx->mac_lock);
|
||||
|
||||
@ -3961,6 +3978,35 @@ out_unlock:
|
||||
return rc;
|
||||
}
|
||||
|
||||
/* EF10 may have multiple datapath firmware variants within a
|
||||
* single version. Report which variants are running.
|
||||
*/
|
||||
static size_t efx_ef10_print_additional_fwver(struct efx_nic *efx, char *buf,
|
||||
size_t len)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
|
||||
return scnprintf(buf, len, " rx%x tx%x",
|
||||
nic_data->rx_dpcpu_fw_id,
|
||||
nic_data->tx_dpcpu_fw_id);
|
||||
}
|
||||
|
||||
static unsigned int ef10_check_caps(const struct efx_nic *efx,
|
||||
u8 flag,
|
||||
u32 offset)
|
||||
{
|
||||
const struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
|
||||
switch (offset) {
|
||||
case(MC_CMD_GET_CAPABILITIES_V4_OUT_FLAGS1_OFST):
|
||||
return nic_data->datapath_caps & BIT_ULL(flag);
|
||||
case(MC_CMD_GET_CAPABILITIES_V4_OUT_FLAGS2_OFST):
|
||||
return nic_data->datapath_caps2 & BIT_ULL(flag);
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
#define EF10_OFFLOAD_FEATURES \
|
||||
(NETIF_F_IP_CSUM | \
|
||||
NETIF_F_HW_VLAN_CTAG_FILTER | \
|
||||
@ -4027,7 +4073,7 @@ const struct efx_nic_type efx_hunt_a0_vf_nic_type = {
|
||||
.ev_process = efx_ef10_ev_process,
|
||||
.ev_read_ack = efx_ef10_ev_read_ack,
|
||||
.ev_test_generate = efx_ef10_ev_test_generate,
|
||||
.filter_table_probe = efx_mcdi_filter_table_probe,
|
||||
.filter_table_probe = efx_ef10_filter_table_probe,
|
||||
.filter_table_restore = efx_mcdi_filter_table_restore,
|
||||
.filter_table_remove = efx_mcdi_filter_table_remove,
|
||||
.filter_update_rx_scatter = efx_mcdi_update_rx_scatter,
|
||||
@ -4073,6 +4119,8 @@ const struct efx_nic_type efx_hunt_a0_vf_nic_type = {
|
||||
.hwtstamp_filters = 1 << HWTSTAMP_FILTER_NONE |
|
||||
1 << HWTSTAMP_FILTER_ALL,
|
||||
.rx_hash_key_size = 40,
|
||||
.check_caps = ef10_check_caps,
|
||||
.print_additional_fwver = efx_ef10_print_additional_fwver,
|
||||
};
|
||||
|
||||
const struct efx_nic_type efx_hunt_a0_nic_type = {
|
||||
@ -4139,7 +4187,7 @@ const struct efx_nic_type efx_hunt_a0_nic_type = {
|
||||
.ev_process = efx_ef10_ev_process,
|
||||
.ev_read_ack = efx_ef10_ev_read_ack,
|
||||
.ev_test_generate = efx_ef10_ev_test_generate,
|
||||
.filter_table_probe = efx_mcdi_filter_table_probe,
|
||||
.filter_table_probe = efx_ef10_filter_table_probe,
|
||||
.filter_table_restore = efx_mcdi_filter_table_restore,
|
||||
.filter_table_remove = efx_mcdi_filter_table_remove,
|
||||
.filter_update_rx_scatter = efx_mcdi_update_rx_scatter,
|
||||
@ -4208,4 +4256,6 @@ const struct efx_nic_type efx_hunt_a0_nic_type = {
|
||||
.hwtstamp_filters = 1 << HWTSTAMP_FILTER_NONE |
|
||||
1 << HWTSTAMP_FILTER_ALL,
|
||||
.rx_hash_key_size = 40,
|
||||
.check_caps = ef10_check_caps,
|
||||
.print_additional_fwver = efx_ef10_print_additional_fwver,
|
||||
};
|
||||
|
@ -232,15 +232,14 @@ fail:
|
||||
|
||||
static int efx_ef10_vadaptor_alloc_set_features(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
u32 port_flags;
|
||||
int rc;
|
||||
|
||||
rc = efx_ef10_vadaptor_alloc(efx, nic_data->vport_id);
|
||||
rc = efx_ef10_vadaptor_alloc(efx, efx->vport_id);
|
||||
if (rc)
|
||||
goto fail_vadaptor_alloc;
|
||||
|
||||
rc = efx_ef10_vadaptor_query(efx, nic_data->vport_id,
|
||||
rc = efx_ef10_vadaptor_query(efx, efx->vport_id,
|
||||
&port_flags, NULL, NULL);
|
||||
if (rc)
|
||||
goto fail_vadaptor_query;
|
||||
@ -281,11 +280,11 @@ int efx_ef10_vswitching_probe_pf(struct efx_nic *efx)
|
||||
|
||||
rc = efx_ef10_vport_alloc(efx, EVB_PORT_ID_ASSIGNED,
|
||||
MC_CMD_VPORT_ALLOC_IN_VPORT_TYPE_NORMAL,
|
||||
EFX_EF10_NO_VLAN, &nic_data->vport_id);
|
||||
EFX_EF10_NO_VLAN, &efx->vport_id);
|
||||
if (rc)
|
||||
goto fail2;
|
||||
|
||||
rc = efx_ef10_vport_add_mac(efx, nic_data->vport_id, net_dev->dev_addr);
|
||||
rc = efx_ef10_vport_add_mac(efx, efx->vport_id, net_dev->dev_addr);
|
||||
if (rc)
|
||||
goto fail3;
|
||||
ether_addr_copy(nic_data->vport_mac, net_dev->dev_addr);
|
||||
@ -296,11 +295,11 @@ int efx_ef10_vswitching_probe_pf(struct efx_nic *efx)
|
||||
|
||||
return 0;
|
||||
fail4:
|
||||
efx_ef10_vport_del_mac(efx, nic_data->vport_id, nic_data->vport_mac);
|
||||
efx_ef10_vport_del_mac(efx, efx->vport_id, nic_data->vport_mac);
|
||||
eth_zero_addr(nic_data->vport_mac);
|
||||
fail3:
|
||||
efx_ef10_vport_free(efx, nic_data->vport_id);
|
||||
nic_data->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
efx_ef10_vport_free(efx, efx->vport_id);
|
||||
efx->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
fail2:
|
||||
efx_ef10_vswitch_free(efx, EVB_PORT_ID_ASSIGNED);
|
||||
fail1:
|
||||
@ -355,22 +354,22 @@ void efx_ef10_vswitching_remove_pf(struct efx_nic *efx)
|
||||
|
||||
efx_ef10_sriov_free_vf_vswitching(efx);
|
||||
|
||||
efx_ef10_vadaptor_free(efx, nic_data->vport_id);
|
||||
efx_ef10_vadaptor_free(efx, efx->vport_id);
|
||||
|
||||
if (nic_data->vport_id == EVB_PORT_ID_ASSIGNED)
|
||||
if (efx->vport_id == EVB_PORT_ID_ASSIGNED)
|
||||
return; /* No vswitch was ever created */
|
||||
|
||||
if (!is_zero_ether_addr(nic_data->vport_mac)) {
|
||||
efx_ef10_vport_del_mac(efx, nic_data->vport_id,
|
||||
efx_ef10_vport_del_mac(efx, efx->vport_id,
|
||||
efx->net_dev->dev_addr);
|
||||
eth_zero_addr(nic_data->vport_mac);
|
||||
}
|
||||
efx_ef10_vport_free(efx, nic_data->vport_id);
|
||||
nic_data->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
efx_ef10_vport_free(efx, efx->vport_id);
|
||||
efx->vport_id = EVB_PORT_ID_ASSIGNED;
|
||||
|
||||
/* 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);
|
||||
efx_ef10_vswitch_free(efx, efx->vport_id);
|
||||
}
|
||||
|
||||
void efx_ef10_vswitching_remove_vf(struct efx_nic *efx)
|
||||
|
@ -1425,23 +1425,16 @@ void efx_mcdi_print_fwver(struct efx_nic *efx, char *buf, size_t len)
|
||||
le16_to_cpu(ver_words[2]),
|
||||
le16_to_cpu(ver_words[3]));
|
||||
|
||||
/* EF10 may have multiple datapath firmware variants within a
|
||||
* single version. Report which variants are running.
|
||||
if (efx->type->print_additional_fwver)
|
||||
offset += efx->type->print_additional_fwver(efx, buf + offset,
|
||||
len - offset);
|
||||
|
||||
/* It's theoretically possible for the string to exceed 31
|
||||
* characters, though in practice the first three version
|
||||
* components are short enough that this doesn't happen.
|
||||
*/
|
||||
if (efx_nic_rev(efx) >= EFX_REV_HUNT_A0) {
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
|
||||
offset += scnprintf(buf + offset, len - offset, " rx%x tx%x",
|
||||
nic_data->rx_dpcpu_fw_id,
|
||||
nic_data->tx_dpcpu_fw_id);
|
||||
|
||||
/* It's theoretically possible for the string to exceed 31
|
||||
* characters, though in practice the first three version
|
||||
* components are short enough that this doesn't happen.
|
||||
*/
|
||||
if (WARN_ON(offset >= len))
|
||||
buf[0] = 0;
|
||||
}
|
||||
if (WARN_ON(offset >= len))
|
||||
buf[0] = 0;
|
||||
|
||||
return;
|
||||
|
||||
|
@ -326,6 +326,18 @@ void efx_mcdi_sensor_event(struct efx_nic *efx, efx_qword_t *ev);
|
||||
#define MCDI_EVENT_FIELD(_ev, _field) \
|
||||
EFX_QWORD_FIELD(_ev, MCDI_EVENT_ ## _field)
|
||||
|
||||
#define MCDI_CAPABILITY(field) \
|
||||
MC_CMD_GET_CAPABILITIES_V4_OUT_ ## field ## _LBN
|
||||
|
||||
#define MCDI_CAPABILITY_OFST(field) \
|
||||
MC_CMD_GET_CAPABILITIES_V4_OUT_ ## field ## _OFST
|
||||
|
||||
/* field is FLAGS1 or FLAGS2 */
|
||||
#define efx_has_cap(efx, flag, field) \
|
||||
efx->type->check_caps(efx, \
|
||||
MCDI_CAPABILITY(flag), \
|
||||
MCDI_CAPABILITY_OFST(field))
|
||||
|
||||
void efx_mcdi_print_fwver(struct efx_nic *efx, char *buf, size_t len);
|
||||
int efx_mcdi_get_board_cfg(struct efx_nic *efx, u8 *mac_address,
|
||||
u16 *fw_subtype_list, u32 *capabilities);
|
||||
|
@ -186,7 +186,6 @@ static void efx_mcdi_filter_push_prep(struct efx_nic *efx,
|
||||
struct efx_rss_context *ctx,
|
||||
bool replacing)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
u32 flags = spec->flags;
|
||||
|
||||
memset(inbuf, 0, MC_CMD_FILTER_OP_EXT_IN_LEN);
|
||||
@ -211,7 +210,7 @@ static void efx_mcdi_filter_push_prep(struct efx_nic *efx,
|
||||
efx_mcdi_filter_push_prep_set_match_fields(efx, spec, inbuf);
|
||||
}
|
||||
|
||||
MCDI_SET_DWORD(inbuf, FILTER_OP_IN_PORT_ID, nic_data->vport_id);
|
||||
MCDI_SET_DWORD(inbuf, FILTER_OP_IN_PORT_ID, efx->vport_id);
|
||||
MCDI_SET_DWORD(inbuf, FILTER_OP_IN_RX_DEST,
|
||||
spec->dmaq_id == EFX_FILTER_RX_DMAQ_ID_DROP ?
|
||||
MC_CMD_FILTER_OP_IN_RX_DEST_DROP :
|
||||
@ -332,7 +331,6 @@ static s32 efx_mcdi_filter_insert_locked(struct efx_nic *efx,
|
||||
bool replace_equal)
|
||||
{
|
||||
DECLARE_BITMAP(mc_rem_map, EFX_EF10_FILTER_SEARCH_LIMIT);
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
struct efx_mcdi_filter_table *table;
|
||||
struct efx_filter_spec *saved_spec;
|
||||
struct efx_rss_context *ctx = NULL;
|
||||
@ -461,7 +459,7 @@ static s32 efx_mcdi_filter_insert_locked(struct efx_nic *efx,
|
||||
rc = efx_mcdi_filter_push(efx, spec, &table->entry[ins_index].handle,
|
||||
ctx, replacing);
|
||||
|
||||
if (rc == -EINVAL && nic_data->must_realloc_vis)
|
||||
if (rc == -EINVAL && efx->must_realloc_vis)
|
||||
/* The MC rebooted under us, causing it to reject our filter
|
||||
* insertion as pointing to an invalid VI (spec->dmaq_id).
|
||||
*/
|
||||
@ -813,7 +811,7 @@ static int efx_mcdi_filter_insert_def(struct efx_nic *efx,
|
||||
enum efx_encap_type encap_type,
|
||||
bool multicast, bool rollback)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
struct efx_mcdi_filter_table *table = efx->filter_state;
|
||||
enum efx_filter_flags filter_flags;
|
||||
struct efx_filter_spec spec;
|
||||
u8 baddr[ETH_ALEN];
|
||||
@ -830,8 +828,7 @@ static int efx_mcdi_filter_insert_def(struct efx_nic *efx,
|
||||
efx_filter_set_uc_def(&spec);
|
||||
|
||||
if (encap_type) {
|
||||
if (nic_data->datapath_caps &
|
||||
(1 << MC_CMD_GET_CAPABILITIES_OUT_VXLAN_NVGRE_LBN))
|
||||
if (efx_has_cap(efx, VXLAN_NVGRE, FLAGS1))
|
||||
efx_filter_set_encap_type(&spec, encap_type);
|
||||
else
|
||||
/*
|
||||
@ -899,7 +896,7 @@ static int efx_mcdi_filter_insert_def(struct efx_nic *efx,
|
||||
|
||||
EFX_WARN_ON_PARANOID(*id != EFX_EF10_FILTER_ID_INVALID);
|
||||
*id = efx_mcdi_filter_get_unsafe_id(rc);
|
||||
if (!nic_data->workaround_26807 && !encap_type) {
|
||||
if (!table->mc_chaining && !encap_type) {
|
||||
/* Also need an Ethernet broadcast filter */
|
||||
efx_filter_init_rx(&spec, EFX_FILTER_PRI_AUTO,
|
||||
filter_flags, 0);
|
||||
@ -965,7 +962,6 @@ static void efx_mcdi_filter_vlan_sync_rx_mode(struct efx_nic *efx,
|
||||
struct efx_mcdi_filter_vlan *vlan)
|
||||
{
|
||||
struct efx_mcdi_filter_table *table = efx->filter_state;
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
|
||||
/*
|
||||
* Do not install unspecified VID if VLAN filtering is enabled.
|
||||
@ -1012,11 +1008,10 @@ static void efx_mcdi_filter_vlan_sync_rx_mode(struct efx_nic *efx,
|
||||
* If changing promiscuous state with cascaded multicast filters, remove
|
||||
* old filters first, so that packets are dropped rather than duplicated
|
||||
*/
|
||||
if (nic_data->workaround_26807 &&
|
||||
table->mc_promisc_last != table->mc_promisc)
|
||||
if (table->mc_chaining && table->mc_promisc_last != table->mc_promisc)
|
||||
efx_mcdi_filter_remove_old(efx);
|
||||
if (table->mc_promisc) {
|
||||
if (nic_data->workaround_26807) {
|
||||
if (table->mc_chaining) {
|
||||
/*
|
||||
* If we failed to insert promiscuous filters, rollback
|
||||
* and fall back to individual multicast filters
|
||||
@ -1051,7 +1046,7 @@ static void efx_mcdi_filter_vlan_sync_rx_mode(struct efx_nic *efx,
|
||||
*/
|
||||
if (efx_mcdi_filter_insert_addr_list(efx, vlan, true, true)) {
|
||||
/* Changing promisc state, so remove old filters */
|
||||
if (nic_data->workaround_26807)
|
||||
if (table->mc_chaining)
|
||||
efx_mcdi_filter_remove_old(efx);
|
||||
if (efx_mcdi_filter_insert_def(efx, vlan,
|
||||
EFX_ENCAP_TYPE_NONE,
|
||||
@ -1288,12 +1283,10 @@ efx_mcdi_filter_table_probe_matches(struct efx_nic *efx,
|
||||
return 0;
|
||||
}
|
||||
|
||||
int efx_mcdi_filter_table_probe(struct efx_nic *efx)
|
||||
int efx_mcdi_filter_table_probe(struct efx_nic *efx, bool multicast_chaining)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
struct net_device *net_dev = efx->net_dev;
|
||||
struct efx_mcdi_filter_table *table;
|
||||
struct efx_mcdi_filter_vlan *vlan;
|
||||
int rc;
|
||||
|
||||
if (!efx_rwsem_assert_write_locked(&efx->filter_sem))
|
||||
@ -1306,12 +1299,12 @@ int efx_mcdi_filter_table_probe(struct efx_nic *efx)
|
||||
if (!table)
|
||||
return -ENOMEM;
|
||||
|
||||
table->mc_chaining = multicast_chaining;
|
||||
table->rx_match_count = 0;
|
||||
rc = efx_mcdi_filter_table_probe_matches(efx, table, false);
|
||||
if (rc)
|
||||
goto fail;
|
||||
if (nic_data->datapath_caps &
|
||||
(1 << MC_CMD_GET_CAPABILITIES_OUT_VXLAN_NVGRE_LBN))
|
||||
if (efx_has_cap(efx, VXLAN_NVGRE, FLAGS1))
|
||||
rc = efx_mcdi_filter_table_probe_matches(efx, table, true);
|
||||
if (rc)
|
||||
goto fail;
|
||||
@ -1342,22 +1335,22 @@ int efx_mcdi_filter_table_probe(struct efx_nic *efx)
|
||||
|
||||
efx->filter_state = table;
|
||||
|
||||
list_for_each_entry(vlan, &nic_data->vlan_list, list) {
|
||||
rc = efx_mcdi_filter_add_vlan(efx, vlan->vid);
|
||||
if (rc)
|
||||
goto fail_add_vlan;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
fail_add_vlan:
|
||||
efx_mcdi_filter_cleanup_vlans(efx);
|
||||
efx->filter_state = NULL;
|
||||
fail:
|
||||
kfree(table);
|
||||
return rc;
|
||||
}
|
||||
|
||||
void efx_mcdi_filter_table_reset_mc_allocations(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_mcdi_filter_table *table = efx->filter_state;
|
||||
|
||||
if (table) {
|
||||
table->must_restore_filters = true;
|
||||
table->must_restore_rss_contexts = true;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Caller must hold efx->filter_sem for read if race against
|
||||
* efx_mcdi_filter_table_remove() is possible
|
||||
@ -1365,7 +1358,6 @@ fail:
|
||||
void efx_mcdi_filter_table_restore(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_mcdi_filter_table *table = efx->filter_state;
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
unsigned int invalid_filters = 0, failed = 0;
|
||||
struct efx_mcdi_filter_vlan *vlan;
|
||||
struct efx_filter_spec *spec;
|
||||
@ -1377,7 +1369,7 @@ void efx_mcdi_filter_table_restore(struct efx_nic *efx)
|
||||
|
||||
WARN_ON(!rwsem_is_locked(&efx->filter_sem));
|
||||
|
||||
if (!nic_data->must_restore_filters)
|
||||
if (!table->must_restore_filters)
|
||||
return;
|
||||
|
||||
if (!table)
|
||||
@ -1456,7 +1448,7 @@ not_restored:
|
||||
netif_err(efx, hw, efx->net_dev,
|
||||
"unable to restore %u filters\n", failed);
|
||||
else
|
||||
nic_data->must_restore_filters = false;
|
||||
table->must_restore_filters = false;
|
||||
}
|
||||
|
||||
void efx_mcdi_filter_table_remove(struct efx_nic *efx)
|
||||
@ -1921,7 +1913,6 @@ static int efx_mcdi_filter_alloc_rss_context(struct efx_nic *efx, bool exclusive
|
||||
{
|
||||
MCDI_DECLARE_BUF(inbuf, MC_CMD_RSS_CONTEXT_ALLOC_IN_LEN);
|
||||
MCDI_DECLARE_BUF(outbuf, MC_CMD_RSS_CONTEXT_ALLOC_OUT_LEN);
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
size_t outlen;
|
||||
int rc;
|
||||
u32 alloc_type = exclusive ?
|
||||
@ -1939,12 +1930,11 @@ static int efx_mcdi_filter_alloc_rss_context(struct efx_nic *efx, bool exclusive
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (nic_data->datapath_caps &
|
||||
1 << MC_CMD_GET_CAPABILITIES_OUT_RX_RSS_LIMITED_LBN)
|
||||
if (efx_has_cap(efx, RX_RSS_LIMITED, FLAGS1))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
MCDI_SET_DWORD(inbuf, RSS_CONTEXT_ALLOC_IN_UPSTREAM_PORT_ID,
|
||||
nic_data->vport_id);
|
||||
efx->vport_id);
|
||||
MCDI_SET_DWORD(inbuf, RSS_CONTEXT_ALLOC_IN_TYPE, alloc_type);
|
||||
MCDI_SET_DWORD(inbuf, RSS_CONTEXT_ALLOC_IN_NUM_QUEUES, rss_spread);
|
||||
|
||||
@ -1961,8 +1951,7 @@ static int efx_mcdi_filter_alloc_rss_context(struct efx_nic *efx, bool exclusive
|
||||
if (context_size)
|
||||
*context_size = rss_spread;
|
||||
|
||||
if (nic_data->datapath_caps &
|
||||
1 << MC_CMD_GET_CAPABILITIES_OUT_ADDITIONAL_RSS_MODES_LBN)
|
||||
if (efx_has_cap(efx, ADDITIONAL_RSS_MODES, FLAGS1))
|
||||
efx_mcdi_set_rss_context_flags(efx, ctx);
|
||||
|
||||
return 0;
|
||||
@ -2030,14 +2019,14 @@ void efx_mcdi_rx_free_indir_table(struct efx_nic *efx)
|
||||
static int efx_mcdi_filter_rx_push_shared_rss_config(struct efx_nic *efx,
|
||||
unsigned *context_size)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
struct efx_mcdi_filter_table *table = efx->filter_state;
|
||||
int rc = efx_mcdi_filter_alloc_rss_context(efx, false, &efx->rss_context,
|
||||
context_size);
|
||||
|
||||
if (rc != 0)
|
||||
return rc;
|
||||
|
||||
nic_data->rx_rss_context_exclusive = false;
|
||||
table->rx_rss_context_exclusive = false;
|
||||
efx_set_default_rx_indir_table(efx, &efx->rss_context);
|
||||
return 0;
|
||||
}
|
||||
@ -2046,12 +2035,12 @@ static int efx_mcdi_filter_rx_push_exclusive_rss_config(struct efx_nic *efx,
|
||||
const u32 *rx_indir_table,
|
||||
const u8 *key)
|
||||
{
|
||||
struct efx_mcdi_filter_table *table = efx->filter_state;
|
||||
u32 old_rx_rss_context = efx->rss_context.context_id;
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
int rc;
|
||||
|
||||
if (efx->rss_context.context_id == EFX_MCDI_RSS_CONTEXT_INVALID ||
|
||||
!nic_data->rx_rss_context_exclusive) {
|
||||
!table->rx_rss_context_exclusive) {
|
||||
rc = efx_mcdi_filter_alloc_rss_context(efx, true, &efx->rss_context,
|
||||
NULL);
|
||||
if (rc == -EOPNOTSUPP)
|
||||
@ -2068,7 +2057,7 @@ static int efx_mcdi_filter_rx_push_exclusive_rss_config(struct efx_nic *efx,
|
||||
if (efx->rss_context.context_id != old_rx_rss_context &&
|
||||
old_rx_rss_context != EFX_MCDI_RSS_CONTEXT_INVALID)
|
||||
WARN_ON(efx_mcdi_filter_free_rss_context(efx, old_rx_rss_context) != 0);
|
||||
nic_data->rx_rss_context_exclusive = true;
|
||||
table->rx_rss_context_exclusive = true;
|
||||
if (rx_indir_table != efx->rss_context.rx_indir_table)
|
||||
memcpy(efx->rss_context.rx_indir_table, rx_indir_table,
|
||||
sizeof(efx->rss_context.rx_indir_table));
|
||||
@ -2182,13 +2171,13 @@ int efx_mcdi_rx_pull_rss_config(struct efx_nic *efx)
|
||||
|
||||
void efx_mcdi_rx_restore_rss_contexts(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
struct efx_mcdi_filter_table *table = efx->filter_state;
|
||||
struct efx_rss_context *ctx;
|
||||
int rc;
|
||||
|
||||
WARN_ON(!mutex_is_locked(&efx->rss_lock));
|
||||
|
||||
if (!nic_data->must_restore_rss_contexts)
|
||||
if (!table->must_restore_rss_contexts)
|
||||
return;
|
||||
|
||||
list_for_each_entry(ctx, &efx->rss_context.list, list) {
|
||||
@ -2204,7 +2193,7 @@ void efx_mcdi_rx_restore_rss_contexts(struct efx_nic *efx)
|
||||
"; RSS filters may fail to be applied\n",
|
||||
ctx->user_id, rc);
|
||||
}
|
||||
nic_data->must_restore_rss_contexts = false;
|
||||
table->must_restore_rss_contexts = false;
|
||||
}
|
||||
|
||||
int efx_mcdi_pf_rx_push_rss_config(struct efx_nic *efx, bool user,
|
||||
|
@ -55,6 +55,8 @@ struct efx_mcdi_filter_table {
|
||||
u32 rx_match_mcdi_flags[
|
||||
MC_CMD_GET_PARSER_DISP_INFO_OUT_SUPPORTED_MATCHES_MAXNUM * 2];
|
||||
unsigned int rx_match_count;
|
||||
/* Our RSS context is exclusive (as opposed to shared) */
|
||||
bool rx_rss_context_exclusive;
|
||||
|
||||
struct rw_semaphore lock; /* Protects entries */
|
||||
struct {
|
||||
@ -75,14 +77,27 @@ struct efx_mcdi_filter_table {
|
||||
/* Whether in multicast promiscuous mode when last changed */
|
||||
bool mc_promisc_last;
|
||||
bool mc_overflow; /* Too many MC addrs; should always imply mc_promisc */
|
||||
/* RSS contexts have yet to be restored after MC reboot */
|
||||
bool must_restore_rss_contexts;
|
||||
/* filters have yet to be restored after MC reboot */
|
||||
bool must_restore_filters;
|
||||
/* Multicast filter chaining allows less-specific filters to receive
|
||||
* multicast packets that matched more-specific filters. Early EF10
|
||||
* firmware didn't support this (SF bug 26807); if mc_chaining == false
|
||||
* then we still subscribe the dev_mc_list even when mc_promisc to
|
||||
* prevent another VI stealing the traffic.
|
||||
*/
|
||||
bool mc_chaining;
|
||||
bool vlan_filter;
|
||||
struct list_head vlan_list;
|
||||
};
|
||||
|
||||
int efx_mcdi_filter_table_probe(struct efx_nic *efx);
|
||||
int efx_mcdi_filter_table_probe(struct efx_nic *efx, bool multicast_chaining);
|
||||
void efx_mcdi_filter_table_remove(struct efx_nic *efx);
|
||||
void efx_mcdi_filter_table_restore(struct efx_nic *efx);
|
||||
|
||||
void efx_mcdi_filter_table_reset_mc_allocations(struct efx_nic *efx);
|
||||
|
||||
/*
|
||||
* The filter table(s) are managed by firmware and we have write-only
|
||||
* access. When removing filters we must identify them to the
|
||||
|
@ -168,21 +168,18 @@ int efx_mcdi_tx_init(struct efx_tx_queue *tx_queue, bool tso_v2)
|
||||
size_t entries = tx_queue->txd.buf.len / EFX_BUF_SIZE;
|
||||
struct efx_channel *channel = tx_queue->channel;
|
||||
struct efx_nic *efx = tx_queue->efx;
|
||||
struct efx_ef10_nic_data *nic_data;
|
||||
dma_addr_t dma_addr;
|
||||
size_t inlen;
|
||||
int rc, i;
|
||||
|
||||
BUILD_BUG_ON(MC_CMD_INIT_TXQ_OUT_LEN != 0);
|
||||
|
||||
nic_data = efx->nic_data;
|
||||
|
||||
MCDI_SET_DWORD(inbuf, INIT_TXQ_IN_SIZE, tx_queue->ptr_mask + 1);
|
||||
MCDI_SET_DWORD(inbuf, INIT_TXQ_IN_TARGET_EVQ, channel->channel);
|
||||
MCDI_SET_DWORD(inbuf, INIT_TXQ_IN_LABEL, tx_queue->queue);
|
||||
MCDI_SET_DWORD(inbuf, INIT_TXQ_IN_INSTANCE, tx_queue->queue);
|
||||
MCDI_SET_DWORD(inbuf, INIT_TXQ_IN_OWNER_ID, 0);
|
||||
MCDI_SET_DWORD(inbuf, INIT_TXQ_IN_PORT_ID, nic_data->vport_id);
|
||||
MCDI_SET_DWORD(inbuf, INIT_TXQ_IN_PORT_ID, efx->vport_id);
|
||||
|
||||
dma_addr = tx_queue->txd.buf.dma_addr;
|
||||
|
||||
@ -276,7 +273,6 @@ void efx_mcdi_rx_init(struct efx_rx_queue *rx_queue)
|
||||
struct efx_channel *channel = efx_rx_queue_channel(rx_queue);
|
||||
size_t entries = rx_queue->rxd.buf.len / EFX_BUF_SIZE;
|
||||
struct efx_nic *efx = rx_queue->efx;
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
dma_addr_t dma_addr;
|
||||
size_t inlen;
|
||||
int rc;
|
||||
@ -295,7 +291,7 @@ void efx_mcdi_rx_init(struct efx_rx_queue *rx_queue)
|
||||
INIT_RXQ_IN_FLAG_PREFIX, 1,
|
||||
INIT_RXQ_IN_FLAG_TIMESTAMP, 1);
|
||||
MCDI_SET_DWORD(inbuf, INIT_RXQ_IN_OWNER_ID, 0);
|
||||
MCDI_SET_DWORD(inbuf, INIT_RXQ_IN_PORT_ID, nic_data->vport_id);
|
||||
MCDI_SET_DWORD(inbuf, INIT_RXQ_IN_PORT_ID, efx->vport_id);
|
||||
|
||||
dma_addr = rx_queue->rxd.buf.dma_addr;
|
||||
|
||||
|
@ -722,11 +722,8 @@ static int efx_mcdi_mac_stats(struct efx_nic *efx,
|
||||
MAC_STATS_IN_PERIOD_MS, period);
|
||||
MCDI_SET_DWORD(inbuf, MAC_STATS_IN_DMA_LEN, dma_len);
|
||||
|
||||
if (efx_nic_rev(efx) >= EFX_REV_HUNT_A0) {
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
|
||||
MCDI_SET_DWORD(inbuf, MAC_STATS_IN_PORT_ID, nic_data->vport_id);
|
||||
}
|
||||
if (efx_nic_rev(efx) >= EFX_REV_HUNT_A0)
|
||||
MCDI_SET_DWORD(inbuf, MAC_STATS_IN_PORT_ID, efx->vport_id);
|
||||
|
||||
rc = efx_mcdi_rpc_quiet(efx, MC_CMD_MAC_STATS, inbuf, sizeof(inbuf),
|
||||
NULL, 0, NULL);
|
||||
|
@ -887,8 +887,10 @@ struct efx_async_filter_insertion {
|
||||
* @rss_context: Main RSS context. Its @list member is the head of the list of
|
||||
* RSS contexts created by user requests
|
||||
* @rss_lock: Protects custom RSS context software state in @rss_context.list
|
||||
* @vport_id: The function's vport ID, only relevant for PFs
|
||||
* @int_error_count: Number of internal errors seen recently
|
||||
* @int_error_expire: Time at which error count will be expired
|
||||
* @must_realloc_vis: Flag: VIs have yet to be reallocated after MC reboot
|
||||
* @irq_soft_enabled: Are IRQs soft-enabled? If not, IRQ handler will
|
||||
* acknowledge but do nothing else.
|
||||
* @irq_status: Interrupt status buffer
|
||||
@ -1044,10 +1046,12 @@ struct efx_nic {
|
||||
bool rx_scatter;
|
||||
struct efx_rss_context rss_context;
|
||||
struct mutex rss_lock;
|
||||
u32 vport_id;
|
||||
|
||||
unsigned int_error_count;
|
||||
unsigned long int_error_expire;
|
||||
|
||||
bool must_realloc_vis;
|
||||
bool irq_soft_enabled;
|
||||
struct efx_buffer irq_status;
|
||||
unsigned irq_zero_count;
|
||||
@ -1292,6 +1296,7 @@ struct efx_udp_tunnel {
|
||||
* @udp_tnl_add_port: Add a UDP tunnel port
|
||||
* @udp_tnl_has_port: Check if a port has been added as UDP tunnel
|
||||
* @udp_tnl_del_port: Remove a UDP tunnel port
|
||||
* @print_additional_fwver: Dump NIC-specific additional FW version info
|
||||
* @revision: Hardware architecture revision
|
||||
* @txd_ptr_tbl_base: TX descriptor ring base address
|
||||
* @rxd_ptr_tbl_base: RX descriptor ring base address
|
||||
@ -1352,6 +1357,9 @@ struct efx_nic_type {
|
||||
void (*get_wol)(struct efx_nic *efx, struct ethtool_wolinfo *wol);
|
||||
int (*set_wol)(struct efx_nic *efx, u32 type);
|
||||
void (*resume_wol)(struct efx_nic *efx);
|
||||
unsigned int (*check_caps)(const struct efx_nic *efx,
|
||||
u8 flag,
|
||||
u32 offset);
|
||||
int (*test_chip)(struct efx_nic *efx, struct efx_self_tests *tests);
|
||||
int (*test_nvram)(struct efx_nic *efx);
|
||||
void (*mcdi_request)(struct efx_nic *efx,
|
||||
@ -1462,6 +1470,8 @@ struct efx_nic_type {
|
||||
int (*udp_tnl_add_port)(struct efx_nic *efx, struct efx_udp_tunnel tnl);
|
||||
bool (*udp_tnl_has_port)(struct efx_nic *efx, __be16 port);
|
||||
int (*udp_tnl_del_port)(struct efx_nic *efx, struct efx_udp_tunnel tnl);
|
||||
size_t (*print_additional_fwver)(struct efx_nic *efx, char *buf,
|
||||
size_t len);
|
||||
|
||||
int revision;
|
||||
unsigned int txd_ptr_tbl_base;
|
||||
|
@ -360,10 +360,6 @@ enum {
|
||||
* @warm_boot_count: Last seen MC warm boot count
|
||||
* @vi_base: Absolute index of first VI in this function
|
||||
* @n_allocated_vis: Number of VIs allocated to this function
|
||||
* @must_realloc_vis: Flag: VIs have yet to be reallocated after MC reboot
|
||||
* @must_restore_rss_contexts: Flag: RSS contexts have yet to be restored after
|
||||
* MC reboot
|
||||
* @must_restore_filters: Flag: filters have yet to be restored after MC reboot
|
||||
* @n_piobufs: Number of PIO buffers allocated to this function
|
||||
* @wc_membase: Base address of write-combining mapping of the memory BAR
|
||||
* @pio_write_base: Base address for writing PIO buffers
|
||||
@ -372,7 +368,6 @@ enum {
|
||||
* @piobuf_size: size of a single PIO buffer
|
||||
* @must_restore_piobufs: Flag: PIO buffers have yet to be restored after MC
|
||||
* reboot
|
||||
* @rx_rss_context_exclusive: Whether our RSS context is exclusive or shared
|
||||
* @stats: Hardware statistics
|
||||
* @workaround_35388: Flag: firmware supports workaround for bug 35388
|
||||
* @workaround_26807: Flag: firmware supports workaround for bug 26807
|
||||
@ -385,7 +380,6 @@ enum {
|
||||
* %MC_CMD_GET_CAPABILITIES response)
|
||||
* @rx_dpcpu_fw_id: Firmware ID of the RxDPCPU
|
||||
* @tx_dpcpu_fw_id: Firmware ID of the TxDPCPU
|
||||
* @vport_id: The function's vport ID, only relevant for PFs
|
||||
* @must_probe_vswitching: Flag: vswitching has yet to be setup after MC reboot
|
||||
* @pf_index: The number for this PF, or the parent PF if this is a VF
|
||||
#ifdef CONFIG_SFC_SRIOV
|
||||
@ -404,16 +398,12 @@ struct efx_ef10_nic_data {
|
||||
u16 warm_boot_count;
|
||||
unsigned int vi_base;
|
||||
unsigned int n_allocated_vis;
|
||||
bool must_realloc_vis;
|
||||
bool must_restore_rss_contexts;
|
||||
bool must_restore_filters;
|
||||
unsigned int n_piobufs;
|
||||
void __iomem *wc_membase, *pio_write_base;
|
||||
unsigned int pio_write_vi_base;
|
||||
unsigned int piobuf_handle[EF10_TX_PIOBUF_COUNT];
|
||||
u16 piobuf_size;
|
||||
bool must_restore_piobufs;
|
||||
bool rx_rss_context_exclusive;
|
||||
u64 stats[EF10_STAT_COUNT];
|
||||
bool workaround_35388;
|
||||
bool workaround_26807;
|
||||
@ -423,7 +413,6 @@ struct efx_ef10_nic_data {
|
||||
u32 datapath_caps2;
|
||||
unsigned int rx_dpcpu_fw_id;
|
||||
unsigned int tx_dpcpu_fw_id;
|
||||
unsigned int vport_id;
|
||||
bool must_probe_vswitching;
|
||||
unsigned int pf_index;
|
||||
u8 port_id[ETH_ALEN];
|
||||
|
@ -352,12 +352,7 @@ static int efx_phc_enable(struct ptp_clock_info *ptp,
|
||||
|
||||
bool efx_ptp_use_mac_tx_timestamps(struct efx_nic *efx)
|
||||
{
|
||||
struct efx_ef10_nic_data *nic_data = efx->nic_data;
|
||||
|
||||
return ((efx_nic_rev(efx) >= EFX_REV_HUNT_A0) &&
|
||||
(nic_data->datapath_caps2 &
|
||||
(1 << MC_CMD_GET_CAPABILITIES_V2_OUT_TX_MAC_TIMESTAMPING_LBN)
|
||||
));
|
||||
return efx_has_cap(efx, TX_MAC_TIMESTAMPING, FLAGS2);
|
||||
}
|
||||
|
||||
/* PTP 'extra' channel is still a traffic channel, but we only create TX queues
|
||||
|
@ -948,6 +948,13 @@ fail:
|
||||
|
||||
#endif /* CONFIG_SFC_MTD */
|
||||
|
||||
unsigned int siena_check_caps(const struct efx_nic *efx,
|
||||
u8 flag, u32 offset)
|
||||
{
|
||||
/* Siena did not support MC_CMD_GET_CAPABILITIES */
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* Revision-dependent attributes used by efx.c and nic.c
|
||||
|
Loading…
Reference in New Issue
Block a user