[PATCH net-next 09/17] net: dsa: Split up creating/destroying of DSA and CPU ports

2016-06-03 Thread Andrew Lunn
Refactor the code to setup a single DSA/CPU port into a function of
its own, and export it, so it can be used by the new binding.

Similarly, refactor the destroy code into a function.  When destroying
the ports, don't put the of node. They should be released at the end
along with the normal ports.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
rfc->v1:
* Extend commit message with comment about wrong of_node_put()
* Fix destroy of cpu and dsa ports.
---
 net/dsa/dsa.c  | 86 --
 net/dsa/dsa_priv.h |  3 ++
 2 files changed, 54 insertions(+), 35 deletions(-)

diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index bfe1d03d4730..7140de475c07 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -180,36 +180,47 @@ __ATTRIBUTE_GROUPS(dsa_hwmon);
 #endif /* CONFIG_NET_DSA_HWMON */
 
 /* basic switch operations **/
-static int dsa_cpu_dsa_setup(struct dsa_switch *ds, struct net_device *master)
+int dsa_cpu_dsa_setup(struct dsa_switch *ds, struct device *dev,
+ struct device_node *port_dn, int port)
 {
-   struct device_node *port_dn;
struct phy_device *phydev;
-   int ret, port, mode;
+   int ret, mode;
+
+   if (of_phy_is_fixed_link(port_dn)) {
+   ret = of_phy_register_fixed_link(port_dn);
+   if (ret) {
+   dev_err(dev, "failed to register fixed PHY\n");
+   return ret;
+   }
+   phydev = of_phy_find_device(port_dn);
+
+   mode = of_get_phy_mode(port_dn);
+   if (mode < 0)
+   mode = PHY_INTERFACE_MODE_NA;
+   phydev->interface = mode;
+
+   genphy_config_init(phydev);
+   genphy_read_status(phydev);
+   if (ds->drv->adjust_link)
+   ds->drv->adjust_link(ds, port, phydev);
+   }
+
+   return 0;
+}
+
+static int dsa_cpu_dsa_setups(struct dsa_switch *ds, struct device *dev)
+{
+   struct device_node *port_dn;
+   int ret, port;
 
for (port = 0; port < DSA_MAX_PORTS; port++) {
if (!(dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port)))
continue;
 
port_dn = ds->ports[port].dn;
-   if (of_phy_is_fixed_link(port_dn)) {
-   ret = of_phy_register_fixed_link(port_dn);
-   if (ret) {
-   netdev_err(master,
-  "failed to register fixed PHY\n");
-   return ret;
-   }
-   phydev = of_phy_find_device(port_dn);
-
-   mode = of_get_phy_mode(port_dn);
-   if (mode < 0)
-   mode = PHY_INTERFACE_MODE_NA;
-   phydev->interface = mode;
-
-   genphy_config_init(phydev);
-   genphy_read_status(phydev);
-   if (ds->drv->adjust_link)
-   ds->drv->adjust_link(ds, port, phydev);
-   }
+   ret = dsa_cpu_dsa_setup(ds, dev, port_dn, port);
+   if (ret)
+   return ret;
}
return 0;
 }
@@ -340,7 +351,7 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
}
 
