From bbb8d793994c894eef2a48a35fac6de3c6b4fa93 Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Wed, 13 Apr 2016 02:40:39 +0200 Subject: [PATCH 1/7] net: dsa: Pass the dsa device to the switch drivers By passing a device structure to the switch devices, it allows them to use devm_* methods for resource management. Signed-off-by: Andrew Lunn Acked-by: Florian Fainelli Tested-by: Vivien Didelot Signed-off-by: David S. Miller --- drivers/net/dsa/bcm_sf2.c | 3 ++- drivers/net/dsa/mv88e6060.c | 3 ++- drivers/net/dsa/mv88e6123.c | 3 ++- drivers/net/dsa/mv88e6131.c | 3 ++- drivers/net/dsa/mv88e6171.c | 3 ++- drivers/net/dsa/mv88e6352.c | 3 ++- include/net/dsa.h | 3 ++- net/dsa/dsa.c | 7 ++++--- 8 files changed, 18 insertions(+), 10 deletions(-) diff --git a/drivers/net/dsa/bcm_sf2.c b/drivers/net/dsa/bcm_sf2.c index 780f22876538..18a79579141f 100644 --- a/drivers/net/dsa/bcm_sf2.c +++ b/drivers/net/dsa/bcm_sf2.c @@ -135,7 +135,8 @@ static int bcm_sf2_sw_get_sset_count(struct dsa_switch *ds) return BCM_SF2_STATS_SIZE; } -static char *bcm_sf2_sw_probe(struct device *host_dev, int sw_addr) +static char *bcm_sf2_sw_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr) { return "Broadcom Starfighter 2"; } diff --git a/drivers/net/dsa/mv88e6060.c b/drivers/net/dsa/mv88e6060.c index 0527f485c3dc..34d0f9fe19db 100644 --- a/drivers/net/dsa/mv88e6060.c +++ b/drivers/net/dsa/mv88e6060.c @@ -57,7 +57,8 @@ static int reg_write(struct dsa_switch *ds, int addr, int reg, u16 val) return __ret; \ }) -static char *mv88e6060_probe(struct device *host_dev, int sw_addr) +static char *mv88e6060_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr) { struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); int ret; diff --git a/drivers/net/dsa/mv88e6123.c b/drivers/net/dsa/mv88e6123.c index 69a6f79dcb10..ede4c6f0b31a 100644 --- a/drivers/net/dsa/mv88e6123.c +++ b/drivers/net/dsa/mv88e6123.c @@ -29,7 +29,8 @@ static const struct mv88e6xxx_switch_id mv88e6123_table[] = { { PORT_SWITCH_ID_6165_A2, "Marvell 88e6165 (A2)" }, }; -static char *mv88e6123_probe(struct device *host_dev, int sw_addr) +static char *mv88e6123_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr) { return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6123_table, ARRAY_SIZE(mv88e6123_table)); diff --git a/drivers/net/dsa/mv88e6131.c b/drivers/net/dsa/mv88e6131.c index 24070287c2bc..bfadfd2cbb8d 100644 --- a/drivers/net/dsa/mv88e6131.c +++ b/drivers/net/dsa/mv88e6131.c @@ -25,7 +25,8 @@ static const struct mv88e6xxx_switch_id mv88e6131_table[] = { { PORT_SWITCH_ID_6185, "Marvell 88E6185" }, }; -static char *mv88e6131_probe(struct device *host_dev, int sw_addr) +static char *mv88e6131_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr) { return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6131_table, ARRAY_SIZE(mv88e6131_table)); diff --git a/drivers/net/dsa/mv88e6171.c b/drivers/net/dsa/mv88e6171.c index 0e62f3b5bc81..fb35d3ac1644 100644 --- a/drivers/net/dsa/mv88e6171.c +++ b/drivers/net/dsa/mv88e6171.c @@ -24,7 +24,8 @@ static const struct mv88e6xxx_switch_id mv88e6171_table[] = { { PORT_SWITCH_ID_6351, "Marvell 88E6351" }, }; -static char *mv88e6171_probe(struct device *host_dev, int sw_addr) +static char *mv88e6171_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr) { return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6171_table, ARRAY_SIZE(mv88e6171_table)); diff --git a/drivers/net/dsa/mv88e6352.c b/drivers/net/dsa/mv88e6352.c index 7f452e4a04a5..577ab2cfa944 100644 --- a/drivers/net/dsa/mv88e6352.c +++ b/drivers/net/dsa/mv88e6352.c @@ -37,7 +37,8 @@ static const struct mv88e6xxx_switch_id mv88e6352_table[] = { { PORT_SWITCH_ID_6352_A1, "Marvell 88E6352 (A1)" }, }; -static char *mv88e6352_probe(struct device *host_dev, int sw_addr) +static char *mv88e6352_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr) { return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6352_table, ARRAY_SIZE(mv88e6352_table)); diff --git a/include/net/dsa.h b/include/net/dsa.h index 18d1be3ad62d..0f9f6f38f255 100644 --- a/include/net/dsa.h +++ b/include/net/dsa.h @@ -212,7 +212,8 @@ struct dsa_switch_driver { /* * Probing and setup. */ - char *(*probe)(struct device *host_dev, int sw_addr); + char *(*probe)(struct device *dsa_dev, struct device *host_dev, + int sw_addr); int (*setup)(struct dsa_switch *ds); int (*set_addr)(struct dsa_switch *ds, u8 *addr); u32 (*get_phy_flags)(struct dsa_switch *ds, int port); diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c index c28c47463b7e..c06275311cb2 100644 --- a/net/dsa/dsa.c +++ b/net/dsa/dsa.c @@ -51,7 +51,8 @@ void unregister_switch_driver(struct dsa_switch_driver *drv) EXPORT_SYMBOL_GPL(unregister_switch_driver); static struct dsa_switch_driver * -dsa_switch_probe(struct device *host_dev, int sw_addr, char **_name) +dsa_switch_probe(struct device *parent, struct device *host_dev, int sw_addr, + char **_name) { struct dsa_switch_driver *ret; struct list_head *list; @@ -66,7 +67,7 @@ dsa_switch_probe(struct device *host_dev, int sw_addr, char **_name) drv = list_entry(list, struct dsa_switch_driver, list); - name = drv->probe(host_dev, sw_addr); + name = drv->probe(parent, host_dev, sw_addr); if (name != NULL) { ret = drv; break; @@ -387,7 +388,7 @@ dsa_switch_setup(struct dsa_switch_tree *dst, int index, /* * Probe for switch model. */ - drv = dsa_switch_probe(host_dev, pd->sw_addr, &name); + drv = dsa_switch_probe(parent, host_dev, pd->sw_addr, &name); if (drv == NULL) { netdev_err(dst->master_netdev, "[%d]: could not detect attached switch\n", index); From 7543a6d5359e371ce9434955dbe6a79f548ea321 Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Wed, 13 Apr 2016 02:40:40 +0200 Subject: [PATCH 2/7] net: dsa: Have the switch driver allocate there own private memory Now the switch devices have a dev pointer, make use of it for allocating the drivers private data structures using a devm_kzalloc(). Signed-off-by: Andrew Lunn Acked-by: Florian Fainelli Tested-by: Vivien Didelot Signed-off-by: David S. Miller --- drivers/net/dsa/bcm_sf2.c | 10 ++++++++-- drivers/net/dsa/mv88e6060.c | 3 ++- drivers/net/dsa/mv88e6123.c | 17 ++++++++++++++--- drivers/net/dsa/mv88e6131.c | 17 ++++++++++++++--- drivers/net/dsa/mv88e6171.c | 17 ++++++++++++++--- drivers/net/dsa/mv88e6352.c | 17 ++++++++++++++--- drivers/net/dsa/mv88e6xxx.c | 6 ++++-- drivers/net/dsa/mv88e6xxx.h | 3 +++ include/net/dsa.h | 10 ++++++++-- net/dsa/dsa.c | 8 +++++--- 10 files changed, 86 insertions(+), 22 deletions(-) diff --git a/drivers/net/dsa/bcm_sf2.c b/drivers/net/dsa/bcm_sf2.c index 18a79579141f..7d62802a66d5 100644 --- a/drivers/net/dsa/bcm_sf2.c +++ b/drivers/net/dsa/bcm_sf2.c @@ -136,8 +136,15 @@ static int bcm_sf2_sw_get_sset_count(struct dsa_switch *ds) } static char *bcm_sf2_sw_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr) + int sw_addr, void **_priv) { + struct bcm_sf2_priv *priv; + + priv = devm_kzalloc(dsa_dev, sizeof(*priv), GFP_KERNEL); + if (!priv) + return NULL; + *_priv = priv; + return "Broadcom Starfighter 2"; } @@ -1363,7 +1370,6 @@ static int bcm_sf2_sw_set_wol(struct dsa_switch *ds, int port, static struct dsa_switch_driver bcm_sf2_switch_driver = { .tag_protocol = DSA_TAG_PROTO_BRCM, - .priv_size = sizeof(struct bcm_sf2_priv), .probe = bcm_sf2_sw_probe, .setup = bcm_sf2_sw_setup, .set_addr = bcm_sf2_sw_set_addr, diff --git a/drivers/net/dsa/mv88e6060.c b/drivers/net/dsa/mv88e6060.c index 34d0f9fe19db..41195f1417f1 100644 --- a/drivers/net/dsa/mv88e6060.c +++ b/drivers/net/dsa/mv88e6060.c @@ -58,11 +58,12 @@ static int reg_write(struct dsa_switch *ds, int addr, int reg, u16 val) }) static char *mv88e6060_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr) + int sw_addr, void **priv) { struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); int ret; + *priv = NULL; if (bus == NULL) return NULL; diff --git a/drivers/net/dsa/mv88e6123.c b/drivers/net/dsa/mv88e6123.c index ede4c6f0b31a..bcab3ef22448 100644 --- a/drivers/net/dsa/mv88e6123.c +++ b/drivers/net/dsa/mv88e6123.c @@ -30,10 +30,20 @@ static const struct mv88e6xxx_switch_id mv88e6123_table[] = { }; static char *mv88e6123_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr) + int sw_addr, void **priv) { - return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6123_table, + struct mv88e6xxx_priv_state *ps; + char *name; + + name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6123_table, ARRAY_SIZE(mv88e6123_table)); + if (name) { + ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); + if (!ps) + return NULL; + *priv = ps; + } + return name; } static int mv88e6123_setup_global(struct dsa_switch *ds) @@ -74,6 +84,8 @@ static int mv88e6123_setup(struct dsa_switch *ds) struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); int ret; + ps->ds = ds; + ret = mv88e6xxx_setup_common(ds); if (ret < 0) return ret; @@ -103,7 +115,6 @@ static int mv88e6123_setup(struct dsa_switch *ds) struct dsa_switch_driver mv88e6123_switch_driver = { .tag_protocol = DSA_TAG_PROTO_EDSA, - .priv_size = sizeof(struct mv88e6xxx_priv_state), .probe = mv88e6123_probe, .setup = mv88e6123_setup, .set_addr = mv88e6xxx_set_addr_indirect, diff --git a/drivers/net/dsa/mv88e6131.c b/drivers/net/dsa/mv88e6131.c index bfadfd2cbb8d..b9f9b009f65a 100644 --- a/drivers/net/dsa/mv88e6131.c +++ b/drivers/net/dsa/mv88e6131.c @@ -26,10 +26,20 @@ static const struct mv88e6xxx_switch_id mv88e6131_table[] = { }; static char *mv88e6131_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr) + int sw_addr, void **priv) { - return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6131_table, + struct mv88e6xxx_priv_state *ps; + char *name; + + name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6131_table, ARRAY_SIZE(mv88e6131_table)); + if (name) { + ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); + if (!ps) + return NULL; + *priv = ps; + } + return name; } static int mv88e6131_setup_global(struct dsa_switch *ds) @@ -92,6 +102,8 @@ static int mv88e6131_setup(struct dsa_switch *ds) struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); int ret; + ps->ds = ds; + ret = mv88e6xxx_setup_common(ds); if (ret < 0) return ret; @@ -160,7 +172,6 @@ mv88e6131_phy_write(struct dsa_switch *ds, struct dsa_switch_driver mv88e6131_switch_driver = { .tag_protocol = DSA_TAG_PROTO_DSA, - .priv_size = sizeof(struct mv88e6xxx_priv_state), .probe = mv88e6131_probe, .setup = mv88e6131_setup, .set_addr = mv88e6xxx_set_addr_direct, diff --git a/drivers/net/dsa/mv88e6171.c b/drivers/net/dsa/mv88e6171.c index fb35d3ac1644..15200928cecc 100644 --- a/drivers/net/dsa/mv88e6171.c +++ b/drivers/net/dsa/mv88e6171.c @@ -25,10 +25,20 @@ static const struct mv88e6xxx_switch_id mv88e6171_table[] = { }; static char *mv88e6171_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr) + int sw_addr, void **priv) { - return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6171_table, + struct mv88e6xxx_priv_state *ps; + char *name; + + name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6171_table, ARRAY_SIZE(mv88e6171_table)); + if (name) { + ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); + if (!ps) + return NULL; + *priv = ps; + } + return name; } static int mv88e6171_setup_global(struct dsa_switch *ds) @@ -70,6 +80,8 @@ static int mv88e6171_setup(struct dsa_switch *ds) struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); int ret; + ps->ds = ds; + ret = mv88e6xxx_setup_common(ds); if (ret < 0) return ret; @@ -89,7 +101,6 @@ static int mv88e6171_setup(struct dsa_switch *ds) struct dsa_switch_driver mv88e6171_switch_driver = { .tag_protocol = DSA_TAG_PROTO_EDSA, - .priv_size = sizeof(struct mv88e6xxx_priv_state), .probe = mv88e6171_probe, .setup = mv88e6171_setup, .set_addr = mv88e6xxx_set_addr_indirect, diff --git a/drivers/net/dsa/mv88e6352.c b/drivers/net/dsa/mv88e6352.c index 577ab2cfa944..7081a78a67e1 100644 --- a/drivers/net/dsa/mv88e6352.c +++ b/drivers/net/dsa/mv88e6352.c @@ -38,10 +38,20 @@ static const struct mv88e6xxx_switch_id mv88e6352_table[] = { }; static char *mv88e6352_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr) + int sw_addr, void **priv) { - return mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6352_table, + struct mv88e6xxx_priv_state *ps; + char *name; + + name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6352_table, ARRAY_SIZE(mv88e6352_table)); + if (name) { + ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); + if (!ps) + return NULL; + *priv = ps; + } + return name; } static int mv88e6352_setup_global(struct dsa_switch *ds) @@ -82,6 +92,8 @@ static int mv88e6352_setup(struct dsa_switch *ds) struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); int ret; + ps->ds = ds; + ret = mv88e6xxx_setup_common(ds); if (ret < 0) return ret; @@ -303,7 +315,6 @@ static int mv88e6352_set_eeprom(struct dsa_switch *ds, struct dsa_switch_driver mv88e6352_switch_driver = { .tag_protocol = DSA_TAG_PROTO_EDSA, - .priv_size = sizeof(struct mv88e6xxx_priv_state), .probe = mv88e6352_probe, .setup = mv88e6352_setup, .set_addr = mv88e6xxx_set_addr_indirect, diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c index 62320fca6712..085fc4a49eb2 100644 --- a/drivers/net/dsa/mv88e6xxx.c +++ b/drivers/net/dsa/mv88e6xxx.c @@ -281,7 +281,7 @@ static void mv88e6xxx_ppu_reenable_work(struct work_struct *ugly) ps = container_of(ugly, struct mv88e6xxx_priv_state, ppu_work); if (mutex_trylock(&ps->ppu_mutex)) { - struct dsa_switch *ds = ((struct dsa_switch *)ps) - 1; + struct dsa_switch *ds = ps->ds; if (mv88e6xxx_ppu_enable(ds) == 0) ps->ppu_disabled = 0; @@ -2322,7 +2322,7 @@ static void mv88e6xxx_bridge_work(struct work_struct *work) int port; ps = container_of(work, struct mv88e6xxx_priv_state, bridge_work); - ds = ((struct dsa_switch *)ps) - 1; + ds = ps->ds; mutex_lock(&ps->smi_mutex); @@ -2670,6 +2670,8 @@ int mv88e6xxx_setup_common(struct dsa_switch *ds) { struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); + ps->ds = ds; + mutex_init(&ps->smi_mutex); ps->id = REG_READ(REG_PORT(0), PORT_SWITCH_ID) & 0xfff0; diff --git a/drivers/net/dsa/mv88e6xxx.h b/drivers/net/dsa/mv88e6xxx.h index 236bcaa606e7..0322e3e0e7d9 100644 --- a/drivers/net/dsa/mv88e6xxx.h +++ b/drivers/net/dsa/mv88e6xxx.h @@ -397,6 +397,9 @@ struct mv88e6xxx_priv_port { }; struct mv88e6xxx_priv_state { + /* The dsa_switch this private structure is related to */ + struct dsa_switch *ds; + /* When using multi-chip addressing, this mutex protects * access to the indirect access registers. (In single-chip * mode, this mutex is effectively useless.) diff --git a/include/net/dsa.h b/include/net/dsa.h index 0f9f6f38f255..7bc7bd9b5ded 100644 --- a/include/net/dsa.h +++ b/include/net/dsa.h @@ -129,6 +129,12 @@ struct dsa_switch { struct dsa_switch_tree *dst; int index; + /* + * Give the switch driver somewhere to hang its private data + * structure. + */ + void *priv; + /* * Tagging protocol understood by this switch */ @@ -213,7 +219,7 @@ struct dsa_switch_driver { * Probing and setup. */ char *(*probe)(struct device *dsa_dev, struct device *host_dev, - int sw_addr); + int sw_addr, void **priv); int (*setup)(struct dsa_switch *ds); int (*set_addr)(struct dsa_switch *ds, u8 *addr); u32 (*get_phy_flags)(struct dsa_switch *ds, int port); @@ -342,7 +348,7 @@ struct mii_bus *dsa_host_dev_to_mii_bus(struct device *dev); static inline void *ds_to_priv(struct dsa_switch *ds) { - return (void *)(ds + 1); + return ds->priv; } static inline bool dsa_uses_tagged_protocol(struct dsa_switch_tree *dst) diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c index c06275311cb2..7ef8a92a9e39 100644 --- a/net/dsa/dsa.c +++ b/net/dsa/dsa.c @@ -52,7 +52,7 @@ EXPORT_SYMBOL_GPL(unregister_switch_driver); static struct dsa_switch_driver * dsa_switch_probe(struct device *parent, struct device *host_dev, int sw_addr, - char **_name) + char **_name, void **priv) { struct dsa_switch_driver *ret; struct list_head *list; @@ -67,7 +67,7 @@ dsa_switch_probe(struct device *parent, struct device *host_dev, int sw_addr, drv = list_entry(list, struct dsa_switch_driver, list); - name = drv->probe(parent, host_dev, sw_addr); + name = drv->probe(parent, host_dev, sw_addr, priv); if (name != NULL) { ret = drv; break; @@ -384,11 +384,12 @@ dsa_switch_setup(struct dsa_switch_tree *dst, int index, struct dsa_switch *ds; int ret; char *name; + void *priv; /* * Probe for switch model. */ - drv = dsa_switch_probe(parent, host_dev, pd->sw_addr, &name); + drv = dsa_switch_probe(parent, host_dev, pd->sw_addr, &name, &priv); if (drv == NULL) { netdev_err(dst->master_netdev, "[%d]: could not detect attached switch\n", index); @@ -409,6 +410,7 @@ dsa_switch_setup(struct dsa_switch_tree *dst, int index, ds->index = index; ds->pd = pd; ds->drv = drv; + ds->priv = priv; ds->tag_protocol = drv->tag_protocol; ds->master_dev = host_dev; From 5feebd0a8a799fe076c606b7c3bc267ae8c4344a Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Wed, 13 Apr 2016 02:40:41 +0200 Subject: [PATCH 3/7] net: dsa: Remove allocation of driver private memory The drivers now allocate their own memory for private usage. Remove the allocation from the core code. Signed-off-by: Andrew Lunn Acked-by: Florian Fainelli Tested-by: Vivien Didelot Signed-off-by: David S. Miller --- include/net/dsa.h | 1 - net/dsa/dsa.c | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/include/net/dsa.h b/include/net/dsa.h index 7bc7bd9b5ded..165c2e10615c 100644 --- a/include/net/dsa.h +++ b/include/net/dsa.h @@ -213,7 +213,6 @@ struct dsa_switch_driver { struct list_head list; enum dsa_tag_protocol tag_protocol; - int priv_size; /* * Probing and setup. diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c index 7ef8a92a9e39..14bf12f637d2 100644 --- a/net/dsa/dsa.c +++ b/net/dsa/dsa.c @@ -402,7 +402,7 @@ dsa_switch_setup(struct dsa_switch_tree *dst, int index, /* * Allocate and initialise switch state. */ - ds = devm_kzalloc(parent, sizeof(*ds) + drv->priv_size, GFP_KERNEL); + ds = devm_kzalloc(parent, sizeof(*ds), GFP_KERNEL); if (ds == NULL) return ERR_PTR(-ENOMEM); From a77d43f1e9d59791b138b9903c58b89fffb0df97 Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Wed, 13 Apr 2016 02:40:42 +0200 Subject: [PATCH 4/7] net: dsa: Keep the mii bus and address in the private structure Rather than looking up the mii bus and address every time, do it once at probe, and keep it in the private structure. Centralise this probe code in mv88e6xxx. Signed-off-by: Andrew Lunn Acked-by: Florian Fainelli Tested-by: Vivien Didelot Signed-off-by: David S. Miller --- drivers/net/dsa/mv88e6060.c | 44 ++++++++++++++++++++++--------------- drivers/net/dsa/mv88e6060.h | 11 ++++++++++ drivers/net/dsa/mv88e6123.c | 15 +++---------- drivers/net/dsa/mv88e6131.c | 15 +++---------- drivers/net/dsa/mv88e6171.c | 15 +++---------- drivers/net/dsa/mv88e6352.c | 15 +++---------- drivers/net/dsa/mv88e6xxx.c | 43 ++++++++++++++++++++++++------------ drivers/net/dsa/mv88e6xxx.h | 14 +++++++++--- 8 files changed, 89 insertions(+), 83 deletions(-) diff --git a/drivers/net/dsa/mv88e6060.c b/drivers/net/dsa/mv88e6060.c index 41195f1417f1..46fe5dc65a99 100644 --- a/drivers/net/dsa/mv88e6060.c +++ b/drivers/net/dsa/mv88e6060.c @@ -19,12 +19,9 @@ static int reg_read(struct dsa_switch *ds, int addr, int reg) { - struct mii_bus *bus = dsa_host_dev_to_mii_bus(ds->master_dev); + struct mv88e6060_priv *priv = ds_to_priv(ds); - if (bus == NULL) - return -EINVAL; - - return mdiobus_read_nested(bus, ds->pd->sw_addr + addr, reg); + return mdiobus_read_nested(priv->bus, priv->sw_addr + addr, reg); } #define REG_READ(addr, reg) \ @@ -40,12 +37,9 @@ static int reg_read(struct dsa_switch *ds, int addr, int reg) static int reg_write(struct dsa_switch *ds, int addr, int reg, u16 val) { - struct mii_bus *bus = dsa_host_dev_to_mii_bus(ds->master_dev); + struct mv88e6060_priv *priv = ds_to_priv(ds); - if (bus == NULL) - return -EINVAL; - - return mdiobus_write_nested(bus, ds->pd->sw_addr + addr, reg, val); + return mdiobus_write_nested(priv->bus, priv->sw_addr + addr, reg, val); } #define REG_WRITE(addr, reg, val) \ @@ -57,16 +51,10 @@ static int reg_write(struct dsa_switch *ds, int addr, int reg, u16 val) return __ret; \ }) -static char *mv88e6060_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr, void **priv) +static char *mv88e6060_get_name(struct mii_bus *bus, int sw_addr) { - struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); int ret; - *priv = NULL; - if (bus == NULL) - return NULL; - ret = mdiobus_read(bus, sw_addr + REG_PORT(0), PORT_SWITCH_ID); if (ret >= 0) { if (ret == PORT_SWITCH_ID_6060) @@ -81,6 +69,26 @@ static char *mv88e6060_probe(struct device *dsa_dev, struct device *host_dev, return NULL; } +static char *mv88e6060_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr, void **_priv) +{ + struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); + struct mv88e6060_priv *priv; + char *name; + + name = mv88e6060_get_name(bus, sw_addr); + if (name) { + priv = devm_kzalloc(dsa_dev, sizeof(*priv), GFP_KERNEL); + if (!priv) + return NULL; + *_priv = priv; + priv->bus = bus; + priv->sw_addr = sw_addr; + } + + return name; +} + static int mv88e6060_switch_reset(struct dsa_switch *ds) { int i; @@ -176,8 +184,8 @@ static int mv88e6060_setup_port(struct dsa_switch *ds, int p) static int mv88e6060_setup(struct dsa_switch *ds) { - int i; int ret; + int i; ret = mv88e6060_switch_reset(ds); if (ret < 0) diff --git a/drivers/net/dsa/mv88e6060.h b/drivers/net/dsa/mv88e6060.h index cc9b2ed4aff4..10249bd16292 100644 --- a/drivers/net/dsa/mv88e6060.h +++ b/drivers/net/dsa/mv88e6060.h @@ -108,4 +108,15 @@ #define GLOBAL_ATU_MAC_23 0x0e #define GLOBAL_ATU_MAC_45 0x0f +struct mv88e6060_priv { + /* MDIO bus and address on bus to use. When in single chip + * mode, address is 0, and the switch uses multiple addresses + * on the bus. When in multi-chip mode, the switch uses a + * single address which contains two registers used for + * indirect access to more registers. + */ + struct mii_bus *bus; + int sw_addr; +}; + #endif diff --git a/drivers/net/dsa/mv88e6123.c b/drivers/net/dsa/mv88e6123.c index bcab3ef22448..8aaac0894752 100644 --- a/drivers/net/dsa/mv88e6123.c +++ b/drivers/net/dsa/mv88e6123.c @@ -32,18 +32,9 @@ static const struct mv88e6xxx_switch_id mv88e6123_table[] = { static char *mv88e6123_probe(struct device *dsa_dev, struct device *host_dev, int sw_addr, void **priv) { - struct mv88e6xxx_priv_state *ps; - char *name; - - name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6123_table, - ARRAY_SIZE(mv88e6123_table)); - if (name) { - ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); - if (!ps) - return NULL; - *priv = ps; - } - return name; + return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, + mv88e6123_table, + ARRAY_SIZE(mv88e6123_table)); } static int mv88e6123_setup_global(struct dsa_switch *ds) diff --git a/drivers/net/dsa/mv88e6131.c b/drivers/net/dsa/mv88e6131.c index b9f9b009f65a..9e6edf94a855 100644 --- a/drivers/net/dsa/mv88e6131.c +++ b/drivers/net/dsa/mv88e6131.c @@ -28,18 +28,9 @@ static const struct mv88e6xxx_switch_id mv88e6131_table[] = { static char *mv88e6131_probe(struct device *dsa_dev, struct device *host_dev, int sw_addr, void **priv) { - struct mv88e6xxx_priv_state *ps; - char *name; - - name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6131_table, - ARRAY_SIZE(mv88e6131_table)); - if (name) { - ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); - if (!ps) - return NULL; - *priv = ps; - } - return name; + return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, + mv88e6131_table, + ARRAY_SIZE(mv88e6131_table)); } static int mv88e6131_setup_global(struct dsa_switch *ds) diff --git a/drivers/net/dsa/mv88e6171.c b/drivers/net/dsa/mv88e6171.c index 15200928cecc..6ab86071391f 100644 --- a/drivers/net/dsa/mv88e6171.c +++ b/drivers/net/dsa/mv88e6171.c @@ -27,18 +27,9 @@ static const struct mv88e6xxx_switch_id mv88e6171_table[] = { static char *mv88e6171_probe(struct device *dsa_dev, struct device *host_dev, int sw_addr, void **priv) { - struct mv88e6xxx_priv_state *ps; - char *name; - - name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6171_table, - ARRAY_SIZE(mv88e6171_table)); - if (name) { - ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); - if (!ps) - return NULL; - *priv = ps; - } - return name; + return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, + mv88e6171_table, + ARRAY_SIZE(mv88e6171_table)); } static int mv88e6171_setup_global(struct dsa_switch *ds) diff --git a/drivers/net/dsa/mv88e6352.c b/drivers/net/dsa/mv88e6352.c index 7081a78a67e1..764b10ffb631 100644 --- a/drivers/net/dsa/mv88e6352.c +++ b/drivers/net/dsa/mv88e6352.c @@ -40,18 +40,9 @@ static const struct mv88e6xxx_switch_id mv88e6352_table[] = { static char *mv88e6352_probe(struct device *dsa_dev, struct device *host_dev, int sw_addr, void **priv) { - struct mv88e6xxx_priv_state *ps; - char *name; - - name = mv88e6xxx_lookup_name(host_dev, sw_addr, mv88e6352_table, - ARRAY_SIZE(mv88e6352_table)); - if (name) { - ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); - if (!ps) - return NULL; - *priv = ps; - } - return name; + return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, + mv88e6352_table, + ARRAY_SIZE(mv88e6352_table)); } static int mv88e6352_setup_global(struct dsa_switch *ds) diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c index 085fc4a49eb2..c242ffd8eb09 100644 --- a/drivers/net/dsa/mv88e6xxx.c +++ b/drivers/net/dsa/mv88e6xxx.c @@ -94,15 +94,12 @@ static int __mv88e6xxx_reg_read(struct mii_bus *bus, int sw_addr, int addr, static int _mv88e6xxx_reg_read(struct dsa_switch *ds, int addr, int reg) { - struct mii_bus *bus = dsa_host_dev_to_mii_bus(ds->master_dev); + struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); int ret; assert_smi_lock(ds); - if (bus == NULL) - return -EINVAL; - - ret = __mv88e6xxx_reg_read(bus, ds->pd->sw_addr, addr, reg); + ret = __mv88e6xxx_reg_read(ps->bus, ps->sw_addr, addr, reg); if (ret < 0) return ret; @@ -159,17 +156,14 @@ static int __mv88e6xxx_reg_write(struct mii_bus *bus, int sw_addr, int addr, static int _mv88e6xxx_reg_write(struct dsa_switch *ds, int addr, int reg, u16 val) { - struct mii_bus *bus = dsa_host_dev_to_mii_bus(ds->master_dev); + struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); assert_smi_lock(ds); - if (bus == NULL) - return -EINVAL; - dev_dbg(ds->master_dev, "-> addr: 0x%.2x reg: 0x%.2x val: 0x%.4x\n", addr, reg, val); - return __mv88e6xxx_reg_write(bus, ds->pd->sw_addr, addr, reg, val); + return __mv88e6xxx_reg_write(ps->bus, ps->sw_addr, addr, reg, val); } int mv88e6xxx_reg_write(struct dsa_switch *ds, int addr, int reg, u16 val) @@ -2671,7 +2665,6 @@ int mv88e6xxx_setup_common(struct dsa_switch *ds) struct mv88e6xxx_priv_state *ps = ds_to_priv(ds); ps->ds = ds; - mutex_init(&ps->smi_mutex); ps->id = REG_READ(REG_PORT(0), PORT_SWITCH_ID) & 0xfff0; @@ -3075,9 +3068,9 @@ int mv88e6xxx_get_temp_alarm(struct dsa_switch *ds, bool *alarm) } #endif /* CONFIG_NET_DSA_HWMON */ -char *mv88e6xxx_lookup_name(struct device *host_dev, int sw_addr, - const struct mv88e6xxx_switch_id *table, - unsigned int num) +static char *mv88e6xxx_lookup_name(struct device *host_dev, int sw_addr, + const struct mv88e6xxx_switch_id *table, + unsigned int num) { struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); int i, ret; @@ -3107,6 +3100,28 @@ char *mv88e6xxx_lookup_name(struct device *host_dev, int sw_addr, return NULL; } +char *mv88e6xxx_drv_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr, void **priv, + const struct mv88e6xxx_switch_id *table, + unsigned int num) +{ + struct mv88e6xxx_priv_state *ps; + char *name; + + name = mv88e6xxx_lookup_name(host_dev, sw_addr, table, num); + if (name) { + ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); + if (!ps) + return NULL; + *priv = ps; + ps->bus = dsa_host_dev_to_mii_bus(host_dev); + if (!ps->bus) + return NULL; + ps->sw_addr = sw_addr; + } + return name; +} + static int __init mv88e6xxx_init(void) { #if IS_ENABLED(CONFIG_NET_DSA_MV88E6131) diff --git a/drivers/net/dsa/mv88e6xxx.h b/drivers/net/dsa/mv88e6xxx.h index 0322e3e0e7d9..5d27decc85cb 100644 --- a/drivers/net/dsa/mv88e6xxx.h +++ b/drivers/net/dsa/mv88e6xxx.h @@ -406,6 +406,12 @@ struct mv88e6xxx_priv_state { */ struct mutex smi_mutex; + /* The MII bus and the address on the bus that is used to + * communication with the switch + */ + struct mii_bus *bus; + int sw_addr; + #ifdef CONFIG_NET_DSA_MV88E6XXX_NEED_PPU /* Handles automatic disabling and re-enabling of the PHY * polling unit. @@ -456,9 +462,11 @@ struct mv88e6xxx_hw_stat { }; int mv88e6xxx_switch_reset(struct dsa_switch *ds, bool ppu_active); -char *mv88e6xxx_lookup_name(struct device *host_dev, int sw_addr, - const struct mv88e6xxx_switch_id *table, - unsigned int num); +char *mv88e6xxx_drv_probe(struct device *dsa_dev, struct device *host_dev, + int sw_addr, void **priv, + const struct mv88e6xxx_switch_id *table, + unsigned int num); + int mv88e6xxx_setup_ports(struct dsa_switch *ds); int mv88e6xxx_setup_common(struct dsa_switch *ds); int mv88e6xxx_setup_global(struct dsa_switch *ds); From e49bad319630dedeeda3a638a707ec7b5d402ad5 Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Wed, 13 Apr 2016 02:40:43 +0200 Subject: [PATCH 5/7] net: dsa: Rename DSA probe function. Rename the function called from the DSA to perform a probe for the switch. This makes the normal _probe() name available for a standard Linux device driver probe function. Signed-off-by: Andrew Lunn Tested-by: Vivien Didelot Acked-by: Florian Fainelli Signed-off-by: David S. Miller --- drivers/net/dsa/bcm_sf2.c | 7 ++++--- drivers/net/dsa/mv88e6060.c | 7 ++++--- drivers/net/dsa/mv88e6123.c | 7 ++++--- drivers/net/dsa/mv88e6131.c | 7 ++++--- drivers/net/dsa/mv88e6171.c | 7 ++++--- drivers/net/dsa/mv88e6352.c | 7 ++++--- 6 files changed, 24 insertions(+), 18 deletions(-) diff --git a/drivers/net/dsa/bcm_sf2.c b/drivers/net/dsa/bcm_sf2.c index 7d62802a66d5..50caa525cda3 100644 --- a/drivers/net/dsa/bcm_sf2.c +++ b/drivers/net/dsa/bcm_sf2.c @@ -135,8 +135,9 @@ static int bcm_sf2_sw_get_sset_count(struct dsa_switch *ds) return BCM_SF2_STATS_SIZE; } -static char *bcm_sf2_sw_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr, void **_priv) +static char *bcm_sf2_sw_drv_probe(struct device *dsa_dev, + struct device *host_dev, + int sw_addr, void **_priv) { struct bcm_sf2_priv *priv; @@ -1370,7 +1371,7 @@ static int bcm_sf2_sw_set_wol(struct dsa_switch *ds, int port, static struct dsa_switch_driver bcm_sf2_switch_driver = { .tag_protocol = DSA_TAG_PROTO_BRCM, - .probe = bcm_sf2_sw_probe, + .probe = bcm_sf2_sw_drv_probe, .setup = bcm_sf2_sw_setup, .set_addr = bcm_sf2_sw_set_addr, .get_phy_flags = bcm_sf2_sw_get_phy_flags, diff --git a/drivers/net/dsa/mv88e6060.c b/drivers/net/dsa/mv88e6060.c index 46fe5dc65a99..adb608ccd9aa 100644 --- a/drivers/net/dsa/mv88e6060.c +++ b/drivers/net/dsa/mv88e6060.c @@ -69,8 +69,9 @@ static char *mv88e6060_get_name(struct mii_bus *bus, int sw_addr) return NULL; } -static char *mv88e6060_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr, void **_priv) +static char *mv88e6060_drv_probe(struct device *dsa_dev, + struct device *host_dev, + int sw_addr, void **_priv) { struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); struct mv88e6060_priv *priv; @@ -248,7 +249,7 @@ mv88e6060_phy_write(struct dsa_switch *ds, int port, int regnum, u16 val) static struct dsa_switch_driver mv88e6060_switch_driver = { .tag_protocol = DSA_TAG_PROTO_TRAILER, - .probe = mv88e6060_probe, + .probe = mv88e6060_drv_probe, .setup = mv88e6060_setup, .set_addr = mv88e6060_set_addr, .phy_read = mv88e6060_phy_read, diff --git a/drivers/net/dsa/mv88e6123.c b/drivers/net/dsa/mv88e6123.c index 8aaac0894752..c34283d929c4 100644 --- a/drivers/net/dsa/mv88e6123.c +++ b/drivers/net/dsa/mv88e6123.c @@ -29,8 +29,9 @@ static const struct mv88e6xxx_switch_id mv88e6123_table[] = { { PORT_SWITCH_ID_6165_A2, "Marvell 88e6165 (A2)" }, }; -static char *mv88e6123_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr, void **priv) +static char *mv88e6123_drv_probe(struct device *dsa_dev, + struct device *host_dev, + int sw_addr, void **priv) { return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, mv88e6123_table, @@ -106,7 +107,7 @@ static int mv88e6123_setup(struct dsa_switch *ds) struct dsa_switch_driver mv88e6123_switch_driver = { .tag_protocol = DSA_TAG_PROTO_EDSA, - .probe = mv88e6123_probe, + .probe = mv88e6123_drv_probe, .setup = mv88e6123_setup, .set_addr = mv88e6xxx_set_addr_indirect, .phy_read = mv88e6xxx_phy_read, diff --git a/drivers/net/dsa/mv88e6131.c b/drivers/net/dsa/mv88e6131.c index 9e6edf94a855..f5d75fce1e96 100644 --- a/drivers/net/dsa/mv88e6131.c +++ b/drivers/net/dsa/mv88e6131.c @@ -25,8 +25,9 @@ static const struct mv88e6xxx_switch_id mv88e6131_table[] = { { PORT_SWITCH_ID_6185, "Marvell 88E6185" }, }; -static char *mv88e6131_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr, void **priv) +static char *mv88e6131_drv_probe(struct device *dsa_dev, + struct device *host_dev, + int sw_addr, void **priv) { return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, mv88e6131_table, @@ -163,7 +164,7 @@ mv88e6131_phy_write(struct dsa_switch *ds, struct dsa_switch_driver mv88e6131_switch_driver = { .tag_protocol = DSA_TAG_PROTO_DSA, - .probe = mv88e6131_probe, + .probe = mv88e6131_drv_probe, .setup = mv88e6131_setup, .set_addr = mv88e6xxx_set_addr_direct, .phy_read = mv88e6131_phy_read, diff --git a/drivers/net/dsa/mv88e6171.c b/drivers/net/dsa/mv88e6171.c index 6ab86071391f..f5622506cdfa 100644 --- a/drivers/net/dsa/mv88e6171.c +++ b/drivers/net/dsa/mv88e6171.c @@ -24,8 +24,9 @@ static const struct mv88e6xxx_switch_id mv88e6171_table[] = { { PORT_SWITCH_ID_6351, "Marvell 88E6351" }, }; -static char *mv88e6171_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr, void **priv) +static char *mv88e6171_drv_probe(struct device *dsa_dev, + struct device *host_dev, + int sw_addr, void **priv) { return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, mv88e6171_table, @@ -92,7 +93,7 @@ static int mv88e6171_setup(struct dsa_switch *ds) struct dsa_switch_driver mv88e6171_switch_driver = { .tag_protocol = DSA_TAG_PROTO_EDSA, - .probe = mv88e6171_probe, + .probe = mv88e6171_drv_probe, .setup = mv88e6171_setup, .set_addr = mv88e6xxx_set_addr_indirect, .phy_read = mv88e6xxx_phy_read_indirect, diff --git a/drivers/net/dsa/mv88e6352.c b/drivers/net/dsa/mv88e6352.c index 764b10ffb631..e54ee27db129 100644 --- a/drivers/net/dsa/mv88e6352.c +++ b/drivers/net/dsa/mv88e6352.c @@ -37,8 +37,9 @@ static const struct mv88e6xxx_switch_id mv88e6352_table[] = { { PORT_SWITCH_ID_6352_A1, "Marvell 88E6352 (A1)" }, }; -static char *mv88e6352_probe(struct device *dsa_dev, struct device *host_dev, - int sw_addr, void **priv) +static char *mv88e6352_drv_probe(struct device *dsa_dev, + struct device *host_dev, + int sw_addr, void **priv) { return mv88e6xxx_drv_probe(dsa_dev, host_dev, sw_addr, priv, mv88e6352_table, @@ -306,7 +307,7 @@ static int mv88e6352_set_eeprom(struct dsa_switch *ds, struct dsa_switch_driver mv88e6352_switch_driver = { .tag_protocol = DSA_TAG_PROTO_EDSA, - .probe = mv88e6352_probe, + .probe = mv88e6352_drv_probe, .setup = mv88e6352_setup, .set_addr = mv88e6xxx_set_addr_indirect, .phy_read = mv88e6xxx_phy_read_indirect, From 74c3e2a54b7d9eb57f23fb0e157b90bb6dae629f Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Wed, 13 Apr 2016 02:40:44 +0200 Subject: [PATCH 6/7] dsa: Rename phys_port_mask to enabled_port_mask The phys in phys_port_mask suggests this mask is about PHYs. In fact, it means physical ports. Rename to enabled_port_mask, indicating external enabled ports of the switch, which is hopefully less confusing. Signed-off-by: Andrew Lunn Tested-by: Vivien Didelot Acked-by: Florian Fainelli Signed-off-by: David S. Miller --- drivers/net/dsa/bcm_sf2.c | 19 ++++++++++--------- drivers/net/dsa/mv88e6060.c | 2 +- include/net/dsa.h | 4 ++-- net/dsa/dsa.c | 8 ++++---- 4 files changed, 17 insertions(+), 16 deletions(-) diff --git a/drivers/net/dsa/bcm_sf2.c b/drivers/net/dsa/bcm_sf2.c index 50caa525cda3..7a5f0ef46bd6 100644 --- a/drivers/net/dsa/bcm_sf2.c +++ b/drivers/net/dsa/bcm_sf2.c @@ -160,7 +160,7 @@ static void bcm_sf2_imp_vlan_setup(struct dsa_switch *ds, int cpu_port) * the same VLAN. */ for (i = 0; i < priv->hw_params.num_ports; i++) { - if (!((1 << i) & ds->phys_port_mask)) + if (!((1 << i) & ds->enabled_port_mask)) continue; reg = core_readl(priv, CORE_PORT_VLAN_CTL_PORT(i)); @@ -1009,7 +1009,7 @@ static int bcm_sf2_sw_setup(struct dsa_switch *ds) /* Enable all valid ports and disable those unused */ for (port = 0; port < priv->hw_params.num_ports; port++) { /* IMP port receives special treatment */ - if ((1 << port) & ds->phys_port_mask) + if ((1 << port) & ds->enabled_port_mask) bcm_sf2_port_setup(ds, port, NULL); else if (dsa_is_cpu_port(ds, port)) bcm_sf2_imp_setup(ds, port); @@ -1022,11 +1022,12 @@ static int bcm_sf2_sw_setup(struct dsa_switch *ds) * 7445D0, since 7445E0 disconnects the internal switch pseudo-PHY such * that we can use the regular SWITCH_MDIO master controller instead. * - * By default, DSA initializes ds->phys_mii_mask to ds->phys_port_mask - * to have a 1:1 mapping between Port address and PHY address in order - * to utilize the slave_mii_bus instance to read from Port PHYs. This is - * not what we want here, so we initialize phys_mii_mask 0 to always - * utilize the "master" MDIO bus backed by the "mdio-unimac" driver. + * By default, DSA initializes ds->phys_mii_mask to + * ds->enabled_port_mask to have a 1:1 mapping between Port address + * and PHY address in order to utilize the slave_mii_bus instance to + * read from Port PHYs. This is not what we want here, so we + * initialize phys_mii_mask 0 to always utilize the "master" MDIO + * bus backed by the "mdio-unimac" driver. */ if (of_machine_is_compatible("brcm,bcm7445d0")) ds->phys_mii_mask |= ((1 << BRCM_PSEUDO_PHY_ADDR) | (1 << 0)); @@ -1284,7 +1285,7 @@ static int bcm_sf2_sw_suspend(struct dsa_switch *ds) * bcm_sf2_sw_setup */ for (port = 0; port < DSA_MAX_PORTS; port++) { - if ((1 << port) & ds->phys_port_mask || + if ((1 << port) & ds->enabled_port_mask || dsa_is_cpu_port(ds, port)) bcm_sf2_port_disable(ds, port, NULL); } @@ -1308,7 +1309,7 @@ static int bcm_sf2_sw_resume(struct dsa_switch *ds) bcm_sf2_gphy_enable_set(ds, true); for (port = 0; port < DSA_MAX_PORTS; port++) { - if ((1 << port) & ds->phys_port_mask) + if ((1 << port) & ds->enabled_port_mask) bcm_sf2_port_setup(ds, port, NULL); else if (dsa_is_cpu_port(ds, port)) bcm_sf2_imp_setup(ds, port); diff --git a/drivers/net/dsa/mv88e6060.c b/drivers/net/dsa/mv88e6060.c index adb608ccd9aa..92cebab9383e 100644 --- a/drivers/net/dsa/mv88e6060.c +++ b/drivers/net/dsa/mv88e6060.c @@ -170,7 +170,7 @@ static int mv88e6060_setup_port(struct dsa_switch *ds, int p) REG_WRITE(addr, PORT_VLAN_MAP, ((p & 0xf) << PORT_VLAN_MAP_DBNUM_SHIFT) | (dsa_is_cpu_port(ds, p) ? - ds->phys_port_mask : + ds->enabled_port_mask : BIT(ds->dst->cpu_port))); /* Port Association Vector: when learning source addresses diff --git a/include/net/dsa.h b/include/net/dsa.h index 165c2e10615c..689ebd3542ba 100644 --- a/include/net/dsa.h +++ b/include/net/dsa.h @@ -167,7 +167,7 @@ struct dsa_switch { * Slave mii_bus and devices for the individual ports. */ u32 dsa_port_mask; - u32 phys_port_mask; + u32 enabled_port_mask; u32 phys_mii_mask; struct mii_bus *slave_mii_bus; struct net_device *ports[DSA_MAX_PORTS]; @@ -185,7 +185,7 @@ static inline bool dsa_is_dsa_port(struct dsa_switch *ds, int p) static inline bool dsa_is_port_initialized(struct dsa_switch *ds, int p) { - return ds->phys_port_mask & (1 << p) && ds->ports[p]; + return ds->enabled_port_mask & (1 << p) && ds->ports[p]; } static inline u8 dsa_upstream_port(struct dsa_switch *ds) diff --git a/net/dsa/dsa.c b/net/dsa/dsa.c index 14bf12f637d2..60ea98481806 100644 --- a/net/dsa/dsa.c +++ b/net/dsa/dsa.c @@ -246,7 +246,7 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, struct device *parent) } else if (!strcmp(name, "dsa")) { ds->dsa_port_mask |= 1 << i; } else { - ds->phys_port_mask |= 1 << i; + ds->enabled_port_mask |= 1 << i; } valid_name_found = true; } @@ -259,7 +259,7 @@ static int dsa_switch_setup_one(struct dsa_switch *ds, struct device *parent) /* Make the built-in MII bus mask match the number of ports, * switch drivers can override this later */ - ds->phys_mii_mask = ds->phys_port_mask; + ds->phys_mii_mask = ds->enabled_port_mask; /* * If the CPU connects to this switch, set the switch tree @@ -325,7 +325,7 @@ 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++) { - if (!(ds->phys_port_mask & (1 << i))) + if (!(ds->enabled_port_mask & (1 << i))) continue; ret = dsa_slave_create(ds, parent, i, pd->port_names[i]); @@ -435,7 +435,7 @@ static void dsa_switch_destroy(struct dsa_switch *ds) /* Destroy network devices for physical switch ports. */ for (port = 0; port < DSA_MAX_PORTS; port++) { - if (!(ds->phys_port_mask & (1 << port))) + if (!(ds->enabled_port_mask & (1 << port))) continue; if (!ds->ports[port]) From c156913b5d62cbaa0e3be29409de562b7d2e006e Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Wed, 13 Apr 2016 02:40:45 +0200 Subject: [PATCH 7/7] dsa: mv88e6xxx: Use bus in mv88e6xxx_lookup_name() mv88e6xxx_lookup_name() returns the model name of a switch at a given address on an MII bus. Using mii_bus to identify the bus rather than the host device is more logical, so change the parameter. Signed-off-by: Andrew Lunn Tested-by: Vivien Didelot Reviewed-by: Vivien Didelot Signed-off-by: David S. Miller --- drivers/net/dsa/mv88e6xxx.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/drivers/net/dsa/mv88e6xxx.c b/drivers/net/dsa/mv88e6xxx.c index c242ffd8eb09..9985a0cf31f1 100644 --- a/drivers/net/dsa/mv88e6xxx.c +++ b/drivers/net/dsa/mv88e6xxx.c @@ -3068,11 +3068,10 @@ int mv88e6xxx_get_temp_alarm(struct dsa_switch *ds, bool *alarm) } #endif /* CONFIG_NET_DSA_HWMON */ -static char *mv88e6xxx_lookup_name(struct device *host_dev, int sw_addr, +static char *mv88e6xxx_lookup_name(struct mii_bus *bus, int sw_addr, const struct mv88e6xxx_switch_id *table, unsigned int num) { - struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); int i, ret; if (!bus) @@ -3090,7 +3089,8 @@ static char *mv88e6xxx_lookup_name(struct device *host_dev, int sw_addr, /* Look up only the product number */ for (i = 0; i < num; ++i) { if (table[i].id == (ret & PORT_SWITCH_ID_PROD_NUM_MASK)) { - dev_warn(host_dev, "unknown revision %d, using base switch 0x%x\n", + dev_warn(&bus->dev, + "unknown revision %d, using base switch 0x%x\n", ret & PORT_SWITCH_ID_REV_MASK, ret & PORT_SWITCH_ID_PROD_NUM_MASK); return table[i].name; @@ -3106,9 +3106,13 @@ char *mv88e6xxx_drv_probe(struct device *dsa_dev, struct device *host_dev, unsigned int num) { struct mv88e6xxx_priv_state *ps; + struct mii_bus *bus = dsa_host_dev_to_mii_bus(host_dev); char *name; - name = mv88e6xxx_lookup_name(host_dev, sw_addr, table, num); + if (!bus) + return NULL; + + name = mv88e6xxx_lookup_name(bus, sw_addr, table, num); if (name) { ps = devm_kzalloc(dsa_dev, sizeof(*ps), GFP_KERNEL); if (!ps)