mirror of
https://github.com/openwrt/openwrt.git
synced 2024-12-26 08:51:13 +00:00
327b6dbd98
Backport qca8k mdio improvement patch merged upstream, where we use eth packet when available to send mdio commands. This should improve speed and cause less load on the CPU. Signed-off-by: Ansuel Smith <ansuelsmth@gmail.com>
121 lines
3.6 KiB
Diff
121 lines
3.6 KiB
Diff
From 11fd667dac315ea3f2469961f6d2869271a46cae Mon Sep 17 00:00:00 2001
|
|
From: Vladimir Oltean <vladimir.oltean@nxp.com>
|
|
Date: Thu, 6 Jan 2022 01:11:17 +0200
|
|
Subject: [PATCH 6/6] net: dsa: setup master before ports
|
|
|
|
It is said that as soon as a network interface is registered, all its
|
|
resources should have already been prepared, so that it is available for
|
|
sending and receiving traffic. One of the resources needed by a DSA
|
|
slave interface is the master.
|
|
|
|
dsa_tree_setup
|
|
-> dsa_tree_setup_ports
|
|
-> dsa_port_setup
|
|
-> dsa_slave_create
|
|
-> register_netdevice
|
|
-> dsa_tree_setup_master
|
|
-> dsa_master_setup
|
|
-> sets up master->dsa_ptr, which enables reception
|
|
|
|
Therefore, there is a short period of time after register_netdevice()
|
|
during which the master isn't prepared to pass traffic to the DSA layer
|
|
(master->dsa_ptr is checked by eth_type_trans). Same thing during
|
|
unregistration, there is a time frame in which packets might be missed.
|
|
|
|
Note that this change opens us to another race: dsa_master_find_slave()
|
|
will get invoked potentially earlier than the slave creation, and later
|
|
than the slave deletion. Since dp->slave starts off as a NULL pointer,
|
|
the earlier calls aren't a problem, but the later calls are. To avoid
|
|
use-after-free, we should zeroize dp->slave before calling
|
|
dsa_slave_destroy().
|
|
|
|
In practice I cannot really test real life improvements brought by this
|
|
change, since in my systems, netdevice creation races with PHY autoneg
|
|
which takes a few seconds to complete, and that masks quite a few races.
|
|
Effects might be noticeable in a setup with fixed links all the way to
|
|
an external system.
|
|
|
|
Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com>
|
|
Signed-off-by: David S. Miller <davem@davemloft.net>
|
|
---
|
|
net/dsa/dsa2.c | 23 +++++++++++++----------
|
|
1 file changed, 13 insertions(+), 10 deletions(-)
|
|
|
|
diff --git a/net/dsa/dsa2.c b/net/dsa/dsa2.c
|
|
index ea0f02a24b8b..3d21521453fe 100644
|
|
--- a/net/dsa/dsa2.c
|
|
+++ b/net/dsa/dsa2.c
|
|
@@ -561,6 +561,7 @@ static void dsa_port_teardown(struct dsa_port *dp)
|
|
struct devlink_port *dlp = &dp->devlink_port;
|
|
struct dsa_switch *ds = dp->ds;
|
|
struct dsa_mac_addr *a, *tmp;
|
|
+ struct net_device *slave;
|
|
|
|
if (!dp->setup)
|
|
return;
|
|
@@ -582,9 +583,11 @@ static void dsa_port_teardown(struct dsa_port *dp)
|
|
dsa_port_link_unregister_of(dp);
|
|
break;
|
|
case DSA_PORT_TYPE_USER:
|
|
- if (dp->slave) {
|
|
- dsa_slave_destroy(dp->slave);
|
|
+ slave = dp->slave;
|
|
+
|
|
+ if (slave) {
|
|
dp->slave = NULL;
|
|
+ dsa_slave_destroy(slave);
|
|
}
|
|
break;
|
|
}
|
|
@@ -1134,17 +1137,17 @@ static int dsa_tree_setup(struct dsa_switch_tree *dst)
|
|
if (err)
|
|
goto teardown_cpu_ports;
|
|
|
|
- err = dsa_tree_setup_ports(dst);
|
|
+ err = dsa_tree_setup_master(dst);
|
|
if (err)
|
|
goto teardown_switches;
|
|
|
|
- err = dsa_tree_setup_master(dst);
|
|
+ err = dsa_tree_setup_ports(dst);
|
|
if (err)
|
|
- goto teardown_ports;
|
|
+ goto teardown_master;
|
|
|
|
err = dsa_tree_setup_lags(dst);
|
|
if (err)
|
|
- goto teardown_master;
|
|
+ goto teardown_ports;
|
|
|
|
dst->setup = true;
|
|
|
|
@@ -1152,10 +1155,10 @@ static int dsa_tree_setup(struct dsa_switch_tree *dst)
|
|
|
|
return 0;
|
|
|
|
-teardown_master:
|
|
- dsa_tree_teardown_master(dst);
|
|
teardown_ports:
|
|
dsa_tree_teardown_ports(dst);
|
|
+teardown_master:
|
|
+ dsa_tree_teardown_master(dst);
|
|
teardown_switches:
|
|
dsa_tree_teardown_switches(dst);
|
|
teardown_cpu_ports:
|
|
@@ -1173,10 +1176,10 @@ static void dsa_tree_teardown(struct dsa_switch_tree *dst)
|
|
|
|
dsa_tree_teardown_lags(dst);
|
|
|
|
- dsa_tree_teardown_master(dst);
|
|
-
|
|
dsa_tree_teardown_ports(dst);
|
|
|
|
+ dsa_tree_teardown_master(dst);
|
|
+
|
|
dsa_tree_teardown_switches(dst);
|
|
|
|
dsa_tree_teardown_cpu_ports(dst);
|
|
--
|
|
2.34.1
|
|
|