1 /*
2  * Copyright (c) 2006-2024 RT-Thread Development Team
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  *
6  * Change Logs:
7  * Date           Author       Notes
8  * 2020-10-14     wangqiang    the first version
9  * 2022-08-17     xjy198903    add 1000M definition
10  * 2024-10-08     zhujiale     add phy v2.0
11  */
12 #ifndef __NET_PHY_H__
13 #define __NET_PHY_H__
14 #include <rtthread.h>
15 #include <drivers/core/driver.h>
16 
17 #ifdef RT_USING_PHY_V2
18 #include <ofw.h>
19 #include <mdio.h>
20 #include <general_phy.h>
21 #define RT_PHY_FIXED_ID 0xa5a55a5a
22 #define RT_PHY_NCSI_ID  0xbeefcafe
23 
24 
25 /* Indicates what features are supported by the interface. */
26 #define RT_SUPPORTED_10baseT_Half      (1 << 0)
27 #define RT_SUPPORTED_10baseT_Full      (1 << 1)
28 #define RT_SUPPORTED_100baseT_Half     (1 << 2)
29 #define RT_SUPPORTED_100baseT_Full     (1 << 3)
30 #define RT_SUPPORTED_1000baseT_Half    (1 << 4)
31 #define RT_SUPPORTED_1000baseT_Full    (1 << 5)
32 #define RT_SUPPORTED_Autoneg           (1 << 6)
33 #define RT_SUPPORTED_TP                (1 << 7)
34 #define RT_SUPPORTED_AUI               (1 << 8)
35 #define RT_SUPPORTED_MII               (1 << 9)
36 #define RT_SUPPORTED_FIBRE             (1 << 10)
37 #define RT_SUPPORTED_BNC               (1 << 11)
38 #define RT_SUPPORTED_10000baseT_Full   (1 << 12)
39 #define RT_SUPPORTED_Pause             (1 << 13)
40 #define RT_SUPPORTED_Asym_Pause        (1 << 14)
41 #define RT_SUPPORTED_2500baseX_Full    (1 << 15)
42 #define RT_SUPPORTED_Backplane         (1 << 16)
43 #define RT_SUPPORTED_1000baseKX_Full   (1 << 17)
44 #define RT_SUPPORTED_10000baseKX4_Full (1 << 18)
45 #define RT_SUPPORTED_10000baseKR_Full  (1 << 19)
46 #define RT_SUPPORTED_10000baseR_FEC    (1 << 20)
47 #define RT_SUPPORTED_1000baseX_Half    (1 << 21)
48 #define RT_SUPPORTED_1000baseX_Full    (1 << 22)
49 
50 #define RT_PHY_FLAG_BROKEN_RESET (1 << 0) /* soft reset not supported */
51 #define RT_PHY_DEFAULT_FEATURES  (RT_SUPPORTED_Autoneg | RT_SUPPORTED_TP | RT_SUPPORTED_MII)
52 
53 #define RT_PHY_10BT_FEATURES (RT_SUPPORTED_10baseT_Half | RT_SUPPORTED_10baseT_Full)
54 
55 #define RT_PHY_100BT_FEATURES (RT_SUPPORTED_100baseT_Half | RT_SUPPORTED_100baseT_Full)
56 
57 #define RT_PHY_1000BT_FEATURES (RT_SUPPORTED_1000baseT_Half | RT_SUPPORTED_1000baseT_Full)
58 
59 #define RT_PHY_BASIC_FEATURES (RT_PHY_10BT_FEATURES | RT_PHY_100BT_FEATURES | RT_PHY_DEFAULT_FEATURES)
60 
61 #define RT_PHY_GBIT_FEATURES (RT_PHY_BASIC_FEATURES | RT_PHY_1000BT_FEATURES)
62 
63 #define RT_PHY_10G_FEATURES (RT_PHY_GBIT_FEATURES | RT_SUPPORTED_10000baseT_Full)
64 struct rt_phy_device
65 {
66     struct rt_device      parent;
67     struct mii_bus       *bus;
68     struct rt_phy_driver *drv;
69     rt_uint32_t           phy_id;
70     rt_uint32_t           mmds;
71     int                   speed;
72     int                   duplex;
73     int                   link;
74     int                   port;
75     rt_uint32_t           advertising;
76     rt_uint32_t           supported;
77     rt_bool_t             autoneg;
78     int                   pause;
79     rt_ubase_t            addr;
80     rt_bool_t             is_c45;
81     rt_uint32_t           flags;
82     rt_phy_interface      interface;
83 
84 #ifdef RT_USING_OFW
85     struct rt_ofw_node *node;
86 #endif
87     void *priv;
88 };
89 
90 struct rt_phy_driver
91 {
92     struct rt_driver parent;
93     char             name[RT_NAME_MAX];
94     rt_uint64_t      uid;
95     rt_uint64_t      mask;
96     rt_uint64_t      mmds;
97     rt_uint32_t      features;
98 
99     int (*probe)(struct rt_phy_device *phydev);
100     int (*config)(struct rt_phy_device *phydev);
101     int (*startup)(struct rt_phy_device *phydev);
102     int (*shutdown)(struct rt_phy_device *phydev);
103     int (*read)(struct rt_phy_device *phydev, int addr, int devad, int reg);
104     int (*write)(struct rt_phy_device *phydev, int addr, int devad, int reg,
105                  rt_uint16_t val);
106     int (*read_mmd)(struct rt_phy_device *phydev, int devad, int reg);
107     int (*write_mmd)(struct rt_phy_device *phydev, int devad, int reg,
108                      rt_uint16_t val);
109 
110     /* driver private data */
111     void *data;
112 };
113 
114 int rt_phy_read(struct rt_phy_device *phydev, int devad, int regnum);
115 int rt_phy_write(struct rt_phy_device *phydev, int devad, int regnum, rt_uint16_t val);
116 int rt_phy_read_mmd(struct rt_phy_device *phydev, int devad, int regnum);
117 int rt_phy_write_mmd(struct rt_phy_device *phydev, int devad, int regnum, rt_uint16_t val);
118 int rt_phy_reset(struct rt_phy_device *phydev);
119 int rt_phy_startup(struct rt_phy_device *phydev);
120 int rt_phy_config(struct rt_phy_device *phydev);
121 int rt_phy_shutdown(struct rt_phy_device *phydev);
122 int rt_phy_read_mmd(struct rt_phy_device *phydev, int devad, int regnum);
123 int rt_phy_set_supported(struct rt_phy_device *phydev, rt_uint32_t max_speed);
124 
125 void rt_phy_mmd_start_indirect(struct rt_phy_device *phydev, int devad, int regnum);
126 
127 rt_err_t rt_phy_device_register(struct rt_phy_device *pdev);
128 rt_err_t rt_phy_driver_register(struct rt_phy_driver *pdrv);
129 rt_err_t rt_ofw_get_phyid(struct rt_ofw_node *np,rt_uint32_t *id);
130 
131 struct rt_phy_device *rt_phy_device_create(struct mii_bus *bus, int addr, rt_uint32_t phy_id, rt_bool_t is_c45);
132 struct rt_phy_device *rt_phy_find_by_mask(struct mii_bus *bus, unsigned int phy_mask);
133 struct rt_phy_device *rt_ofw_create_phy(struct mii_bus *bus, struct rt_ofw_node *np, int phyaddr);
134 struct rt_phy_device *rt_phy_get_device(struct mii_bus *bus, struct rt_ofw_node *np, int addr, rt_phy_interface interface);
135 
136 #define RT_PHY_DEVICE_REGISTER(phy_dev)      \
137 static int rt_##phy_dev##_register(void)     \
138 {                                            \
139     rt_phy_device_register(&phy_dev);        \
140     return 0;                                \
141 }                                            \
142 INIT_PREV_EXPORT(rt_##phy_dev##_register);
143 
144 #define RT_PHY_DRIVER_REGISTER(phy_drv)      \
145 static int rt_##phy_drv##_register(void)     \
146 {                                            \
147     rt_phy_driver_register(&phy_drv);        \
148     return 0;                                \
149 }                                            \
150 INIT_PREV_EXPORT(rt_##phy_drv##_register);
151 #endif
152 
153 #ifdef RT_USING_PHY
154 #ifdef __cplusplus
155 extern "C"
156 {
157 #endif
158 
159 struct rt_mdio_bus_ops
160 {
161     rt_bool_t (*init)(void *bus, rt_uint32_t src_clock_hz);
162     rt_size_t (*read)(void *bus, rt_uint32_t addr, rt_uint32_t reg, void *data, rt_uint32_t size);
163     rt_size_t (*write)(void *bus, rt_uint32_t addr, rt_uint32_t reg, void *data, rt_uint32_t size);
164     rt_bool_t (*uninit)(void *bus);
165 };
166 
167 struct rt_mdio_bus
168 {
169     void *hw_obj;
170     char *name;
171     struct rt_mdio_bus_ops *ops;
172 };
173 
174 typedef struct rt_mdio_bus rt_mdio_t;
175 
176 /* Defines the PHY link speed. This is align with the speed for MAC. */
177 #define PHY_SPEED_10M   0U     /* PHY 10M speed. */
178 #define PHY_SPEED_100M  1U     /* PHY 100M speed. */
179 #define PHY_SPEED_1000M 2U     /* PHY 1000M speed. */
180 
181 /* Defines the PHY link duplex. */
182 #define PHY_HALF_DUPLEX 0U     /* PHY half duplex. */
183 #define PHY_FULL_DUPLEX 1U     /* PHY full duplex. */
184 
185 /*! @brief Defines the PHY loopback mode. */
186 #define PHY_LOCAL_LOOP  0U     /* PHY local loopback. */
187 #define PHY_REMOTE_LOOP 1U     /* PHY remote loopback. */
188 
189 #define PHY_STATUS_OK      0U
190 #define PHY_STATUS_FAIL    1U
191 #define PHY_STATUS_TIMEOUT 2U
192 
193 typedef struct rt_phy_msg
194 {
195     rt_uint32_t reg;
196     rt_uint32_t value;
197 }rt_phy_msg_t;
198 
199 typedef struct rt_phy_device
200 {
201     struct rt_device parent;
202     struct rt_mdio_bus *bus;
203     rt_uint32_t addr;
204     struct rt_phy_ops *ops;
205 }rt_phy_t;
206 
207 typedef rt_int32_t rt_phy_status;
208 
209 struct rt_phy_ops
210 {
211     rt_phy_status (*init)(void *object, rt_uint32_t phy_addr, rt_uint32_t src_clock_hz);
212     rt_phy_status (*read)(rt_phy_t *phy, rt_uint32_t reg, rt_uint32_t *data);
213     rt_phy_status (*write)(rt_phy_t *phy, rt_uint32_t reg, rt_uint32_t data);
214     rt_phy_status (*loopback)(rt_phy_t *phy, rt_uint32_t mode, rt_uint32_t speed, rt_bool_t enable);
215     rt_phy_status (*get_link_status)(rt_phy_t *phy, rt_bool_t *status);
216     rt_phy_status (*get_link_speed_duplex)(rt_phy_t *phy, rt_uint32_t *speed, rt_uint32_t *duplex);
217 };
218 
219 rt_err_t rt_hw_phy_register(struct rt_phy_device *phy, const char *name);
220 
221 #ifdef __cplusplus
222 }
223 #endif
224 #endif
225 #endif
226