/* Perform configuration of the CPU and DSA ports */
-   ret = dsa_cpu_dsa_setup(ds, dst->master_netdev);
+   ret = dsa_cpu_dsa_setups(ds, parent);
if (ret < 0) {
netdev_err(dst->master_netdev, "[%d] : can't configure CPU and 
DSA ports\n",
   index);
@@ -423,10 +434,21 @@ dsa_switch_setup(struct dsa_switch_tree *dst, int index,
return ds;
 }
 
-static void dsa_switch_destroy(struct dsa_switch *ds)
+void dsa_cpu_dsa_destroy(struct device_node *port_dn)
 {
-   struct device_node *port_dn;
struct phy_device *phydev;
+
+   if (of_phy_is_fixed_link(port_dn)) {
+   phydev = of_phy_find_device(port_dn);
+   if (phydev) {
+   phy_device_free(phydev);
+   fixed_phy_unregister(phydev);
+   }
+   }
+}
+
+static void dsa_switch_destroy(struct dsa_switch *ds)
+{
int port;
 
 #ifdef CONFIG_NET_DSA_HWMON
@@ -445,17 +467,11 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
dsa_slave_destroy(ds->ports[port].netdev);
}
 
-   /* Remove any fixed link PHYs */
+   /* Disable configuration of the CPU and DSA ports */
for (port = 0; port < DSA_MAX_PORTS; port++) {
-   port_dn = ds->ports[port].dn;
-   if (of_phy_is_fixed_link(port_dn)) {
-   phydev = of_phy_find_dev

[PATCH net-next 12/17] net: dsa: Make mdio bus optional

2016-06-03 Thread Andrew Lunn
The switch may want to instantiate its own MDIO bus. Only do it
centrally if the switch has not already created one, and the read op
is implemented.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 net/dsa/dsa.c | 24 +---
 1 file changed, 13 insertions(+), 11 deletions(-)

diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 221ebde4318d..6c314f300424 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -340,17 +340,18 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
if (ret < 0)
goto out;
 
-   ds->slave_mii_bus = devm_mdiobus_alloc(parent);
-   if (ds->slave_mii_bus == NULL) {
-   ret = -ENOMEM;
-   goto out;
-   }
-   dsa_slave_mii_bus_init(ds);
-
-   ret = mdiobus_register(ds->slave_mii_bus);
-   if (ret < 0)
-   goto out;
+   if (!ds->slave_mii_bus && drv->phy_read) {
+   ds->slave_mii_bus = devm_mdiobus_alloc(parent);
+   if (!ds->slave_mii_bus) {
+   ret = -ENOMEM;
+   goto out;
+   }
+   dsa_slave_mii_bus_init(ds);
 
+   ret = mdiobus_register(ds->slave_mii_bus);
+   if (ret < 0)
+   goto out;
+   }
 
/*
 * Create network devices for physical switch ports.
@@ -493,7 +494,8 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
dsa_cpu_dsa_destroy(ds->ports[port].dn);
}
 
-   mdiobus_unregister(ds->slave_mii_bus);
+   if (ds->slave_mii_bus && ds->drv->phy_read)
+   mdiobus_unregister(ds->slave_mii_bus);
 }
 
 #ifdef CONFIG_PM_SLEEP
-- 
2.8.1



[PATCH net-next 11/17] net: dsa: Refactor selection of tag ops into a function

2016-06-03 Thread Andrew Lunn
Replace the two switch statements with an array lookup, and store the
result in the dsa tree structure. The drivers no longer need to know
the selected tag protocol, so remove it from the dsa switch structure.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
rfc->v1:
Rename _DSA_TAG_LAST to DSA_TAG_LAST and add a comment.
---
 include/net/dsa.h  |  8 +-
 net/dsa/dsa.c  | 71 ++
 net/dsa/dsa_priv.h |  1 +
 net/dsa/slave.c| 35 +--
 4 files changed, 54 insertions(+), 61 deletions(-)

diff --git a/include/net/dsa.h b/include/net/dsa.h
index a306a17b7f2e..11e8f09d32e3 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -26,6 +26,7 @@ enum dsa_tag_protocol {
DSA_TAG_PROTO_TRAILER,
DSA_TAG_PROTO_EDSA,
DSA_TAG_PROTO_BRCM,
+   DSA_TAG_LAST,   /* MUST BE LAST */
 };
 
 #define DSA_MAX_SWITCHES   4
@@ -99,7 +100,6 @@ struct dsa_switch_tree {
   struct net_device *dev,
   struct packet_type *pt,
   struct net_device *orig_dev);
-   enum dsa_tag_protocol   tag_protocol;
 
/*
 * Original copy of the master netdev ethtool_ops
@@ -116,6 +116,12 @@ struct dsa_switch_tree {
 * Data for the individual switch chips.
 */
struct dsa_switch   *ds[DSA_MAX_SWITCHES];
+
+   /*
+* Tagging protocol operations for adding and removing an
+* encapsulation tag.
+*/
+   const struct dsa_device_ops *tag_ops;
 };
 
 struct dsa_port {
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 7140de475c07..221ebde4318d 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -29,6 +29,33 @@
 
 char dsa_driver_version[] = "0.1";
 
+static struct sk_buff *dsa_slave_notag_xmit(struct sk_buff *skb,
+   struct net_device *dev)
+{
+   /* Just return the original SKB */
+   return skb;
+}
+
+static const struct dsa_device_ops none_ops = {
+   .xmit   = dsa_slave_notag_xmit,
+   .rcv= NULL,
+};
+
+const struct dsa_device_ops *dsa_device_ops[DSA_TAG_LAST] = {
+#ifdef CONFIG_NET_DSA_TAG_DSA
+   [DSA_TAG_PROTO_DSA] = _netdev_ops,
+#endif
+#ifdef CONFIG_NET_DSA_TAG_EDSA
+   [DSA_TAG_PROTO_EDSA] = _netdev_ops,
+#endif
+#ifdef CONFIG_NET_DSA_TAG_TRAILER
+   [DSA_TAG_PROTO_TRAILER] = _netdev_ops,
+#endif
+#ifdef CONFIG_NET_DSA_TAG_BRCM
+   [DSA_TAG_PROTO_BRCM] = _netdev_ops,
+#endif
+   [DSA_TAG_PROTO_NONE] = _ops,
+};
 
 /* switch driver registration ***/
 static DEFINE_MUTEX(dsa_switch_drivers_mutex);
@@ -225,6 +252,20 @@ static int dsa_cpu_dsa_setups(struct dsa_switch *ds, 
struct device *dev)
return 0;
 }
 
+const struct dsa_device_ops *dsa_resolve_tag_protocol(int tag_protocol)
+{
+   const struct dsa_device_ops *ops;
+
+   if (tag_protocol >= DSA_TAG_LAST)
+   return ERR_PTR(-EINVAL);
+   ops = dsa_device_ops[tag_protocol];
+
+   if (!ops)
+   return ERR_PTR(-ENOPROTOOPT);
+
+   return ops;
+}
+
 static int dsa_switch_setup_one(struct dsa_switch *ds, struct device *parent)
 {
struct dsa_switch_driver *drv = ds->drv;
@@ -277,35 +318,13 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
 * switch.
 */
if (dst->cpu_switch == index) {
-   switch (drv->tag_protocol) {
-#ifdef CONFIG_NET_DSA_TAG_DSA
-   case DSA_TAG_PROTO_DSA:
-   dst->rcv = dsa_netdev_ops.rcv;
-   break;
-#endif
-#ifdef CONFIG_NET_DSA_TAG_EDSA
-   case DSA_TAG_PROTO_EDSA:
-   dst->rcv = edsa_netdev_ops.rcv;
-   break;
-#endif
-#ifdef CONFIG_NET_DSA_TAG_TRAILER
-   case DSA_TAG_PROTO_TRAILER:
-   dst->rcv = trailer_netdev_ops.rcv;
-   break;
-#endif
-#ifdef CONFIG_NET_DSA_TAG_BRCM
-   case DSA_TAG_PROTO_BRCM:
-   dst->rcv = brcm_netdev_ops.rcv;
-   break;
-#endif
-   case DSA_TAG_PROTO_NONE:
-   break;
-   default:
-   ret = -ENOPROTOOPT;
+   dst->tag_ops = dsa_resolve_tag_protocol(drv->tag_protocol);
+   if (IS_ERR(dst->tag_ops)) {
+   ret = PTR_ERR(dst->tag_ops);
goto out;
}
 
-   dst->tag_protocol = drv->tag_protocol;
+   dst->rcv = dst->tag_ops->rcv;
}
 
memcpy(ds->rtable, cd->rtable, sizeof(ds->rtable));
diff --git a/net/dsa/dsa_priv.h b/net/dsa/dsa_priv.h
index dbea5d9e7f75..72f7b8989cfb 100644
--- a/net/dsa/dsa_priv.h
+++ b/net/dsa/dsa_priv.h
@@ -53,6 +53,7 @@ extern 

Re: [PATCH v3 3/7] binding: mdio-mux: Add DT binding doc for Broadcom MDIO bus mutiplexer

2016-06-03 Thread Andrew Lunn
> +Properties for an MDIO bus mutiplexer found in Broadcom iProc based SoCs.
> +
> +This MDIO bus multiplexer defines buses that could be internal as well as
> +external to SoCs and could accept MDIO transaction compatible to C-22 or
> +C-45 Clause. When child bus is selected, one needs to select these two
> +properties as well to generate desired MDIO trascation on appropriate bus.
> +

nit pick: transactions

Reviewed-by: Andrew Lunn <and...@lunn.ch>

 Andrew


[PATCH net-next 13/17] net: dsa: mv88e6xxx: Rename _phy_ to _mdio_

2016-06-03 Thread Andrew Lunn
The switch implements a generic MDIO bus, which could host more than
PHYs. It is conventional to use _mdio_ or _mii_ in the function name,
so rename them. Also postfix make the historically first read/write
function with _direct, to help distinguish it from _indirect and _ppu.

While touching these functions, remove some of the _ prefixes, which
we are deprecating.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c | 126 ++--
 1 file changed, 63 insertions(+), 63 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 11845eccf670..b8e65e604f75 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -238,16 +238,16 @@ int mv88e6xxx_set_addr(struct dsa_switch *ds, u8 *addr)
return mv88e6xxx_set_addr_direct(ds, addr);
 }
 
-static int _mv88e6xxx_phy_read(struct mv88e6xxx_priv_state *ps, int addr,
-  int regnum)
+static int mv88e6xxx_mdio_read_direct(struct mv88e6xxx_priv_state *ps,
+ int addr, int regnum)
 {
if (addr >= 0)
return _mv88e6xxx_reg_read(ps, addr, regnum);
return 0x;
 }
 
-static int _mv88e6xxx_phy_write(struct mv88e6xxx_priv_state *ps, int addr,
-   int regnum, u16 val)
+static int mv88e6xxx_mdio_write_direct(struct mv88e6xxx_priv_state *ps,
+  int addr, int regnum, u16 val)
 {
if (addr >= 0)
return _mv88e6xxx_reg_write(ps, addr, regnum, val);
@@ -378,8 +378,8 @@ void mv88e6xxx_ppu_state_init(struct mv88e6xxx_priv_state 
*ps)
ps->ppu_timer.function = mv88e6xxx_ppu_reenable_timer;
 }
 
-static int mv88e6xxx_phy_read_ppu(struct mv88e6xxx_priv_state *ps, int addr,
- int regnum)
+static int mv88e6xxx_mdio_read_ppu(struct mv88e6xxx_priv_state *ps, int addr,
+  int regnum)
 {
int ret;
 
@@ -392,8 +392,8 @@ static int mv88e6xxx_phy_read_ppu(struct 
mv88e6xxx_priv_state *ps, int addr,
return ret;
 }
 
-static int mv88e6xxx_phy_write_ppu(struct mv88e6xxx_priv_state *ps, int addr,
-  int regnum, u16 val)
+static int mv88e6xxx_mdio_write_ppu(struct mv88e6xxx_priv_state *ps, int addr,
+   int regnum, u16 val)
 {
int ret;
 
@@ -829,7 +829,7 @@ static int mv88e6xxx_wait(struct mv88e6xxx_priv_state *ps, 
int reg,
return ret;
 }
 
-static int _mv88e6xxx_phy_wait(struct mv88e6xxx_priv_state *ps)
+static int mv88e6xxx_mdio_wait(struct mv88e6xxx_priv_state *ps)
 {
return _mv88e6xxx_wait(ps, REG_GLOBAL2, GLOBAL2_SMI_OP,
   GLOBAL2_SMI_OP_BUSY);
@@ -1076,7 +1076,7 @@ static int _mv88e6xxx_atu_wait(struct 
mv88e6xxx_priv_state *ps)
   GLOBAL_ATU_OP_BUSY);
 }
 
-static int _mv88e6xxx_phy_read_indirect(struct mv88e6xxx_priv_state *ps,
+static int mv88e6xxx_mdio_read_indirect(struct mv88e6xxx_priv_state *ps,
int addr, int regnum)
 {
int ret;
@@ -1087,7 +1087,7 @@ static int _mv88e6xxx_phy_read_indirect(struct 
mv88e6xxx_priv_state *ps,
if (ret < 0)
return ret;
 
-   ret = _mv88e6xxx_phy_wait(ps);
+   ret = mv88e6xxx_mdio_wait(ps);
if (ret < 0)
return ret;
 
@@ -1096,7 +1096,7 @@ static int _mv88e6xxx_phy_read_indirect(struct 
mv88e6xxx_priv_state *ps,
return ret;
 }
 
-static int _mv88e6xxx_phy_write_indirect(struct mv88e6xxx_priv_state *ps,
+static int mv88e6xxx_mdio_write_indirect(struct mv88e6xxx_priv_state *ps,
 int addr, int regnum, u16 val)
 {
int ret;
@@ -1109,7 +1109,7 @@ static int _mv88e6xxx_phy_write_indirect(struct 
mv88e6xxx_priv_state *ps,
   GLOBAL2_SMI_OP_22_WRITE | (addr << 5) |
   regnum);
 
-   return _mv88e6xxx_phy_wait(ps);
+   return mv88e6xxx_mdio_wait(ps);
 }
 
 static int mv88e6xxx_get_eee(struct dsa_switch *ds, int port,
@@ -1123,7 +1123,7 @@ static int mv88e6xxx_get_eee(struct dsa_switch *ds, int 
port,
 
mutex_lock(>smi_mutex);
 
-   reg = _mv88e6xxx_phy_read_indirect(ps, port, 16);
+   reg = mv88e6xxx_mdio_read_indirect(ps, port, 16);
if (reg < 0)
goto out;
 
@@ -1154,7 +1154,7 @@ static int mv88e6xxx_set_eee(struct dsa_switch *ds, int 
port,
 
mutex_lock(>smi_mutex);
 
-   ret = _mv88e6xxx_phy_read_indirect(ps, port, 16);
+   ret = mv88e6xxx_mdio_read_indirect(ps, port, 16);
if (ret < 0)
goto out;
 
@@ -1164,7 +1164,7 @@ static int mv88e6xxx_set_eee(struct dsa_switch *ds, int 
port,
if (e->tx_lpi_enabled)
reg |= 0x0100;
 
-   ret = _mv88e6xxx_phy_writ

[PATCH net-next 17/17] net: dsa: Document new binding

2016-06-03 Thread Andrew Lunn
Add the new binding to the documentation of the existing binding.
Mark the old binding as deprecated.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
Signed-off-by: Florian Fainelli <f.faine...@gmail.com>
---
 Documentation/devicetree/bindings/net/dsa/dsa.txt | 278 +-
 1 file changed, 276 insertions(+), 2 deletions(-)

diff --git a/Documentation/devicetree/bindings/net/dsa/dsa.txt 
b/Documentation/devicetree/bindings/net/dsa/dsa.txt
index 9f4807f90c31..8c9e1b80cb65 100644
--- a/Documentation/devicetree/bindings/net/dsa/dsa.txt
+++ b/Documentation/devicetree/bindings/net/dsa/dsa.txt
@@ -1,5 +1,279 @@
-Marvell Distributed Switch Architecture Device Tree Bindings
-
+Distributed Switch Architecture Device Tree Bindings
+
+
+Two bindings exist, one of which has been deprecated due to
+limitations.
+
+Current Binding
+---
+
+Switches are true Linux devices and can be probes by any means. Once
+probed, they register to the DSA framework, passing a node
+pointer. This node is expected to fulfil the following binding, and
+may contain additional properties as required by the device it is
+embedded within.
+
+Required properties:
+
+- ports: A container for child nodes representing switch ports.
+
+Optional properties:
+
+- dsa,member   : A two element list indicates which DSA cluster, and position
+ within the cluster a switch takes. <0 0> is cluster 0,
+ switch 0. <0 1> is cluster 0, switch 1. <1 0> is cluster 1,
+ switch 0. A switch not part of any cluster (single device
+ hanging off a CPU port) must not specify this property
+
+The ports container has the following properties
+
+Required properties:
+
+- #address-cells   : Must be 1
+- #size-cells  : Must be 0
+
+Each port children node must have the following mandatory properties:
+- reg  : Describes the port address in the switch
+- label: Describes the label associated with this 
port, which
+  will become the netdev name. Special labels are
+ "cpu" to indicate a CPU port and "dsa" to
+ indicate an uplink/downlink port between switches in
+ the cluster.
+
+A port labelled "dsa" has the following mandatory property:
+
+- link : Should be a list of phandles to other switch's DSA
+ port. This port is used as the outgoing port
+ towards the phandle ports. The full routing
+ information must be given, not just the one hop
+ routes to neighbouring switches.
+
+A port labelled "cpu" has the following mandatory property:
+
+- ethernet : Should be a phandle to a valid Ethernet device node.
+  This host device is what the switch port is
+ connected to.
+
+Port child nodes may also contain the following optional standardised
+properties, described in binding documents:
+
+- phy-handle   : Phandle to a PHY on an MDIO bus. See
+ Documentation/devicetree/bindings/net/ethernet.txt
+ for details.
+
+- phy-mode : See
+ Documentation/devicetree/bindings/net/ethernet.txt
+ for details.
+
+- fixed-link   : Fixed-link subnode describing a link to a non-MDIO
+ managed entity. See
+ Documentation/devicetree/bindings/net/fixed-link.txt
+ for details.
+
+Example
+
+The following example shows three switches on three MDIO busses,
+linked into one DSA cluster.
+
+ {
+   #address-cells = <1>;
+   #size-cells = <0>;
+
+   switch0: switch0@0 {
+   compatible = "marvell,mv88e6085";
+   #address-cells = <1>;
+   #size-cells = <0>;
+   reg = <0>;
+
+   dsa,member = <0 0>;
+
+   ports {
+   #address-cells = <1>;
+   #size-cells = <0>;
+   port@0 {
+   reg = <0>;
+   label = "lan0";
+   };
+
+   port@1 {
+   reg = <1>;
+   label = "lan1";
+   };
+
+   port@2 {
+   reg = <2>;
+   label = "lan2";
+   };
+
+   switch0port5: port@5 {
+  

[PATCH net-next 02/17] net: dsa: mv88e6xxx: fix circular lock in PPU work

2016-06-03 Thread Andrew Lunn
From: Vivien Didelot 

Lock debugging shows that there is a possible circular lock in the PPU
work code. Switch the lock order of smi_mutex and ppu_mutex to fix this.

Here's the full trace:

[4.341325] ==
[4.347519] [ INFO: possible circular locking dependency detected ]
[4.353800] 4.6.0 #4 Not tainted
[4.357039] ---
[4.363315] kworker/0:1/328 is trying to acquire lock:
[4.368463]  (>smi_mutex){+.+.+.}, at: [<8049c758>] 
mv88e6xxx_reg_read+0x30/0x54
[4.376313]
[4.376313] but task is already holding lock:
[4.382160]  (>ppu_mutex){+.+...}, at: [<8049cac0>] 
mv88e6xxx_ppu_reenable_work+0x28/0xd4
[4.390772]
[4.390772] which lock already depends on the new lock.
[4.390772]
[4.398963]
[4.398963] the existing dependency chain (in reverse order) is:
[4.406461]
[4.406461] -> #1 (>ppu_mutex){+.+...}:
[4.410897][<806d86bc>] mutex_lock_nested+0x54/0x360
[4.416606][<8049a800>] mv88e6xxx_ppu_access_get+0x28/0x100
[4.422906][<8049b778>] mv88e6xxx_phy_read+0x90/0xdc
[4.428599][<806a4534>] dsa_slave_phy_read+0x3c/0x40
[4.434300][<804943ec>] mdiobus_read+0x68/0x80
[4.439481][<804939d4>] get_phy_device+0x58/0x1d8
[4.444914][<80493ed0>] mdiobus_scan+0x24/0xf4
[4.450078][<8049409c>] __mdiobus_register+0xfc/0x1ac
[4.455857][<806a40b0>] dsa_probe+0x860/0xca8
[4.460934][<8043246c>] platform_drv_probe+0x5c/0xc0
[4.466627][<804305a0>] driver_probe_device+0x118/0x450
[4.472589][<80430b00>] __device_attach_driver+0xac/0x128
[4.478724][<8042e350>] bus_for_each_drv+0x74/0xa8
[4.484235][<804302d8>] __device_attach+0xc4/0x154
[4.489755][<80430cec>] device_initial_probe+0x1c/0x20
[4.495612][<8042f620>] bus_probe_device+0x98/0xa0
[4.501123][<8042fbd0>] deferred_probe_work_func+0x4c/0xd4
[4.507328][<8013a794>] process_one_work+0x1a8/0x604
[4.513030][<8013ac54>] worker_thread+0x64/0x528
[4.518367][<801409e8>] kthread+0xec/0x100
[4.523201][<80108f30>] ret_from_fork+0x14/0x24
[4.528462]
[4.528462] -> #0 (>smi_mutex){+.+.+.}:
[4.532895][<8015ad5c>] lock_acquire+0xb4/0x1dc
[4.538154][<806d86bc>] mutex_lock_nested+0x54/0x360
[4.543856][<8049c758>] mv88e6xxx_reg_read+0x30/0x54
[4.549549][<8049cad8>] mv88e6xxx_ppu_reenable_work+0x40/0xd4
[4.556022][<8013a794>] process_one_work+0x1a8/0x604
[4.561707][<8013ac54>] worker_thread+0x64/0x528
[4.567053][<801409e8>] kthread+0xec/0x100
[4.571878][<80108f30>] ret_from_fork+0x14/0x24
[4.577139]
[4.577139] other info that might help us debug this:
[4.577139]
[4.585159]  Possible unsafe locking scenario:
[4.585159]
[4.591093]CPU0CPU1
[4.595631]
[4.600169]   lock(>ppu_mutex);
[4.603693]lock(>smi_mutex);
[4.609742]lock(>ppu_mutex);
[4.615790]   lock(>smi_mutex);
[4.619314]
[4.619314]  *** DEADLOCK ***
[4.619314]
[4.625256] 3 locks held by kworker/0:1/328:
[4.629537]  #0:  ("events"){.+.+..}, at: [<8013a704>] 
process_one_work+0x118/0x604
[4.637288]  #1:  ((>ppu_work)){+.+...}, at: [<8013a704>] 
process_one_work+0x118/0x604
[4.645653]  #2:  (>ppu_mutex){+.+...}, at: [<8049cac0>] 
mv88e6xxx_ppu_reenable_work+0x28/0xd4
[4.654714]
[4.654714] stack backtrace:
[4.659098] CPU: 0 PID: 328 Comm: kworker/0:1 Not tainted 4.6.0 #4
[4.665286] Hardware name: Freescale Vybrid VF5xx/VF6xx (Device Tree)
[4.671748] Workqueue: events mv88e6xxx_ppu_reenable_work
[4.677174] Backtrace:
[4.679674] [<8010d354>] (dump_backtrace) from [<8010d5a0>] 
(show_stack+0x20/0x24)
[4.687252]  r6:80fb3c88 r5:80fb3c88 r4:80fb4728 r3:0002
[4.693003] [<8010d580>] (show_stack) from [<803b45e8>] 
(dump_stack+0x24/0x28)
[4.700246] [<803b45c4>] (dump_stack) from [<80157398>] 
(print_circular_bug+0x208/0x32c)
[4.708361] [<80157190>] (print_circular_bug) from [<8015a630>] 
(__lock_acquire+0x185c/0x1b80)
[4.716982]  r10:9ec22a00 r9:0060 r8:8164b6bc r7:0040 
r6:0003 r5:8163a5b4
[4.724905]  r4:0003 r3:9ec22de8
[4.728537] [<80158dd4>] (__lock_acquire) from [<8015ad5c>] 
(lock_acquire+0xb4/0x1dc)
[4.736378]  r10:6013 

[PATCH net-next 10/17] net: dsa: mv88e6xxx: Only support EDSA tagging

2016-06-03 Thread Andrew Lunn
The merged driver no longer offers the option to use DSA tagging. So
remove the code to setup the switch to do DSA tagging and hard code
the use of EDSA.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c | 8 ++--
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 492801a6398c..11845eccf670 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -2725,11 +2725,8 @@ static int mv88e6xxx_setup_port(struct 
mv88e6xxx_priv_state *ps, int port)
if (mv88e6xxx_6352_family(ps) || mv88e6xxx_6351_family(ps) ||
mv88e6xxx_6165_family(ps) || mv88e6xxx_6097_family(ps) ||
mv88e6xxx_6320_family(ps)) {
-   if (ds->dst->tag_protocol == DSA_TAG_PROTO_EDSA)
-   reg |= PORT_CONTROL_FRAME_ETHER_TYPE_DSA;
-   else
-   reg |= PORT_CONTROL_FRAME_MODE_DSA;
-   reg |= PORT_CONTROL_FORWARD_UNKNOWN |
+   reg |= PORT_CONTROL_FRAME_ETHER_TYPE_DSA |
+   PORT_CONTROL_FORWARD_UNKNOWN |
PORT_CONTROL_FORWARD_UNKNOWN_MC;
}
 
@@ -2737,7 +2734,6 @@ static int mv88e6xxx_setup_port(struct 
mv88e6xxx_priv_state *ps, int port)
mv88e6xxx_6165_family(ps) || mv88e6xxx_6097_family(ps) ||
mv88e6xxx_6095_family(ps) || mv88e6xxx_6065_family(ps) ||
mv88e6xxx_6185_family(ps) || mv88e6xxx_6320_family(ps)) {
-   if (ds->dst->tag_protocol == DSA_TAG_PROTO_EDSA)
reg |= PORT_CONTROL_EGRESS_ADD_TAG;
}
}
-- 
2.8.1



[PATCH net-next 07/17] net: dsa: Remove dynamic allocate of routing table

2016-06-03 Thread Andrew Lunn
With a maximum of four switches, the size of the routing table is the
same as the pointer to it. Removing it makes the code simpler.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c |  3 +--
 include/net/dsa.h   |  9 -
 net/dsa/dsa.c   | 12 
 3 files changed, 5 insertions(+), 19 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 85332d9a245a..d622c0fb76cc 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -3024,8 +3024,7 @@ static int mv88e6xxx_setup_global(struct 
mv88e6xxx_priv_state *ps)
for (i = 0; i < 32; i++) {
int nexthop = 0x1f;
 
-   if (ps->ds->cd->rtable &&
-   i != ps->ds->index && i < ps->ds->dst->pd->nr_chips)
+   if (i != ps->ds->index && i < ps->ds->dst->pd->nr_chips)
nexthop = ps->ds->cd->rtable[i] & 0x1f;
 
err = _mv88e6xxx_reg_write(
diff --git a/include/net/dsa.h b/include/net/dsa.h
index 8314197d028f..4e3afa9648ca 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -58,12 +58,11 @@ struct dsa_chip_data {
struct device_node *port_dn[DSA_MAX_PORTS];
 
/*
-* An array (with nr_chips elements) of which element [a]
-* indicates which port on this switch should be used to
-* send packets to that are destined for switch a.  Can be
-* NULL if there is only one switch chip.
+* An array of which element [a] indicates which port on this
+* switch should be used to send packets to that are destined
+* for switch a. Can be NULL if there is only one switch chip.
 */
-   s8  *rtable;
+   s8  rtable[DSA_MAX_SWITCHES];
 };
 
 struct dsa_platform_data {
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 5907f8cd13b6..6177dd750847 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -587,17 +587,6 @@ static int dsa_of_setup_routing_table(struct 
dsa_platform_data *pd,
if (link_sw_addr >= pd->nr_chips)
return -EINVAL;
 
-   /* First time routing table allocation */
-   if (!cd->rtable) {
-   cd->rtable = kmalloc_array(pd->nr_chips, sizeof(s8),
-  GFP_KERNEL);
-   if (!cd->rtable)
-   return -ENOMEM;
-
-   /* default to no valid uplink/downlink */
-   memset(cd->rtable, -1, pd->nr_chips * sizeof(s8));
-   }
-
cd->rtable[link_sw_addr] = port_index;
 
return 0;
@@ -639,7 +628,6 @@ static void dsa_of_free_platform_data(struct 
dsa_platform_data *pd)
kfree(pd->chip[i].port_names[port_index]);
port_index++;
}
-   kfree(pd->chip[i].rtable);
 
/* Drop our reference to the MDIO bus device */
if (pd->chip[i].host_dev)
-- 
2.8.1



Re: [PATCH v3 5/7] net:mdio-mux: Add MDIO mux driver for iProc SoCs

2016-06-03 Thread Andrew Lunn
On Fri, Jun 03, 2016 at 08:56:06PM +0530, Pramod Kumar wrote:
> iProc based SoCs supports the integrated mdio multiplexer which
> has the bus selection as well as mdio transaction generation logic
> inside.
> 
> This mutiplexer has child buses for PCIe, SATA, USB and ETH. These

multiplexer 

> buses could be internal or external to SOC where PHYs are attached.
> These buses could use C-45 or C-22 mdio transaction.
> 
> Signed-off-by: Pramod Kumar 
> ---
>  drivers/net/phy/Kconfig  |  11 ++
>  drivers/net/phy/Makefile |   1 +
>  drivers/net/phy/mdio-mux-bcm-iproc.c | 246 
> +++
>  3 files changed, 258 insertions(+)
>  create mode 100644 drivers/net/phy/mdio-mux-bcm-iproc.c
> 
> diff --git a/drivers/net/phy/Kconfig b/drivers/net/phy/Kconfig
> index 6dad9a9..38faecf 100644
> --- a/drivers/net/phy/Kconfig
> +++ b/drivers/net/phy/Kconfig
> @@ -254,6 +254,17 @@ config MDIO_BUS_MUX_MMIOREG
>  
> Currently, only 8-bit registers are supported.
>  
> +config MDIO_BUS_MUX_BCM_IPROC
> + tristate "Support for iProc based MDIO bus multiplexers"
> + depends on OF && OF_MDIO && (ARCH_BCM_IPROC || COMPILE_TEST)
> + select MDIO_BUS_MUX
> + default ARCH_BCM_IPROC
> + help
> +   This module provides a driver for MDIO bus multiplexers found in
> +   iProc based Broadcom SoCs. This mulitplexer connects one of several

multiplexer


> +   child MDIO bus to a parent bus. Buses could be interal as well as

internal

Maybe you should turn on the spelling checker in your text editor?

> +static int start_miim_ops(void __iomem *base,
> +   u16 phyid, u32 reg, u16 val, u32 op)
> +{
> + u32 param;
> + int ret;
> +
> + writel(0, base + MDIO_CTRL_OFFSET);
> + ret = iproc_mdio_wait_for_idle(base, 0);
> + if (ret)
> + goto err;
> +
> + param = readl(base + MDIO_PARAM_OFFSET);
> + param |= phyid << MDIO_PARAM_PHY_ID;
> + param |= val << MDIO_PARAM_PHY_DATA;
> + if (reg & MII_ADDR_C45)
> + param |= (1 << MDIO_PARAM_C45_SEL);

You could use BIT(MDIO_PARAM_C45_SEL) here

> +static int mdio_mux_iproc_remove(struct platform_device *pdev)
> +{
> + struct iproc_mdiomux_desc *md = dev_get_platdata(>dev);
> +
> + mdio_mux_uninit(md->mux_handle);
> +
> + return 0;

You should unregister and free the parent MDIO device.

Andrew



[PATCH net-next 05/17] net: dsa: Add a ports structure and use it in the switch structure

2016-06-03 Thread Andrew Lunn
There are going to be more per-port members added to the switch
structure. So add a port structure and move the netdev into it.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/bcm_sf2.c   |  4 ++--
 drivers/net/dsa/mv88e6xxx.c | 27 ---
 include/net/dsa.h   |  8 ++--
 net/dsa/dsa.c   |  8 
 net/dsa/slave.c |  4 ++--
 net/dsa/tag_brcm.c  |  4 ++--
 net/dsa/tag_dsa.c   |  4 ++--
 net/dsa/tag_edsa.c  |  4 ++--
 net/dsa/tag_trailer.c   |  4 ++--
 9 files changed, 38 insertions(+), 29 deletions(-)

diff --git a/drivers/net/dsa/bcm_sf2.c b/drivers/net/dsa/bcm_sf2.c
index 10ddd5a5dfb6..73df91bb0466 100644
--- a/drivers/net/dsa/bcm_sf2.c
+++ b/drivers/net/dsa/bcm_sf2.c
@@ -804,7 +804,7 @@ static int bcm_sf2_sw_fdb_dump(struct dsa_switch *ds, int 
port,
   int (*cb)(struct switchdev_obj *obj))
 {
struct bcm_sf2_priv *priv = ds_to_priv(ds);
-   struct net_device *dev = ds->ports[port];
+   struct net_device *dev = ds->ports[port].netdev;
struct bcm_sf2_arl_entry results[2];
unsigned int count = 0;
int ret;
@@ -1248,7 +1248,7 @@ static void bcm_sf2_sw_fixed_link_update(struct 
dsa_switch *ds, int port,
 * state machine and make it go in PHY_FORCING state instead.
 */
if (!status->link)
-   netif_carrier_off(ds->ports[port]);
+   netif_carrier_off(ds->ports[port].netdev);
status->duplex = 1;
} else {
status->link = 1;
diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index c361036e7f9c..85332d9a245a 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -1327,7 +1327,7 @@ static int _mv88e6xxx_port_state(struct 
mv88e6xxx_priv_state *ps, int port,
if (ret)
return ret;
 
-   netdev_dbg(ds->ports[port], "PortState %s (was %s)\n",
+   netdev_dbg(ds->ports[port].netdev, "PortState %s (was %s)\n",
   mv88e6xxx_port_state_names[state],
   mv88e6xxx_port_state_names[oldstate]);
}
@@ -1405,7 +1405,8 @@ static void mv88e6xxx_port_stp_state_set(struct 
dsa_switch *ds, int port,
mutex_unlock(>smi_mutex);
 
if (err)
-   netdev_err(ds->ports[port], "failed to update state to %s\n",
+   netdev_err(ds->ports[port].netdev,
+  "failed to update state to %s\n",
   mv88e6xxx_port_state_names[stp_state]);
 }
 
@@ -1431,8 +1432,8 @@ static int _mv88e6xxx_port_pvid(struct 
mv88e6xxx_priv_state *ps, int port,
if (ret < 0)
return ret;
 
-   netdev_dbg(ds->ports[port], "DefaultVID %d (was %d)\n", *new,
-  pvid);
+   netdev_dbg(ds->ports[port].netdev,
+  "DefaultVID %d (was %d)\n", *new, pvid);
}
 
if (old)
@@ -1847,7 +1848,8 @@ static int _mv88e6xxx_port_fid(struct 
mv88e6xxx_priv_state *ps, int port,
if (ret < 0)
return ret;
 
-   netdev_dbg(ds->ports[port], "FID %d (was %d)\n", *new, fid);
+   netdev_dbg(ds->ports[port].netdev,
+  "FID %d (was %d)\n", *new, fid);
}
 
if (old)
@@ -2028,7 +2030,7 @@ static int mv88e6xxx_port_check_hw_vlan(struct dsa_switch 
*ds, int port,
ps->ports[port].bridge_dev)
break; /* same bridge, check next VLAN */
 
-   netdev_warn(ds->ports[port],
+   netdev_warn(ds->ports[port].netdev,
"hardware VLAN %d already used by %s\n",
vlan.vid,
netdev_name(ps->ports[i].bridge_dev));
@@ -2078,7 +2080,7 @@ static int mv88e6xxx_port_vlan_filtering(struct 
dsa_switch *ds, int port,
if (ret < 0)
goto unlock;
 
-   netdev_dbg(ds->ports[port], "802.1Q Mode %s (was %s)\n",
+   netdev_dbg(ds->ports[port].netdev, "802.1Q Mode %s (was %s)\n",
   mv88e6xxx_port_8021q_mode_names[new],
   mv88e6xxx_port_8021q_mode_names[old]);
}
@@ -2147,11 +2149,12 @@ static void mv88e6xxx_port_vlan_add(struct dsa_switch 
*ds, int port,
 
for (vid = vlan->vid_begin; vid <= vlan->vid_end; ++vid)
if (_mv88e6xxx_port_vlan_add(ps, port, vid, untagged))
-   netdev_err(ds->ports[port], "failed to add VLAN %d%c\

[PATCH net-next 01/17] net: dsa: slave: chip data is optional, don't dereference NULL

2016-06-03 Thread Andrew Lunn
The new binding does not make use of dsa_chip_data, a.k.a cd.  When
retrieving the size of the EEPROM attached to a switch, don't assume
there is a cd attached to the switch structure.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 net/dsa/slave.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 152436cdab30..135a91706755 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -615,7 +615,7 @@ static int dsa_slave_get_eeprom_len(struct net_device *dev)
struct dsa_slave_priv *p = netdev_priv(dev);
struct dsa_switch *ds = p->parent;
 
-   if (ds->cd->eeprom_len)
+   if (ds->cd && ds->cd->eeprom_len)
return ds->cd->eeprom_len;
 
if (ds->drv->get_eeprom_len)
-- 
2.8.1



[PATCH net-next 16/17] arm: dt: vf610-zii-devel-b: Make use of new DSA binding

2016-06-03 Thread Andrew Lunn
Hang the three switches of the three MDIO busses using the new DSA
binding. Also, make use of the mdio-bus and explicitly list the phys
on one device. This is not required, but good for testing.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 arch/arm/boot/dts/vf610-zii-dev-rev-b.dts | 328 --
 1 file changed, 170 insertions(+), 158 deletions(-)

diff --git a/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts 
b/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts
index 6c60b7f91104..5c1fcab4a6f7 100644
--- a/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts
+++ b/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts
@@ -85,187 +85,199 @@
reg = <1>;
#address-cells = <1>;
#size-cells = <0>;
+
+   switch0: switch0@0 {
+   compatible = "marvell,mv88e6085";
+   #address-cells = <1>;
+   #size-cells = <0>;
+   reg = <0>;
+   dsa,member = <0 0>;
+
+   ports {
+   #address-cells = <1>;
+   #size-cells = <0>;
+   port@0 {
+   reg = <0>;
+   label = "lan0";
+   };
+
+   port@1 {
+   reg = <1>;
+   label = "lan1";
+   };
+
+   port@2 {
+   reg = <2>;
+   label = "lan2";
+   };
+
+   switch0port5: port@5 {
+   reg = <5>;
+   label = "dsa";
+   phy-mode = "rgmii-txid";
+   link = <
+   >;
+   fixed-link {
+   speed = <1000>;
+   full-duplex;
+   };
+   };
+
+   port@6 {
+   reg = <6>;
+   label = "cpu";
+   ethernet = <>;
+   fixed-link {
+   speed = <100>;
+   full-duplex;
+   };
+   };
+   };
+   };
};
 
mdio_mux_2: mdio@2 {
reg = <2>;
#address-cells = <1>;
#size-cells = <0>;
-   };
-
-   mdio_mux_4: mdio@4 {
-   reg = <4>;
-   #address-cells = <1>;
-   #size-cells = <0>;
-   };
-
-   mdio_mux_8: mdio@8 {
-   reg = <8>;
-   #address-cells = <1>;
-   #size-cells = <0>;
-   };
-   };
-
-   dsa {
-   compatible = "marvell,dsa";
-   #address-cells = <2>;
-   #size-cells = <0>;
-   dsa,ethernet = <>;
-   dsa,mii-bus = <_mux_1>;
-
-   /* 6352 - Primary - 7 ports */
-   switch0: switch@0-0 {
-   #address-cells = <1>;
-   #size-cells = <0>;
-   reg = <0x00 0>;
-   eeprom-length = <512>;
 
-   port@0 {
+   switch1: switch1@0 {
+   compatible = "marvell,mv88e6085";
+   #address-cells = <1>;
+   #size-cells = <0>;
reg = <0>;
-   label = "lan0";
-   };
-
-   port@1 {
- 

[PATCH net-next 06/17] net: dsa: Move port device node into port structure

2016-06-03 Thread Andrew Lunn
Move the port device node structure into the port structure, from the
chip data. This information is needed in the next step of implementing
the new binding.

The chip data structure is used while parsing the whole old binding,
before the individual switch structures exist. With the new bindings,
this is reversed, the switches exist first, and the interconnections
between the switches is derived from the individual switch
bindings. Thus this chip data structure becomes unneeded.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 include/net/dsa.h | 1 +
 net/dsa/dsa.c | 8 
 net/dsa/slave.c   | 5 ++---
 3 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/include/net/dsa.h b/include/net/dsa.h
index 9aed8572037c..8314197d028f 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -121,6 +121,7 @@ struct dsa_switch_tree {
 
 struct dsa_port {
struct net_device   *netdev;
+   struct device_node  *dn;
 };
 
 struct dsa_switch {
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 18086e0cc617..5907f8cd13b6 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -182,7 +182,6 @@ __ATTRIBUTE_GROUPS(dsa_hwmon);
 /* basic switch operations **/
 static int dsa_cpu_dsa_setup(struct dsa_switch *ds, struct net_device *master)
 {
-   struct dsa_chip_data *cd = ds->cd;
struct device_node *port_dn;
struct phy_device *phydev;
int ret, port, mode;
@@ -191,7 +190,7 @@ static int dsa_cpu_dsa_setup(struct dsa_switch *ds, struct 
net_device *master)
if (!(dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port)))
continue;
 
-   port_dn = cd->port_dn[port];
+   port_dn = ds->ports[port].dn;
if (of_phy_is_fixed_link(port_dn)) {
ret = of_phy_register_fixed_link(port_dn);
if (ret) {
@@ -325,6 +324,8 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
 * Create network devices for physical switch ports.
 */
for (i = 0; i < DSA_MAX_PORTS; i++) {
+   ds->ports[i].dn = cd->port_dn[i];
+
if (!(ds->enabled_port_mask & (1 << i)))
continue;
 
@@ -424,7 +425,6 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
 {
struct device_node *port_dn;
struct phy_device *phydev;
-   struct dsa_chip_data *cd = ds->cd;
int port;
 
 #ifdef CONFIG_NET_DSA_HWMON
@@ -445,7 +445,7 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
 
/* Remove any fixed link PHYs */
for (port = 0; port < DSA_MAX_PORTS; port++) {
-   port_dn = cd->port_dn[port];
+   port_dn = ds->ports[port].dn;
if (of_phy_is_fixed_link(port_dn)) {
phydev = of_phy_find_device(port_dn);
if (phydev) {
diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 169abacbc6ce..52f1183c42a0 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -998,13 +998,12 @@ static int dsa_slave_phy_setup(struct dsa_slave_priv *p,
struct net_device *slave_dev)
 {
struct dsa_switch *ds = p->parent;
-   struct dsa_chip_data *cd = ds->cd;
struct device_node *phy_dn, *port_dn;
bool phy_is_fixed = false;
u32 phy_flags = 0;
int mode, ret;
 
-   port_dn = cd->port_dn[p->port];
+   port_dn = ds->ports[p->port].dn;
mode = of_get_phy_mode(port_dn);
if (mode < 0)
mode = PHY_INTERFACE_MODE_NA;
@@ -1146,7 +1145,7 @@ int dsa_slave_create(struct dsa_switch *ds, struct device 
*parent,
 NULL);
 
SET_NETDEV_DEV(slave_dev, parent);
-   slave_dev->dev.of_node = ds->cd->port_dn[port];
+   slave_dev->dev.of_node = ds->ports[port].dn;
slave_dev->vlan_features = master->vlan_features;
 
p = netdev_priv(slave_dev);
-- 
2.8.1



[PATCH net-next 04/17] net: dsa: tag_{e}dsa.c: Remove dependency on platform data

2016-06-03 Thread Andrew Lunn
The platform data nr_chips is used when validating a received packet,
to ensure it comes from a know switch chip. The number of possible
switches is limited to DSA_MAX_SWITCHES, so use this as the first
validation step. The new binding allows holes in the dst->ds[] array,
so also ensure ensure there is a valid dsa_switch for this packet.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 net/dsa/tag_dsa.c  | 6 +-
 net/dsa/tag_edsa.c | 6 +-
 2 files changed, 10 insertions(+), 2 deletions(-)

diff --git a/net/dsa/tag_dsa.c b/net/dsa/tag_dsa.c
index aa780e4ac0bd..f9832f097681 100644
--- a/net/dsa/tag_dsa.c
+++ b/net/dsa/tag_dsa.c
@@ -107,9 +107,13 @@ static int dsa_rcv(struct sk_buff *skb, struct net_device 
*dev,
 * Check that the source device exists and that the source
 * port is a registered DSA port.
 */
-   if (source_device >= dst->pd->nr_chips)
+   if (source_device >= DSA_MAX_SWITCHES)
goto out_drop;
+
ds = dst->ds[source_device];
+   if (!ds)
+   goto out_drop;
+
if (source_port >= DSA_MAX_PORTS || ds->ports[source_port] == NULL)
goto out_drop;
 
diff --git a/net/dsa/tag_edsa.c b/net/dsa/tag_edsa.c
index 2288c8098c42..3890aac8190f 100644
--- a/net/dsa/tag_edsa.c
+++ b/net/dsa/tag_edsa.c
@@ -120,9 +120,13 @@ static int edsa_rcv(struct sk_buff *skb, struct net_device 
*dev,
 * Check that the source device exists and that the source
 * port is a registered DSA port.
 */
-   if (source_device >= dst->pd->nr_chips)
+   if (source_device >= DSA_MAX_SWITCHES)
goto out_drop;
+
ds = dst->ds[source_device];
+   if (!ds)
+   goto out_drop;
+
if (source_port >= DSA_MAX_PORTS || ds->ports[source_port] == NULL)
goto out_drop;
 
-- 
2.8.1



[PATCH net-next 15/17] net: dsa: Add new binding implementation

2016-06-03 Thread Andrew Lunn
The existing DSA binding has a number of limitations and problems. The
main problem is that it cannot represent a switch as a linux device,
hanging off some bus. It is limited to one CPU port. The DSA platform
device is artificial, and does not really represent hardware.

Implement a new binding which can be embedded into any type of node on
a bus to represent one switch device, and its links to other switches.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
Signed-off-by: Florian Fainelli <f.faine...@gmail.com>
---
 drivers/net/dsa/mv88e6xxx.c |   7 +
 include/net/dsa.h   |  20 ++
 net/dsa/Makefile|   2 +-
 net/dsa/dsa.c   |   1 +
 net/dsa/dsa2.c  | 653 
 net/dsa/dsa_priv.h  |   2 +-
 net/dsa/slave.c |   8 +-
 7 files changed, 689 insertions(+), 4 deletions(-)
 create mode 100644 net/dsa/dsa2.c

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 192b39cbdbcd..ee06055444f9 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -3748,6 +3748,12 @@ int mv88e6xxx_probe(struct mdio_device *mdiodev)
 
dev_set_drvdata(dev, ds);
 
+   err = dsa_register_switch(ds, mdiodev->dev.of_node);
+   if (err) {
+   mv88e6xxx_mdio_unregister(ps);
+   return err;
+   }
+
dev_info(dev, "switch 0x%x probed: %s, revision %u\n",
 prod_num, ps->info->name, rev);
 
@@ -3759,6 +3765,7 @@ static void mv88e6xxx_remove(struct mdio_device *mdiodev)
struct dsa_switch *ds = dev_get_drvdata(>dev);
struct mv88e6xxx_priv_state *ps = ds_to_priv(ds);
 
+   dsa_unregister_switch(ds);
put_device(>bus->dev);
 
mv88e6xxx_mdio_unregister(ps);
diff --git a/include/net/dsa.h b/include/net/dsa.h
index 11e8f09d32e3..d6ed5dee73e5 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -85,6 +85,17 @@ struct dsa_platform_data {
 struct packet_type;
 
 struct dsa_switch_tree {
+   struct list_headlist;
+
+   /* Tree identifier */
+   u32 tree;
+
+   /* Number of switches attached to this tree */
+   struct kref refcount;
+
+   /* Has this tree been applied to the hardware? */
+   bool applied;
+
/*
 * Configuration data for the platform device that owns
 * this dsa switch tree instance.
@@ -171,9 +182,15 @@ struct dsa_switch {
 #endif
 
/*
+* The lower device this switch uses to talk to the host
+*/
+   struct net_device *master_netdev;
+
+   /*
 * Slave mii_bus and devices for the individual ports.
 */
u32 dsa_port_mask;
+   u32 cpu_port_mask;
u32 enabled_port_mask;
u32 phys_mii_mask;
struct dsa_port ports[DSA_MAX_PORTS];
@@ -362,4 +379,7 @@ static inline bool dsa_uses_tagged_protocol(struct 
dsa_switch_tree *dst)
 {
return dst->rcv != NULL;
 }
+
+void dsa_unregister_switch(struct dsa_switch *ds);
+int dsa_register_switch(struct dsa_switch *ds, struct device_node *np);
 #endif
diff --git a/net/dsa/Makefile b/net/dsa/Makefile
index da06ed1df620..8af4ded70f1c 100644
--- a/net/dsa/Makefile
+++ b/net/dsa/Makefile
@@ -1,6 +1,6 @@
 # the core
 obj-$(CONFIG_NET_DSA) += dsa_core.o
-dsa_core-y += dsa.o slave.o
+dsa_core-y += dsa.o slave.o dsa2.o
 
 # tagging formats
 dsa_core-$(CONFIG_NET_DSA_TAG_BRCM) += tag_brcm.o
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 6c314f300424..d8cb2acd4f0a 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -294,6 +294,7 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
}
dst->cpu_switch = index;
dst->cpu_port = i;
+   ds->cpu_port_mask |= 1 << i;
} else if (!strcmp(name, "dsa")) {
ds->dsa_port_mask |= 1 << i;
} else {
diff --git a/net/dsa/dsa2.c b/net/dsa/dsa2.c
new file mode 100644
index ..4e5051bed643
--- /dev/null
+++ b/net/dsa/dsa2.c
@@ -0,0 +1,653 @@
+/*
+ * net/dsa/dsa2.c - Hardware switch handling, binding version 2
+ * Copyright (c) 2008-2009 Marvell Semiconductor
+ * Copyright (c) 2013 Florian Fainelli <flor...@openwrt.org>
+ * Copyright (c) 2016 Andrew Lunn <and...@lunn.ch>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include "dsa_priv.h"
+
+static LIST_HEAD(dsa_switch_trees);
+static DEFINE_MUTEX(dsa2_mutex);
+
+static struct dsa_switc

[PATCH net-next 03/17] net: dsa: slave: Remove MDIO address from switch MDIO bus name

2016-06-03 Thread Andrew Lunn
The DSA layer should no longer assume the switch is connected to an
MDIO bus. As a result, we cannot use the address on the MDIO bus when
forming the name of the switches internal MDIO bus for its builtin and
possibly external PHYs. The switch index is sufficient to make the
name unique, so drop the MDIO address.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 net/dsa/slave.c | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 135a91706755..f640a48a6ff3 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -49,8 +49,7 @@ void dsa_slave_mii_bus_init(struct dsa_switch *ds)
ds->slave_mii_bus->name = "dsa slave smi";
ds->slave_mii_bus->read = dsa_slave_phy_read;
ds->slave_mii_bus->write = dsa_slave_phy_write;
-   snprintf(ds->slave_mii_bus->id, MII_BUS_ID_SIZE, "dsa-%d:%.2x",
-   ds->index, ds->cd->sw_addr);
+   snprintf(ds->slave_mii_bus->id, MII_BUS_ID_SIZE, "dsa-%d", ds->index);
ds->slave_mii_bus->parent = ds->dev;
ds->slave_mii_bus->phy_mask = ~ds->phys_mii_mask;
 }
-- 
2.8.1



Re: [PATCH v3 RESEND 0/7] Add MDIO bus multiplexer support for iProc SoCs

2016-06-03 Thread Andrew Lunn
> Reason for resend:
> -Rebased on v4.7-rc1

How do you see this getting merged? Via netdev? If so, you should be
based on net-next/master, not v4.7-rc1.

  Andrew


[PATCH net-next 08/17] net: dsa: Copy the routing table into the switch structure

2016-06-03 Thread Andrew Lunn
The new binding will not have a chip data structure, it will place the
routing directly into the switch structure. To enable backwards
compatibility, copy the routing from the chip data into the switch
structure.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c |  4 ++--
 include/net/dsa.h   | 10 +-
 net/dsa/dsa.c   |  2 ++
 3 files changed, 13 insertions(+), 3 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index d622c0fb76cc..492801a6398c 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -3024,8 +3024,8 @@ static int mv88e6xxx_setup_global(struct 
mv88e6xxx_priv_state *ps)
for (i = 0; i < 32; i++) {
int nexthop = 0x1f;
 
-   if (i != ps->ds->index && i < ps->ds->dst->pd->nr_chips)
-   nexthop = ps->ds->cd->rtable[i] & 0x1f;
+   if (i != ds->index && i < DSA_MAX_SWITCHES)
+   nexthop = ds->rtable[i] & 0x1f;
 
err = _mv88e6xxx_reg_write(
ps, REG_GLOBAL2,
diff --git a/include/net/dsa.h b/include/net/dsa.h
index 4e3afa9648ca..a306a17b7f2e 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -148,6 +148,14 @@ struct dsa_switch {
 */
struct dsa_switch_driver*drv;
 
+   /*
+* An array of which element [a] indicates which port on this
+* switch should be used to send packets to that are destined
+* for switch a.  Can be NULL if there is only one switch
+* chip.
+*/
+   s8  rtable[DSA_MAX_SWITCHES];
+
 #ifdef CONFIG_NET_DSA_HWMON
/*
 * Hardware monitoring information
@@ -194,7 +202,7 @@ static inline u8 dsa_upstream_port(struct dsa_switch *ds)
if (dst->cpu_switch == ds->index)
return dst->cpu_port;
else
-   return ds->cd->rtable[dst->cpu_switch];
+   return ds->rtable[dst->cpu_switch];
 }
 
 struct switchdev_trans;
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 6177dd750847..bfe1d03d4730 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -297,6 +297,8 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
dst->tag_protocol = drv->tag_protocol;
}
 
+   memcpy(ds->rtable, cd->rtable, sizeof(ds->rtable));
+
/*
 * Do basic register setup.
 */
-- 
2.8.1



Re: [PATCH v3 7/7] phy: Add Northstar2 PCI Phy support

2016-06-03 Thread Andrew Lunn
On Fri, Jun 03, 2016 at 08:56:08PM +0530, Pramod Kumar wrote:
> Add PCI Phy support for Broadcom Northstar2 SoCs.  This driver uses the
> interface from the iproc mdio mux driver to enable the devices
> respective phys.
> 
> Signed-off-by: Jon Mason <jonma...@broadcom.com>
> Signed-off-by: Pramod Kumar <pramod.ku...@broadcom.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew   


[PATCH net-next 14/17] net: dsa: mv88e6xxx: Refactor MDIO so driver registers mdio bus

2016-06-03 Thread Andrew Lunn
Have the switch driver register its own MDIO bus. This allows for an
mdio property in the device tree, with child nodes for phys, which
can be referenced via phandles, etc.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c | 89 -
 drivers/net/dsa/mv88e6xxx.h |  6 +++
 2 files changed, 86 insertions(+), 9 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index b8e65e604f75..192b39cbdbcd 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -21,6 +21,7 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -3130,13 +3131,11 @@ static int mv88e6xxx_setup(struct dsa_switch *ds)
int i;
 
ps->ds = ds;
+   ds->slave_mii_bus = ps->mdio_bus;
 
if (mv88e6xxx_has(ps, MV88E6XXX_FLAG_EEPROM))
mutex_init(>eeprom_mutex);
 
-   if (mv88e6xxx_has(ps, MV88E6XXX_FLAG_PPU))
-   mv88e6xxx_ppu_state_init(ps);
-
mutex_lock(>smi_mutex);
 
err = mv88e6xxx_switch_reset(ps);
@@ -3192,9 +3191,9 @@ static int mv88e6xxx_port_to_mdio_addr(struct 
mv88e6xxx_priv_state *ps,
return -EINVAL;
 }
 
-static int mv88e6xxx_mdio_read(struct dsa_switch *ds, int port, int regnum)
+static int mv88e6xxx_mdio_read(struct mii_bus *bus, int port, int regnum)
 {
-   struct mv88e6xxx_priv_state *ps = ds_to_priv(ds);
+   struct mv88e6xxx_priv_state *ps = bus->priv;
int addr = mv88e6xxx_port_to_mdio_addr(ps, port);
int ret;
 
@@ -3214,10 +3213,10 @@ static int mv88e6xxx_mdio_read(struct dsa_switch *ds, 
int port, int regnum)
return ret;
 }
 
-static int mv88e6xxx_mdio_write(struct dsa_switch *ds, int port, int regnum,
+static int mv88e6xxx_mdio_write(struct mii_bus *bus, int port, int regnum,
u16 val)
 {
-   struct mv88e6xxx_priv_state *ps = ds_to_priv(ds);
+   struct mv88e6xxx_priv_state *ps = bus->priv;
int addr = mv88e6xxx_port_to_mdio_addr(ps, port);
int ret;
 
@@ -3237,6 +3236,66 @@ static int mv88e6xxx_mdio_write(struct dsa_switch *ds, 
int port, int regnum,
return ret;
 }
 
+static int mv88e6xxx_mdio_register(struct mv88e6xxx_priv_state *ps,
+  struct device_node *np)
+{
+   static int index;
+   struct mii_bus *bus;
+   int err;
+
+   if (mv88e6xxx_has(ps, MV88E6XXX_FLAG_PPU))
+   mv88e6xxx_ppu_state_init(ps);
+
+   if (np)
+   ps->mdio_np = of_get_child_by_name(np, "mdio");
+
+   bus = devm_mdiobus_alloc(ps->dev);
+   if (!bus)
+   return -ENOMEM;
+
+   bus->priv = (void *)ps;
+   if (np) {
+   bus->name = np->full_name;
+   snprintf(bus->id, MII_BUS_ID_SIZE, "%s", np->full_name);
+   } else {
+   bus->name = "mv88e6xxx SMI";
+   snprintf(bus->id, MII_BUS_ID_SIZE, "mv88e6xxx-%d", index++);
+   }
+
+   bus->read = mv88e6xxx_mdio_read;
+   bus->write = mv88e6xxx_mdio_write;
+   bus->parent = ps->dev;
+
+   if (ps->mdio_np)
+   err = of_mdiobus_register(bus, ps->mdio_np);
+   else
+   err = mdiobus_register(bus);
+   if (err) {
+   dev_err(ps->dev, "Cannot register MDIO bus (%d)\n", err);
+   goto out;
+   }
+   ps->mdio_bus = bus;
+
+   return 0;
+
+out:
+   if (ps->mdio_np)
+   of_node_put(ps->mdio_np);
+
+   return err;
+}
+
+static void mv88e6xxx_mdio_unregister(struct mv88e6xxx_priv_state *ps)
+
+{
+   struct mii_bus *bus = ps->mdio_bus;
+
+   mdiobus_unregister(bus);
+
+   if (ps->mdio_np)
+   of_node_put(ps->mdio_np);
+}
+
 #ifdef CONFIG_NET_DSA_HWMON
 
 static int mv88e61xx_get_temp(struct dsa_switch *ds, int *temp)
@@ -3549,6 +3608,7 @@ static const char *mv88e6xxx_drv_probe(struct device 
*dsa_dev,
struct mii_bus *bus;
const char *name;
int id, prod_num, rev;
+   int err;
 
bus = dsa_host_dev_to_mii_bus(host_dev);
if (!bus)
@@ -3575,8 +3635,13 @@ static const char *mv88e6xxx_drv_probe(struct device 
*dsa_dev,
ps->bus = bus;
ps->sw_addr = sw_addr;
ps->info = info;
+   ps->dev = dsa_dev;
mutex_init(>smi_mutex);
 
+   err = mv88e6xxx_mdio_register(ps, NULL);
+   if (err)
+   return NULL;
+
*priv = ps;
 
dev_info(>bus->dev, "switch 0x%x probed: %s, revision %u\n",
@@ -3590,8 +3655,6 @@ struct dsa_switch_driver mv88e6xxx_switch_driver = {
.probe  = mv88e6xxx_drv_probe,
.setup  = mv88e6xxx_setup,
.set_addr   = mv88e6xxx_set_addr,
-   .phy_read   = mv88e6xxx_mdio_

Re: [PATCH v2 2/7] DT: phy.txt: Add mdio-integrated-mux property

2016-06-02 Thread Andrew Lunn
On Thu, Jun 02, 2016 at 06:27:03PM -0500, Rob Herring wrote:
> On Tue, May 31, 2016 at 07:06:36PM +0530, Pramod Kumar wrote:
> > This property is used by integrated MDIO multiplexer
> > which has bus selection and mdio transaction generation logic,
> > integrated inside.
> > 
> > Signed-off-by: Pramod Kumar 
> > ---
> >  Documentation/devicetree/bindings/net/mdio-mux.txt | 9 -
> >  1 file changed, 8 insertions(+), 1 deletion(-)
> > 
> > diff --git a/Documentation/devicetree/bindings/net/mdio-mux.txt 
> > b/Documentation/devicetree/bindings/net/mdio-mux.txt
> > index 491f5bd..b5ad83e 100644
> > --- a/Documentation/devicetree/bindings/net/mdio-mux.txt
> > +++ b/Documentation/devicetree/bindings/net/mdio-mux.txt
> > @@ -5,13 +5,20 @@ numbered uniquely in a device dependent manner.  The 
> > nodes for an MDIO
> >  bus multiplexer/switch will have one child node for each child bus.
> >  
> >  Required properties:
> > -- mdio-parent-bus : phandle to the parent MDIO bus.
> >  - #address-cells = <1>;
> >  - #size-cells = <0>;
> >  
> >  Optional properties:
> > +- mdio-parent-bus : phandle to the parent MDIO bus. Should be used
> > +   if parent mdio bus is not part of multiplexer.
> 
> You don't appear to be using this. When would you?

He is moving it to optional. The mdio-mux-mmio and mdio-mux-gpio do
however use it, which follow this binding.

Andrew


[PATCH] net: igb: Only dma sync frame length

2016-06-03 Thread Andrew Lunn
On some platforms, syncing a buffer for DMA is expensive. Rather than
sync the whole 2K receive buffer, only synchronise the length of the
frame, which will typically be the MTU, or a much smaller TCP ACK.

For an IMX6Q, this gives around 6% increased TCP receive performance,
which is cache operations bound and reduces CPU load for TCP transmit.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/ethernet/intel/igb/igb_main.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/net/ethernet/intel/igb/igb_main.c 
b/drivers/net/ethernet/intel/igb/igb_main.c
index 0a289dda604a..670e3d612283 100644
--- a/drivers/net/ethernet/intel/igb/igb_main.c
+++ b/drivers/net/ethernet/intel/igb/igb_main.c
@@ -6915,6 +6915,7 @@ static struct sk_buff *igb_fetch_rx_buffer(struct 
igb_ring *rx_ring,
 {
struct igb_rx_buffer *rx_buffer;
struct page *page;
+   unsigned int size = le16_to_cpu(rx_desc->wb.upper.length);
 
rx_buffer = _ring->rx_buffer_info[rx_ring->next_to_clean];
page = rx_buffer->page;
@@ -6948,7 +6949,7 @@ static struct sk_buff *igb_fetch_rx_buffer(struct 
igb_ring *rx_ring,
dma_sync_single_range_for_cpu(rx_ring->dev,
  rx_buffer->dma,
  rx_buffer->page_offset,
- IGB_RX_BUFSZ,
+ size,
  DMA_FROM_DEVICE);
 
/* pull page into skb */
-- 
2.8.1



[PATCHv2 net-next] net: igb: Only dma sync frame length

2016-06-03 Thread Andrew Lunn
On some platforms, syncing a buffer for DMA is expensive. Rather than
sync the whole 2K receive buffer, only synchronise the length of the
frame, which will typically be the MTU, or a much smaller TCP ACK.

For an IMX6Q, this gives around 6% increased TCP receive performance,
which is cache operations bound and reduces CPU load for TCP transmit.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
v2:
Christmas tree the local variables
Pass size into igb_add_rx_frag() rather than repeating the endiness swap.
---
 drivers/net/ethernet/intel/igb/igb_main.c | 7 ---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/drivers/net/ethernet/intel/igb/igb_main.c 
b/drivers/net/ethernet/intel/igb/igb_main.c
index 0a289dda604a..8fa9e6e8c3b0 100644
--- a/drivers/net/ethernet/intel/igb/igb_main.c
+++ b/drivers/net/ethernet/intel/igb/igb_main.c
@@ -6856,12 +6856,12 @@ static bool igb_can_reuse_rx_page(struct igb_rx_buffer 
*rx_buffer,
  **/
 static bool igb_add_rx_frag(struct igb_ring *rx_ring,
struct igb_rx_buffer *rx_buffer,
+   unsigned int size,
union e1000_adv_rx_desc *rx_desc,
struct sk_buff *skb)
 {
struct page *page = rx_buffer->page;
unsigned char *va = page_address(page) + rx_buffer->page_offset;
-   unsigned int size = le16_to_cpu(rx_desc->wb.upper.length);
 #if (PAGE_SIZE < 8192)
unsigned int truesize = IGB_RX_BUFSZ;
 #else
@@ -6913,6 +6913,7 @@ static struct sk_buff *igb_fetch_rx_buffer(struct 
igb_ring *rx_ring,
   union e1000_adv_rx_desc *rx_desc,
   struct sk_buff *skb)
 {
+   unsigned int size = le16_to_cpu(rx_desc->wb.upper.length);
struct igb_rx_buffer *rx_buffer;
struct page *page;
 
@@ -6948,11 +6949,11 @@ static struct sk_buff *igb_fetch_rx_buffer(struct 
igb_ring *rx_ring,
dma_sync_single_range_for_cpu(rx_ring->dev,
  rx_buffer->dma,
  rx_buffer->page_offset,
- IGB_RX_BUFSZ,
+ size,
  DMA_FROM_DEVICE);
 
/* pull page into skb */
-   if (igb_add_rx_frag(rx_ring, rx_buffer, rx_desc, skb)) {
+   if (igb_add_rx_frag(rx_ring, rx_buffer, size, rx_desc, skb)) {
/* hand second half of page back to the ring */
igb_reuse_rx_page(rx_ring, rx_buffer);
} else {
-- 
2.8.1



Re: [PATCH 09/12] net: mediatek: increase watchdog_timeo

2016-06-05 Thread Andrew Lunn
On Sun, Jun 05, 2016 at 08:33:02AM +0200, John Crispin wrote:
> During stress testing, after reducing the threshold value, we have seen
> TX timeouts that were caused by the watchdog_timeo value being too low.
> Increase the value to 5 * HZ which is a value commonly used by many other
> drivers.

I've never studied what watchdog_timeo actually means. Does it mean a
transmit has not completed in that amount of time? Would this imply
you have 5 seconds worth of packets in your transmit queue? Do you
know what the driver is doing during this 5 seconds?

Thanks
Andrew


Re: [PATCH net-next v4 5/6] net: dsa: Initialize CPU port ethtool ops per tree

2016-06-08 Thread Andrew Lunn
On Tue, Jun 07, 2016 at 04:32:42PM -0700, Florian Fainelli wrote:
> Now that we can properly support multiple distinct trees in the system,
> using a global variable: dsa_cpu_port_ethtool_ops is getting clobbered
> as soon as the second switch tree gets probed, and we don't want that.
> 
> We need to move this to be dynamically allocated, and since we can't
> really be comparing addresses anymore to determine first time
> initialization versus any other times, just move this to dsa.c and
> dsa2.c where the remainder of the dst/ds initialization happens.
> 
> The operations teardown restores the master netdev's ethtool_ops to its
> original ethtool_ops pointer (typically within the Ethernet driver)
> 
> Signed-off-by: Florian Fainelli <f.faine...@gmail.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH net-next v4 0/6] net: dsa: misc improvements

2016-06-08 Thread Andrew Lunn
On Tue, Jun 07, 2016 at 04:32:37PM -0700, Florian Fainelli wrote:
> Hi all,
> 
> This patch series builds on top of Andrew's "New DSA bind, switches as 
> devices"
> patch set and does the following:

Hi Florian

Thanks for the patience with my nit picking.

This is now ready to be applied.

 Thanks
Andrew


Re: [PATCH] net: stmmac: dwmac-rk: keep PHY up for WoL

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 03:25:38PM -0700, Vincent Palatin wrote:
> On Tue, Jun 7, 2016 at 12:23 AM, Giuseppe CAVALLARO
>  wrote:
> > Hello
> >
> > On 6/3/2016 7:29 PM, Vincent Palatin wrote:
> >>
> >> Do not shutdown the PHY if Wake-on-Lan is enabled, else it cannot wake
> >> us up.
> >>
> >
> > I do not understand why you need that.
> > This is done inside the PHY layer and it is tested on our platforms
> > he idea is: If the parent wants to Wake the system then the PHY should
> > not power-down.
> 
> I'm not sure I understand :
> you mean that this path is not called if WoL is enabled ?
> [ currently stmmac_pltfr_suspend() is calling priv->plat->exit() which
> is the rk_gmac_exit() code I'm modifying ]
> or the RK driver code should not power down the phy in its exit() callback ?

Take a look at phy_suspend().

 Andrew


Re: [PATCH net-next v3 5/6] net: dsa: Initialize CPU port ethtool ops per tree

2016-06-07 Thread Andrew Lunn
On Tue, Jun 07, 2016 at 03:13:35PM -0700, Florian Fainelli wrote:
> On 06/07/2016 02:51 PM, Andrew Lunn wrote:
> >> +int dsa_cpu_port_ethtool_setup(struct dsa_switch_tree *dst,
> >> + struct dsa_switch *ds)
> >> +{
> >> +  struct net_device *master;
> >> +  struct ethtool_ops *cpu_ops;
> >> +
> >> +  master = ds->dst->master_netdev;
> > 
> > You pass in dst as a parameter, and then don't use it!
> 
> I do use it here:
> 
> memcpy(>master_ethtool_ops, master->ethtool_ops,
>sizeof(struct ethtool_ops));

Yes, i noticed this. I also expect the compiler has also noticed, and
has optimized away one of the parameters.
 
> I sure could simplify that and use ds->dst instead if you find it more
> elegant, works for me.

I would prefer the code to be consistent. Either use ds->dst
everywhere and drop the parameter, or use the parameter everywhere it
is usable.

   Thanks
Andrew


Re: [PATCH net-next v3 5/6] net: dsa: Initialize CPU port ethtool ops per tree

2016-06-07 Thread Andrew Lunn
> +int dsa_cpu_port_ethtool_setup(struct dsa_switch_tree *dst,
> +struct dsa_switch *ds)
> +{
> + struct net_device *master;
> + struct ethtool_ops *cpu_ops;
> +
> + master = ds->dst->master_netdev;

You pass in dst as a parameter, and then don't use it!

> +void dsa_cpu_port_ethtool_restore(struct dsa_switch_tree *dst,
> +   struct dsa_switch *ds)
> +{
> + struct net_device *master;
> +
> + master = ds->dst->master_netdev;

Same here.

 Andrew


Re: [PATCH net-next v3 3/6] net: dsa: Provide a slave MII bus if needed

2016-06-07 Thread Andrew Lunn
On Tue, Jun 07, 2016 at 02:06:53PM -0700, Florian Fainelli wrote:
> Mimic what net/dsa/dsa.c does and provide a slave MII bus by default
> which will be created if the driver implements a phy_read method.
> 
> Signed-off-by: Florian Fainelli <f.faine...@gmail.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH net-next v3 2/6] net: dsa: Initialize ds->enabled_port_mask and ds->phys_mii_mask

2016-06-07 Thread Andrew Lunn
On Tue, Jun 07, 2016 at 02:06:52PM -0700, Florian Fainelli wrote:
> Some drivers rely on these two bitmasks to contain the correct values
> for them to successfully probe and initialize at drv->setup() time,
> calculate correct values to put in both masks as early as possible in
> dsa_get_ports_dn().
> 
> Signed-off-by: Florian Fainelli <f.faine...@gmail.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH net-next v2 2/5] net: dsa: Initialize ds->enabled_port_mask and ds->phys_mii_mask

2016-06-07 Thread Andrew Lunn
On Tue, Jun 07, 2016 at 02:22:12AM +0200, Andrew Lunn wrote:
> > @@ -304,6 +312,18 @@ static int dsa_ds_apply(struct dsa_switch_tree *dst, 
> > struct dsa_switch *ds)
> > if (err < 0)
> > return err;
> >  
> > +   if (!ds->slave_mii_bus && ds->drv->phy_read) {
> > +   ds->slave_mii_bus = devm_mdiobus_alloc(ds->dev);
> > +   if (!ds->slave_mii_bus)
> > +   return err;
> > +
> > +   dsa_slave_mii_bus_init(ds);
> > +
> > +   err = mdiobus_register(ds->slave_mii_bus);
> > +   if (err < 0)
> > +   return err;
> > +   }
> > +
> > for (index = 0; index < DSA_MAX_PORTS; index++) {
> > port = ds->ports[index].dn;
> > if (!port)
> 
> Hi Florian

...
 
> It is also missing the unregister in dsa_ds_unapply().

Looking at this again...

You use devm_mdiobus_alloc(), so the memory for the bus will get freed
eventually. However, it won't get unregistered before it is freed.  So
an explicit unregister is needed. Doing that in dsa_ds_unapply() makes
sense, so we have a clear life cycle for this mdio bus.

   Andrew



Re: [PATCH 09/12] net: mediatek: increase watchdog_timeo

2016-06-06 Thread Andrew Lunn
> Hi Andrew,
> 
> it is waiting for the watchdog to trigger :-) TBH the 1s seems to be too
> short to for the dma ring length to be flushed and i had to pick some
> value and 5 is used most places.
> 
> it really depends on the amount of packets in the queue, their length
> and the mac setting. the timeout needs to be large enough that it would
> not trigger incorrectly even if the mac is on 10mbit half duplex and all
> frames in the queue were maximum size.

So you are saying there is 5 seconds worth of traffic in the transmit ring.

As a general point, not specific to this driver, is that wise? Isn't
that really bad buffer bloat?

I just wondered what happened to cause it to have 5 seconds worth of
traffic in the transmit ring. Did downstream signal a pause?  But i
thought the byte queue limit was designed to prevent a big backlog in
the transmit queue? At 10/Half, is it not reacting fast enough?  Since
it is half duplex, do you have a lot of traffic coming the other way
and something is not being fair at distributing up and down traffic?

I'm just wondering if by increasing the watchdog to 5 seconds, you are
just hiding a problem.

Andrew


Re: [PATCH v4 2/7] binding: Make "mdio-parent-bus" property from mandatory to optional

2016-06-06 Thread Andrew Lunn
On Mon, Jun 06, 2016 at 06:11:35PM +0530, Pramod Kumar wrote:
> Change "mdio-parent-bus" from mandatory section to optional
> as it won't be required by integrated MDIO multiplexer
> which has bus selection and mdio transaction generation logic,
> integrated inside.
> 
> Signed-off-by: Pramod Kumar <pramod.ku...@broadcom.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH v4 1/7] mdio: mux: Enhanced MDIO mux framework for integrated multiplexers

2016-06-06 Thread Andrew Lunn
On Mon, Jun 06, 2016 at 06:11:34PM +0530, Pramod Kumar wrote:
> An integrated multiplexer uses same address space for
> "muxed bus selection" and "generation of mdio transaction"
> hence its good to register parent bus from mux driver.
> 
> Hence added a mechanism where mux driver could register a
> parent bus and pass it down to framework via mdio_mux_init api.
> 
> Signed-off-by: Pramod Kumar <pramod.ku...@broadcom.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

 Andrew


Re: [PATCH v4 5/7] net: mdio-mux: Add MDIO mux driver for iProc SoCs

2016-06-06 Thread Andrew Lunn
On Mon, Jun 06, 2016 at 06:11:38PM +0530, Pramod Kumar wrote:
> iProc based SoCs supports the integrated mdio multiplexer which
> has the bus selection as well as mdio transaction generation logic
> inside.
> 
> This multiplexer has child buses for PCIe, SATA, USB and ETH. These
> buses could be internal or external to SOC where PHYs are attached.
> These buses could use C-45 or C-22 mdio transaction.
> 
> Signed-off-by: Pramod Kumar <pramod.ku...@broadcom.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

 Andrew


Re: [PATCH v3] r8152: Add support for setting pass through MAC address on RTL8153-AD

2016-06-06 Thread Andrew Lunn
> + /* returns _AUXMAC_#AABBCCDDEEFF# */
> + status = acpi_evaluate_object(NULL, "\\_SB.AMAC", NULL, );
> + obj = (union acpi_object *)buffer.pointer;
> + if (ACPI_SUCCESS(status)) {
> + if (obj->type != ACPI_TYPE_BUFFER ||
> + obj->string.length != 0x17) {
> + pr_warn("r8152: get_passthru_addr: Invalid buffer");

Please don't use pr_warn() when you can use the better alternatives
like dev_warn().

 Andrew


Re: [PATCH net-next v2 5/5] net: dsa: bcm_sf2: Register our slave MDIO bus

2016-06-07 Thread Andrew Lunn
On Tue, Jun 07, 2016 at 12:48:37PM -0400, Vivien Didelot wrote:
> Hi Florian, Andrew,
> 
> Vivien Didelot  writes:
> 
> > Hum reviewing that again, I see that if one of the 2 subsequent calls to
> > request_irq fails, you end up with an unregistered MDIO bus.
> >
> > We have the same issue in the mv88e6xxx legacy probe code if dsa.c fails
> > to allocate the dsa_switch structure. I'm moving the MDIO register code
> > to the setup function like you are doing here (good idea!) to fix that.
> 
> In fact it doesn't fix the issue because dsa_switch_driver doesn't
> provide any remove/teardown function, in which mv88e6xxx and sf2 could
> unregister their MDIO bus on switch removal.
> 
> Would it be worth it to add such optional function to DSA drivers?

It is not needed with DSA2 binding. The driver is always in control,
and it performs the unregister from the core. So it knows when to
unregister the mdio bus, either because probe has failed for some
reason, or it is being unloaded. That is also why i register the mdio
bus in probe, and unregister it in remove. Normal practice for a
driver.

With the legacy interface it is tricky. When would you call such a
remove/tairdown function when using the old binding?

Andrew



Re: [PATCH net-next 1/5] net: dsa: b53: Add support for Broadcom RoboSwitch

2016-06-10 Thread Andrew Lunn
> +static void b53_switch_reset_gpio(struct b53_device *dev)
> +{
> + int gpio = dev->reset_gpio;
> +
> + if (gpio < 0)
> + return;
> +
> + /* Reset sequence: RESET low(50ms)->high(20ms)
> +  */
> + gpio_set_value(gpio, 0);
> + mdelay(50);
> +
> + gpio_set_value(gpio, 1);
> + mdelay(20);
> +
> + dev->current_page = 0xff;
> +}

Hi Florian

It would be better to use the gpiod API here, so the active hi/active
low flag is respected.

> + dev->reset_gpio = b53_switch_get_reset_gpio(dev);
> + if (dev->reset_gpio >= 0) {
> + ret = devm_gpio_request_one(dev->dev, dev->reset_gpio,
> + GPIOF_OUT_INIT_HIGH, "robo_reset");
> + if (ret)
> + return ret;
> + }
> +
> + return 0;
> +}

> +static inline int b53_switch_get_reset_gpio(struct b53_device *dev)
> +{
> + enum bcm47xx_board board = bcm47xx_board_get();
> +
> + switch (board) {
> + case BCM47XX_BOARD_LINKSYS_WRT300NV11:
> + case BCM47XX_BOARD_LINKSYS_WRT310NV1:
> + return 8;

Rather than hard coding it, could we get it from device tree?

   Andrew


Re: [PATCH net-next 4/4] net: dsa: bcm_sf2: Add VLAN support

2016-06-10 Thread Andrew Lunn
> @@ -148,6 +155,9 @@ struct bcm_sf2_priv {
>   struct device_node  *master_mii_dn;
>   struct mii_bus  *slave_mii_bus;
>   struct mii_bus  *master_mii_bus;
> +
> + /* Cache of programmed VLANs */
> + struct bcm_sf2_vlan vlans[VLAN_N_VID];

Hi Florian

This is a 16Kbyte array. So i assume the whole priv structure needs 5
pages. Have you had any trouble allocating this much memory,
particularly once it has been used for a while and fragmented?

I just wondered if it might be better to use vmalloc() for the
vlans.

Andrew


Re: [PATCH] phy: marvell: remove LED config override

2016-06-10 Thread Andrew Lunn
On Fri, Jun 10, 2016 at 07:42:52PM +0200, Clemens Gruber wrote:
> Configuring the PHY LED registers for the Marvell 88E1510 and others is
> not possible, because regardless of the values in marvell,reg-init, it
> is later overridden in m88e1121_config_aneg with a non-standard default.
> 
> This became visible after we moved the call of marvell_of_reg_init in
> commit 79be1a1c9090 ("phy: marvell: Fix and unify reg-init behavior").
> Moving it to _config_init was necessary due to the PHY state machine
> getting stuck if the PHY interrupts were not enabled early on.
> As that default LED configuration is set in _config_aneg, it overrides
> the marvell,reg-init configuration from the device tree.
> 
> This patch removes this override and allows the user to again set the
> PHY LED configuration through marvell,reg-init or if that does not
> exist, keep the original defaults as documented in the datasheet.

That override code exists for a reason. I don't like just removing it
without understanding why it is there. Sergei Poselenov added it as
part of the 1121 support. Maybe he knows why it is there?

 Andrew


Re: [PATCH net-next 4/4] net: dsa: bcm_sf2: Add VLAN support

2016-06-10 Thread Andrew Lunn
On Fri, Jun 10, 2016 at 11:47:48AM -0700, Florian Fainelli wrote:
> On 06/10/2016 05:00 AM, Andrew Lunn wrote:
> >> @@ -148,6 +155,9 @@ struct bcm_sf2_priv {
> >>struct device_node  *master_mii_dn;
> >>struct mii_bus  *slave_mii_bus;
> >>struct mii_bus  *master_mii_bus;
> >> +
> >> +  /* Cache of programmed VLANs */
> >> +  struct bcm_sf2_vlan vlans[VLAN_N_VID];
> > 
> > Hi Florian
> > 
> > This is a 16Kbyte array. So i assume the whole priv structure needs 5
> > pages. Have you had any trouble allocating this much memory,
> > particularly once it has been used for a while and fragmented?
> 
> Well, since this is using the old binding, we can't unload the driver,
> it's built into the kernel, so initializes early enough we have got
> plenty of memory.

Don't you want to use the new binding at some point?

> > I just wondered if it might be better to use vmalloc() for the
> > vlans.
> 
> That's a very good point, I can't really see a drawback to doing this,
> will submit a patch moving this to a dynamic allocation.
> 
> Another possible approach would have been to allocate the vlan structure
> upong port_vlan_prepare() though that would typically result in more
> fragmentation over time once se start using more VLANs.

It is a trade off, code complexity vs saved memory. I don't think such
a table is too bad, assuming your not trying to run the whole system
in 32Mbyes of RAM.

   Andrew


Re: [PATCH net-next 1/5] net: dsa: b53: Add support for Broadcom RoboSwitch

2016-06-10 Thread Andrew Lunn
> >> +static inline int b53_switch_get_reset_gpio(struct b53_device *dev)
> >> +{
> >> +  enum bcm47xx_board board = bcm47xx_board_get();
> >> +
> >> +  switch (board) {
> >> +  case BCM47XX_BOARD_LINKSYS_WRT300NV11:
> >> +  case BCM47XX_BOARD_LINKSYS_WRT310NV1:
> >> +  return 8;
> > 
> > Rather than hard coding it, could we get it from device tree?
> 
> Difficult for now, this is for in-tree MIPS-based platforms under
> arch/mips/bcm47xx, which are using SSB/platform data.

Ah, O.K.

But it would not harm to also support getting the GPIO from device
tree, if device tree is available. But maybe that should wait until
such a user comes along.

 Andrew


Re: [PATCH] phy: marvell: remove LED config override

2016-06-10 Thread Andrew Lunn
> We could move that 0x30 LED configuration to .config_init instead of
> .config_aneg, so that if nobody configures it with marvell,reg-init, the
> behavior does not change. I'd have to create a new .config_init function
> for the 1121, 1318 and 1510.
> 
> Would you prefer that?

Hi Clemens

Yes, i would prefer that.

 Thanks
Andrew


Re: [PATCH net-next 4/8] net: dsa: mv88e6xxx: do not increment bus refcount

2016-06-10 Thread Andrew Lunn
On Fri, Jun 10, 2016 at 03:59:22PM -0400, Vivien Didelot wrote:
> Hi,
> 
> Andrew Lunn <and...@lunn.ch> writes:
> 
> > On Wed, Jun 08, 2016 at 08:44:52PM -0400, Vivien Didelot wrote:
> >> The MDIO device probe and remove functions are respectively incrementing
> >> and decrementing the bus refcount themselves. Since these bus level
> >> actions are out of the device scope, remove them.
> >
> > I agree with the patch. But have you checked the mdio layer is doing
> > the right thing? If not, we should fix that first.
> 
> So I added some printing after incrementing/decrementing the refcount in
> get_device/put_device to track >bus->dev, which name is "0.1".
> 
> Regardless having this patch or not, the refcount of the 0.1 mii_bus
> device is 5 before loading the mv88e6xxx module on vf610-zii-dev-rev-b.
> 
> Below is a portion of dmesg:
> 
> [8.921647] get_device: 400d1000.etherne refcount: 4
> [8.926225] get_device: 0.1 refcount: 2
> [8.929561] get_device: mdio-mux refcount: 5
> [8.934076] get_device: 0.1 refcount: 3
> [8.937446] get_device: 0.1 refcount: 4
> [8.940792] put_device: 0.1 refcount: 3
> [8.944181] libphy: mdio_mux: probed
> [8.947885] mdio_bus 0.1:00: mdio_device_register
> [8.952649] get_device: 0.1:00 refcount: 2
> [8.956283] get_device: 0.1 refcount: 4
> [8.959838] get_device: 0.1:00 refcount: 3
> [8.963991] get_device: 0.1:00 refcount: 4
> [8.967598] put_device: 0.1:00 refcount: 3
> [8.971298] get_device: 0.2 refcount: 2
> [8.974687] get_device: mdio-mux refcount: 7
> 
> So it seems like of_ is managing the bus refcount on events such as a
> new child node (0.1:00).

Great, thanks for looking at this.

Acked-by: Andrew Lunn <and...@lunn.ch>

Andrew


[PATCH net-next 00/17] New DSA bind, switches as devices

2016-06-03 Thread Andrew Lunn
The interesting patches here are the last three. They implement a new
binding for DSA, which removes a few limitations of the current DSA
binding. In particular, it allows switches to be true Linux devices.
These devices can be on any type of bus, unlike the old DSA binding
which assumes MDIO. See the commit log for more details. The second to
last patch modifies an existing boards device tree to use the new
binding, giving a good example of how switches can be true MDIO
devices. The last patch documents the new binding.

I know both John Crispin and Bryan Whitehead are interesting in
implementing DSA drivers, hence i have CC: you. Comments welcome.

Thanks go to Florian and Vivien for reviewing, testing and bug fixing
these patches.

Since RFC:

* Split the mv88e6xxx MDIO refactor into a rename patch and a refactor
  patch.
* Extend commit message with comment about wrong of_node_put()
* Fix destroy of cpu and dsa ports.
* Rename _DSA_TAG_LAST to DSA_TAG_LAST and add a comment.

Andrew Lunn (16):
  net: dsa: slave: chip data is optional, don't dereference NULL
  net: dsa: slave: Remove MDIO address from switch MDIO bus name
  net: dsa: tag_{e}dsa.c: Remove dependency on platform data
  net: dsa: Add a ports structure and use it in the switch structure
  net: dsa: Move port device node into port structure
  net: dsa: Remove dynamic allocate of routing table
  net: dsa: Copy the routing table into the switch structure
  net: dsa: Split up creating/destroying of DSA and CPU ports
  net: dsa: mv88e6xxx: Only support EDSA tagging
  net: dsa: Refactor selection of tag ops into a function
  net: dsa: Make mdio bus optional
  net: dsa: mv88e6xxx: Rename _phy_ to _mdio_
  net: dsa: mv88e6xxx: Refactor MDIO so driver registers mdio bus
  net: dsa: Add new binding implementation
  arm: dt: vf610-zii-devel-b: Make use of new DSA binding
  net: dsa: Document new binding

Vivien Didelot (1):
  net: dsa: mv88e6xxx: fix circular lock in PPU work

 Documentation/devicetree/bindings/net/dsa/dsa.txt | 278 -
 arch/arm/boot/dts/vf610-zii-dev-rev-b.dts | 328 +--
 drivers/net/dsa/bcm_sf2.c |   4 +-
 drivers/net/dsa/mv88e6xxx.c   | 267 ++---
 drivers/net/dsa/mv88e6xxx.h   |   6 +
 include/net/dsa.h |  56 +-
 net/dsa/Makefile  |   2 +-
 net/dsa/dsa.c | 210 ---
 net/dsa/dsa2.c| 653 ++
 net/dsa/dsa_priv.h|   6 +-
 net/dsa/slave.c   |  57 +-
 net/dsa/tag_brcm.c|   4 +-
 net/dsa/tag_dsa.c |  10 +-
 net/dsa/tag_edsa.c|  10 +-
 net/dsa/tag_trailer.c |   4 +-
 15 files changed, 1485 insertions(+), 410 deletions(-)
 create mode 100644 net/dsa/dsa2.c

-- 
2.8.1



Re: [PATCH v6] r8152: Add support for setting pass through MAC address on RTL8153-AD

2016-06-11 Thread Andrew Lunn
On Fri, Jun 10, 2016 at 10:51:56PM -0700, David Miller wrote:
> From: Mario Limonciello <mario_limoncie...@dell.com>
> Date: Tue,  7 Jun 2016 13:22:37 -0500
> 
> > The RTL8153-AD supports a persistent system specific MAC address.
> > This means a device plugged into two different systems with host side
> > support will show different (but persistent) MAC addresses.
> > 
> > This information for the system's persistent MAC address is burned in when
> > the system HW is built and available under \_SB.AMAC in the DSDT at runtime.
> > 
> > This technology is currently implemented in the Dell TB15 and WD15 Type-C
> > docks.  More information is available here:
> > http://www.dell.com/support/article/us/en/04/SLN301147
> > 
> > Signed-off-by: Mario Limonciello <mario_limoncie...@dell.com>
> > ---
> > Changes from v5:
> >  * Correct return value if hex2bin succesful but invalid ether addr
> 
> Have things calmed down enough now that I can apply this?

Hi David

I think the code has reaching the level of maturity needed for
acceptance. So for the code quality:

Reviewed-by: Andrew Lunn <and...@lunn.ch>

What is still open is do we want to accept it at all? Do we accept the
concept of putting the same MAC address on multiple interfaces at
hotplug time? Do we trust BIOS vendors to not keep changing DSDT
property name, since it is not standardised?

Do we want this at all should be decided by somebody more senior then
those passing comments on the code.

Andrew


Re: [PATCH] phy: marvell: fix LED configuration via marvell,reg-init

2016-06-11 Thread Andrew Lunn
On Sat, Jun 11, 2016 at 05:21:26PM +0200, Clemens Gruber wrote:
> Configuring the PHY LED registers for the Marvell 88E1510 and others is
> not possible, because regardless of the values in marvell,reg-init, it
> is later overridden in m88e1121_config_aneg with a non-standard default.
> 
> This patch moves that default configuration to .config_init to allow
> setting the LED configuration through marvell,reg-init in the device
> tree, which should override said default if it exists.
> 
> Signed-off-by: Clemens Gruber <clemens.gru...@pqgruber.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH 1/3] net: Add MDIO bus driver for the Hisilicon FEMAC

2016-06-13 Thread Andrew Lunn
On Mon, Jun 13, 2016 at 02:07:54PM +0800, Dongpo Li wrote:
> This patch adds a separate driver for the MDIO interface of the
> Hisilicon Fast Ethernet MAC.
> 
> Reviewed-by: Jiancheng Xue 
> Signed-off-by: Dongpo Li 
> ---
>  .../bindings/net/hisilicon-femac-mdio.txt  |  22 +++
>  drivers/net/phy/Kconfig|   8 +
>  drivers/net/phy/Makefile   |   1 +
>  drivers/net/phy/mdio-hisi-femac.c  | 165 
> +
>  4 files changed, 196 insertions(+)
>  create mode 100644 
> Documentation/devicetree/bindings/net/hisilicon-femac-mdio.txt
>  create mode 100644 drivers/net/phy/mdio-hisi-femac.c
> 
> diff --git a/Documentation/devicetree/bindings/net/hisilicon-femac-mdio.txt 
> b/Documentation/devicetree/bindings/net/hisilicon-femac-mdio.txt
> new file mode 100644
> index 000..6f46337
> --- /dev/null
> +++ b/Documentation/devicetree/bindings/net/hisilicon-femac-mdio.txt
> @@ -0,0 +1,22 @@
> +Hisilicon Fast Ethernet MDIO Controller interface
> +
> +Required properties:
> +- compatible: should be "hisilicon,hisi-femac-mdio".
> +- reg: address and length of the register set for the device.
> +- clocks: A phandle to the reference clock for this device.
> +
> +- PHY subnode: inherits from phy binding [1]
> +[1] Documentation/devicetree/bindings/net/phy.txt
> +
> +Example:
> +mdio: mdio@10091100 {
> + compatible = "hisilicon,hisi-femac-mdio";
> + reg = <0x10091100 0x10>;
> + clocks = < HI3518EV200_MDIO_CLK>;
> + #address-cells = <1>;
> + #size-cells = <0>;
> +
> + phy0: phy@1 {
> + reg = <1>;
> + };
> +};
> diff --git a/drivers/net/phy/Kconfig b/drivers/net/phy/Kconfig
> index 6dad9a9..e257322 100644
> --- a/drivers/net/phy/Kconfig
> +++ b/drivers/net/phy/Kconfig
> @@ -271,6 +271,14 @@ config MDIO_BCM_IPROC
> This module provides a driver for the MDIO busses found in the
> Broadcom iProc SoC's.
>  
> +config MDIO_HISI_FEMAC
> + tristate "Hisilicon FEMAC MDIO bus controller"
> + depends on ARCH_HISI
> + depends on HAS_IOMEM && OF_MDIO
> + help
> +   This module provides a driver for the MDIO busses found in the
> +   Hisilicon SoC that have an Fast Ethernet MAC.
> +
>  endif # PHYLIB
>  
>  config MICREL_KS8995MA
> diff --git a/drivers/net/phy/Makefile b/drivers/net/phy/Makefile
> index fcdbb92..039c4be 100644
> --- a/drivers/net/phy/Makefile
> +++ b/drivers/net/phy/Makefile
> @@ -44,3 +44,4 @@ obj-$(CONFIG_MDIO_MOXART)   += mdio-moxart.o
>  obj-$(CONFIG_MDIO_BCM_UNIMAC)+= mdio-bcm-unimac.o
>  obj-$(CONFIG_MICROCHIP_PHY)  += microchip.o
>  obj-$(CONFIG_MDIO_BCM_IPROC) += mdio-bcm-iproc.o
> +obj-$(CONFIG_MDIO_HISI_FEMAC)+= mdio-hisi-femac.o
> diff --git a/drivers/net/phy/mdio-hisi-femac.c 
> b/drivers/net/phy/mdio-hisi-femac.c
> new file mode 100644
> index 000..a9eea61
> --- /dev/null
> +++ b/drivers/net/phy/mdio-hisi-femac.c
> @@ -0,0 +1,165 @@
> +/*
> + * Hisilicon Fast Ethernet MDIO Bus Driver
> + *
> + * Copyright (c) 2016 HiSilicon Technologies Co., Ltd.
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program. If not, see .
> + */
> +
> +#include 
> +#include 
> +#include 
> +#include 
> +#include 
> +#include 
> +#include 
> +
> +#define MDIO_RWCTRL  0x00
> +#define MDIO_RO_DATA 0x04
> +#define MDIO_WRITE   BIT(13)
> +#define MDIO_RW_FINISH   BIT(15)
> +#define BIT_PHY_ADDR_OFFSET  8
> +#define BIT_WR_DATA_OFFSET   16
> +
> +struct hisi_femac_mdio_data {
> + struct clk *clk;
> + void __iomem *membase;
> +};
> +

Hi Dongpo

Overall this looks good. Just some minor comments

> +static int hisi_femac_mdio_wait_ready(struct mii_bus *bus)
> +{
> + struct hisi_femac_mdio_data *data = bus->priv;

You could just pass data here. Your read and write functions already
have it.

> + data->clk = devm_clk_get(>dev, NULL);
> + if (IS_ERR(data->clk)) {
> + ret = -ENODEV;
> + goto err_out_free_mdiobus;
> + }

Return the error which devm_clk_get() gives you.

> +
> + ret = clk_prepare_enable(data->clk);
> + if (ret)
> + goto err_out_free_mdiobus;
> +
> + ret = of_mdiobus_register(bus, np);
> + if (ret)
> + goto err_out_free_mdiobus;

You leave the clock prepared and 

Re: [PATCH v6] r8152: Add support for setting pass through MAC address on RTL8153-AD

2016-06-14 Thread Andrew Lunn
> > It is same, how to handle two network cards which tell us, that they
> > have same MAC addresses.
> > 
> 
> The kernel handles this just fine.  In doing this patch I checked to see
> what it does in that scenario.  Two devices are made.  systemd doesn't
> rename the second device via the MAC name (eg enxAABBCCDDEEFF).

What does you dhcp server do? Does it gives out the same IP address?
You then have two interfaces on the same network, with the same MAC
address and IP address. Then what happens?

 Andrew


Re: [PATCH] net: smsc911x: If PHY doesn't have an interrupt then POLL

2016-06-14 Thread Andrew Lunn
On Tue, Jun 14, 2016 at 11:16:02AM -0500, Jeremy Linton wrote:
> If the interrupt configuration isn't set and we are using the
> internal phy, then we need to poll the phy to reliably detect
> phy state changes.

Hi Jeremy

Why does the external phy not have the exact same problem?

Andrew


Re: [PATCH] net: smsc911x: If PHY doesn't have an interrupt then POLL

2016-06-14 Thread Andrew Lunn
On Tue, Jun 14, 2016 at 10:49:20PM +0300, Sergei Shtylyov wrote:
> On 06/14/2016 10:27 PM, Sergei Shtylyov wrote:
> 
> >>>If the interrupt configuration isn't set and we are using the
> >>>internal phy, then we need to poll the phy to reliably detect
> >>>phy state changes.
> >>>
> >>>Signed-off-by: Jeremy Linton 
> >>>---
> >>> drivers/net/ethernet/smsc/smsc911x.c | 3 +++
> >>> 1 file changed, 3 insertions(+)
> >>>
> >>>diff --git a/drivers/net/ethernet/smsc/smsc911x.c
> >>>b/drivers/net/ethernet/smsc/smsc911x.c
> >>>index 8af2556..369dc7d 100644
> >>>--- a/drivers/net/ethernet/smsc/smsc911x.c
> >>>+++ b/drivers/net/ethernet/smsc/smsc911x.c
> >>>@@ -1020,6 +1020,9 @@ static int smsc911x_mii_probe(struct net_device *dev)
> >>> return -ENODEV;
> >>> }
> >>>
> >>>+if ((!phydev->irq) && (!pdata->using_extphy))
> >>
> >>   Inner parens aren't needed at all.
> >
> >   Hm, 'phydev->irq' shouldn't be 0 in the first place. It seems to me we
> >should correctly initialize 'pdata->phy_irq[]' in smsc911x_mii_init()...

Hi Sergei

The mdio layer, when it allocates the mdiobus structure, will
initialise all the phy interrupts to polling.

>And looking at that array, I doubt it's really useful for
> anything... And the memcpy() there seems buggy as well -- it copies
> just 4 bytes of this array to 'pdata->mii_bus->irq'.

0 is not a valid interrupt. So it should probably loop over the array
and copy any which are not 0 into pdata->mii_bus->irq[].

Andrew


Re: Avoiding bridge flood of multicast when L2 switch is used

2016-06-14 Thread Andrew Lunn
> netdev experts,
> 
> When there is a L2 switch underneath the network interface a flooding of
> multicast at the bridge interface results in one copy of this going through 
> each
> of the slave resulting in multiple multicast packets reaching the underlying 
> switch.

Yes, this is something Florian, Vivien and i have discussed. We don't
yet see a way around it. Neither the Marvell or Broadcast switches
have a mechanism to say: Send this frame out of this list of
interfaces. All we can do is send it out a single interface. Even if
we could direct a single frame out multiple interfaces, we still have
the problem of how to teach the bridge about this, in a clean and
elegant fashion.

Overall, this seems like a hard problem. Since it is a hard problem,
implementing IGMP snooping first would make sense. Don't forward the
packet out a port unless you know there is somebody interested in it.
The swichdev parts of IGMP snooping are in place, we just need to
continue them down into DSA.

> L2 switch also duplicates the multicast packet on each egress port as done
> in software bridge. This is undesirable as it reduces the available bandwidth 
> to
> half when multicast packets are involved.

Once you have a DSA driver, the switch will not do this replication.
So you will gain something there.

 Andrew



Re: [PATCH] mdio: mux: avoid 'maybe-uninitialized' warning

2016-06-14 Thread Andrew Lunn
On Tue, Jun 14, 2016 at 12:03:17PM +0200, Arnd Bergmann wrote:
> The latest changes to the MDIO code introduced a false-positive
> warning with gcc-6 (possibly others):
> 
> drivers/net/phy/mdio-mux.c: In function 'mdio_mux_init':
> drivers/net/phy/mdio-mux.c:188:3: error: 'parent_bus_node' may be used 
> uninitialized in this function [-Werror=maybe-uninitialized]
> 
> It's easy to avoid the warning by making sure the parent_bus_node
> is initialized in both cases at the start of the function, since
> the later 'of_node_put()' call is also valid for a NULL pointer
> argument.
> 
> Signed-off-by: Arnd Bergmann <a...@arndb.de>
> Fixes: f20e6657a875 ("mdio: mux: Enhanced MDIO mux framework for integrated 
> multiplexers")

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Thanks Arnd

Andrew


Re: [PATCH net-next 2/9] net: dsa: Add support for parsing the old binding

2016-06-05 Thread Andrew Lunn
> How much support do we want to have for the old binding for in tree
> platforms? Is the plan to migrate them all to the new binding?

I think there are three cases to consider.

1) There are some old boards using setup.c files which have a platform
   device, platform data, etc. I've never used DSA in this way, and it
   could be all the recent additions have broken this. We might want
   to test this, and if it is in fact broken, and has been for a
   while, it indicates nobody uses those boards any more. We might
   suggest removing them. Even if they do work, i doubt anybody is
   interested in converting them to device tree. So we might have to
   keep the platform data support around.

2) In tree devices using the DT binding. We can update them all to the
   new binding. The kirkwood boards don't have a u-boot which is DT
   capable. Some of the armada boards do have a DT capable uboot, but
   all these boards have been added by the community, so i suspect
   they are not flashed never to be changed again.

3) Out of tree devices using the DT binding. As far as i can see,
   there is no in three board actually using the Broadcom SF2 driver
   and its odd binding. However from talking to you, i know there are
   devices out in the wild using this binding, and their DT blob is
   fixed, never to be changed again.

It actually seems odd to me that we have a nice new binding and an
implement which is reasonably clean, and we want to add code to
support a legacy binding for an out of tree board.

I need to think on this for a while. However, i don't see the old code
and binding going away anytime soon. It will take a few cycles to
determine if the old platform device/platform data still works, and to
remove the old boards if not. We can update the in tree devices to the
new binding, but we should keep the old binding a while to aid the
transition.

I'm tempted to say you should keep using the old code to support your
out of tree devices. You should define a new binding for SF2 which
conforms to the device tree binding document which just got accepted,
and add it to SF 2 alongside the legacy binding. And it would be great
if you could go the last step and actually add a boards device tree
file using it.

I'm hesitant to add legacy binding support for SF2 to the new DSA2
code. We should try to keep it free of cruft, and set a good example
for others to follow when they bring along there new drivers.

Andrew


Re: [PATCH net-next v2 5/5] net: dsa: bcm_sf2: Register our slave MDIO bus

2016-06-06 Thread Andrew Lunn
On Mon, Jun 06, 2016 at 04:14:55PM -0700, Florian Fainelli wrote:
> Register a slave MDIO bus which allows us to divert problematic
> read/writes towards conflicting pseudo-PHY address (30). Do no longer
> rely on DSA's slave_mii_bus, but instead provide our own implementation
> which offers more flexibility as to what to do, and when to register it.
> 
> We need to register it by the time we are able to get access to our
> memory mapped registers, which is not until drv->setup() time. In order
> to avoid forward declarations, we need to re-order the function bodies a
> bit.
> 
> Signed-off-by: Florian Fainelli <f.faine...@gmail.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

 Andrew


Re: [PATCH net-next v2 2/5] net: dsa: Initialize ds->enabled_port_mask and ds->phys_mii_mask

2016-06-06 Thread Andrew Lunn
> @@ -304,6 +312,18 @@ static int dsa_ds_apply(struct dsa_switch_tree *dst, 
> struct dsa_switch *ds)
>   if (err < 0)
>   return err;
>  
> + if (!ds->slave_mii_bus && ds->drv->phy_read) {
> + ds->slave_mii_bus = devm_mdiobus_alloc(ds->dev);
> + if (!ds->slave_mii_bus)
> + return err;
> +
> + dsa_slave_mii_bus_init(ds);
> +
> + err = mdiobus_register(ds->slave_mii_bus);
> + if (err < 0)
> + return err;
> + }
> +
>   for (index = 0; index < DSA_MAX_PORTS; index++) {
>   port = ds->ports[index].dn;
>   if (!port)

Hi Florian

This hunk does not seem to fit in this patch.

It is also missing the unregister in dsa_ds_unapply().

   Andrew


Re: [PATCH net-next v2 4/5] net: dsa: Initialize CPU port ethtool ops per tree

2016-06-06 Thread Andrew Lunn
On Mon, Jun 06, 2016 at 04:14:54PM -0700, Florian Fainelli wrote:
> Now that we can properly support multiple distinct trees in the system,
> using a global variable: dsa_cpu_port_ethtool_ops is getting clobbered
> as soon as the second switch tree gets probed, and we don't want that.
> 
> We need to move this to be dynamically allocated, and since we can't
> really be comparing addresses anymore to determine first time
> initialization versus any other times, just move this to dsa.c and
> dsa2.c where the remainder of the dst/ds initialization happens.
> 
> Signed-off-by: Florian Fainelli 
> ---
>  net/dsa/dsa.c  | 28 
>  net/dsa/dsa2.c |  4 
>  net/dsa/dsa_priv.h |  2 ++
>  net/dsa/slave.c| 10 --
>  4 files changed, 34 insertions(+), 10 deletions(-)
> 
> diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
> index ce3b942dce76..37026f04ee4d 100644
> --- a/net/dsa/dsa.c
> +++ b/net/dsa/dsa.c
> @@ -266,6 +266,30 @@ const struct dsa_device_ops 
> *dsa_resolve_tag_protocol(int tag_protocol)
>   return ops;
>  }
>  
> +int dsa_cpu_port_ethtool_setup(struct dsa_switch_tree *dst,
> +struct dsa_switch *ds)
> +{
> + struct net_device *master;
> + struct ethtool_ops *cpu_ops;
> +
> + master = ds->dst->master_netdev;
> + if (ds->master_netdev)
> + master = ds->master_netdev;
> +
> + cpu_ops = devm_kzalloc(ds->dev, sizeof(*cpu_ops), GFP_KERNEL);
> + if (!cpu_ops)
> + return -ENOMEM;
> +
> + memcpy(>master_ethtool_ops, master->ethtool_ops,
> +sizeof(struct ethtool_ops));
> + memcpy(cpu_ops, >master_ethtool_ops,
> +sizeof(struct ethtool_ops));
> + dsa_cpu_port_ethtool_init(cpu_ops);
> + master->ethtool_ops = cpu_ops;
> +
> + return 0;
> +}

Hi Florian

Why is there not a symmetrical dsa_cpu_port_ethertool_destroy method,
which will restore master->ethtool_ops when the switch module is
unloaded. I think at the moment, you end up with master->ethtool_ops
pointing at released memory.

 Andrew


Re: [PATCH net-next 7/9] net: dsa: Initialize CPU port ethtool ops per tree

2016-06-05 Thread Andrew Lunn
On Sun, Jun 05, 2016 at 03:29:01PM -0700, Florian Fainelli wrote:
> Le 04/06/2016 13:38, Andrew Lunn a écrit :
> >> index e8386157de30..938262010524 100644
> >> --- a/net/dsa/dsa2.c
> >> +++ b/net/dsa/dsa2.c
> >> @@ -346,7 +346,7 @@ static int dsa_ds_apply(struct dsa_switch_tree *dst, 
> >> struct dsa_switch *ds)
> >>continue;
> >>}
> >>  
> >> -  return 0;
> >> +  return dsa_cpu_port_ethtool_setup(dst, ds);
> > 
> > Hi Florian
> > 
> > This is wrong. Remember, multiple CPU ports. You need to apply this to
> > each CPU port.
> 
> We do not quite support that properly though, we still do not create a
> "cpu" network device, and there is only a single master netdev per
> dsa_switch at the moment, making the secondary CPU port interfaces
> impossible to overlay their backing "master" netdev with their companion
> switch port statistics at the moment.

Hi Florian.

Using that argument, you should probably call
dsa_cpu_port_ethtool_setup() in dsa_dst_apply, since that is what
manipulates the master interface to make it handle DSA frames.

Andrew


Re: [PATCH net-next v2 5/5] net: dsa: bcm_sf2: Register our slave MDIO bus

2016-06-07 Thread Andrew Lunn
> > With the legacy interface it is tricky. When would you call such a
> > remove/tairdown function when using the old binding?
> 
> That'd go in dsa_switch_destroy I guess, but it just covers the case
> where the whole DSA code is unloaded...

I don't think that helps you. It should not be possible to unload the
DSA core while there is an active driver. The drivers needs to unload
first

Andrew


Re: [PATCH net-next 7/8] net: dsa: mv88e6xxx: explicit compatible devices

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 08:44:55PM -0400, Vivien Didelot wrote:
> Thanks to the new device probing, we can explicit the exact switch model
> in the device tree.
> 
> Name the driver "mv88e6xxx" and list all its compatible supported chips.

No. This goes against the usual way of doing device tree compatible
strings. As far as probing goes, all the currently supported switches
are compatible with 6095. We can at run time determine the specific
switch model. This list is just a pain to managed, and has no value.

We only need to add a new compatible string when we cannot determine
at probe time what a switch model is, or we need to read the ID
register in a different way.

 Andrew


Re: [PATCH net-next 1/8] net: dsa: mv88e6xxx: fix style issues

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 08:44:49PM -0400, Vivien Didelot wrote:
> This patch fixes 5 style problems reported by checkpatch:
> 
> WARNING: suspect code indent for conditional statements (8, 24)
> #492: FILE: drivers/net/dsa/mv88e6xxx.c:492:
> + if (phydev->link)
> + reg |= PORT_PCS_CTRL_LINK_UP;
> 
> CHECK: Logical continuations should be on the previous line
> #1318: FILE: drivers/net/dsa/mv88e6xxx.c:1318:
> +  oldstate == PORT_CONTROL_STATE_FORWARDING)
> + && (state == PORT_CONTROL_STATE_DISABLED ||
> 
> CHECK: multiple assignments should be avoided
> #1662: FILE: drivers/net/dsa/mv88e6xxx.c:1662:
> + vlan->vid_begin = vlan->vid_end = next.vid;
> 
> WARNING: line over 80 characters
> #2097: FILE: drivers/net/dsa/mv88e6xxx.c:2097:
> +const struct switchdev_obj_port_vlan 
> *vlan,
> 
> WARNING: suspect code indent for conditional statements (16, 32)
> #2734: FILE: drivers/net/dsa/mv88e6xxx.c:2734:
> + if (mv88e6xxx_6352_family(ps) || mv88e6xxx_6351_family(ps) ||
> [...]
> + reg |= PORT_CONTROL_EGRESS_ADD_TAG;
> 
> total: 0 errors, 3 warnings, 2 checks, 3805 lines checked
> 
> Signed-off-by: Vivien Didelot <vivien.dide...@savoirfairelinux.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH net-next 8/8] net: dsa: mv88e6xxx: fail on mismatching probe

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 08:44:56PM -0400, Vivien Didelot wrote:
> Now that we have access at probe time to the chip info described in the
> device tree, check if the probed device matches the device node,
> otherwise warn the user and fail.

What good is this? So what if the device tree says a different
model. We don't care, we don't use that information at all, we read it
from the device itself.

The only thing that might make sense to check is the number of ports
in device tree against what we know the switch has. I don't think we
currently do this. But that actually requires a new method in the
driver structure, so the core can ask the driver after probe how many
ports it has.

   Andrew


Re: [PATCH net-next 5/8] net: dsa: mv88e6xxx: add switch register helpers

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 08:44:53PM -0400, Vivien Didelot wrote:
> Extract the allocation and registration code related to the dsa_switch
> structure in a mv88e6xxx_register_switch helper function.
> 
> For symmetry in the code, add a mv88e6xxx_unregister_switch function.

You say what you are doing, but not why?

Andrew


Re: [PATCH net-next 3/8] net: dsa: mv88e6xxx: use already declared variables

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 08:44:51PM -0400, Vivien Didelot wrote:
> In the MDIO probing function, dev is already assigned to >dev
> and np is already assigned to mdiodev->dev.of_node, so use them.
> 
> Signed-off-by: Vivien Didelot <vivien.dide...@savoirfairelinux.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH net-next 2/8] net: dsa: mv88e6xxx: remove redundant assignments

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 08:44:50PM -0400, Vivien Didelot wrote:
> The chip->ds and ds->slave_mii_bus assignments are common to both legacy
> and new MDIO probing and are already done in the later setup code.
> 
> Remove the duplicated assignments from the MDIO probing code.
> 
> Signed-off-by: Vivien Didelot <vivien.dide...@savoirfairelinux.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

Andrew


Re: [PATCH net-next 4/8] net: dsa: mv88e6xxx: do not increment bus refcount

2016-06-08 Thread Andrew Lunn
On Wed, Jun 08, 2016 at 08:44:52PM -0400, Vivien Didelot wrote:
> The MDIO device probe and remove functions are respectively incrementing
> and decrementing the bus refcount themselves. Since these bus level
> actions are out of the device scope, remove them.

I agree with the patch. But have you checked the mdio layer is doing
the right thing? If not, we should fix that first.

Andrew


Re: [RFC v2 2/2] NET: PHY: lantiq: add LED configuration support

2016-05-28 Thread Andrew Lunn
> Do you know for which PHY I could implement this? I only have access to
> the documentation for the Lantiq / Intel PHYs.

Maybe actually implementing them is too far. But you could take a look
at available datasheets and thing about how you would implement the
binding. A quick search found:

http://www.davicom.com.tw/userfile/24247/DM9161-DS-F05_091008.pdf
http://www.o2xygen.com/photo/VSC8201XVZ/VSC8201XVZ_001.pdf
http://www.ti.com.cn/cn/lit/ds/symlink/dp83640.pdf
http://www.ti.com/lit/ds/symlink/dp83848-ep.pdf
http://ww1.microchip.com/downloads/en/DeviceDoc/KSZ8081MNX-RNB.pdf

Is what you have defined flexible enough?
 
> Should this documentation file be specific for this PHY driver or
> should I add two files for documentation one describing the generic
> interface and then an additional one describing the concrete
> capabilities of this PHY?

Yes, have a generic document which any PHY should be able to use, and
a specific one per PHY.

> I also thought about this, but as far as I know there is no standard
> interface for these properties. I think setting the max speed is
> standardized by the ieee. Should there be a callback with the
> information needed for the PHY driver? I think having the parsing in the
> generic code will not make the PHY driver much simpler, but we could
> later provide these settings for different places like change the
> configuration from user space.

What we don't want is X PHYs with Y different LED bindings. We should
be aiming to describe a binding which fits the majority of PHYs. And
since it should fit the majority of PHYs we can pull parts of it into
the infrastructure. That itself will prevent people doing something
different.

Andrew


Re: [RFC v2 1/2] NET: PHY: adds driver for Lantiq PHY11G

2016-05-28 Thread Andrew Lunn
On Sat, May 28, 2016 at 06:59:00PM +0200, Hauke Mehrtens wrote:

Hi Hauke

> + /**
> +  * In most cases only one LED is connected to this phy, so
> +  * configure them all to constant on and plue mode. LED3 is

pulse not plue?

> +  * only available in some packages, let it in its reset

leave, not let?

   Andrew


Re: [RFC v2 2/2] NET: PHY: lantiq: add LED configuration support

2016-05-28 Thread Andrew Lunn
On Sat, May 28, 2016 at 06:59:01PM +0200, Hauke Mehrtens wrote:
> This makes it possible to configure the behavior of the LEDs connected
> to a PHY. The LEDs are controlled by the chip, this makes it possible
> to configure the behavior when the hardware should activate and
> deactivate the LEDs.
> 
> Signed-off-by: Hauke Mehrtens 

Hi Hauke

This is interesting. But you definitely needs to Cc: the device tree
list.

It would also be good to see basic implementations for other PHYs, so
we know the binding is generic enough.

> +LED configuration for Ethernet phys
> +
> +Property names:
> + led-const-on: conditions the LED should be constant on
> + led-pules: condition the LED should be pulsed on
> + led-blink-slow: condition the LED should slowly blink
> + led-blink-fast: condition the LED should fast blink

A binding should make it clear if properties are required or optional.

led-pulse, not led-pules.

These properties also seem to be mutually exclusive. How can it be
constantly on, yet blink? You need better descriptions.

> +property values:
> + PHY_LED_OFF:LED is off
> + PHY_LED_LINK10: link is 10MBit/s
> + PHY_LED_LINK100:link is 100MBit/s
> + PHY_LED_LINK1000:   link is 1000MBit/s
> + PHY_LED_PDOWN:  link is powered down
> + PHY_LED_EEE:link is in EEE mode
> + PHY_LED_ANEG:   auto negotiation is running
> + PHY_LED_ABIST:  analog self testing is running
> + PHY_LED_CDIAG:  cable diagnostics is running
> + PHY_LED_COPPER: copper interface detected
> + PHY_LED_FIBER:  fiber interface detected
> + PHY_LED_TXACT:  Transmit activity
> + PHY_LED_RXACT:  Receive activity
> + PHY_LED_COL:Collision

There should be a comment that not all PHYs implement all values, or
even all properties. And some PHYS will accept an ORed list of
properties, where as other will only accept a single value.

And there should be a comment to look at the binding document for the
specific PHY for what it supports. And you need such a document for
the lantiq.

Maybe some of the implementation should be pushed into the phylib.
phy_probe() already looks for the max-speed property, so it could also
parse these properties and call a function in the phy_driver
structure.

Andrew


Re: [PATCH 5/7] net:mdio-mux: Add MDIO mux driver for iProc SoCs

2016-05-30 Thread Andrew Lunn
On Mon, May 30, 2016 at 12:40:49PM +0530, Pramod Kumar wrote:
> iProc based SoCs supports the integrated mdio multiplexer which
> has the bus selection as well as mdio transaction generation logic
> inside.

Hi Pramod

Great to see you using the existing MDIO framework. Thanks.

> +static int mdio_mux_iproc_switch_fn(int current_child, int desired_child,
> + void *data)
> +{
> + struct iproc_mdiomux_desc *md = data;
> + struct mdiomux_bus_param *bp = >bus_param[desired_child];
> + u32 param, bus_id;
> + bool bus_dir;
> +
> + /* select bus and its properties */
> + bus_dir = (desired_child < EXT_BUS_START_ADDR);
> + bus_id = bus_dir ? desired_child : (desired_child - EXT_BUS_START_ADDR);
> +
> + param = (bus_dir ? 1 : 0) << MDIO_PARAM_INTERNAL_SEL;
> + param |= (bp->is_c45 ? 1 : 0) << MDIO_PARAM_C45_SEL;
> + param |= (bus_id << MDIO_PARAM_BUS_ID);
> +
> + writel(param, md->base + MDIO_PARAM_OFFSET);
> + return 0;
> +}

What i don't yet see is why you went for the concept of an integrated
MDIO and MUX. This function above is the mux function, and it looks
like it could be used to implement a standard mdio-mux driver.

Thanks
 Andrew


Re: [PATCH 3/7] binding: mdio-mux: Add DT binding doc for Broadcom MDIO bus mutiplexer

2016-05-30 Thread Andrew Lunn
On Mon, May 30, 2016 at 12:40:47PM +0530, Pramod Kumar wrote:
> Add DT binding doc for Broadcom MDIO bus mutiplexer driver.
> 
> Signed-off-by: Pramod Kumar 
> ---
>  .../bindings/net/brcm,mdio-mux-iproc.txt   | 64 
> ++
>  1 file changed, 64 insertions(+)
>  create mode 100644 
> Documentation/devicetree/bindings/net/brcm,mdio-mux-iproc.txt
> 
> diff --git a/Documentation/devicetree/bindings/net/brcm,mdio-mux-iproc.txt 
> b/Documentation/devicetree/bindings/net/brcm,mdio-mux-iproc.txt
> new file mode 100644
> index 000..dd74ee0
> --- /dev/null
> +++ b/Documentation/devicetree/bindings/net/brcm,mdio-mux-iproc.txt
> @@ -0,0 +1,64 @@
> +Properties for an MDIO bus mutiplexer found in Broadcom iProc based SoCs.
> +
> +This MDIO bus multiplexer defines buses that could be internal as well as
> +external to SoCs and could accept MDIO transaction compatible to C-22 or
> +C-45 Clause. When Child bus is selected, one need to select these two
> +properties as well to generate desired MDIO trascation on appropriate bus.
> +
> +Required properties in addition to the generic multiplexer properties:
> +
> +MDIO multiplexer node:
> +- complatible: brcm,mdio-mux-iproc.
> +
> +Child bus node:
> +-brcm,is-c45: Boolean property indicating PHYs attached to this bus supports
> +   C-45 mdio transaction.

This is-c45 seems to be at the wrong level. As far as i know, you can
mix C22 and C45 devices on a bus. It is a property of the individual
MDIO device if it uses C45 or not.

I would expect your MDIO device PHY drivers to logically OR
MII_ADDR_C45 into the address when doing an MDIO read/write using C45.

 Andrew


Re: [PATCH] net: stmmac: Fix incorrect memcpy source memory

2016-05-25 Thread Andrew Lunn
On Thu, May 26, 2016 at 12:40:23AM +0200, Marek Vasut wrote:
> The memcpy() currently copies mdio_bus_data into new_bus->irq, which
> makes no sense, since the mdio_bus_data structure contains more than
> just irqs. The code was likely supposed to copy mdio_bus_data->irqs
> into the new_bus->irq instead, so fix this.
> 
> Signed-off-by: Marek Vasut <ma...@denx.de>
> Cc: David S. Miller <da...@davemloft.net>
> Cc: Giuseppe Cavallaro <peppe.cavall...@st.com>
> Cc: Alexandre Torgue <alexandre.tor...@st.com>

Reviewed-by: Andrew Lunn <and...@lunn.ch>

 Andrew


Re: usbnet: smsc95xx: fix link detection for disabled autonegotiation

2016-05-25 Thread Andrew Lunn
On Thu, May 26, 2016 at 04:06:47AM +0200, Christoph Fritz wrote:
> To detect link status up/down for connections where autonegotiation is
> explicitly disabled, we don't get an irq but need to poll the status
> register for link up/down detection.
> This patch adds a workqueue to poll for link status.

Did you consider using the phylib? It probably does the needed polling
already, and it looks like the functions needed to implement an MDIO
bus are already in place.

Andrew


Re: [RFC PATCH 14/16] net: dsa: Add new binding implementation

2016-05-27 Thread Andrew Lunn
On Fri, May 27, 2016 at 04:39:05PM -0400, Vivien Didelot wrote:
> 
> Hi Andrew, Florian,
> 
> Here again, I'd suggested an implicit namespace for functions taking a
> dsa_switch_tree structure as first argument, i.e. dsa_tree_do_foo().

Using tree actually makes things worse, since tree is never used
anywhere in the current code. It is always called dst. If you do this,
you also need to replace every instance of dst with tree.

We mostly have a good convention

struct dsa_switch *ds;
dsa_switch_tree *dst;

What is not quite consistent is

struct dsa_chip_data *cd

which should really be

struct dsa_chip_data *dcd

but we are consistent with using cd everywhere.
 
> Since we are likely to spend some time in net/dsa, it'd be great to
> introduce the new bindings and an intuitive API at the same time ;-)

They are two separate things. And the binding will be set in stone,
never to be changed again in incompatible ways, where as the API we
can change as much as we like. We should be concentrate on the
binding.

Andrew


Re: [RFC PATCH 09/16] dsa: dsa: Split up creating/destroying of DSA and CPU ports

2016-05-27 Thread Andrew Lunn
On Fri, May 27, 2016 at 03:25:47PM -0400, Vivien Didelot wrote:
> Hi Andrew, Florian,
> 
> I suggest to use this RFC to agree on a consistent and robust API for
> the DSA layer. Some functions have non-intuitive names or signatures.

Nope.

What is important is getting this patchset accepted and merged, so
people can write drivers using it.

Changes like this can come later, since hopefully all changes like
this are internal. They don't affect the drivers, or the API to the
core.

Andrew


Re: [RFC PATCH 11/16] net: dsa: Refactor selection of tag ops into a function

2016-05-27 Thread Andrew Lunn
On Fri, May 27, 2016 at 03:35:57PM -0400, Vivien Didelot wrote:
> Hi Andrew,
> 
> Andrew Lunn <and...@lunn.ch> writes:
> 
> > @@ -26,6 +26,7 @@ enum dsa_tag_protocol {
> > DSA_TAG_PROTO_TRAILER,
> > DSA_TAG_PROTO_EDSA,
> > DSA_TAG_PROTO_BRCM,
> > +   _DSA_TAG_LAST,
> >  };
> 
> I would avoid _ prefixed functions or symbols, we've seen in mv88e6xxx
> that it doesn't make the code really readable.

The point is to make is special, so that people look at it, wonder why
it is special, and don't make the stupid mistakes of adding a new
protocol after it.

However, if you don't like the _, we can just add a comment
/* MUST BE LAST */

> I don't see the need to add a dsa_device_ops array. I'd keep the switch
> case on tag_protocol within this new dsa_resolve_tag_protocol function,
> to make it more readable (no value checking necessary).

I don't see one way being better than the other. I see it as a
personal preference. If you don't like it, i won't NACK a patch
submitted after it has been accepted which changes it to your personal
preference.

  Andrew


Re: [RFC PATCH 09/16] dsa: dsa: Split up creating/destroying of DSA and CPU ports

2016-05-27 Thread Andrew Lunn
> dsa_cpu_dsa_setups is not really meaningful and doesn't add much
> value.

I would disagree.  Quoting Documentation/CodingStyle

Chapter 6: Functions

Functions should be short and sweet, and do just one thing.  They should
fit on one or two screenfuls of text (the ISO/ANSI screen size is 80x24,
as we all know), and do one thing and do that well.

dsa_cpu_dsa_setups iterates the ports and find the dsa and cpu ports
that need setting up.

dsa_cpu_dsa_setup() does the actual setup.

These are completely different things, and so should be in different
functions.

Andrew


Re: [RFC PATCH 09/16] dsa: dsa: Split up creating/destroying of DSA and CPU ports

2016-05-27 Thread Andrew Lunn
On Fri, May 27, 2016 at 10:33:49AM -0400, Vivien Didelot wrote:
> Hi Andrew,
> 
> Andrew Lunn <and...@lunn.ch> writes:
> 
> > -static void dsa_switch_destroy(struct dsa_switch *ds)
> > +void dsa_cpu_dsa_destroy(struct device_node *port_dn)
> >  {
> > -   struct device_node *port_dn;
> > struct phy_device *phydev;
> > +
> > +   if (of_phy_is_fixed_link(port_dn)) {
> > +   phydev = of_phy_find_device(port_dn);
> > +   if (phydev) {
> > +   phy_device_free(phydev);
> > +   fixed_phy_unregister(phydev);
> > +   }
> > +   }
> > +}
> > +
> > +static void dsa_switch_destroy(struct dsa_switch *ds)
> > +{
> > int port;
> >  
> >  #ifdef CONFIG_NET_DSA_HWMON
> > @@ -445,17 +467,11 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
> > dsa_slave_destroy(ds->ports[port].netdev);
> > }
> >  
> > -   /* Remove any fixed link PHYs */
> > +   /* Disable configuration of the CPU and DSA ports */
> > for (port = 0; port < DSA_MAX_PORTS; port++) {
> > -   port_dn = ds->ports[port].dn;
> > -   if (of_phy_is_fixed_link(port_dn)) {
> > -   phydev = of_phy_find_device(port_dn);
> > -   if (phydev) {
> > -   phy_device_free(phydev);
> > -   of_node_put(port_dn);
> 
> Why does dsa_cpu_dsa_destroy drop that of_node_put call?

The of node reference counting is broken. The DT maintainers actually
say not to care, the whole reference counting scheme is broken. Which
is a bit sad really. There was a discussion about this a couple of
months ago.

Anyway, the reference is taken in dsa_of_probe() as part of the
or_each_available_child_of_node(child, port). This reference has
nothing to do with the port being a fixed link or not. So freeing it
here is inappropriate. The correct place to free it would probably be
in dsa_of_remove.
 
> > -   fixed_phy_unregister(phydev);
> > -   }
> > -   }
> > +   if ((dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port)))
> > +   continue;
> 
> Why do we skip DSA and CPU ports here? The previous code didn't.
> 
> > +   dsa_cpu_dsa_destroy(ds->ports[port].dn);

They are now destroyed by the newly added dsa_cpu_dsa_destroy().  I'm
making the code more symmetrical and easier to re-use. The inverse of
this function is dsa_switch_setup_one() and it also uses a helper
function to setup the dsa and cpu ports, dsa_cpu_dsa_setups().

 Andrew


Re: [RFC PATCH 12/16] dsa: Make mdio bus optional

2016-05-27 Thread Andrew Lunn
On Fri, May 27, 2016 at 10:55:45AM -0400, Vivien Didelot wrote:
> Hi Andrew,
> 
> Andrew Lunn <and...@lunn.ch> writes:
> 
> > -   mdiobus_unregister(ds->slave_mii_bus);
> > +   if (ds->slave_mii_bus && ds->drv->phy_read)
> > +   mdiobus_unregister(ds->slave_mii_bus);
> 
> So if a driver registered the slave MII bus itself, it may have
> unregistered it itself as well, so checking ds->slave_mii_bus is OK
> (assuming the driver correctly zero'ed it).
> 
> But is it necessary to check ds->drv->phy_read?

It makes the code symmetrical to the register code, which makes the
same check. My experience is that keeping the code symmetrical results
in less surprises late on.

One such surprise could be a driver that does not zero
ds->slave_mii_bus. In fact, mv88e6xxx does not zero it. So we would
get a double unregister happening. We also don't want the core
unregistering it, since we have other cleanup work to do, we have an
of_node_put() to call.

Andrew


Re: [PATCH v2 3/5] drivers: net: phy: Add MDIO driver

2016-05-31 Thread Andrew Lunn
On Tue, May 31, 2016 at 05:10:38PM -0700, Iyappan Subramanian wrote:
> +static int xgene_mdio_reset(struct xgene_mdio_pdata *pdata)
> +{
> + int ret;
> +
> + if (pdata->mdio_id == XGENE_MDIO_RGMII) {
> + if (pdata->dev->of_node) {
> + clk_prepare_enable(pdata->clk);
> + clk_disable_unprepare(pdata->clk);
> + clk_prepare_enable(pdata->clk);

Hi Iyappan

Is that a workaround for a hardware problem? If so, i would suggest
adding a comment, to stop people submitting a patch simplifying it.


> +static int xgene_mdio_probe(struct platform_device *pdev)
> +{
> + struct device *dev = >dev;
> + struct mii_bus *mdio_bus;
> + const struct of_device_id *of_id;
> + struct resource *res;
> + struct xgene_mdio_pdata *pdata;
> + void __iomem *csr_addr;
> + int mdio_id = 0, ret = 0;
> +


> + of_id = of_match_device(xgene_mdio_of_match, >dev);
> + if (mdio_id == XGENE_MDIO_RGMII) {
> + mdio_bus->read = xgene_mdio_rgmii_read;
> + mdio_bus->write = xgene_mdio_rgmii_write;
> + } else {
> + mdio_bus->read = xgene_xfi_mdio_read;
> + mdio_bus->write = xgene_xfi_mdio_write;
> + }

> +static const struct of_device_id xgene_mdio_of_match[] = {
> + {
> + .compatible = "apm,xgene-mdio-rgmii",
> + .data = (void *)XGENE_MDIO_RGMII
> + },
> + {
> + .compatible = "apm,xgene-mdio-xfi",
> + .data = (void *)XGENE_MDIO_XFI},
> + {},
> +};


This all makes me think you should have two separate MDIO drivers, one
for each compatible string. There is not that much shared code.

Andrew


Re: FWD: [PATCH v2] Marvell phy: add fiber status check for some components

2016-06-02 Thread Andrew Lunn
On Fri, May 27, 2016 at 11:23:22AM +0200, Charles-Antoine Couret wrote:
> 
> Hello,
> I'm sorry to repost that, but after one month, I need a answer to continue to 
> imrpove my patch in the right direction. :)

Hi Charles-Aontine

Florian and I had a quick discussion. We think going with the Marvell
datasheet documentation is best.

Please just be careful to ensure the generic code does not try to
unconditionally read the registers, only the Marvell driver. I'm
talking about functions like genphy_config_advert(),
genphy_setup_forced(), genphy_restart_aneg() etc. We need to ensure we
are consistently using the correct page.

  Andrew


Re: [PATCH] r8152: Add support for setting MAC to system's Auxiliary MAC address

2016-06-02 Thread Andrew Lunn
> > 
> > > + pr_info("r8152: Using system auxiliary MAC address");
> > 
> > It would be great to write also mac address into that pr_info

And since there could be multiple r8152 in the system, it would be
good to indicate which of them is having its MAC changed. So
netdev_info() or dev_info().

  Andrew


Re: [PATCH v2] r8152: Add support for setting MAC to system's Auxiliary MAC address

2016-06-02 Thread Andrew Lunn
> > And you want to check this for all Dell devices?  Please be model
> > specific, I doubt a bunch of Dell servers wants to run this code...
> > 
> 
> Tracking model specific is really going to turn into a giant list never 
> ending list.
> To drill down more specifically, I can match on chassis too.

Does Dell happen to use its own USB Vendor ID for the USB device in
the dock? You could go at this problem from the other direction if it
does have a unique vendor ID.

 Andrew


[RFC PATCH 02/16] net: dsa: mv88e6xxx: fix circular lock in PPU work

2016-05-26 Thread Andrew Lunn
From: Vivien Didelot 

Lock debugging shows that there is a possible circular lock in the PPU
work code. Switch the lock order of smi_mutex and ppu_mutex to fix this.

Here's the full trace:

[4.341325] ==
[4.347519] [ INFO: possible circular locking dependency detected ]
[4.353800] 4.6.0 #4 Not tainted
[4.357039] ---
[4.363315] kworker/0:1/328 is trying to acquire lock:
[4.368463]  (>smi_mutex){+.+.+.}, at: [<8049c758>] 
mv88e6xxx_reg_read+0x30/0x54
[4.376313]
[4.376313] but task is already holding lock:
[4.382160]  (>ppu_mutex){+.+...}, at: [<8049cac0>] 
mv88e6xxx_ppu_reenable_work+0x28/0xd4
[4.390772]
[4.390772] which lock already depends on the new lock.
[4.390772]
[4.398963]
[4.398963] the existing dependency chain (in reverse order) is:
[4.406461]
[4.406461] -> #1 (>ppu_mutex){+.+...}:
[4.410897][<806d86bc>] mutex_lock_nested+0x54/0x360
[4.416606][<8049a800>] mv88e6xxx_ppu_access_get+0x28/0x100
[4.422906][<8049b778>] mv88e6xxx_phy_read+0x90/0xdc
[4.428599][<806a4534>] dsa_slave_phy_read+0x3c/0x40
[4.434300][<804943ec>] mdiobus_read+0x68/0x80
[4.439481][<804939d4>] get_phy_device+0x58/0x1d8
[4.444914][<80493ed0>] mdiobus_scan+0x24/0xf4
[4.450078][<8049409c>] __mdiobus_register+0xfc/0x1ac
[4.455857][<806a40b0>] dsa_probe+0x860/0xca8
[4.460934][<8043246c>] platform_drv_probe+0x5c/0xc0
[4.466627][<804305a0>] driver_probe_device+0x118/0x450
[4.472589][<80430b00>] __device_attach_driver+0xac/0x128
[4.478724][<8042e350>] bus_for_each_drv+0x74/0xa8
[4.484235][<804302d8>] __device_attach+0xc4/0x154
[4.489755][<80430cec>] device_initial_probe+0x1c/0x20
[4.495612][<8042f620>] bus_probe_device+0x98/0xa0
[4.501123][<8042fbd0>] deferred_probe_work_func+0x4c/0xd4
[4.507328][<8013a794>] process_one_work+0x1a8/0x604
[4.513030][<8013ac54>] worker_thread+0x64/0x528
[4.518367][<801409e8>] kthread+0xec/0x100
[4.523201][<80108f30>] ret_from_fork+0x14/0x24
[4.528462]
[4.528462] -> #0 (>smi_mutex){+.+.+.}:
[4.532895][<8015ad5c>] lock_acquire+0xb4/0x1dc
[4.538154][<806d86bc>] mutex_lock_nested+0x54/0x360
[4.543856][<8049c758>] mv88e6xxx_reg_read+0x30/0x54
[4.549549][<8049cad8>] mv88e6xxx_ppu_reenable_work+0x40/0xd4
[4.556022][<8013a794>] process_one_work+0x1a8/0x604
[4.561707][<8013ac54>] worker_thread+0x64/0x528
[4.567053][<801409e8>] kthread+0xec/0x100
[4.571878][<80108f30>] ret_from_fork+0x14/0x24
[4.577139]
[4.577139] other info that might help us debug this:
[4.577139]
[4.585159]  Possible unsafe locking scenario:
[4.585159]
[4.591093]CPU0CPU1
[4.595631]
[4.600169]   lock(>ppu_mutex);
[4.603693]lock(>smi_mutex);
[4.609742]lock(>ppu_mutex);
[4.615790]   lock(>smi_mutex);
[4.619314]
[4.619314]  *** DEADLOCK ***
[4.619314]
[4.625256] 3 locks held by kworker/0:1/328:
[4.629537]  #0:  ("events"){.+.+..}, at: [<8013a704>] 
process_one_work+0x118/0x604
[4.637288]  #1:  ((>ppu_work)){+.+...}, at: [<8013a704>] 
process_one_work+0x118/0x604
[4.645653]  #2:  (>ppu_mutex){+.+...}, at: [<8049cac0>] 
mv88e6xxx_ppu_reenable_work+0x28/0xd4
[4.654714]
[4.654714] stack backtrace:
[4.659098] CPU: 0 PID: 328 Comm: kworker/0:1 Not tainted 4.6.0 #4
[4.665286] Hardware name: Freescale Vybrid VF5xx/VF6xx (Device Tree)
[4.671748] Workqueue: events mv88e6xxx_ppu_reenable_work
[4.677174] Backtrace:
[4.679674] [<8010d354>] (dump_backtrace) from [<8010d5a0>] 
(show_stack+0x20/0x24)
[4.687252]  r6:80fb3c88 r5:80fb3c88 r4:80fb4728 r3:0002
[4.693003] [<8010d580>] (show_stack) from [<803b45e8>] 
(dump_stack+0x24/0x28)
[4.700246] [<803b45c4>] (dump_stack) from [<80157398>] 
(print_circular_bug+0x208/0x32c)
[4.708361] [<80157190>] (print_circular_bug) from [<8015a630>] 
(__lock_acquire+0x185c/0x1b80)
[4.716982]  r10:9ec22a00 r9:0060 r8:8164b6bc r7:0040 
r6:0003 r5:8163a5b4
[4.724905]  r4:0003 r3:9ec22de8
[4.728537] [<80158dd4>] (__lock_acquire) from [<8015ad5c>] 
(lock_acquire+0xb4/0x1dc)
[4.736378]  r10:6013 

[RFC PATCH 14/16] net: dsa: Add new binding implementation

2016-05-26 Thread Andrew Lunn
The existing DSA binding has a number of limitations and problems. The
main problem is that it cannot represent a switch as a linux device,
hanging off some bus. It is limited to one CPU port. The DSA platform
device is artificial, and does not really represent hardware.

Implement a new binding which can be embedded into any type of node on
a bus to represent one switch device, and its links to other switches.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
Signed-off-by: Florian Fainelli <f.faine...@gmail.com>
---
 drivers/net/dsa/mv88e6xxx.c |   7 +
 include/net/dsa.h   |  20 ++
 net/dsa/Makefile|   2 +-
 net/dsa/dsa.c   |   1 +
 net/dsa/dsa2.c  | 653 
 net/dsa/dsa_priv.h  |   2 +-
 net/dsa/slave.c |   8 +-
 7 files changed, 689 insertions(+), 4 deletions(-)
 create mode 100644 net/dsa/dsa2.c

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 8fbc771f0475..a6ccfdfbe225 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -3749,6 +3749,12 @@ int mv88e6xxx_probe(struct mdio_device *mdiodev)
 
dev_set_drvdata(dev, ds);
 
+   err = dsa_register_switch(ds, mdiodev->dev.of_node);
+   if (err) {
+   mv88e6xxx_mdio_unregister(ps);
+   return err;
+   }
+
dev_info(dev, "switch 0x%x probed: %s, revision %u\n",
 prod_num, ps->info->name, rev);
 
@@ -3760,6 +3766,7 @@ static void mv88e6xxx_remove(struct mdio_device *mdiodev)
struct dsa_switch *ds = dev_get_drvdata(>dev);
struct mv88e6xxx_priv_state *ps = ds_to_priv(ds);
 
+   dsa_unregister_switch(ds);
put_device(>bus->dev);
 
mv88e6xxx_mdio_unregister(ps);
diff --git a/include/net/dsa.h b/include/net/dsa.h
index adb75422bc6c..032f6efa4b3e 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -86,6 +86,17 @@ struct dsa_platform_data {
 struct packet_type;
 
 struct dsa_switch_tree {
+   struct list_headlist;
+
+   /* Tree identifier */
+   u32 tree;
+
+   /* Number of switches attached to this tree */
+   struct kref refcount;
+
+   /* Has this tree been applied to the hardware? */
+   bool applied;
+
/*
 * Configuration data for the platform device that owns
 * this dsa switch tree instance.
@@ -172,9 +183,15 @@ struct dsa_switch {
 #endif
 
/*
+* The lower device this switch uses to talk to the host
+*/
+   struct net_device *master_netdev;
+
+   /*
 * Slave mii_bus and devices for the individual ports.
 */
u32 dsa_port_mask;
+   u32 cpu_port_mask;
u32 enabled_port_mask;
u32 phys_mii_mask;
struct dsa_port ports[DSA_MAX_PORTS];
@@ -363,4 +380,7 @@ static inline bool dsa_uses_tagged_protocol(struct 
dsa_switch_tree *dst)
 {
return dst->rcv != NULL;
 }
+
+void dsa_unregister_switch(struct dsa_switch *ds);
+int dsa_register_switch(struct dsa_switch *ds, struct device_node *np);
 #endif
diff --git a/net/dsa/Makefile b/net/dsa/Makefile
index da06ed1df620..8af4ded70f1c 100644
--- a/net/dsa/Makefile
+++ b/net/dsa/Makefile
@@ -1,6 +1,6 @@
 # the core
 obj-$(CONFIG_NET_DSA) += dsa_core.o
-dsa_core-y += dsa.o slave.o
+dsa_core-y += dsa.o slave.o dsa2.o
 
 # tagging formats
 dsa_core-$(CONFIG_NET_DSA_TAG_BRCM) += tag_brcm.o
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index b1787e2f4bb3..b3cada3ecab7 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -294,6 +294,7 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
}
dst->cpu_switch = index;
dst->cpu_port = i;
+   ds->cpu_port_mask |= 1 << i;
} else if (!strcmp(name, "dsa")) {
ds->dsa_port_mask |= 1 << i;
} else {
diff --git a/net/dsa/dsa2.c b/net/dsa/dsa2.c
new file mode 100644
index ..4e5051bed643
--- /dev/null
+++ b/net/dsa/dsa2.c
@@ -0,0 +1,653 @@
+/*
+ * net/dsa/dsa2.c - Hardware switch handling, binding version 2
+ * Copyright (c) 2008-2009 Marvell Semiconductor
+ * Copyright (c) 2013 Florian Fainelli <flor...@openwrt.org>
+ * Copyright (c) 2016 Andrew Lunn <and...@lunn.ch>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include "dsa_priv.h"
+
+static LIST_HEAD(dsa_switch_trees);
+static DEFINE_MUTEX(dsa2_mutex);
+
+static struct dsa_switc

[RFC PATCH 13/16] net: dsa: mv88e6xxx: Refactor MDIO so driver registers mdio bus

2016-05-26 Thread Andrew Lunn
Have the switch driver register its own MDIO bus. This allows for an
mdio property in the device tree, with child nodes for phys, which
can be referenced via phandles, etc.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c | 204 ++--
 drivers/net/dsa/mv88e6xxx.h |   6 ++
 2 files changed, 144 insertions(+), 66 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 11845eccf670..8fbc771f0475 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -21,6 +21,7 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -238,16 +239,16 @@ int mv88e6xxx_set_addr(struct dsa_switch *ds, u8 *addr)
return mv88e6xxx_set_addr_direct(ds, addr);
 }
 
-static int _mv88e6xxx_phy_read(struct mv88e6xxx_priv_state *ps, int addr,
-  int regnum)
+static int _mv88e6xxx_mdio_read(struct mv88e6xxx_priv_state *ps, int addr,
+   int regnum)
 {
if (addr >= 0)
return _mv88e6xxx_reg_read(ps, addr, regnum);
return 0x;
 }
 
-static int _mv88e6xxx_phy_write(struct mv88e6xxx_priv_state *ps, int addr,
-   int regnum, u16 val)
+static int _mv88e6xxx_mdio_write(struct mv88e6xxx_priv_state *ps, int addr,
+int regnum, u16 val)
 {
if (addr >= 0)
return _mv88e6xxx_reg_write(ps, addr, regnum, val);
@@ -378,8 +379,8 @@ void mv88e6xxx_ppu_state_init(struct mv88e6xxx_priv_state 
*ps)
ps->ppu_timer.function = mv88e6xxx_ppu_reenable_timer;
 }
 
-static int mv88e6xxx_phy_read_ppu(struct mv88e6xxx_priv_state *ps, int addr,
- int regnum)
+static int mv88e6xxx_mdio_read_ppu(struct mv88e6xxx_priv_state *ps, int addr,
+  int regnum)
 {
int ret;
 
@@ -392,8 +393,8 @@ static int mv88e6xxx_phy_read_ppu(struct 
mv88e6xxx_priv_state *ps, int addr,
return ret;
 }
 
-static int mv88e6xxx_phy_write_ppu(struct mv88e6xxx_priv_state *ps, int addr,
-  int regnum, u16 val)
+static int mv88e6xxx_mdio_write_ppu(struct mv88e6xxx_priv_state *ps, int addr,
+   int regnum, u16 val)
 {
int ret;
 
@@ -829,7 +830,7 @@ static int mv88e6xxx_wait(struct mv88e6xxx_priv_state *ps, 
int reg,
return ret;
 }
 
-static int _mv88e6xxx_phy_wait(struct mv88e6xxx_priv_state *ps)
+static int _mv88e6xxx_mdio_wait(struct mv88e6xxx_priv_state *ps)
 {
return _mv88e6xxx_wait(ps, REG_GLOBAL2, GLOBAL2_SMI_OP,
   GLOBAL2_SMI_OP_BUSY);
@@ -1076,8 +1077,8 @@ static int _mv88e6xxx_atu_wait(struct 
mv88e6xxx_priv_state *ps)
   GLOBAL_ATU_OP_BUSY);
 }
 
-static int _mv88e6xxx_phy_read_indirect(struct mv88e6xxx_priv_state *ps,
-   int addr, int regnum)
+static int _mv88e6xxx_mdio_read_indirect(struct mv88e6xxx_priv_state *ps,
+int addr, int regnum)
 {
int ret;
 
@@ -1087,7 +1088,7 @@ static int _mv88e6xxx_phy_read_indirect(struct 
mv88e6xxx_priv_state *ps,
if (ret < 0)
return ret;
 
-   ret = _mv88e6xxx_phy_wait(ps);
+   ret = _mv88e6xxx_mdio_wait(ps);
if (ret < 0)
return ret;
 
@@ -1096,8 +1097,8 @@ static int _mv88e6xxx_phy_read_indirect(struct 
mv88e6xxx_priv_state *ps,
return ret;
 }
 
-static int _mv88e6xxx_phy_write_indirect(struct mv88e6xxx_priv_state *ps,
-int addr, int regnum, u16 val)
+static int _mv88e6xxx_mdio_write_indirect(struct mv88e6xxx_priv_state *ps,
+ int addr, int regnum, u16 val)
 {
int ret;
 
@@ -1109,7 +1110,7 @@ static int _mv88e6xxx_phy_write_indirect(struct 
mv88e6xxx_priv_state *ps,
   GLOBAL2_SMI_OP_22_WRITE | (addr << 5) |
   regnum);
 
-   return _mv88e6xxx_phy_wait(ps);
+   return _mv88e6xxx_mdio_wait(ps);
 }
 
 static int mv88e6xxx_get_eee(struct dsa_switch *ds, int port,
@@ -1123,7 +1124,7 @@ static int mv88e6xxx_get_eee(struct dsa_switch *ds, int 
port,
 
mutex_lock(>smi_mutex);
 
-   reg = _mv88e6xxx_phy_read_indirect(ps, port, 16);
+   reg = _mv88e6xxx_mdio_read_indirect(ps, port, 16);
if (reg < 0)
goto out;
 
@@ -1154,7 +1155,7 @@ static int mv88e6xxx_set_eee(struct dsa_switch *ds, int 
port,
 
mutex_lock(>smi_mutex);
 
-   ret = _mv88e6xxx_phy_read_indirect(ps, port, 16);
+   ret = _mv88e6xxx_mdio_read_indirect(ps, port, 16);
if (ret < 0)
goto out;
 
@@ -1164,7 +1165,7 @@ static int mv88e6xxx_set_eee(struct dsa_switch *ds, int 
port,
if (e->tx_lpi_enabled)
  

[RFC PATCH 12/16] dsa: Make mdio bus optional

2016-05-26 Thread Andrew Lunn
The switch may want to instantiate its own MDIO bus. Only do it
centrally if the switch has not already created one, and the read op
is implemented.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 net/dsa/dsa.c | 24 +---
 1 file changed, 13 insertions(+), 11 deletions(-)

diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 49cdf143c822..b1787e2f4bb3 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -340,17 +340,18 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
if (ret < 0)
goto out;
 
-   ds->slave_mii_bus = devm_mdiobus_alloc(parent);
-   if (ds->slave_mii_bus == NULL) {
-   ret = -ENOMEM;
-   goto out;
-   }
-   dsa_slave_mii_bus_init(ds);
-
-   ret = mdiobus_register(ds->slave_mii_bus);
-   if (ret < 0)
-   goto out;
+   if (!ds->slave_mii_bus && drv->phy_read) {
+   ds->slave_mii_bus = devm_mdiobus_alloc(parent);
+   if (!ds->slave_mii_bus) {
+   ret = -ENOMEM;
+   goto out;
+   }
+   dsa_slave_mii_bus_init(ds);
 
+   ret = mdiobus_register(ds->slave_mii_bus);
+   if (ret < 0)
+   goto out;
+   }
 
/*
 * Create network devices for physical switch ports.
@@ -493,7 +494,8 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
dsa_cpu_dsa_destroy(ds->ports[port].dn);
}
 
-   mdiobus_unregister(ds->slave_mii_bus);
+   if (ds->slave_mii_bus && ds->drv->phy_read)
+   mdiobus_unregister(ds->slave_mii_bus);
 }
 
 #ifdef CONFIG_PM_SLEEP
-- 
2.8.1



[RFC PATCH 11/16] net: dsa: Refactor selection of tag ops into a function

2016-05-26 Thread Andrew Lunn
Replace the two switch statements with an array lookup, and store the
result in the dsa tree structure. The drivers no longer need to know
the selected tag protocol, so remove it from the dsa switch structure.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 include/net/dsa.h  |  8 +-
 net/dsa/dsa.c  | 71 ++
 net/dsa/dsa_priv.h |  1 +
 net/dsa/slave.c| 35 +--
 4 files changed, 54 insertions(+), 61 deletions(-)

diff --git a/include/net/dsa.h b/include/net/dsa.h
index ea0e7d30342b..adb75422bc6c 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -26,6 +26,7 @@ enum dsa_tag_protocol {
DSA_TAG_PROTO_TRAILER,
DSA_TAG_PROTO_EDSA,
DSA_TAG_PROTO_BRCM,
+   _DSA_TAG_LAST,
 };
 
 #define DSA_MAX_SWITCHES   4
@@ -100,7 +101,6 @@ struct dsa_switch_tree {
   struct net_device *dev,
   struct packet_type *pt,
   struct net_device *orig_dev);
-   enum dsa_tag_protocol   tag_protocol;
 
/*
 * Original copy of the master netdev ethtool_ops
@@ -117,6 +117,12 @@ struct dsa_switch_tree {
 * Data for the individual switch chips.
 */
struct dsa_switch   *ds[DSA_MAX_SWITCHES];
+
+   /*
+* Tagging protocol operations for adding and removing an
+* encapsulation tag.
+*/
+   const struct dsa_device_ops *tag_ops;
 };
 
 struct dsa_port {
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 20eede3facf5..49cdf143c822 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -29,6 +29,33 @@
 
 char dsa_driver_version[] = "0.1";
 
+static struct sk_buff *dsa_slave_notag_xmit(struct sk_buff *skb,
+   struct net_device *dev)
+{
+   /* Just return the original SKB */
+   return skb;
+}
+
+static const struct dsa_device_ops none_ops = {
+   .xmit   = dsa_slave_notag_xmit,
+   .rcv= NULL,
+};
+
+const struct dsa_device_ops *dsa_device_ops[_DSA_TAG_LAST] = {
+#ifdef CONFIG_NET_DSA_TAG_DSA
+   [DSA_TAG_PROTO_DSA] = _netdev_ops,
+#endif
+#ifdef CONFIG_NET_DSA_TAG_EDSA
+   [DSA_TAG_PROTO_EDSA] = _netdev_ops,
+#endif
+#ifdef CONFIG_NET_DSA_TAG_TRAILER
+   [DSA_TAG_PROTO_TRAILER] = _netdev_ops,
+#endif
+#ifdef CONFIG_NET_DSA_TAG_BRCM
+   [DSA_TAG_PROTO_BRCM] = _netdev_ops,
+#endif
+   [DSA_TAG_PROTO_NONE] = _ops,
+};
 
 /* switch driver registration ***/
 static DEFINE_MUTEX(dsa_switch_drivers_mutex);
@@ -225,6 +252,20 @@ static int dsa_cpu_dsa_setups(struct dsa_switch *ds, 
struct device *dev)
return 0;
 }
 
+const struct dsa_device_ops *dsa_resolve_tag_protocol(int tag_protocol)
+{
+   const struct dsa_device_ops *ops;
+
+   if (tag_protocol >= _DSA_TAG_LAST)
+   return ERR_PTR(-EINVAL);
+   ops = dsa_device_ops[tag_protocol];
+
+   if (!ops)
+   return ERR_PTR(-ENOPROTOOPT);
+
+   return ops;
+}
+
 static int dsa_switch_setup_one(struct dsa_switch *ds, struct device *parent)
 {
struct dsa_switch_driver *drv = ds->drv;
@@ -277,35 +318,13 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
 * switch.
 */
if (dst->cpu_switch == index) {
-   switch (drv->tag_protocol) {
-#ifdef CONFIG_NET_DSA_TAG_DSA
-   case DSA_TAG_PROTO_DSA:
-   dst->rcv = dsa_netdev_ops.rcv;
-   break;
-#endif
-#ifdef CONFIG_NET_DSA_TAG_EDSA
-   case DSA_TAG_PROTO_EDSA:
-   dst->rcv = edsa_netdev_ops.rcv;
-   break;
-#endif
-#ifdef CONFIG_NET_DSA_TAG_TRAILER
-   case DSA_TAG_PROTO_TRAILER:
-   dst->rcv = trailer_netdev_ops.rcv;
-   break;
-#endif
-#ifdef CONFIG_NET_DSA_TAG_BRCM
-   case DSA_TAG_PROTO_BRCM:
-   dst->rcv = brcm_netdev_ops.rcv;
-   break;
-#endif
-   case DSA_TAG_PROTO_NONE:
-   break;
-   default:
-   ret = -ENOPROTOOPT;
+   dst->tag_ops = dsa_resolve_tag_protocol(drv->tag_protocol);
+   if (IS_ERR(dst->tag_ops)) {
+   ret = PTR_ERR(dst->tag_ops);
goto out;
}
 
-   dst->tag_protocol = drv->tag_protocol;
+   dst->rcv = dst->tag_ops->rcv;
}
 
memcpy(ds->rtable, cd->rtable, sizeof(ds->rtable));
diff --git a/net/dsa/dsa_priv.h b/net/dsa/dsa_priv.h
index dbea5d9e7f75..72f7b8989cfb 100644
--- a/net/dsa/dsa_priv.h
+++ b/net/dsa/dsa_priv.h
@@ -53,6 +53,7 @@ extern char dsa_driver_version[];
 int dsa_cpu_dsa_setup(struct dsa_switch *ds, struct devi

[RFC PATCH 10/16] net: dsa: mv88e6xxx: Only support EDSA tagging

2016-05-26 Thread Andrew Lunn
The merged driver no longer offers the option to use DSA tagging. So
remove the code to setup the switch to do DSA tagging and hard code
the use of EDSA.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c | 8 ++--
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 492801a6398c..11845eccf670 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -2725,11 +2725,8 @@ static int mv88e6xxx_setup_port(struct 
mv88e6xxx_priv_state *ps, int port)
if (mv88e6xxx_6352_family(ps) || mv88e6xxx_6351_family(ps) ||
mv88e6xxx_6165_family(ps) || mv88e6xxx_6097_family(ps) ||
mv88e6xxx_6320_family(ps)) {
-   if (ds->dst->tag_protocol == DSA_TAG_PROTO_EDSA)
-   reg |= PORT_CONTROL_FRAME_ETHER_TYPE_DSA;
-   else
-   reg |= PORT_CONTROL_FRAME_MODE_DSA;
-   reg |= PORT_CONTROL_FORWARD_UNKNOWN |
+   reg |= PORT_CONTROL_FRAME_ETHER_TYPE_DSA |
+   PORT_CONTROL_FORWARD_UNKNOWN |
PORT_CONTROL_FORWARD_UNKNOWN_MC;
}
 
@@ -2737,7 +2734,6 @@ static int mv88e6xxx_setup_port(struct 
mv88e6xxx_priv_state *ps, int port)
mv88e6xxx_6165_family(ps) || mv88e6xxx_6097_family(ps) ||
mv88e6xxx_6095_family(ps) || mv88e6xxx_6065_family(ps) ||
mv88e6xxx_6185_family(ps) || mv88e6xxx_6320_family(ps)) {
-   if (ds->dst->tag_protocol == DSA_TAG_PROTO_EDSA)
reg |= PORT_CONTROL_EGRESS_ADD_TAG;
}
}
-- 
2.8.1



[RFC PATCH 04/16] dsa: tag_{e}dsa.c: Remove dependency on platform data

2016-05-26 Thread Andrew Lunn
The platform data nr_chips is used when validating a received packet,
to ensure it comes from a know switch chip. The number of possible
switches is limited to DSA_MAX_SWITCHES, so use this as the first
validation step. The new binding allows holes in the dst->ds[] array,
so also ensure ensure there is a valid dsa_switch for this packet.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 net/dsa/tag_dsa.c  | 6 +-
 net/dsa/tag_edsa.c | 6 +-
 2 files changed, 10 insertions(+), 2 deletions(-)

diff --git a/net/dsa/tag_dsa.c b/net/dsa/tag_dsa.c
index aa780e4ac0bd..f9832f097681 100644
--- a/net/dsa/tag_dsa.c
+++ b/net/dsa/tag_dsa.c
@@ -107,9 +107,13 @@ static int dsa_rcv(struct sk_buff *skb, struct net_device 
*dev,
 * Check that the source device exists and that the source
 * port is a registered DSA port.
 */
-   if (source_device >= dst->pd->nr_chips)
+   if (source_device >= DSA_MAX_SWITCHES)
goto out_drop;
+
ds = dst->ds[source_device];
+   if (!ds)
+   goto out_drop;
+
if (source_port >= DSA_MAX_PORTS || ds->ports[source_port] == NULL)
goto out_drop;
 
diff --git a/net/dsa/tag_edsa.c b/net/dsa/tag_edsa.c
index 2288c8098c42..3890aac8190f 100644
--- a/net/dsa/tag_edsa.c
+++ b/net/dsa/tag_edsa.c
@@ -120,9 +120,13 @@ static int edsa_rcv(struct sk_buff *skb, struct net_device 
*dev,
 * Check that the source device exists and that the source
 * port is a registered DSA port.
 */
-   if (source_device >= dst->pd->nr_chips)
+   if (source_device >= DSA_MAX_SWITCHES)
goto out_drop;
+
ds = dst->ds[source_device];
+   if (!ds)
+   goto out_drop;
+
if (source_port >= DSA_MAX_PORTS || ds->ports[source_port] == NULL)
goto out_drop;
 
-- 
2.8.1



[RFC PATCH 06/16] dsa: Move port device node into port structure

2016-05-26 Thread Andrew Lunn
Move the port device node structure into the port structure, from the
chip data. This information is needed in the next step of implementing
the new binding.

The chip data structure is used while parsing the whole old binding,
before the individual switch structures exist. With the new bindings,
this is reversed, the switches exist first, and the interconnections
between the switches is derived from the individual switch
bindings. Thus this chip data structure becomes unneeded.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 include/net/dsa.h | 1 +
 net/dsa/dsa.c | 8 
 net/dsa/slave.c   | 5 ++---
 3 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/include/net/dsa.h b/include/net/dsa.h
index 9aed8572037c..8314197d028f 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -121,6 +121,7 @@ struct dsa_switch_tree {
 
 struct dsa_port {
struct net_device   *netdev;
+   struct device_node  *dn;
 };
 
 struct dsa_switch {
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 18086e0cc617..5907f8cd13b6 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -182,7 +182,6 @@ __ATTRIBUTE_GROUPS(dsa_hwmon);
 /* basic switch operations **/
 static int dsa_cpu_dsa_setup(struct dsa_switch *ds, struct net_device *master)
 {
-   struct dsa_chip_data *cd = ds->cd;
struct device_node *port_dn;
struct phy_device *phydev;
int ret, port, mode;
@@ -191,7 +190,7 @@ static int dsa_cpu_dsa_setup(struct dsa_switch *ds, struct 
net_device *master)
if (!(dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port)))
continue;
 
-   port_dn = cd->port_dn[port];
+   port_dn = ds->ports[port].dn;
if (of_phy_is_fixed_link(port_dn)) {
ret = of_phy_register_fixed_link(port_dn);
if (ret) {
@@ -325,6 +324,8 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
 * Create network devices for physical switch ports.
 */
for (i = 0; i < DSA_MAX_PORTS; i++) {
+   ds->ports[i].dn = cd->port_dn[i];
+
if (!(ds->enabled_port_mask & (1 << i)))
continue;
 
@@ -424,7 +425,6 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
 {
struct device_node *port_dn;
struct phy_device *phydev;
-   struct dsa_chip_data *cd = ds->cd;
int port;
 
 #ifdef CONFIG_NET_DSA_HWMON
@@ -445,7 +445,7 @@ static void dsa_switch_destroy(struct dsa_switch *ds)
 
/* Remove any fixed link PHYs */
for (port = 0; port < DSA_MAX_PORTS; port++) {
-   port_dn = cd->port_dn[port];
+   port_dn = ds->ports[port].dn;
if (of_phy_is_fixed_link(port_dn)) {
phydev = of_phy_find_device(port_dn);
if (phydev) {
diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 169abacbc6ce..52f1183c42a0 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -998,13 +998,12 @@ static int dsa_slave_phy_setup(struct dsa_slave_priv *p,
struct net_device *slave_dev)
 {
struct dsa_switch *ds = p->parent;
-   struct dsa_chip_data *cd = ds->cd;
struct device_node *phy_dn, *port_dn;
bool phy_is_fixed = false;
u32 phy_flags = 0;
int mode, ret;
 
-   port_dn = cd->port_dn[p->port];
+   port_dn = ds->ports[p->port].dn;
mode = of_get_phy_mode(port_dn);
if (mode < 0)
mode = PHY_INTERFACE_MODE_NA;
@@ -1146,7 +1145,7 @@ int dsa_slave_create(struct dsa_switch *ds, struct device 
*parent,
 NULL);
 
SET_NETDEV_DEV(slave_dev, parent);
-   slave_dev->dev.of_node = ds->cd->port_dn[port];
+   slave_dev->dev.of_node = ds->ports[port].dn;
slave_dev->vlan_features = master->vlan_features;
 
p = netdev_priv(slave_dev);
-- 
2.8.1



[RFC PATCH 08/16] dsa: Copy the routing table into the switch structure

2016-05-26 Thread Andrew Lunn
The new binding will not have a chip data structure, it will place the
routing directly into the switch structure. To enable backwards
compatibility, copy the routing from the chip data into the switch
structure.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c |  4 ++--
 include/net/dsa.h   | 10 +-
 net/dsa/dsa.c   |  2 ++
 3 files changed, 13 insertions(+), 3 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index d622c0fb76cc..492801a6398c 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -3024,8 +3024,8 @@ static int mv88e6xxx_setup_global(struct 
mv88e6xxx_priv_state *ps)
for (i = 0; i < 32; i++) {
int nexthop = 0x1f;
 
-   if (i != ps->ds->index && i < ps->ds->dst->pd->nr_chips)
-   nexthop = ps->ds->cd->rtable[i] & 0x1f;
+   if (i != ds->index && i < DSA_MAX_SWITCHES)
+   nexthop = ds->rtable[i] & 0x1f;
 
err = _mv88e6xxx_reg_write(
ps, REG_GLOBAL2,
diff --git a/include/net/dsa.h b/include/net/dsa.h
index 37e8e179d85a..ea0e7d30342b 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -149,6 +149,14 @@ struct dsa_switch {
 */
struct dsa_switch_driver*drv;
 
+   /*
+* An array of which element [a] indicates which port on this
+* switch should be used to send packets to that are destined
+* for switch a.  Can be NULL if there is only one switch
+* chip.
+*/
+   s8  rtable[DSA_MAX_SWITCHES];
+
 #ifdef CONFIG_NET_DSA_HWMON
/*
 * Hardware monitoring information
@@ -195,7 +203,7 @@ static inline u8 dsa_upstream_port(struct dsa_switch *ds)
if (dst->cpu_switch == ds->index)
return dst->cpu_port;
else
-   return ds->cd->rtable[dst->cpu_switch];
+   return ds->rtable[dst->cpu_switch];
 }
 
 struct switchdev_trans;
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 6177dd750847..bfe1d03d4730 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -297,6 +297,8 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, 
struct device *parent)
dst->tag_protocol = drv->tag_protocol;
}
 
+   memcpy(ds->rtable, cd->rtable, sizeof(ds->rtable));
+
/*
 * Do basic register setup.
 */
-- 
2.8.1



[RFC PATCH 03/16] dsa: slave: Remove MDIO address from switch MDIO bus name

2016-05-26 Thread Andrew Lunn
The DSA layer should no longer assume the switch is connected to an
MDIO bus. As a result, we cannot use the address on the MDIO bus when
forming the name of the switches internal MDIO bus for its builtin and
possibly external PHYs. The switch index is sufficient to make the
name unique, so drop the MDIO address.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 net/dsa/slave.c | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 135a91706755..f640a48a6ff3 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -49,8 +49,7 @@ void dsa_slave_mii_bus_init(struct dsa_switch *ds)
ds->slave_mii_bus->name = "dsa slave smi";
ds->slave_mii_bus->read = dsa_slave_phy_read;
ds->slave_mii_bus->write = dsa_slave_phy_write;
-   snprintf(ds->slave_mii_bus->id, MII_BUS_ID_SIZE, "dsa-%d:%.2x",
-   ds->index, ds->cd->sw_addr);
+   snprintf(ds->slave_mii_bus->id, MII_BUS_ID_SIZE, "dsa-%d", ds->index);
ds->slave_mii_bus->parent = ds->dev;
ds->slave_mii_bus->phy_mask = ~ds->phys_mii_mask;
 }
-- 
2.8.1



[RFC PATCH 07/16] dsa: Remove dynamic allocate of routing table

2016-05-26 Thread Andrew Lunn
With a maximum of four switches, the size of the routing table is the
same as the pointer to it. Removing it makes the code simpler.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/mv88e6xxx.c |  3 +--
 include/net/dsa.h   | 10 +-
 net/dsa/dsa.c   | 12 
 3 files changed, 6 insertions(+), 19 deletions(-)

diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index 85332d9a245a..d622c0fb76cc 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -3024,8 +3024,7 @@ static int mv88e6xxx_setup_global(struct 
mv88e6xxx_priv_state *ps)
for (i = 0; i < 32; i++) {
int nexthop = 0x1f;
 
-   if (ps->ds->cd->rtable &&
-   i != ps->ds->index && i < ps->ds->dst->pd->nr_chips)
+   if (i != ps->ds->index && i < ps->ds->dst->pd->nr_chips)
nexthop = ps->ds->cd->rtable[i] & 0x1f;
 
err = _mv88e6xxx_reg_write(
diff --git a/include/net/dsa.h b/include/net/dsa.h
index 8314197d028f..37e8e179d85a 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -58,12 +58,12 @@ struct dsa_chip_data {
struct device_node *port_dn[DSA_MAX_PORTS];
 
/*
-* An array (with nr_chips elements) of which element [a]
-* indicates which port on this switch should be used to
-* send packets to that are destined for switch a.  Can be
-* NULL if there is only one switch chip.
+* An array of which element [a] indicates which port on this
+* switch should be used to send packets to that are destined
+* for switch a.  Can be NULL if there is only one switch
+* chip.
 */
-   s8  *rtable;
+   s8  rtable[DSA_MAX_SWITCHES];
 };
 
 struct dsa_platform_data {
diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c
index 5907f8cd13b6..6177dd750847 100644
--- a/net/dsa/dsa.c
+++ b/net/dsa/dsa.c
@@ -587,17 +587,6 @@ static int dsa_of_setup_routing_table(struct 
dsa_platform_data *pd,
if (link_sw_addr >= pd->nr_chips)
return -EINVAL;
 
-   /* First time routing table allocation */
-   if (!cd->rtable) {
-   cd->rtable = kmalloc_array(pd->nr_chips, sizeof(s8),
-  GFP_KERNEL);
-   if (!cd->rtable)
-   return -ENOMEM;
-
-   /* default to no valid uplink/downlink */
-   memset(cd->rtable, -1, pd->nr_chips * sizeof(s8));
-   }
-
cd->rtable[link_sw_addr] = port_index;
 
return 0;
@@ -639,7 +628,6 @@ static void dsa_of_free_platform_data(struct 
dsa_platform_data *pd)
kfree(pd->chip[i].port_names[port_index]);
port_index++;
}
-   kfree(pd->chip[i].rtable);
 
/* Drop our reference to the MDIO bus device */
if (pd->chip[i].host_dev)
-- 
2.8.1



[RFC PATCH 00/16] New DSA bind, switches as devices

2016-05-26 Thread Andrew Lunn
This is an RFC patchset and should not be accepted yet.

The interesting patches here are the last three. They implement a new
binding for DSA, which removes a few limitations of the current DSA
binding. In particular, it allows switches to be true Linux devices.
These devices can be on any type of bus, unlike the old DSA binding
which assumes MDIO. See the commit log for more details. The second to
last patch modifies an existing boards device tree to use the new
binding, giving a good example of how switches can be true MDIO
devices. The last patch documents the new binding.

I know both John Crispin and Bryan Whitehead are interesting in
implementing DSA drivers, hence i have CC: you. Comments welcome.

Thanks go to Florian and Vivien for reviewing, testing and bug fixing
these patches.

Andrew Lunn (15):
  dsa: slave: chip data is optional, don't dereference NULL
  dsa: slave: Remove MDIO address from switch MDIO bus name
  dsa: tag_{e}dsa.c: Remove dependency on platform data
  dsa: Add a ports structure and use it in the switch structure
  dsa: Move port device node into port structure
  dsa: Remove dynamic allocate of routing table
  dsa: Copy the routing table into the switch structure
  dsa: dsa: Split up creating/destroying of DSA and CPU ports
  net: dsa: mv88e6xxx: Only support EDSA tagging
  net: dsa: Refactor selection of tag ops into a function
  dsa: Make mdio bus optional
  net: dsa: mv88e6xxx: Refactor MDIO so driver registers mdio bus
  net: dsa: Add new binding implementation
  arm: dt: vf610-zii-devel-b: Make use of new DSA binding
  dsa: Document new binding

Vivien Didelot (1):
  net: dsa: mv88e6xxx: fix circular lock in PPU work

 Documentation/devicetree/bindings/net/dsa/dsa.txt | 278 -
 arch/arm/boot/dts/vf610-zii-dev-rev-b.dts | 328 +--
 drivers/net/dsa/bcm_sf2.c |   4 +-
 drivers/net/dsa/mv88e6xxx.c   | 264 ++---
 drivers/net/dsa/mv88e6xxx.h   |   6 +
 include/net/dsa.h |  57 +-
 net/dsa/Makefile  |   2 +-
 net/dsa/dsa.c | 210 ---
 net/dsa/dsa2.c| 653 ++
 net/dsa/dsa_priv.h|   6 +-
 net/dsa/slave.c   |  57 +-
 net/dsa/tag_brcm.c|   4 +-
 net/dsa/tag_dsa.c |  10 +-
 net/dsa/tag_edsa.c|  10 +-
 net/dsa/tag_trailer.c |   4 +-
 15 files changed, 1485 insertions(+), 408 deletions(-)
 create mode 100644 net/dsa/dsa2.c

-- 
2.8.1



[RFC PATCH 16/16] dsa: Document new binding

2016-05-26 Thread Andrew Lunn
Add the new binding to the documentation of the existing binding.
Mark the old binding as deprecated.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
Signed-off-by: Florian Fainelli <f.faine...@gmail.com>
---
 Documentation/devicetree/bindings/net/dsa/dsa.txt | 278 +-
 1 file changed, 276 insertions(+), 2 deletions(-)

diff --git a/Documentation/devicetree/bindings/net/dsa/dsa.txt 
b/Documentation/devicetree/bindings/net/dsa/dsa.txt
index 9f4807f90c31..8c9e1b80cb65 100644
--- a/Documentation/devicetree/bindings/net/dsa/dsa.txt
+++ b/Documentation/devicetree/bindings/net/dsa/dsa.txt
@@ -1,5 +1,279 @@
-Marvell Distributed Switch Architecture Device Tree Bindings
-
+Distributed Switch Architecture Device Tree Bindings
+
+
+Two bindings exist, one of which has been deprecated due to
+limitations.
+
+Current Binding
+---
+
+Switches are true Linux devices and can be probes by any means. Once
+probed, they register to the DSA framework, passing a node
+pointer. This node is expected to fulfil the following binding, and
+may contain additional properties as required by the device it is
+embedded within.
+
+Required properties:
+
+- ports: A container for child nodes representing switch ports.
+
+Optional properties:
+
+- dsa,member   : A two element list indicates which DSA cluster, and position
+ within the cluster a switch takes. <0 0> is cluster 0,
+ switch 0. <0 1> is cluster 0, switch 1. <1 0> is cluster 1,
+ switch 0. A switch not part of any cluster (single device
+ hanging off a CPU port) must not specify this property
+
+The ports container has the following properties
+
+Required properties:
+
+- #address-cells   : Must be 1
+- #size-cells  : Must be 0
+
+Each port children node must have the following mandatory properties:
+- reg  : Describes the port address in the switch
+- label: Describes the label associated with this 
port, which
+  will become the netdev name. Special labels are
+ "cpu" to indicate a CPU port and "dsa" to
+ indicate an uplink/downlink port between switches in
+ the cluster.
+
+A port labelled "dsa" has the following mandatory property:
+
+- link : Should be a list of phandles to other switch's DSA
+ port. This port is used as the outgoing port
+ towards the phandle ports. The full routing
+ information must be given, not just the one hop
+ routes to neighbouring switches.
+
+A port labelled "cpu" has the following mandatory property:
+
+- ethernet : Should be a phandle to a valid Ethernet device node.
+  This host device is what the switch port is
+ connected to.
+
+Port child nodes may also contain the following optional standardised
+properties, described in binding documents:
+
+- phy-handle   : Phandle to a PHY on an MDIO bus. See
+ Documentation/devicetree/bindings/net/ethernet.txt
+ for details.
+
+- phy-mode : See
+ Documentation/devicetree/bindings/net/ethernet.txt
+ for details.
+
+- fixed-link   : Fixed-link subnode describing a link to a non-MDIO
+ managed entity. See
+ Documentation/devicetree/bindings/net/fixed-link.txt
+ for details.
+
+Example
+
+The following example shows three switches on three MDIO busses,
+linked into one DSA cluster.
+
+ {
+   #address-cells = <1>;
+   #size-cells = <0>;
+
+   switch0: switch0@0 {
+   compatible = "marvell,mv88e6085";
+   #address-cells = <1>;
+   #size-cells = <0>;
+   reg = <0>;
+
+   dsa,member = <0 0>;
+
+   ports {
+   #address-cells = <1>;
+   #size-cells = <0>;
+   port@0 {
+   reg = <0>;
+   label = "lan0";
+   };
+
+   port@1 {
+   reg = <1>;
+   label = "lan1";
+   };
+
+   port@2 {
+   reg = <2>;
+   label = "lan2";
+   };
+
+   switch0port5: port@5 {
+  

[RFC PATCH 15/16] arm: dt: vf610-zii-devel-b: Make use of new DSA binding

2016-05-26 Thread Andrew Lunn
Hang the three switches of the three MDIO busses using the new DSA
binding. Also, make use of the mdio-bus and explicitly list the phys
on one device. This is not required, but good for testing.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 arch/arm/boot/dts/vf610-zii-dev-rev-b.dts | 328 --
 1 file changed, 170 insertions(+), 158 deletions(-)

diff --git a/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts 
b/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts
index 6c60b7f91104..5c1fcab4a6f7 100644
--- a/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts
+++ b/arch/arm/boot/dts/vf610-zii-dev-rev-b.dts
@@ -85,187 +85,199 @@
reg = <1>;
#address-cells = <1>;
#size-cells = <0>;
+
+   switch0: switch0@0 {
+   compatible = "marvell,mv88e6085";
+   #address-cells = <1>;
+   #size-cells = <0>;
+   reg = <0>;
+   dsa,member = <0 0>;
+
+   ports {
+   #address-cells = <1>;
+   #size-cells = <0>;
+   port@0 {
+   reg = <0>;
+   label = "lan0";
+   };
+
+   port@1 {
+   reg = <1>;
+   label = "lan1";
+   };
+
+   port@2 {
+   reg = <2>;
+   label = "lan2";
+   };
+
+   switch0port5: port@5 {
+   reg = <5>;
+   label = "dsa";
+   phy-mode = "rgmii-txid";
+   link = <
+   >;
+   fixed-link {
+   speed = <1000>;
+   full-duplex;
+   };
+   };
+
+   port@6 {
+   reg = <6>;
+   label = "cpu";
+   ethernet = <>;
+   fixed-link {
+   speed = <100>;
+   full-duplex;
+   };
+   };
+   };
+   };
};
 
mdio_mux_2: mdio@2 {
reg = <2>;
#address-cells = <1>;
#size-cells = <0>;
-   };
-
-   mdio_mux_4: mdio@4 {
-   reg = <4>;
-   #address-cells = <1>;
-   #size-cells = <0>;
-   };
-
-   mdio_mux_8: mdio@8 {
-   reg = <8>;
-   #address-cells = <1>;
-   #size-cells = <0>;
-   };
-   };
-
-   dsa {
-   compatible = "marvell,dsa";
-   #address-cells = <2>;
-   #size-cells = <0>;
-   dsa,ethernet = <>;
-   dsa,mii-bus = <_mux_1>;
-
-   /* 6352 - Primary - 7 ports */
-   switch0: switch@0-0 {
-   #address-cells = <1>;
-   #size-cells = <0>;
-   reg = <0x00 0>;
-   eeprom-length = <512>;
 
-   port@0 {
+   switch1: switch1@0 {
+   compatible = "marvell,mv88e6085";
+   #address-cells = <1>;
+   #size-cells = <0>;
reg = <0>;
-   label = "lan0";
-   };
-
-   port@1 {
- 

[RFC PATCH 05/16] dsa: Add a ports structure and use it in the switch structure

2016-05-26 Thread Andrew Lunn
There are going to be more per-port members added to the switch
structure. So add a port structure and move the netdev into it.

Signed-off-by: Andrew Lunn <and...@lunn.ch>
---
 drivers/net/dsa/bcm_sf2.c   |  4 ++--
 drivers/net/dsa/mv88e6xxx.c | 27 ---
 include/net/dsa.h   |  8 ++--
 net/dsa/dsa.c   |  8 
 net/dsa/slave.c |  4 ++--
 net/dsa/tag_brcm.c  |  4 ++--
 net/dsa/tag_dsa.c   |  4 ++--
 net/dsa/tag_edsa.c  |  4 ++--
 net/dsa/tag_trailer.c   |  4 ++--
 9 files changed, 38 insertions(+), 29 deletions(-)

diff --git a/drivers/net/dsa/bcm_sf2.c b/drivers/net/dsa/bcm_sf2.c
index 10ddd5a5dfb6..73df91bb0466 100644
--- a/drivers/net/dsa/bcm_sf2.c
+++ b/drivers/net/dsa/bcm_sf2.c
@@ -804,7 +804,7 @@ static int bcm_sf2_sw_fdb_dump(struct dsa_switch *ds, int 
port,
   int (*cb)(struct switchdev_obj *obj))
 {
struct bcm_sf2_priv *priv = ds_to_priv(ds);
-   struct net_device *dev = ds->ports[port];
+   struct net_device *dev = ds->ports[port].netdev;
struct bcm_sf2_arl_entry results[2];
unsigned int count = 0;
int ret;
@@ -1248,7 +1248,7 @@ static void bcm_sf2_sw_fixed_link_update(struct 
dsa_switch *ds, int port,
 * state machine and make it go in PHY_FORCING state instead.
 */
if (!status->link)
-   netif_carrier_off(ds->ports[port]);
+   netif_carrier_off(ds->ports[port].netdev);
status->duplex = 1;
} else {
status->link = 1;
diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c
index c361036e7f9c..85332d9a245a 100644
--- a/drivers/net/dsa/mv88e6xxx.c
+++ b/drivers/net/dsa/mv88e6xxx.c
@@ -1327,7 +1327,7 @@ static int _mv88e6xxx_port_state(struct 
mv88e6xxx_priv_state *ps, int port,
if (ret)
return ret;
 
-   netdev_dbg(ds->ports[port], "PortState %s (was %s)\n",
+   netdev_dbg(ds->ports[port].netdev, "PortState %s (was %s)\n",
   mv88e6xxx_port_state_names[state],
   mv88e6xxx_port_state_names[oldstate]);
}
@@ -1405,7 +1405,8 @@ static void mv88e6xxx_port_stp_state_set(struct 
dsa_switch *ds, int port,
mutex_unlock(>smi_mutex);
 
if (err)
-   netdev_err(ds->ports[port], "failed to update state to %s\n",
+   netdev_err(ds->ports[port].netdev,
+  "failed to update state to %s\n",
   mv88e6xxx_port_state_names[stp_state]);
 }
 
@@ -1431,8 +1432,8 @@ static int _mv88e6xxx_port_pvid(struct 
mv88e6xxx_priv_state *ps, int port,
if (ret < 0)
return ret;
 
-   netdev_dbg(ds->ports[port], "DefaultVID %d (was %d)\n", *new,
-  pvid);
+   netdev_dbg(ds->ports[port].netdev,
+  "DefaultVID %d (was %d)\n", *new, pvid);
}
 
if (old)
@@ -1847,7 +1848,8 @@ static int _mv88e6xxx_port_fid(struct 
mv88e6xxx_priv_state *ps, int port,
if (ret < 0)
return ret;
 
-   netdev_dbg(ds->ports[port], "FID %d (was %d)\n", *new, fid);
+   netdev_dbg(ds->ports[port].netdev,
+  "FID %d (was %d)\n", *new, fid);
}
 
if (old)
@@ -2028,7 +2030,7 @@ static int mv88e6xxx_port_check_hw_vlan(struct dsa_switch 
*ds, int port,
ps->ports[port].bridge_dev)
break; /* same bridge, check next VLAN */
 
-   netdev_warn(ds->ports[port],
+   netdev_warn(ds->ports[port].netdev,
"hardware VLAN %d already used by %s\n",
vlan.vid,
netdev_name(ps->ports[i].bridge_dev));
@@ -2078,7 +2080,7 @@ static int mv88e6xxx_port_vlan_filtering(struct 
dsa_switch *ds, int port,
if (ret < 0)
goto unlock;
 
-   netdev_dbg(ds->ports[port], "802.1Q Mode %s (was %s)\n",
+   netdev_dbg(ds->ports[port].netdev, "802.1Q Mode %s (was %s)\n",
   mv88e6xxx_port_8021q_mode_names[new],
   mv88e6xxx_port_8021q_mode_names[old]);
}
@@ -2147,11 +2149,12 @@ static void mv88e6xxx_port_vlan_add(struct dsa_switch 
*ds, int port,
 
for (vid = vlan->vid_begin; vid <= vlan->vid_end; ++vid)
if (_mv88e6xxx_port_vlan_add(ps, port, vid, untagged))
-   netdev_err(ds->ports[port], "failed to add VLAN %d%c\

<    1   2   3   4   5   6   7   8   9   10   >