aboutsummaryrefslogtreecommitdiffstats
path: root/target/linux/generic/backport-5.10/765-v5.12-net-dsa-automatically-bring-up-DSA-master-when-openi.patch
diff options
context:
space:
mode:
Diffstat (limited to 'target/linux/generic/backport-5.10/765-v5.12-net-dsa-automatically-bring-up-DSA-master-when-openi.patch')
-rw-r--r--target/linux/generic/backport-5.10/765-v5.12-net-dsa-automatically-bring-up-DSA-master-when-openi.patch85
1 files changed, 85 insertions, 0 deletions
diff --git a/target/linux/generic/backport-5.10/765-v5.12-net-dsa-automatically-bring-up-DSA-master-when-openi.patch b/target/linux/generic/backport-5.10/765-v5.12-net-dsa-automatically-bring-up-DSA-master-when-openi.patch
new file mode 100644
index 0000000000..3b630377f9
--- /dev/null
+++ b/target/linux/generic/backport-5.10/765-v5.12-net-dsa-automatically-bring-up-DSA-master-when-openi.patch
@@ -0,0 +1,85 @@
+From 9d5ef190e5615a7b63af89f88c4106a5bc127974 Mon Sep 17 00:00:00 2001
+From: Vladimir Oltean <vladimir.oltean@nxp.com>
+Date: Fri, 5 Feb 2021 15:37:10 +0200
+Subject: [PATCH] net: dsa: automatically bring up DSA master when opening user
+ port
+
+DSA wants the master interface to be open before the user port is due to
+historical reasons. The promiscuity of interfaces that are down used to
+have issues, as referenced Lennert Buytenhek in commit df02c6ff2e39
+("dsa: fix master interface allmulti/promisc handling").
+
+The bugfix mentioned there, commit b6c40d68ff64 ("net: only invoke
+dev->change_rx_flags when device is UP"), was basically a "don't do
+that" approach to working around the promiscuity while down issue.
+
+Further work done by Vlad Yasevich in commit d2615bf45069 ("net: core:
+Always propagate flag changes to interfaces") has resolved the
+underlying issue, and it is strictly up to the DSA and 8021q drivers
+now, it is no longer mandated by the networking core that the master
+interface must be up when changing its promiscuity.
+
+From DSA's point of view, deciding to error out in dsa_slave_open
+because the master isn't up is
+(a) a bad user experience and
+(b) knocking at an open door.
+Even if there still was an issue with promiscuity while down, DSA could
+still just open the master and avoid it.
+
+Doing it this way has the additional benefit that user space can now
+remove DSA-specific workarounds, like systemd-networkd with BindCarrier:
+https://github.com/systemd/systemd/issues/7478
+
+And we can finally remove one of the 2 bullets in the "Common pitfalls
+using DSA setups" chapter.
+
+Tested with two cascaded DSA switches:
+
+$ ip link set sw0p2 up
+fsl_enetc 0000:00:00.2 eno2: configuring for fixed/internal link mode
+fsl_enetc 0000:00:00.2 eno2: Link is Up - 1Gbps/Full - flow control rx/tx
+mscc_felix 0000:00:00.5 swp0: configuring for fixed/sgmii link mode
+mscc_felix 0000:00:00.5 swp0: Link is Up - 1Gbps/Full - flow control off
+8021q: adding VLAN 0 to HW filter on device swp0
+sja1105 spi2.0 sw0p2: configuring for phy/rgmii-id link mode
+IPv6: ADDRCONF(NETDEV_CHANGE): eno2: link becomes ready
+IPv6: ADDRCONF(NETDEV_CHANGE): swp0: link becomes ready
+
+Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com>
+Reviewed-by: Andrew Lunn <andrew@lunn.ch>
+Reviewed-by: Florian Fainelli <f.fainelli@gmail.com>
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+---
+ Documentation/networking/dsa/dsa.rst | 4 ----
+ net/dsa/slave.c | 7 +++++--
+ 2 files changed, 5 insertions(+), 6 deletions(-)
+
+--- a/Documentation/networking/dsa/dsa.rst
++++ b/Documentation/networking/dsa/dsa.rst
+@@ -273,10 +273,6 @@ will not make us go through the switch t
+ the Ethernet switch on the other end, expecting a tag will typically drop this
+ frame.
+
+-Slave network devices check that the master network device is UP before allowing
+-you to administratively bring UP these slave network devices. A common
+-configuration mistake is forgetting to bring UP the master network device first.
+-
+ Interactions with other subsystems
+ ==================================
+
+--- a/net/dsa/slave.c
++++ b/net/dsa/slave.c
+@@ -68,8 +68,11 @@ static int dsa_slave_open(struct net_dev
+ struct dsa_port *dp = dsa_slave_to_port(dev);
+ int err;
+
+- if (!(master->flags & IFF_UP))
+- return -ENETDOWN;
++ err = dev_open(master, NULL);
++ if (err < 0) {
++ netdev_err(dev, "failed to open master %s\n", master->name);
++ goto out;
++ }
+
+ if (!ether_addr_equal(dev->dev_addr, master->dev_addr)) {
+ err = dev_uc_add(master, dev->dev_addr);