From 3d6af748ebd831524cb22a29433e9092af469ec7 Mon Sep 17 00:00:00 2001 From: Shengzhou Liu Date: Thu, 12 Mar 2015 18:54:59 +0800 Subject: net/phy: Add support for realtek RTL8211F RTL8211F has different registers from RTL8211E. This patch adds support for RTL8211F PHY which can be found on Freescale's T1023 RDB board. Signed-off-by: Shengzhou Liu Acked-by: Joe Hershberger --- drivers/net/phy/realtek.c | 85 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 85 insertions(+) (limited to 'drivers') diff --git a/drivers/net/phy/realtek.c b/drivers/net/phy/realtek.c index ee9707950a8..2e152c9a036 100644 --- a/drivers/net/phy/realtek.c +++ b/drivers/net/phy/realtek.c @@ -29,6 +29,18 @@ /* RTL8211x PHY Interrupt Status Register */ #define MIIM_RTL8211x_PHY_INSR 0x13 +/* RTL8211F PHY Status Register */ +#define MIIM_RTL8211F_PHY_STATUS 0x1a +#define MIIM_RTL8211F_AUTONEG_ENABLE 0x1000 +#define MIIM_RTL8211F_PHYSTAT_SPEED 0x0030 +#define MIIM_RTL8211F_PHYSTAT_GBIT 0x0020 +#define MIIM_RTL8211F_PHYSTAT_100 0x0010 +#define MIIM_RTL8211F_PHYSTAT_DUPLEX 0x0008 +#define MIIM_RTL8211F_PHYSTAT_SPDDONE 0x0800 +#define MIIM_RTL8211F_PHYSTAT_LINK 0x0004 + +#define MIIM_RTL8211F_PAGE_SELECT 0x1f + /* RealTek RTL8211x */ static int rtl8211x_config(struct phy_device *phydev) { @@ -105,6 +117,58 @@ static int rtl8211x_parse_status(struct phy_device *phydev) return 0; } +static int rtl8211f_parse_status(struct phy_device *phydev) +{ + unsigned int speed; + unsigned int mii_reg; + int i = 0; + + phy_write(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211F_PAGE_SELECT, 0xa43); + mii_reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_RTL8211F_PHY_STATUS); + + phydev->link = 1; + while (!(mii_reg & MIIM_RTL8211F_PHYSTAT_LINK)) { + if (i > PHY_AUTONEGOTIATE_TIMEOUT) { + puts(" TIMEOUT !\n"); + phydev->link = 0; + break; + } + + if ((i++ % 1000) == 0) + putc('.'); + udelay(1000); + mii_reg = phy_read(phydev, MDIO_DEVAD_NONE, + MIIM_RTL8211F_PHY_STATUS); + } + + if (mii_reg & MIIM_RTL8211F_PHYSTAT_DUPLEX) + phydev->duplex = DUPLEX_FULL; + else + phydev->duplex = DUPLEX_HALF; + + speed = (mii_reg & MIIM_RTL8211F_PHYSTAT_SPEED); + + switch (speed) { + case MIIM_RTL8211F_PHYSTAT_GBIT: + phydev->speed = SPEED_1000; + break; + case MIIM_RTL8211F_PHYSTAT_100: + phydev->speed = SPEED_100; + break; + default: + phydev->speed = SPEED_10; + } + + if (phydev->interface == PHY_INTERFACE_MODE_RGMII) { + /* enable TXDLY */ + phy_write(phydev, MDIO_DEVAD_NONE, + MIIM_RTL8211F_PAGE_SELECT, 0xd08); + phy_write(phydev, MDIO_DEVAD_NONE, 0x11, 0x109); + } + + return 0; +} + static int rtl8211x_startup(struct phy_device *phydev) { /* Read the Status (2x to make sure link is right) */ @@ -114,6 +178,15 @@ static int rtl8211x_startup(struct phy_device *phydev) return 0; } +static int rtl8211f_startup(struct phy_device *phydev) +{ + /* Read the Status (2x to make sure link is right) */ + genphy_update_link(phydev); + rtl8211f_parse_status(phydev); + + return 0; +} + /* Support for RTL8211B PHY */ static struct phy_driver RTL8211B_driver = { .name = "RealTek RTL8211B", @@ -147,10 +220,22 @@ static struct phy_driver RTL8211DN_driver = { .shutdown = &genphy_shutdown, }; +/* Support for RTL8211F PHY */ +static struct phy_driver RTL8211F_driver = { + .name = "RealTek RTL8211F", + .uid = 0x1cc916, + .mask = 0xffffff, + .features = PHY_GBIT_FEATURES, + .config = &rtl8211x_config, + .startup = &rtl8211f_startup, + .shutdown = &genphy_shutdown, +}; + int phy_realtek_init(void) { phy_register(&RTL8211B_driver); phy_register(&RTL8211E_driver); + phy_register(&RTL8211F_driver); phy_register(&RTL8211DN_driver); return 0; -- cgit v1.2.3 From f566c9949fbdce2e09a900c5343ca9986e5ba360 Mon Sep 17 00:00:00 2001 From: Joe Hershberger Date: Tue, 24 Mar 2015 02:41:49 -0500 Subject: net: Update hardware MAC address if it changes in env When the ethaddr changes in the env, the hardware should also be updated so that MAC filtering will work properly without resetting U-Boot. Also remove the manual calls to set the hwaddr that was included in a few drivers as a result of the framework not doing it. Reported-by: Michal Simek Signed-off-by: Joe Hershberger Tested-by: Michal Simek --- drivers/net/bcm-sf2-eth.c | 6 ------ drivers/net/designware.c | 4 ---- drivers/net/macb.c | 9 --------- 3 files changed, 19 deletions(-) (limited to 'drivers') diff --git a/drivers/net/bcm-sf2-eth.c b/drivers/net/bcm-sf2-eth.c index 51d51463630..eab4c1f9003 100644 --- a/drivers/net/bcm-sf2-eth.c +++ b/drivers/net/bcm-sf2-eth.c @@ -154,12 +154,6 @@ static int bcm_sf2_eth_open(struct eth_device *dev, bd_t *bt) debug("Enabling BCM SF2 Ethernet.\n"); - /* Set MAC address from env */ - if (bcm_sf2_eth_write_hwaddr(dev) != 0) { - error("%s: MAC set error when opening !\n", __func__); - return -1; - } - eth->enable_mac(); /* enable tx and rx DMA */ diff --git a/drivers/net/designware.c b/drivers/net/designware.c index 07281a6ce9d..ae51cf37816 100644 --- a/drivers/net/designware.c +++ b/drivers/net/designware.c @@ -243,10 +243,6 @@ static int _dw_eth_init(struct dw_eth_dev *priv, u8 *enetaddr) mdelay(100); }; - /* Soft reset above clears HW address registers. - * So we have to set it here once again */ - _dw_write_hwaddr(priv, enetaddr); - rx_descs_init(priv); tx_descs_init(priv); diff --git a/drivers/net/macb.c b/drivers/net/macb.c index 4e1a7fe5839..f9491617382 100644 --- a/drivers/net/macb.c +++ b/drivers/net/macb.c @@ -525,7 +525,6 @@ static int macb_phy_init(struct macb_device *macb) return 1; } -static int macb_write_hwaddr(struct eth_device *dev); static int macb_init(struct eth_device *netdev, bd_t *bd) { struct macb_device *macb = to_macb(netdev); @@ -594,14 +593,6 @@ static int macb_init(struct eth_device *netdev, bd_t *bd) #endif /* CONFIG_RMII */ } - /* update the ethaddr */ - if (is_valid_ethaddr(netdev->enetaddr)) { - macb_write_hwaddr(netdev); - } else { - printf("%s: mac address is not valid\n", netdev->name); - return -1; - } - if (!macb_phy_init(macb)) return -1; -- cgit v1.2.3 From 793ea947703899c36a51c30e477466c49a8e9657 Mon Sep 17 00:00:00 2001 From: Shengzhou Liu Date: Fri, 24 Apr 2015 16:57:17 +0800 Subject: net/phy: refactor RTL8211F initialization RTL8211F needs to enalbe TXDLY for RGMII during phy initialization, so move it to rtl8211f_config for early initialization. Signed-off-by: Shengzhou Liu cc: Joe Hershberger Acked-by: Joe Hershberger --- drivers/net/phy/realtek.c | 33 +++++++++++++++++++++++++-------- 1 file changed, 25 insertions(+), 8 deletions(-) (limited to 'drivers') diff --git a/drivers/net/phy/realtek.c b/drivers/net/phy/realtek.c index 2e152c9a036..79452a8df32 100644 --- a/drivers/net/phy/realtek.c +++ b/drivers/net/phy/realtek.c @@ -40,6 +40,7 @@ #define MIIM_RTL8211F_PHYSTAT_LINK 0x0004 #define MIIM_RTL8211F_PAGE_SELECT 0x1f +#define MIIM_RTL8211F_TX_DELAY 0x100 /* RealTek RTL8211x */ static int rtl8211x_config(struct phy_device *phydev) @@ -60,6 +61,29 @@ static int rtl8211x_config(struct phy_device *phydev) return 0; } +static int rtl8211f_config(struct phy_device *phydev) +{ + u16 reg; + + phy_write(phydev, MDIO_DEVAD_NONE, MII_BMCR, BMCR_RESET); + + if (phydev->interface == PHY_INTERFACE_MODE_RGMII) { + /* enable TXDLY */ + phy_write(phydev, MDIO_DEVAD_NONE, + MIIM_RTL8211F_PAGE_SELECT, 0xd08); + reg = phy_read(phydev, MDIO_DEVAD_NONE, 0x11); + reg |= MIIM_RTL8211F_TX_DELAY; + phy_write(phydev, MDIO_DEVAD_NONE, 0x11, reg); + /* restore to default page 0 */ + phy_write(phydev, MDIO_DEVAD_NONE, + MIIM_RTL8211F_PAGE_SELECT, 0x0); + } + + genphy_config_aneg(phydev); + + return 0; +} + static int rtl8211x_parse_status(struct phy_device *phydev) { unsigned int speed; @@ -159,13 +183,6 @@ static int rtl8211f_parse_status(struct phy_device *phydev) phydev->speed = SPEED_10; } - if (phydev->interface == PHY_INTERFACE_MODE_RGMII) { - /* enable TXDLY */ - phy_write(phydev, MDIO_DEVAD_NONE, - MIIM_RTL8211F_PAGE_SELECT, 0xd08); - phy_write(phydev, MDIO_DEVAD_NONE, 0x11, 0x109); - } - return 0; } @@ -226,7 +243,7 @@ static struct phy_driver RTL8211F_driver = { .uid = 0x1cc916, .mask = 0xffffff, .features = PHY_GBIT_FEATURES, - .config = &rtl8211x_config, + .config = &rtl8211f_config, .startup = &rtl8211f_startup, .shutdown = &genphy_shutdown, }; -- cgit v1.2.3 From abbfcbe58eefc1accda5dd120fcfe58d244b63dd Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Wed, 13 May 2015 13:40:40 +0200 Subject: net: phy: Add support for all targets which requires MANUAL_RELOC Targets with CONFIG_NEEDS_MANUAL_RELOC do not use REL/RELA relocation (mostly only GOT) where functions aray are not updated. This patch is fixing function pointers passed to phy_register function. This patch was tested on Microblaze architecture. Signed-off-by: Michal Simek Acked-by: Joe Hershberger --- drivers/net/phy/phy.c | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) (limited to 'drivers') diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c index f5221a3833f..c8d08e8f4f1 100644 --- a/drivers/net/phy/phy.c +++ b/drivers/net/phy/phy.c @@ -21,6 +21,8 @@ #include #include +DECLARE_GLOBAL_DATA_PTR; + /* Generic PHY support and helper functions */ /** @@ -494,6 +496,20 @@ int phy_register(struct phy_driver *drv) INIT_LIST_HEAD(&drv->list); list_add_tail(&drv->list, &phy_drivers); +#ifdef CONFIG_NEEDS_MANUAL_RELOC + if (drv->probe) + drv->probe += gd->reloc_off; + if (drv->config) + drv->config += gd->reloc_off; + if (drv->startup) + drv->startup += gd->reloc_off; + if (drv->shutdown) + drv->shutdown += gd->reloc_off; + if (drv->readext) + drv->readext += gd->reloc_off; + if (drv->writeext) + drv->writeext += gd->reloc_off; +#endif return 0; } -- cgit v1.2.3 From 92ac520821405e196c920d60921bdfa5ab6b878c Mon Sep 17 00:00:00 2001 From: Joe Hershberger Date: Mon, 4 May 2015 14:55:14 -0500 Subject: net: Remove all references to CONFIG_ETHADDR and friends We really don't want boards defining fixed MAC addresses in their config so we just remove the option to set it in a fixed way. If you must have a MAC address that was not provisioned, then use the random MAC address functionality. Signed-off-by: Joe Hershberger Reviewed-by: Simon Glass --- drivers/net/greth.c | 10 +++------- drivers/net/lan91c96.c | 7 ------- 2 files changed, 3 insertions(+), 14 deletions(-) (limited to 'drivers') diff --git a/drivers/net/greth.c b/drivers/net/greth.c index a93b37a5d7d..9bc8a8d1aa1 100644 --- a/drivers/net/greth.c +++ b/drivers/net/greth.c @@ -12,6 +12,7 @@ #include #include +#include #include #include #include @@ -653,13 +654,8 @@ int greth_initialize(bd_t * bis) } } } else { - /* HW Address not found in environment, Set default HW address */ - addr[0] = GRETH_HWADDR_0; /* MSB */ - addr[1] = GRETH_HWADDR_1; - addr[2] = GRETH_HWADDR_2; - addr[3] = GRETH_HWADDR_3; - addr[4] = GRETH_HWADDR_4; - addr[5] = GRETH_HWADDR_5; /* LSB */ + /* No ethaddr set */ + return -EINVAL; } /* set and remember MAC address */ diff --git a/drivers/net/lan91c96.c b/drivers/net/lan91c96.c index 495c0886fae..c4dd01ec2aa 100644 --- a/drivers/net/lan91c96.c +++ b/drivers/net/lan91c96.c @@ -725,12 +725,6 @@ static int smc_get_ethaddr(bd_t *bd, struct eth_device *dev) static int get_rom_mac(struct eth_device *dev, unsigned char *v_rom_mac) { -#ifdef HARDCODE_MAC /* used for testing or to supress run time warnings */ - char hw_mac_addr[] = { 0x02, 0x80, 0xad, 0x20, 0x31, 0xb8 }; - - memcpy (v_rom_mac, hw_mac_addr, 6); - return (1); -#else int i; SMC_SELECT_BANK(dev, 1); for (i=0; i<6; i++) @@ -738,7 +732,6 @@ static int get_rom_mac(struct eth_device *dev, unsigned char *v_rom_mac) v_rom_mac[i] = SMC_inb(dev, LAN91C96_IA0 + i); } return (1); -#endif } /* Structure to detect the device IDs */ -- cgit v1.2.3 From 76ec988b062ed880ab23d0e0d4e9e6c137b55cc3 Mon Sep 17 00:00:00 2001 From: Joe Hershberger Date: Mon, 4 May 2015 14:55:15 -0500 Subject: net: Remove all calls to net_random_ethaddr() Remove the calls to net_random_ethaddr() that some boards and some drivers are calling. This is now implemented inside of net/eth.c Enable the feature for all boards that previously enabled it. Signed-off-by: Joe Hershberger Acked-By: Michael Walle (for the lsxl board part) Series-changes: 2 -Fixed bfin build errors --- drivers/net/dm9000x.c | 6 ------ drivers/net/ftmac110.c | 3 --- 2 files changed, 9 deletions(-) (limited to 'drivers') diff --git a/drivers/net/dm9000x.c b/drivers/net/dm9000x.c index ccd2131f88f..3c41cec3e4d 100644 --- a/drivers/net/dm9000x.c +++ b/drivers/net/dm9000x.c @@ -343,13 +343,7 @@ static int dm9000_init(struct eth_device *dev, bd_t *bd) printf("MAC: %pM\n", dev->enetaddr); if (!is_valid_ethaddr(dev->enetaddr)) { -#ifdef CONFIG_RANDOM_MACADDR - printf("Bad MAC address (uninitialized EEPROM?), randomizing\n"); - net_random_ethaddr(dev->enetaddr); - printf("MAC: %pM\n", dev->enetaddr); -#else printf("WARNING: Bad MAC address (uninitialized EEPROM?)\n"); -#endif } /* fill device MAC address registers */ diff --git a/drivers/net/ftmac110.c b/drivers/net/ftmac110.c index 4bae9ad977c..4f17015bc59 100644 --- a/drivers/net/ftmac110.c +++ b/drivers/net/ftmac110.c @@ -424,9 +424,6 @@ int ftmac110_initialize(bd_t *bis) dev->send = ftmac110_send; dev->recv = ftmac110_recv; - if (!eth_getenv_enetaddr_by_index("eth", card_nr, dev->enetaddr)) - net_random_ethaddr(dev->enetaddr); - /* allocate tx descriptors (it must be 16 bytes aligned) */ chip->txd = dma_alloc_coherent( sizeof(struct ftmac110_desc) * CFG_TXDES_NUM, &chip->txd_dma); -- cgit v1.2.3