sfc:On MCDI timeout, issue an FLR (and mark MCDI to fail-fast)
When an MCDI command times out (whether or not we find it completed when we poll), call efx_mcdi_abandon(), which tells all subsequent MCDI calls to fail-fast, and queues up an FLR. Because an FLR doesn't lead to receiving any reboot even from the MC (unlike most other types of reset), we have to call efx_ef10_reset_mc_allocations. In efx_start_all(), if a reset (of any kind) is pending, we bail out. Without this, attempts to reconfigure (e.g. change mtu) can cause driver/mc state inconsistency if the first MCDI call triggers an FLR. For similar reasons, on EF10, in efx_reset_down(method=RESET_TYPE_MCDI_TIMEOUT), set the number of active queues to zero before calling efx_stop_all(). And, on farch, in efx_reset_up(method=RESET_TYPE_MCDI_TIMEOUT), set active_queues and flushes pending & outstanding to zero. efx_mcdi_mode_{poll,event}() should not take us out of fail-fast mode. Instead, this is done by efx_mcdi_reset() after the FLR completes. The new FLR reset_type RESET_TYPE_MCDI_TIMEOUT doesn't really fit into the hierarchy of reset 'scopes' whereby efx_reset() decides some resets subsume others. Thus, it uses separate logic. Also, fixed up some inconsistency around RESET_TYPE_MC_BIST, which was in the wrong place in that hierarchy. Signed-off-by: Shradha Shah <sshah@solarflare.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:

committed by
David S. Miller

parent
10ec34fcb1
commit
e283546c04
@@ -738,8 +738,11 @@ static int efx_ef10_reset(struct efx_nic *efx, enum reset_type reset_type)
|
||||
/* If it was a port reset, trigger reallocation of MC resources.
|
||||
* Note that on an MC reset nothing needs to be done now because we'll
|
||||
* detect the MC reset later and handle it then.
|
||||
* For an FLR, we never get an MC reset event, but the MC has reset all
|
||||
* resources assigned to us, so we have to trigger reallocation now.
|
||||
*/
|
||||
if (reset_type == RESET_TYPE_ALL && !rc)
|
||||
if ((reset_type == RESET_TYPE_ALL ||
|
||||
reset_type == RESET_TYPE_MCDI_TIMEOUT) && !rc)
|
||||
efx_ef10_reset_mc_allocations(efx);
|
||||
return rc;
|
||||
}
|
||||
@@ -2141,6 +2144,11 @@ static int efx_ef10_fini_dmaq(struct efx_nic *efx)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void efx_ef10_prepare_flr(struct efx_nic *efx)
|
||||
{
|
||||
atomic_set(&efx->active_queues, 0);
|
||||
}
|
||||
|
||||
static bool efx_ef10_filter_equal(const struct efx_filter_spec *left,
|
||||
const struct efx_filter_spec *right)
|
||||
{
|
||||
@@ -3603,6 +3611,8 @@ const struct efx_nic_type efx_hunt_a0_nic_type = {
|
||||
.probe_port = efx_mcdi_port_probe,
|
||||
.remove_port = efx_mcdi_port_remove,
|
||||
.fini_dmaq = efx_ef10_fini_dmaq,
|
||||
.prepare_flr = efx_ef10_prepare_flr,
|
||||
.finish_flr = efx_port_dummy_op_void,
|
||||
.describe_stats = efx_ef10_describe_stats,
|
||||
.update_stats = efx_ef10_update_stats,
|
||||
.start_stats = efx_mcdi_mac_start_stats,
|
||||
|
Reference in New Issue
Block a user