Skip to content

Commit 8fd3635

Browse files
vladimirolteankuba-moo
authored andcommitted
net: dsa: fix panic on shutdown if multi-chip tree failed to probe
DSA probing is atypical because a tree of devices must probe all at once, so out of N switches which call dsa_tree_setup_routing_table() during probe, for (N - 1) of them, "complete" will return false and they will exit probing early. The Nth switch will set up the whole tree on their behalf. The implication is that for (N - 1) switches, the driver binds to the device successfully, without doing anything. When the driver is bound, the ->shutdown() method may run. But if the Nth switch has failed to initialize the tree, there is nothing to do for the (N - 1) driver instances, since the slave devices have not been created, etc. Moreover, dsa_switch_shutdown() expects that the calling @ds has been in fact initialized, so it jumps at dereferencing the various data structures, which is incorrect. Avoid the ensuing NULL pointer dereferences by simply checking whether the Nth switch has previously set "ds->setup = true" for the switch which is currently shutting down. The entire setup is serialized under dsa2_mutex which we already hold. Fixes: 0650bf5 ("net: dsa: be compatible with masters which unregister on shutdown") Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com> Link: https://lore.kernel.org/r/20220318195443.275026-1-vladimir.oltean@nxp.com Signed-off-by: Jakub Kicinski <kuba@kernel.org>
1 parent 60b44ca commit 8fd3635

1 file changed

Lines changed: 5 additions & 0 deletions

File tree

net/dsa/dsa2.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1722,6 +1722,10 @@ void dsa_switch_shutdown(struct dsa_switch *ds)
17221722
struct dsa_port *dp;
17231723

17241724
mutex_lock(&dsa2_mutex);
1725+
1726+
if (!ds->setup)
1727+
goto out;
1728+
17251729
rtnl_lock();
17261730

17271731
dsa_switch_for_each_user_port(dp, ds) {
@@ -1738,6 +1742,7 @@ void dsa_switch_shutdown(struct dsa_switch *ds)
17381742
dp->master->dsa_ptr = NULL;
17391743

17401744
rtnl_unlock();
1745+
out:
17411746
mutex_unlock(&dsa2_mutex);
17421747
}
17431748
EXPORT_SYMBOL_GPL(dsa_switch_shutdown);

0 commit comments

Comments
 (0)