lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [day] [month] [year] [list]
Message-ID: <MWHSPR01MB3550C50AFA0BA60598CE175A4409@MWHSPR01MB355.namprd10.prod.outlook.com>
Date:   Wed, 28 Apr 2021 17:22:20 +0000
From:   Colin Foster <colin.Foster@...advantage.com>
To:     Vladimir Oltean <vladimir.oltean@....com>
CC:     Claudiu Manoil <claudiu.manoil@....com>,
        "alexandre.belloni@...tlin.com" <alexandre.belloni@...tlin.com>,
        "UNGLinuxDriver@...rochip.com" <UNGLinuxDriver@...rochip.com>,
        "netdev@...r.kernel.org" <netdev@...r.kernel.org>
Subject: RE: [PATCH] net: mscc: ocelot: add support for non-mmio regmaps

Hi Vladimir,

> From: Vladimir Oltean <vladimir.oltean@....com> 
> Sent: Wednesday, April 28, 2021 2:20 AM
> To: Colin Foster <colin.Foster@...advantage.com>
> Cc: Claudiu Manoil <claudiu.manoil@....com>; alexandre.belloni@...tlin.com; UNGLinuxDriver@...rochip.com; netdev@...r.kernel.org
> Subject: Re: [PATCH] net: mscc: ocelot: add support for non-mmio regmaps
> 
> Hi Colin,
> 
> On Wed, Apr 28, 2021 at 01:39:36AM +0000, Colin Foster wrote:
> > From 652b52933c59035ddb3f19dcf84e5a683b868115 Mon Sep 17 00:00:00 2001
> > From: Colin Foster <colin.foster@...advantage.com>
> > Date: Tue, 27 Apr 2021 23:50:36 +0000
> > Subject: [PATCH] net: mscc: ocelot: add support for non-mmio regmaps
> > 
> > Control for external VSC75XX chips can be performed via non-mmio 
> > interfaces, e.g. SPI. Adding the offets array (one per target) and the 
> > offset element per port allows the ability to track this location that 
> > would otherwise be found in the MMIO regmap resource.
> 
> Sadly, without more context around what you need for SPI regmaps, I can't judge whether this change is in fact necessary or not (I don't see why it would be, you should be able to provide your own SoC integration file ocelot_vsc7514_spi.c file with the regmap array of your liking, unless what you want is to just reuse an existing one, which is probably more trouble than it's worth). Do you think you can resend when you have a functional port for the SPI-managed switches, so we can see everything in action?

Thank you for this feedback. I'm working in felix_vsc7512_spi.c, which is mostly a copy of felix_vsc9959.c but with SPI probing instead of PCI. The memory addresses are different, and down-shifted by two so that devm_regmap_init_spi can be used without defining a new bus. It is not in a state where it is worth your time to review yet. Once it is, I'll re-submit with your suggestions.

> 
> > Tracking this offset in the ocelot driver and allowing the 
> > ocelot_regmap_init function to be overloaded with a device-specific 
> > initializer. This driver could update the *offset element to handle 
> > the value that would otherwise be mapped via resource *res->start.
> > ---
> 
> Your patch is whitespace damaged and is in fact a multi-part attachment instead of a single plain-text body.
> Can you please try to send using git-send-email? See Documentation/process/submitting-patches.rst for more details.
> 
> Also, some other process-related tips:
> ./scripts/get_maintainer.pl should have shown more people to Cc: than the ones you did.

I'm embarrassed by this blunder. I'll resolve these by my next commit.

