summaryrefslogtreecommitdiff
path: root/drivers/net
diff options
context:
space:
mode:
authorManjunath Hadli <manjunath.hadli@ti.com>2011-10-13 03:40:53 +0000
committerAlbert ARIBAUD <albert.u.boot@aribaud.net>2011-10-27 21:56:36 +0200
commitcc4bd47f4f8d11af50ab56caa9ece29ac13fc5c3 (patch)
treeef6a02ad9aab0e29be9e321ce831e0e327b7cd9f /drivers/net
parentae5c77dd908edaf55025fa3f41095bfb9cb1b973 (diff)
davinci: emac: add new features to autonegotiate for EMAC
add more features like DUPLEX, 100MB link speed etc to auto negotiate in EMAC driver. EMAC controller autonegotiates for these features with PHYs which are on the board. Signed-off-by: Sudhakar Rajashekhara <sudhakar.raj@ti.com> Signed-off-by: Manjunath Hadli <manjunath.hadli@ti.com> Signed-off-by: Sandeep Paulraj <s-paulraj@ti.com>
Diffstat (limited to 'drivers/net')
-rw-r--r--drivers/net/davinci_emac.c30
1 files changed, 28 insertions, 2 deletions
diff --git a/drivers/net/davinci_emac.c b/drivers/net/davinci_emac.c
index a8905b88f1..52617a7fb7 100644
--- a/drivers/net/davinci_emac.c
+++ b/drivers/net/davinci_emac.c
@@ -279,16 +279,42 @@ static int gen_get_link_speed(int phy_addr)
static int gen_auto_negotiate(int phy_addr)
{
u_int16_t tmp;
+ u_int16_t val;
+ unsigned long cntr = 0;
+
+ if (!davinci_eth_phy_read(phy_addr, MII_BMCR, &tmp))
+ return 0;
+
+ val = tmp | BMCR_FULLDPLX | BMCR_ANENABLE |
+ BMCR_SPEED100;
+ davinci_eth_phy_write(phy_addr, MII_BMCR, val);
+
+ if (!davinci_eth_phy_read(phy_addr, MII_ADVERTISE, &val))
+ return 0;
+
+ val |= (ADVERTISE_100FULL | ADVERTISE_100HALF | ADVERTISE_10FULL |
+ ADVERTISE_10HALF);
+ davinci_eth_phy_write(phy_addr, MII_ADVERTISE, val);
if (!davinci_eth_phy_read(phy_addr, MII_BMCR, &tmp))
return(0);
/* Restart Auto_negotiation */
- tmp |= BMCR_ANENABLE;
+ tmp |= BMCR_ANRESTART;
davinci_eth_phy_write(phy_addr, MII_BMCR, tmp);
/*check AutoNegotiate complete */
- udelay (10000);
+ do {
+ udelay(40000);
+ if (!davinci_eth_phy_read(phy_addr, MII_BMSR, &tmp))
+ return 0;
+
+ if (tmp & BMSR_ANEGCOMPLETE)
+ break;
+
+ cntr++;
+ } while (cntr < 200);
+
if (!davinci_eth_phy_read(phy_addr, MII_BMSR, &tmp))
return(0);