From 702c177bec2161a196017eaeffcfed5c7f7e49b9 Mon Sep 17 00:00:00 2001 From: Weiguo Hu Date: Thu, 22 Dec 2016 09:11:56 +0800 Subject: [PATCH] ethernet: rockchip: get and save eth addr in vendor storage Change-Id: I83d8bc81ca8d33e6f2575d0d90a3dc5978500a64 Signed-off-by: Weiguo Hu Signed-off-by: Zhangbin Tong --- .../net/ethernet/stmicro/stmmac/dwmac-rk.c | 32 ++++++++++++++++++- .../net/ethernet/stmicro/stmmac/stmmac_main.c | 3 ++ include/linux/stmmac.h | 1 + 3 files changed, 35 insertions(+), 1 deletion(-) diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-rk.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-rk.c index 6ef30252bfe0..c605a7353925 100644 --- a/drivers/net/ethernet/stmicro/stmmac/dwmac-rk.c +++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-rk.c @@ -22,7 +22,7 @@ #include #include #include - +#include #include "stmmac_platform.h" struct rk_priv_data; @@ -1379,6 +1379,35 @@ static void rk_fix_speed(void *priv, unsigned int speed) } } +static void rk_get_eth_addr(void *priv, unsigned char *addr) +{ + int ret; + struct rk_priv_data *bsp_priv = priv; + struct device *dev = &bsp_priv->pdev->dev; + + if (is_valid_ether_addr(addr)) + goto out; + + ret = rk_vendor_read(LAN_MAC_ID, addr, 6); + if (ret != 6 || is_zero_ether_addr(addr)) { + dev_err(dev, "%s: rk_vendor_read eth mac address failed (%d)", + __func__, ret); + random_ether_addr(addr); + dev_err(dev, "%s: generate random eth mac address: %02x:%02x:%02x:%02x:%02x:%02x", + __func__, addr[0], addr[1], addr[2], + addr[3], addr[4], addr[5]); + ret = rk_vendor_write(LAN_MAC_ID, addr, 6); + if (ret != 0) + dev_err(dev, "%s: rk_vendor_write eth mac address failed (%d)", + __func__, ret); + } + +out: + dev_err(dev, "%s: mac address: %02x:%02x:%02x:%02x:%02x:%02x", + __func__, addr[0], addr[1], addr[2], + addr[3], addr[4], addr[5]); +} + static int rk_gmac_probe(struct platform_device *pdev) { struct plat_stmmacenet_data *plat_dat; @@ -1402,6 +1431,7 @@ static int rk_gmac_probe(struct platform_device *pdev) plat_dat->has_gmac = true; plat_dat->fix_mac_speed = rk_fix_speed; + plat_dat->get_eth_addr = rk_get_eth_addr; plat_dat->bsp_priv = rk_gmac_setup(pdev, plat_dat, data); if (IS_ERR(plat_dat->bsp_priv)) { diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c index 3134f7e669f8..b44833580ca1 100644 --- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c @@ -2280,6 +2280,9 @@ static void stmmac_check_ether_addr(struct stmmac_priv *priv) { if (!is_valid_ether_addr(priv->dev->dev_addr)) { stmmac_get_umac_addr(priv, priv->hw, priv->dev->dev_addr, 0); + if (likely(priv->plat->get_eth_addr)) + priv->plat->get_eth_addr(priv->plat->bsp_priv, + priv->dev->dev_addr); if (!is_valid_ether_addr(priv->dev->dev_addr)) eth_hw_addr_random(priv->dev); dev_info(priv->device, "device MAC address %pM\n", diff --git a/include/linux/stmmac.h b/include/linux/stmmac.h index 15ca6b4167cc..0de2edd1b838 100644 --- a/include/linux/stmmac.h +++ b/include/linux/stmmac.h @@ -182,6 +182,7 @@ struct plat_stmmacenet_data { void (*serdes_powerdown)(struct net_device *ndev, void *priv); int (*init)(struct platform_device *pdev, void *priv); void (*exit)(struct platform_device *pdev, void *priv); + void (*get_eth_addr)(void *priv, unsigned char *addr); struct mac_device_info *(*setup)(void *priv); void *bsp_priv; struct clk *stmmac_clk;