From 03bce705d53607299062818ed3075c16dac77817 Mon Sep 17 00:00:00 2001 From: Jukka Laitinen Date: Mon, 3 Oct 2022 14:57:37 +0400 Subject: [PATCH] arch/risc-v/src/mpfs/mpfs_ethernet.c: Set PHY speed advert after PHY reset This allows properly using 10/100Mbps also with 1G phy. Some gigabit PHYs come out of reset with 1G advertisement enabled, causing other devices to set up link with 1G. If, after this, the link is set to 10/100 on the mpfs, the link won't work. Signed-off-by: Jukka Laitinen --- arch/risc-v/src/mpfs/mpfs_ethernet.c | 52 ++++++++++++++++------------ 1 file changed, 29 insertions(+), 23 deletions(-) diff --git a/arch/risc-v/src/mpfs/mpfs_ethernet.c b/arch/risc-v/src/mpfs/mpfs_ethernet.c index 602c0ef65b1..d36e9adb2e3 100644 --- a/arch/risc-v/src/mpfs/mpfs_ethernet.c +++ b/arch/risc-v/src/mpfs/mpfs_ethernet.c @@ -2355,29 +2355,6 @@ static int mpfs_autonegotiate(struct mpfs_ethmac_s *priv) goto errout; } -#ifndef CONFIG_MPFS_MAC_AUTONEG_DISABLE_1000MBPS - /* Modify the 1000Base-T control register to advertise 1000Base-T full - * and half duplex support. - */ - - ret = mpfs_phyread(priv, priv->phyaddr, GMII_1000BTCR, &btcr); - if (ret < 0) - { - nerr("ERROR: Failed to read 1000BTCR register: %d\n", ret); - goto errout; - } - - btcr |= GMII_1000BTCR_1000BASETFULL | GMII_1000BTCR_1000BASETHALF; - - ret = mpfs_phywrite(priv, priv->phyaddr, GMII_1000BTCR, btcr); - if (ret < 0) - { - nerr("ERROR: Failed to write 1000BTCR register: %d\n", ret); - goto errout; - } - -#endif - /* Restart Auto_negotiation */ ret = mpfs_phyread(priv, priv->phyaddr, GMII_MCR, &phyval); @@ -2453,6 +2430,13 @@ static int mpfs_autonegotiate(struct mpfs_ethmac_s *priv) goto errout; } + ret = mpfs_phyread(priv, priv->phyaddr, GMII_1000BTCR, &btcr); + if (ret < 0) + { + nerr("ERROR: Failed to read 1000BTCR register: %d\n", ret); + goto errout; + } + /* Setup the GMAC link speed */ if ((btsr & GMII_1000BTSR_LP1000BASETFULL) != 0 && @@ -3410,6 +3394,7 @@ static int mpfs_phyreset(struct mpfs_ethmac_s *priv) uint16_t mcr; int timeout; int ret; + uint16_t btcr; ninfo(" mpfs_phyreset\n"); @@ -3446,6 +3431,27 @@ static int mpfs_phyreset(struct mpfs_ethmac_s *priv) } } + /* For gigabit PHYs, set or disable the autonegotiation advertisement for + * 1G speed + */ + + if (mpfs_phyread(priv, priv->phyaddr, GMII_1000BTCR, &btcr) == OK) + { +#if defined(CONFIG_MPFS_MAC_AUTONEG_DISABLE_1000MBPS) || \ + (!defined(CONFIG_MPFS_MAC_AUTONEG) && \ + !defined(CONFIG_MPFS_MAC_ETH1000MBPS)) + btcr &= ~(GMII_1000BTCR_1000BASETFULL | GMII_1000BTCR_1000BASETHALF); +#else + btcr |= GMII_1000BTCR_1000BASETFULL | GMII_1000BTCR_1000BASETHALF; +#endif + + ret = mpfs_phywrite(priv, priv->phyaddr, GMII_1000BTCR, btcr); + if (ret < 0) + { + nerr("ERROR: Failed to write 1000BTCR register: %d\n", ret); + } + } + /* Disable management port */ mpfs_disablemdio(priv);