Message ID | 20200920095724.8251-4-ansuelsmth@gmail.com |
---|---|
State | Not Applicable |
Delegated to: | David Miller |
Headers | show |
Series | Actually implement nvmem support for mtd | expand |
On Sun, Sep 20, 2020 at 3:57 AM Ansuel Smith <ansuelsmth@gmail.com> wrote: > > Lots of embedded devices use the mac-address of other interface > extracted from nvmem cells and increments it by one or two. Add two > bindings to integrate this and directly use the right mac-address for > the interface. Some example are some routers that use the gmac > mac-address stored in the art partition and increments it by one for the > wifi. mac-address-increment-byte bindings is used to tell what byte of > the mac-address has to be increased (if not defined the last byte is > increased) and mac-address-increment tells how much the byte decided > early has to be increased. I'm inclined to say if there's a platform specific way to transform MAC addresses, then there should be platform specific code to do that which then stuffs the DT using standard properties. Otherwise, we have a never ending stream of 'generic' properties to try to handle different platforms' cases. Rob
> -----Original Message----- > From: Rob Herring <robh+dt@kernel.org> > Sent: Friday, September 25, 2020 8:24 PM > To: Ansuel Smith <ansuelsmth@gmail.com> > Cc: Miquel Raynal <miquel.raynal@bootlin.com>; Richard Weinberger > <richard@nod.at>; Vignesh Raghavendra <vigneshr@ti.com>; David S. > Miller <davem@davemloft.net>; Jakub Kicinski <kuba@kernel.org>; > Andrew Lunn <andrew@lunn.ch>; Heiner Kallweit > <hkallweit1@gmail.com>; Russell King <linux@armlinux.org.uk>; Frank > Rowand <frowand.list@gmail.com>; Boris Brezillon > <bbrezillon@kernel.org>; MTD Maling List <linux-mtd@lists.infradead.org>; > devicetree@vger.kernel.org; linux-kernel@vger.kernel.org; netdev > <netdev@vger.kernel.org> > Subject: Re: [PATCH v3 3/4] of_net: add mac-address-increment support > > On Sun, Sep 20, 2020 at 3:57 AM Ansuel Smith <ansuelsmth@gmail.com> > wrote: > > > > Lots of embedded devices use the mac-address of other interface > > extracted from nvmem cells and increments it by one or two. Add two > > bindings to integrate this and directly use the right mac-address for > > the interface. Some example are some routers that use the gmac > > mac-address stored in the art partition and increments it by one for the > > wifi. mac-address-increment-byte bindings is used to tell what byte of > > the mac-address has to be increased (if not defined the last byte is > > increased) and mac-address-increment tells how much the byte decided > > early has to be increased. > > I'm inclined to say if there's a platform specific way to transform > MAC addresses, then there should be platform specific code to do that > which then stuffs the DT using standard properties. Otherwise, we have > a never ending stream of 'generic' properties to try to handle > different platforms' cases. > > Rob I agree about the 'never ending stream'... But I think the increment feature is not that platform specific. I will quote some number by another patch that tried to implement the same feature in a different way, [1] * mtd-mac-address used 497 times in 357 device tree files * mtd-mac-address-increment used 74 times in 58 device tree files * mtd-mac-address-increment-byte used 1 time in 1 device tree file The mtd-mac-address is what this patchset is trying to fix with the nvmem support. The increment is much more than 74 times since it doesn't count SoC that have wifi integrated (it's common practice for SoC with integrated wifi to take the switch mac and use it to set the wifi mac) Actually what is really specific is the increment-byte that can be dropped if we really want to. I still think the increment feature would be very useful to add full support for mac-address extracted from nvmem cell. [1] https://patchwork.ozlabs.org/project/netdev/patch/1555445100-30936-1-git-send-email-ynezz@true.cz/
diff --git a/drivers/of/of_net.c b/drivers/of/of_net.c index 6e411821583e..bafbc833e659 100644 --- a/drivers/of/of_net.c +++ b/drivers/of/of_net.c @@ -45,7 +45,7 @@ int of_get_phy_mode(struct device_node *np, phy_interface_t *interface) } EXPORT_SYMBOL_GPL(of_get_phy_mode); -static const void *of_get_mac_addr(struct device_node *np, const char *name) +static void *of_get_mac_addr(struct device_node *np, const char *name) { struct property *pp = of_find_property(np, name, NULL); @@ -54,26 +54,31 @@ static const void *of_get_mac_addr(struct device_node *np, const char *name) return NULL; } -static const void *of_get_mac_addr_nvmem(struct device_node *np) +static void *of_get_mac_addr_nvmem(struct device_node *np, int *err) { int ret; - const void *mac; + void *mac; u8 nvmem_mac[ETH_ALEN]; struct platform_device *pdev = of_find_device_by_node(np); - if (!pdev) - return ERR_PTR(-ENODEV); + if (!pdev) { + *err = -ENODEV; + return NULL; + } ret = nvmem_get_mac_address(&pdev->dev, &nvmem_mac); if (ret) { put_device(&pdev->dev); - return ERR_PTR(ret); + *err = ret; + return NULL; } mac = devm_kmemdup(&pdev->dev, nvmem_mac, ETH_ALEN, GFP_KERNEL); put_device(&pdev->dev); - if (!mac) - return ERR_PTR(-ENOMEM); + if (!mac) { + *err = -ENOMEM; + return NULL; + } return mac; } @@ -98,24 +103,50 @@ static const void *of_get_mac_addr_nvmem(struct device_node *np) * this case, the real MAC is in 'local-mac-address', and 'mac-address' exists * but is all zeros. * + * DT can tell the system to increment the mac-address after is extracted by + * using: + * - mac-address-increment-byte to decide what byte to increase + * (if not defined is increased the last byte) + * - mac-address-increment to decide how much to increase. The value will + * not overflow to other bytes if the increment is over 255. + * (example 00:01:02:03:04:ff + 1 == 00:01:02:03:04:00) + * * Return: Will be a valid pointer on success and ERR_PTR in case of error. */ const void *of_get_mac_address(struct device_node *np) { - const void *addr; + u32 inc_idx, mac_inc; + int ret = 0; + u8 *addr; + + /* Check first if the increment byte is present and valid. + * If not set assume to increment the last byte if found. + */ + if (of_property_read_u32(np, "mac-address-increment-byte", &inc_idx)) + inc_idx = 5; + if (inc_idx < 3 || inc_idx > 5) + return ERR_PTR(-EINVAL); addr = of_get_mac_addr(np, "mac-address"); if (addr) - return addr; + goto found; addr = of_get_mac_addr(np, "local-mac-address"); if (addr) - return addr; + goto found; addr = of_get_mac_addr(np, "address"); if (addr) - return addr; + goto found; + + addr = of_get_mac_addr_nvmem(np, &ret); + if (ret) + return ERR_PTR(ret); + +found: + if (!of_property_read_u32(np, "mac-address-increment", &mac_inc)) + addr[inc_idx] += mac_inc; - return of_get_mac_addr_nvmem(np); + return addr; } EXPORT_SYMBOL(of_get_mac_address);
Lots of embedded devices use the mac-address of other interface extracted from nvmem cells and increments it by one or two. Add two bindings to integrate this and directly use the right mac-address for the interface. Some example are some routers that use the gmac mac-address stored in the art partition and increments it by one for the wifi. mac-address-increment-byte bindings is used to tell what byte of the mac-address has to be increased (if not defined the last byte is increased) and mac-address-increment tells how much the byte decided early has to be increased. Signed-off-by: Ansuel Smith <ansuelsmth@gmail.com> --- drivers/of/of_net.c | 57 ++++++++++++++++++++++++++++++++++----------- 1 file changed, 44 insertions(+), 13 deletions(-)