]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - drivers/net/phy/et1011c.c
karo: fdt: fix panel-dpi support
[karo-tx-uboot.git] / drivers / net / phy / et1011c.c
1 /*
2  * ET1011C PHY driver
3  *
4  * Derived from Linux kernel driver by Chaithrika U S
5  * Copyright (C) 2013, Texas Instruments, Incorporated - http://www.ti.com/
6  *
7  * SPDX-License-Identifier:     GPL-2.0+
8  */
9 #include <config.h>
10 #include <phy.h>
11
12 #define ET1011C_CONFIG_REG              (0x16)
13 #define ET1011C_TX_FIFO_MASK            (0x3 << 12)
14 #define ET1011C_TX_FIFO_DEPTH_8         (0x0 << 12)
15 #define ET1011C_TX_FIFO_DEPTH_16        (0x1 << 12)
16 #define ET1011C_INTERFACE_MASK          (0x7 << 0)
17 #define ET1011C_GMII_INTERFACE          (0x2 << 0)
18 #define ET1011C_SYS_CLK_EN              (0x1 << 4)
19 #define ET1011C_TX_CLK_EN               (0x1 << 5)
20
21 #define ET1011C_STATUS_REG              (0x1A)
22 #define ET1011C_DUPLEX_STATUS           (0x1 << 7)
23 #define ET1011C_SPEED_MASK              (0x3 << 8)
24 #define ET1011C_SPEED_1000              (0x2 << 8)
25 #define ET1011C_SPEED_100               (0x1 << 8)
26 #define ET1011C_SPEED_10                (0x0 << 8)
27
28 static int et1011c_config(struct phy_device *phydev)
29 {
30         int ctl = 0;
31         ctl = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR);
32         if (ctl < 0)
33                 return ctl;
34         ctl &= ~(BMCR_FULLDPLX | BMCR_SPEED100 | BMCR_SPEED1000 |
35                  BMCR_ANENABLE);
36         /* First clear the PHY */
37         phy_write(phydev, MDIO_DEVAD_NONE, MII_BMCR, ctl | BMCR_RESET);
38
39         return genphy_config_aneg(phydev);
40 }
41
42 static int et1011c_parse_status(struct phy_device *phydev)
43 {
44         int mii_reg;
45         int speed;
46
47         mii_reg = phy_read(phydev, MDIO_DEVAD_NONE, ET1011C_STATUS_REG);
48
49         if (mii_reg & ET1011C_DUPLEX_STATUS)
50                 phydev->duplex = DUPLEX_FULL;
51         else
52                 phydev->duplex = DUPLEX_HALF;
53
54         speed = mii_reg & ET1011C_SPEED_MASK;
55         switch (speed) {
56         case ET1011C_SPEED_1000:
57                 phydev->speed = SPEED_1000;
58                 mii_reg = phy_read(phydev, MDIO_DEVAD_NONE, ET1011C_CONFIG_REG);
59                 mii_reg &= ~ET1011C_TX_FIFO_MASK;
60                 phy_write(phydev, MDIO_DEVAD_NONE, ET1011C_CONFIG_REG,
61                           mii_reg |
62                           ET1011C_GMII_INTERFACE |
63                           ET1011C_SYS_CLK_EN |
64 #ifdef CONFIG_PHY_ET1011C_TX_CLK_FIX
65                           ET1011C_TX_CLK_EN |
66 #endif
67                           ET1011C_TX_FIFO_DEPTH_16);
68                 break;
69         case ET1011C_SPEED_100:
70                 phydev->speed = SPEED_100;
71                 break;
72         case ET1011C_SPEED_10:
73                 phydev->speed = SPEED_10;
74                 break;
75         }
76
77         return 0;
78 }
79
80 static int et1011c_startup(struct phy_device *phydev)
81 {
82         genphy_update_link(phydev);
83         et1011c_parse_status(phydev);
84         return 0;
85 }
86
87 static struct phy_driver et1011c_driver = {
88         .name           = "ET1011C",
89         .uid            = 0x0282f014,
90         .mask           = 0xfffffff0,
91         .features       = PHY_GBIT_FEATURES,
92         .config         = &et1011c_config,
93         .startup        = &et1011c_startup,
94 };
95
96 int phy_et1011c_init(void)
97 {
98         phy_register(&et1011c_driver);
99
100         return 0;
101 }