> 
> And in the networking subsystem, we like to tag patches using git-send-email --subject-prefix="PATCH vN net-next" or --subject-prefix="PATCH vN net" depending on whether it targets this tree (for new features):
> https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git
> or this tree (for bug fixes):
> https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git
> 
> We also review patches even if they aren't fully ready for acceptance for whatever reason, just add "RFC PATCH vN net-next" to your commit.
> But the patches need to tell a full story, and be understandable on their own.
> For example, the merge window should open any time now, and during the merge window, maintainers don't accept patches on their "next" trees.
> In the case of networking, you can check here:
> http://vger.kernel.org/~davem/net-next.html
> (it's open but it will close soon)
> When the development trees are closed you can still send patches as RFC.
> 
> This, and more, mentioned inside Documentation/networking/netdev-FAQ.rst.
> 
> > drivers/net/dsa/ocelot/felix.c        | 11 ++++++++--
> > drivers/net/dsa/ocelot/felix.h        |  2 ++
> > drivers/net/ethernet/mscc/ocelot_io.c | 29 +++++++++++++++++++--------
> > include/soc/mscc/ocelot.h             |  5 ++++-
> > 4 files changed, 36 insertions(+), 11 deletions(-)
> > 
> > diff --git a/drivers/net/dsa/ocelot/felix.c 
> > b/drivers/net/dsa/ocelot/felix.c index 628afb47b579..dcd38653447e 
> > 100644
> > --- a/drivers/net/dsa/ocelot/felix.c
> > +++ b/drivers/net/dsa/ocelot/felix.c
> > @@ -1083,6 +1083,9 @@ static int felix_init_structs(struct felix *felix, int num_phys_ports)
> >     phy_interface_t *port_phy_modes;
> >     struct resource res;
> >     int port, i, err;
> > +    struct regmap *(*local_regmap_init)(struct ocelot *ocelot,
> > +                              struct resource *res,
> > +                              u32 *offset);
> 
> Why don't you just populate ".regmap_init = ocelot_regmap_init" for
> VSC9959 and VSC9953 and remove this local function pointer?

Good idea. Thanks.

> 
> >      ocelot->num_phys_ports = num_phys_ports;
> >     ocelot->ports = devm_kcalloc(ocelot->dev, num_phys_ports, @@ 
> > -1111,6 +1114,10 @@ static int felix_init_structs(struct felix *felix, int num_phys_ports)
> >           return err;
> >     }
> > +    local_regmap_init = (felix->info->regmap_init) ?
> > +                        felix->info->regmap_init :
> > +                        ocelot_regmap_init;
> > +
> >     for (i = 0; i < TARGET_MAX; i++) {
> >           struct regmap *target;
> > @@ -1122,7 +1129,7 @@ static int felix_init_structs(struct felix *felix, int num_phys_ports)
> >           res.start += felix->switch_base;
> >           res.end += felix->switch_base;
> > -          target = ocelot_regmap_init(ocelot, &res);
> > +          target = local_regmap_init(ocelot, &res, 
> > + &ocelot->offsets[i]);
> >           if (IS_ERR(target)) {
> >                dev_err(ocelot->dev,
> >                     "Failed to map device memory space\n"); @@ -1159,7 
> > +1166,7 @@ static int felix_init_structs(struct felix *felix, int num_phys_ports)
> >           res.start += felix->switch_base;
> >           res.end += felix->switch_base;
> > -          target = ocelot_regmap_init(ocelot, &res);
> > +          target = local_regmap_init(ocelot, &res, 
> > + &ocelot_port->offset);
> >           if (IS_ERR(target)) {
> >                dev_err(ocelot->dev,
> >                     "Failed to map memory space for port %d\n", diff 
> > --git a/drivers/net/dsa/ocelot/felix.h 
> > b/drivers/net/dsa/ocelot/felix.h index 4d96cad815d5..8fde304e754f 
> > 100644
> > --- a/drivers/net/dsa/ocelot/felix.h
> > +++ b/drivers/net/dsa/ocelot/felix.h
> > @@ -47,6 +47,8 @@ struct felix_info {
> >                      enum tc_setup_type type, void *type_data);
> >     void (*port_sched_speed_set)(struct ocelot *ocelot, int port,
> >                           u32 speed);
> > +    struct regmap *(*regmap_init)(struct ocelot *ocelot,
> > +                          struct resource *res, u32 *offset);
> > };
> >  extern const struct dsa_switch_ops felix_switch_ops; diff --git 
> > a/drivers/net/ethernet/mscc/ocelot_io.c 
> > b/drivers/net/ethernet/mscc/ocelot_io.c
> > index ea4e83410fe4..2804cd441817 100644
> > --- a/drivers/net/ethernet/mscc/ocelot_io.c
> > +++ b/drivers/net/ethernet/mscc/ocelot_io.c
> > @@ -18,7 +18,9 @@ u32 __ocelot_read_ix(struct ocelot *ocelot, u32 reg, u32 offset)
> >     WARN_ON(!target);
> >      regmap_read(ocelot->targets[target],
> > -              ocelot->map[target][reg & REG_MASK] + offset, &val);
> > +              ocelot->offsets[target] +
> > +                   ocelot->map[target][reg & REG_MASK] + offset,
> > +              &val);
> >     return val;
> > }
> > EXPORT_SYMBOL(__ocelot_read_ix);
> > @@ -30,7 +32,9 @@ void __ocelot_write_ix(struct ocelot *ocelot, u32 val, u32 reg, u32 offset)
> >     WARN_ON(!target);
> >      regmap_write(ocelot->targets[target],
> > -               ocelot->map[target][reg & REG_MASK] + offset, val);
> > +               ocelot->offsets[target] +
> > +                    ocelot->map[target][reg & REG_MASK] + offset,
> > +               val);
> > }
> > EXPORT_SYMBOL(__ocelot_write_ix);
> > @@ -42,7 +46,8 @@ void __ocelot_rmw_ix(struct ocelot *ocelot, u32 val, u32 mask, u32 reg,
> >     WARN_ON(!target);
> >      regmap_update_bits(ocelot->targets[target],
> > -                  ocelot->map[target][reg & REG_MASK] + offset,
> > +                  ocelot->offsets[target] +
> > +                       ocelot->map[target][reg & REG_MASK] + offset,
> >                   mask, val);
> > }
> > EXPORT_SYMBOL(__ocelot_rmw_ix);
> > @@ -55,7 +60,8 @@ u32 ocelot_port_readl(struct ocelot_port *port, u32 reg)
> >      WARN_ON(!target);
> > -    regmap_read(port->target, ocelot->map[target][reg & REG_MASK], &val);
> > +    regmap_read(port->target,
> > +              port->offset + ocelot->map[target][reg & REG_MASK], 
> > + &val);
> >     return val;
> > }
> > EXPORT_SYMBOL(ocelot_port_readl);
> > @@ -67,7 +73,8 @@ void ocelot_port_writel(struct ocelot_port *port, u32 val, u32 reg)
> >      WARN_ON(!target);
> > -    regmap_write(port->target, ocelot->map[target][reg & REG_MASK], val);
> > +    regmap_write(port->target,
> > +               port->offset + ocelot->map[target][reg & REG_MASK], 
> > + val);
> > }
> > EXPORT_SYMBOL(ocelot_port_writel);
> > @@ -85,7 +92,8 @@ u32 __ocelot_target_read_ix(struct ocelot *ocelot, enum ocelot_target target,
> >     u32 val;
> >      regmap_read(ocelot->targets[target],
> > -              ocelot->map[target][reg] + offset, &val);
> > +              ocelot->offsets[target] + ocelot->map[target][reg] + offset,
> > +              &val);
> >     return val;
> > }
> > @@ -93,7 +101,9 @@ void __ocelot_target_write_ix(struct ocelot *ocelot, enum ocelot_target target,
> >                      u32 val, u32 reg, u32 offset) {
> >     regmap_write(ocelot->targets[target],
> > -               ocelot->map[target][reg] + offset, val);
> > +               ocelot->offsets[target] + ocelot->map[target][reg] +
> > +                    offset,
> 
> This could have fit on a single line.

I used clang-format to break up the long lines, but it seems like that causes other issues.  I'll keep an eye out for these.

> 
> > +               val);
> > }
> >  int ocelot_regfields_init(struct ocelot *ocelot, @@ -136,10 +146,13 
> > @@ static struct regmap_config ocelot_regmap_config = {
> >     .reg_stride     = 4,
> > };
> > -struct regmap *ocelot_regmap_init(struct ocelot *ocelot, struct 
> > resource *res)
> > +struct regmap *ocelot_regmap_init(struct ocelot *ocelot, struct resource *res,
> > +                      u32 *offset)
> > {
> >     void __iomem *regs;
> > +    *offset = 0;
> > +
> 
> Please ensure there is one empty line between variable declarations and the code. I think ./scripts/checkpatch.pl will warn about this.

The script did not issue a warning. I will resolve this.

> 
> >     regs = devm_ioremap_resource(ocelot->dev, res);
> >     if (IS_ERR(regs))
> >           return ERR_CAST(regs);
> > diff --git a/include/soc/mscc/ocelot.h b/include/soc/mscc/ocelot.h 
> > index 425ff29d9389..ad45c1af4be9 100644
> > --- a/include/soc/mscc/ocelot.h
> > +++ b/include/soc/mscc/ocelot.h
> > @@ -591,6 +591,7 @@ struct ocelot_port {
> >     struct ocelot              *ocelot;
> >      struct regmap              *target;
> > +    u32                  offset;
> >      bool                 vlan_aware;
> >     /* VLAN that untagged frames are classified to, on ingress */ @@ 
> > -621,6 +622,7 @@ struct ocelot {
> >     const struct ocelot_ops          *ops;
> >     struct regmap              *targets[TARGET_MAX];
> >     struct regmap_field        *regfields[REGFIELD_MAX];
> > +    u32                  offsets[TARGET_MAX];
> >     const u32 *const      *map;
> >     const struct ocelot_stat_layout  *stats_layout;
> >     unsigned int               num_stats;
> > @@ -780,7 +782,8 @@ static inline void ocelot_drain_cpu_queue(struct 
> > ocelot *ocelot, int grp)
> > /* Hardware initialization */
> > int ocelot_regfields_init(struct ocelot *ocelot,
> >                  const struct reg_field *const regfields); -struct 
> > regmap *ocelot_regmap_init(struct ocelot *ocelot, struct resource 
> > *res);
> > +struct regmap *ocelot_regmap_init(struct ocelot *ocelot, struct resource *res,
> > +                      u32 *offset);
> > int ocelot_init(struct ocelot *ocelot); void ocelot_deinit(struct 
> > ocelot *ocelot); void ocelot_init_port(struct ocelot *ocelot, int 
> > port);
> > --
> > 2.17.1
> > 
>

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