blob: 5a3e42382f226b682b303f042b2196587437856b [file] [log] [blame]
developera29111c2023-01-12 10:20:04 +08001diff --git a/drivers/net/phy/Kconfig b/drivers/net/phy/Kconfig
2index 207046b..21a4497 100644
3--- a/drivers/net/phy/Kconfig
4+++ b/drivers/net/phy/Kconfig
5@@ -350,6 +350,11 @@ config AIROHA_EN8801SC_PHY
6 ---help---
7 Currently supports the Airoha EN8801S PHY for MT7981 SoC.
8
9+config AIROHA_EN8811H_PHY
10+ tristate "Drivers for Airoha EN8811H 2.5G Gigabit PHY"
11+ ---help---
12+ Currently supports the Airoha EN8811H PHY.
13+
14 config ADIN_PHY
15 tristate "Analog Devices Industrial Ethernet PHYs"
16 help
17diff --git a/drivers/net/phy/Makefile b/drivers/net/phy/Makefile
18index 1b13c02..744b249 100644
19--- a/drivers/net/phy/Makefile
20+++ b/drivers/net/phy/Makefile
21@@ -71,6 +71,7 @@ ifdef CONFIG_AQUANTIA_PHY_FW_DOWNLOAD
22 ifdef CONFIG_HWMON
23 aquantia-objs += aquantia_hwmon.o
24 endif
25+obj-$(CONFIG_AIROHA_EN8811H_PHY) += air_en8811h.o
26 obj-$(CONFIG_AQUANTIA_PHY) += aquantia.o
27 obj-$(CONFIG_AX88796B_PHY) += ax88796b.o
28 obj-$(CONFIG_AT803X_PHY) += at803x.o
29diff --git a/drivers/net/phy/air_en8811h.c b/drivers/net/phy/air_en8811h.c
30new file mode 100644
31index 0000000..cf564fc
32--- /dev/null
33+++ b/drivers/net/phy/air_en8811h.c
34@@ -0,0 +1,702 @@
35+// SPDX-License-Identifier: GPL-2.0+
36+
37+/* FILE NAME: air_en8811h.c
38+ * PURPOSE:
39+ * EN8811H phy driver for Linux
40+ * NOTES:
41+ *
42+ */
43+
44+/* INCLUDE FILE DECLARATIONS
45+ */
46+#include <linux/kernel.h>
47+#include <linux/errno.h>
48+#include <linux/init.h>
49+#include <linux/module.h>
50+#include <linux/mii.h>
51+#include <linux/phy.h>
52+#include <linux/delay.h>
53+#include <linux/ethtool.h>
54+#include <linux/delay.h>
55+#include <linux/version.h>
56+#include <linux/firmware.h>
57+#include <linux/crc32.h>
58+
59+#include "air_en8811h.h"
60+
61+#if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 5, 0))
62+#define phydev_mdio_bus(_dev) (_dev->bus)
63+#define phydev_addr(_dev) (_dev->addr)
64+#define phydev_dev(_dev) (&_dev->dev)
65+#else
66+#define phydev_mdio_bus(_dev) (_dev->mdio.bus)
67+#define phydev_addr(_dev) (_dev->mdio.addr)
68+#define phydev_dev(_dev) (&_dev->mdio.dev)
69+#endif
70+
71+MODULE_DESCRIPTION("Airoha EN8811H PHY drivers");
72+MODULE_AUTHOR("Airoha");
73+MODULE_LICENSE("GPL");
74+
75+/*
76+GPIO5 <-> BASE_T_LED0,
77+GPIO4 <-> BASE_T_LED1,
78+GPIO3 <-> BASE_T_LED2,
79+*/
80+/* User-defined.B */
81+#define AIR_LED_SUPPORT
82+#ifdef AIR_LED_SUPPORT
83+static const AIR_BASE_T_LED_CFG_T led_cfg[3] =
84+{
85+ /*
86+ * LED Enable, GPIO, LED Polarity, LED ON, LED Blink
87+ */
88+ {LED_ENABLE, AIR_LED0_GPIO5, AIR_ACTIVE_HIGH, BASE_T_LED0_ON_CFG, BASE_T_LED0_BLK_CFG}, /* BASE-T LED0 */
89+ {LED_ENABLE, AIR_LED1_GPIO4, AIR_ACTIVE_HIGH, BASE_T_LED1_ON_CFG, BASE_T_LED1_BLK_CFG}, /* BASE-T LED1 */
90+ {LED_ENABLE, AIR_LED2_GPIO3, AIR_ACTIVE_HIGH, BASE_T_LED2_ON_CFG, BASE_T_LED2_BLK_CFG}, /* BASE-T LED2 */
91+};
92+static const u16 led_dur = UNIT_LED_BLINK_DURATION << AIR_LED_BLK_DUR_64M;
93+#endif
94+/* User-defined.E */
95+
96+/************************************************************************
97+* F U N C T I O N S
98+************************************************************************/
99+#if 0
100+/* Airoha MII read function */
101+static int air_mii_cl22_read(struct mii_bus *ebus, unsigned int phy_addr,unsigned int phy_register)
102+{
103+ int read_data;
104+ read_data = mdiobus_read(ebus, phy_addr, phy_register);
105+ return read_data;
106+}
107+#endif
108+/* Airoha MII write function */
109+static int air_mii_cl22_write(struct mii_bus *ebus, unsigned int phy_addr, unsigned int phy_register,unsigned int write_data)
110+{
111+ int ret = 0;
112+ ret = mdiobus_write(ebus, phy_addr, phy_register, write_data);
113+ return ret;
114+}
115+
116+static int air_mii_cl45_read(struct phy_device *phydev, int devad, u16 reg)
117+{
118+ int ret = 0;
119+ int data;
120+ struct device *dev = phydev_dev(phydev);
121+ ret = phy_write(phydev, MII_MMD_ACC_CTL_REG, devad);
122+ if (ret < 0) {
123+ dev_err(dev, "phy_write, ret: %d\n", ret);
124+ return INVALID_DATA;
125+ }
126+ ret = phy_write(phydev, MII_MMD_ADDR_DATA_REG, reg);
127+ if (ret < 0) {
128+ dev_err(dev, "phy_write, ret: %d\n", ret);
129+ return INVALID_DATA;
130+ }
131+ ret = phy_write(phydev, MII_MMD_ACC_CTL_REG, MMD_OP_MODE_DATA | devad);
132+ if (ret < 0) {
133+ dev_err(dev, "phy_write, ret: %d\n", ret);
134+ return INVALID_DATA;
135+ }
136+ data = phy_read(phydev, MII_MMD_ADDR_DATA_REG);
137+ return data;
138+}
139+
140+static int air_mii_cl45_write(struct phy_device *phydev, int devad, u16 reg, u16 write_data)
141+{
142+ int ret = 0;
143+ struct device *dev = phydev_dev(phydev);
144+ ret = phy_write(phydev, MII_MMD_ACC_CTL_REG, devad);
145+ if (ret < 0) {
146+ dev_err(dev, "phy_write, ret: %d\n", ret);
147+ return ret;
148+ }
149+ ret = phy_write(phydev, MII_MMD_ADDR_DATA_REG, reg);
150+ if (ret < 0) {
151+ dev_err(dev, "phy_write, ret: %d\n", ret);
152+ return ret;
153+ }
154+ ret = phy_write(phydev, MII_MMD_ACC_CTL_REG, MMD_OP_MODE_DATA | devad);
155+ if (ret < 0) {
156+ dev_err(dev, "phy_write, ret: %d\n", ret);
157+ return ret;
158+ }
159+ ret = phy_write(phydev, MII_MMD_ADDR_DATA_REG, write_data);
160+ if (ret < 0) {
161+ dev_err(dev, "phy_write, ret: %d\n", ret);
162+ return ret;
163+ }
164+ return 0;
165+}
166+/* Use default PBUS_PHY_ID */
167+/* EN8811H PBUS write function */
168+static int air_pbus_reg_write(struct phy_device *phydev, unsigned long pbus_address, unsigned long pbus_data)
169+{
170+ struct mii_bus *mbus = phydev_mdio_bus(phydev);
171+ int addr = phydev_addr(phydev);
172+ int ret = 0;
173+ ret = air_mii_cl22_write(mbus, (addr + 8), 0x1F, (unsigned int)(pbus_address >> 6));
174+ AIR_RTN_ERR(ret);
175+ ret = air_mii_cl22_write(mbus, (addr + 8), (unsigned int)((pbus_address >> 2) & 0xf), (unsigned int)(pbus_data & 0xFFFF));
176+ AIR_RTN_ERR(ret);
177+ ret = air_mii_cl22_write(mbus, (addr + 8), 0x10, (unsigned int)(pbus_data >> 16));
178+ AIR_RTN_ERR(ret);
179+ return 0;
180+}
181+
182+/* EN8811H BUCK write function */
183+static int air_buckpbus_reg_write(struct phy_device *phydev, unsigned long pbus_address, unsigned int pbus_data)
184+{
185+ int ret = 0;
186+ struct device *dev = phydev_dev(phydev);
187+ ret = phy_write(phydev, 0x1F, (unsigned int)4); /* page 4 */
188+ if (ret < 0) {
189+ dev_err(dev, "phy_write, ret: %d\n", ret);
190+ return ret;
191+ }
192+ ret = phy_write(phydev, 0x10, (unsigned int)0);
193+ if (ret < 0) {
194+ dev_err(dev, "phy_write, ret: %d\n", ret);
195+ return ret;
196+ }
197+ ret = phy_write(phydev, 0x11, (unsigned int)((pbus_address >> 16) & 0xffff));
198+ if (ret < 0) {
199+ dev_err(dev, "phy_write, ret: %d\n", ret);
200+ return ret;
201+ }
202+ ret = phy_write(phydev, 0x12, (unsigned int)(pbus_address & 0xffff));
203+ if (ret < 0) {
204+ dev_err(dev, "phy_write, ret: %d\n", ret);
205+ return ret;
206+ }
207+ ret = phy_write(phydev, 0x13, (unsigned int)((pbus_data >> 16) & 0xffff));
208+ if (ret < 0) {
209+ dev_err(dev, "phy_write, ret: %d\n", ret);
210+ return ret;
211+ }
212+ ret = phy_write(phydev, 0x14, (unsigned int)(pbus_data & 0xffff));
213+ if (ret < 0) {
214+ dev_err(dev, "phy_write, ret: %d\n", ret);
215+ return ret;
216+ }
217+ ret = phy_write(phydev, 0x1F, 0);
218+ if (ret < 0) {
219+ dev_err(dev, "phy_write, ret: %d\n", ret);
220+ return ret;
221+ }
222+ return 0;
223+}
224+
225+/* EN8811H BUCK read function */
226+static unsigned int air_buckpbus_reg_read(struct phy_device *phydev, unsigned long pbus_address)
227+{
228+ unsigned int pbus_data = 0, pbus_data_low, pbus_data_high;
229+ int ret = 0;
230+ struct device *dev = phydev_dev(phydev);
231+ ret = phy_write(phydev, 0x1F, (unsigned int)4); /* page 4 */
232+ if (ret < 0) {
233+ dev_err(dev, "phy_write, ret: %d\n", ret);
234+ return PBUS_INVALID_DATA;
235+ }
236+ ret = phy_write(phydev, 0x10, (unsigned int)0);
237+ if (ret < 0) {
238+ dev_err(dev, "phy_write, ret: %d\n", ret);
239+ return PBUS_INVALID_DATA;
240+ }
241+ ret = phy_write(phydev, 0x15, (unsigned int)((pbus_address >> 16) & 0xffff));
242+ if (ret < 0) {
243+ dev_err(dev, "phy_write, ret: %d\n", ret);
244+ return PBUS_INVALID_DATA;
245+ }
246+ ret = phy_write(phydev, 0x16, (unsigned int)(pbus_address & 0xffff));
247+ if (ret < 0) {
248+ dev_err(dev, "phy_write, ret: %d\n", ret);
249+ return PBUS_INVALID_DATA;
250+ }
251+
252+ pbus_data_high = phy_read(phydev, 0x17);
253+ pbus_data_low = phy_read(phydev, 0x18);
254+ pbus_data = (pbus_data_high << 16) + pbus_data_low;
255+ ret = phy_write(phydev, 0x1F, 0);
256+ if (ret < 0) {
257+ dev_err(dev, "phy_write, ret: %d\n", ret);
258+ return ret;
259+ }
260+ return pbus_data;
261+}
262+
263+static int MDIOWriteBuf(struct phy_device *phydev, unsigned long address, const struct firmware *fw)
264+{
265+ unsigned int write_data, offset ;
266+ int ret = 0;
267+ struct device *dev = phydev_dev(phydev);
268+ ret = phy_write(phydev, 0x1F, (unsigned int)4); /* page 4 */
269+ if (ret < 0) {
270+ dev_err(dev, "phy_write, ret: %d\n", ret);
271+ return ret;
272+ }
273+ ret = phy_write(phydev, 0x10, (unsigned int)0x8000); /* address increment*/
274+ if (ret < 0) {
275+ dev_err(dev, "phy_write, ret: %d\n", ret);
276+ return ret;
277+ }
278+ ret = phy_write(phydev, 0x11, (unsigned int)((address >> 16) & 0xffff));
279+ if (ret < 0) {
280+ dev_err(dev, "phy_write, ret: %d\n", ret);
281+ return ret;
282+ }
283+ ret = phy_write(phydev, 0x12, (unsigned int)(address & 0xffff));
284+ if (ret < 0) {
285+ dev_err(dev, "phy_write, ret: %d\n", ret);
286+ return ret;
287+ }
288+
289+ for (offset = 0; offset < fw->size; offset += 4)
290+ {
291+ write_data = (fw->data[offset + 3] << 8) | fw->data[offset + 2];
292+ ret = phy_write(phydev, 0x13, write_data);
293+ if (ret < 0) {
294+ dev_err(dev, "phy_write, ret: %d\n", ret);
295+ return ret;
296+ }
297+ write_data = (fw->data[offset + 1] << 8) | fw->data[offset];
298+ ret = phy_write(phydev, 0x14, write_data);
299+ if (ret < 0) {
300+ dev_err(dev, "phy_write, ret: %d\n", ret);
301+ return ret;
302+ }
303+ }
304+ ret = phy_write(phydev, 0x1F, (unsigned int)0);
305+ if (ret < 0) {
306+ dev_err(dev, "phy_write, ret: %d\n", ret);
307+ return ret;
308+ }
309+ return 0;
310+}
311+
312+static int en8811h_load_firmware(struct phy_device *phydev)
313+{
314+ struct device *dev = phydev_dev(phydev);
315+ const struct firmware *fw;
316+ const char *firmware;
317+ int ret = 0;
318+ unsigned int crc32;
319+ u32 pbus_value = 0;
320+
321+ ret = air_buckpbus_reg_write(phydev, 0x0f0018, 0x0);
322+ AIR_RTN_ERR(ret);
323+ pbus_value = air_buckpbus_reg_read(phydev, 0x800000);
324+ pbus_value |= BIT(11);
325+ ret = air_buckpbus_reg_write(phydev, 0x800000, pbus_value);
326+ AIR_RTN_ERR(ret);
327+ firmware = EN8811H_MD32_DM;
328+ ret = request_firmware_direct(&fw, firmware, dev);
329+ if (ret < 0) {
330+ dev_info(dev, "failed to load firmware %s, ret: %d\n", firmware, ret);
331+ return ret;
332+ }
333+ crc32 = ~crc32(~0, fw->data, fw->size);
334+ dev_info(dev, "%s: crc32=0x%x\n", firmware, crc32);
335+ /* Download DM */
336+ ret = MDIOWriteBuf(phydev, 0x00000000, fw);
337+ if (ret < 0) {
338+ dev_info(dev, "MDIOWriteBuf 0x00000000 fail, ret: %d\n", ret);
339+ return ret;
340+ }
341+ release_firmware(fw);
342+
343+ firmware = EN8811H_MD32_DSP;
344+ ret = request_firmware_direct(&fw, firmware, dev);
345+ if (ret < 0) {
346+ dev_info(dev, "failed to load firmware %s, ret: %d\n", firmware, ret);
347+ return ret;
348+ }
349+ crc32 = ~crc32(~0, fw->data, fw->size);
350+ dev_info(dev, "%s: crc32=0x%x\n", firmware, crc32);
351+ /* Download PM */
352+ ret = MDIOWriteBuf(phydev, 0x00100000, fw);
353+ if (ret < 0) {
354+ dev_info(dev, "MDIOWriteBuf 0x00100000 fail , ret: %d\n", ret);
355+ return ret;
356+ }
357+ release_firmware(fw);
358+
359+ pbus_value = air_buckpbus_reg_read(phydev, 0x800000);
360+ pbus_value &= ~BIT(11);
361+ ret = air_buckpbus_reg_write(phydev, 0x800000, pbus_value);
362+ AIR_RTN_ERR(ret);
363+ ret = air_buckpbus_reg_write(phydev, 0x0f0018, 0x01);
364+ AIR_RTN_ERR(ret);
365+ return 0;
366+}
367+
368+#ifdef AIR_LED_SUPPORT
369+static int airoha_led_set_usr_def(struct phy_device *phydev, u8 entity, int polar,
370+ u16 on_evt, u16 blk_evt)
371+{
372+ int ret = 0;
373+ if (AIR_ACTIVE_HIGH == polar) {
374+ on_evt |= LED_ON_POL;
375+ } else {
376+ on_evt &= ~LED_ON_POL ;
377+ }
378+ ret = air_mii_cl45_write(phydev, 0x1f, LED_ON_CTRL(entity), on_evt | LED_ON_EN);
379+ AIR_RTN_ERR(ret);
380+ ret = air_mii_cl45_write(phydev, 0x1f, LED_BLK_CTRL(entity), blk_evt);
381+ AIR_RTN_ERR(ret);
382+ return 0;
383+}
384+
385+static int airoha_led_set_mode(struct phy_device *phydev, u8 mode)
386+{
387+ u16 cl45_data;
388+ int err = 0;
389+ struct device *dev = phydev_dev(phydev);
390+ cl45_data = air_mii_cl45_read(phydev, 0x1f, LED_BCR);
391+ switch (mode) {
392+ case AIR_LED_MODE_DISABLE:
393+ cl45_data &= ~LED_BCR_EXT_CTRL;
394+ cl45_data &= ~LED_BCR_MODE_MASK;
395+ cl45_data |= LED_BCR_MODE_DISABLE;
396+ break;
397+ case AIR_LED_MODE_USER_DEFINE:
398+ cl45_data |= LED_BCR_EXT_CTRL;
399+ cl45_data |= LED_BCR_CLK_EN;
400+ break;
401+ default:
402+ dev_err(dev, "LED mode%d is not supported!\n", mode);
403+ return -EINVAL;
404+ }
405+ err = air_mii_cl45_write(phydev, 0x1f, LED_BCR, cl45_data);
406+ AIR_RTN_ERR(err);
407+ return 0;
408+}
409+
410+static int airoha_led_set_state(struct phy_device *phydev, u8 entity, u8 state)
411+{
412+ u16 cl45_data = 0;
413+ int err;
414+
415+ cl45_data = air_mii_cl45_read(phydev, 0x1f, LED_ON_CTRL(entity));
416+ if (LED_ENABLE == state) {
417+ cl45_data |= LED_ON_EN;
418+ } else {
419+ cl45_data &= ~LED_ON_EN;
420+ }
421+
422+ err = air_mii_cl45_write(phydev, 0x1f, LED_ON_CTRL(entity), cl45_data);
423+ AIR_RTN_ERR(err);
424+ return 0;
425+}
426+
427+static int en8811h_led_init(struct phy_device *phydev)
428+{
429+
430+ unsigned long led_gpio = 0, reg_value = 0;
431+ u16 cl45_data = led_dur;
432+ int ret = 0, led_id;
433+ struct device *dev = phydev_dev(phydev);
434+ ret = air_mii_cl45_write(phydev, 0x1f, LED_BLK_DUR, cl45_data);
435+ AIR_RTN_ERR(ret);
436+ cl45_data >>= 1;
437+ ret = air_mii_cl45_write(phydev, 0x1f, LED_ON_DUR, cl45_data);
438+ AIR_RTN_ERR(ret);
439+ ret = airoha_led_set_mode(phydev, AIR_LED_MODE_USER_DEFINE);
440+ if (ret != 0) {
441+ dev_err(dev, "LED fail to set mode, ret %d !\n", ret);
442+ return ret;
443+ }
444+ for(led_id = 0; led_id < EN8811H_LED_COUNT; led_id++)
445+ {
446+ /* LED0 <-> GPIO5, LED1 <-> GPIO4, LED0 <-> GPIO3 */
447+ if (led_cfg[led_id].gpio != (led_id + (AIR_LED0_GPIO5 - (2 * led_id))))
448+ {
449+ dev_err(dev, "LED%d uses incorrect GPIO%d !\n", led_id, led_cfg[led_id].gpio);
450+ return -EINVAL;
451+ }
452+ ret = airoha_led_set_state(phydev, led_id, led_cfg[led_id].en);
453+ if (ret != 0)
454+ {
455+ dev_err(dev, "LED fail to set state, ret %d !\n", ret);
456+ return ret;
457+ }
458+ if (LED_ENABLE == led_cfg[led_id].en)
459+ {
460+ led_gpio |= BIT(led_cfg[led_id].gpio);
461+ ret = airoha_led_set_usr_def(phydev, led_id, led_cfg[led_id].pol, led_cfg[led_id].on_cfg, led_cfg[led_id].blk_cfg);
462+ if (ret != 0)
463+ {
464+ dev_err(dev, "LED fail to set default, ret %d !\n", ret);
465+ return ret;
466+ }
467+ }
468+ }
469+ reg_value = air_buckpbus_reg_read(phydev, 0xcf8b8) | led_gpio;
470+ ret = air_buckpbus_reg_write(phydev, 0xcf8b8, reg_value);
471+ AIR_RTN_ERR(ret);
472+
473+ dev_info(dev, "LED initialize OK !\n");
474+ return 0;
475+}
476+#endif /* AIR_LED_SUPPORT */
477+#if (LINUX_VERSION_CODE > KERNEL_VERSION(4, 5, 0))
478+static int en8811h_get_features(struct phy_device *phydev)
479+{
480+ int ret;
481+ struct device *dev = phydev_dev(phydev);
482+ dev_info(dev, "%s()\n", __func__);
483+ ret = air_pbus_reg_write(phydev, 0xcf928 , 0x0);
484+ AIR_RTN_ERR(ret);
485+ ret = genphy_read_abilities(phydev);
486+ if (ret)
487+ return ret;
488+
489+ /* EN8811H supports 100M/1G/2.5G speed. */
490+ linkmode_clear_bit(ETHTOOL_LINK_MODE_10baseT_Half_BIT,
491+ phydev->supported);
492+ linkmode_clear_bit(ETHTOOL_LINK_MODE_10baseT_Full_BIT,
493+ phydev->supported);
494+ linkmode_set_bit(ETHTOOL_LINK_MODE_100baseT_Half_BIT,
495+ phydev->supported);
496+ linkmode_set_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT,
497+ phydev->supported);
498+ linkmode_set_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
499+ phydev->supported);
500+ linkmode_set_bit(ETHTOOL_LINK_MODE_2500baseX_Full_BIT,
501+ phydev->supported);
502+ return 0;
503+}
504+#endif
505+static int en8811h_phy_probe(struct phy_device *phydev)
506+{
507+ int ret = 0;
508+ int reg_value, pid1 = 0, pid2 = 0;
509+ u32 pbus_value = 0, retry;
510+ struct device *dev = phydev_dev(phydev);
511+ ret = air_pbus_reg_write(phydev, 0xcf928 , 0x0);
512+ AIR_RTN_ERR(ret);
513+ pid1 = phy_read(phydev, MII_PHYSID1);
514+ if (pid1 < 0)
515+ return pid1;
516+ pid2 = phy_read(phydev, MII_PHYSID2);
517+ if (pid2 < 0)
518+ return pid2;
519+ dev_info(dev, "PHY = %x - %x\n", pid1, pid2);
520+ if ((EN8811H_PHY_ID1 != pid1) || (EN8811H_PHY_ID2 != pid2))
521+ {
522+ dev_err(dev, "EN8811H dose not exist !\n");
523+ return -ENODEV;
524+ }
525+ ret = en8811h_load_firmware(phydev);
526+ if (ret)
527+ {
528+ dev_err(dev,"EN8811H load firmware fail.\n");
529+ return ret;
530+ }
531+ retry = MAX_RETRY;
532+ do {
533+ mdelay(300);
534+ reg_value = air_mii_cl45_read(phydev, 0x1e, 0x8009);
535+ if (EN8811H_PHY_READY == reg_value)
536+ {
537+ dev_info(dev, "EN8811H PHY ready!\n");
538+ break;
539+ }
540+ retry--;
541+ } while (retry);
542+ if (0 == retry)
543+ {
544+ dev_err(dev, "EN8811H initialize fail ! reg: 0x%x\n", reg_value);
545+ return -EIO;
546+ }
547+ /* Mode selection*/
548+ dev_info(dev, "EN8811H Mode 1 !\n");
549+ ret = air_mii_cl45_write(phydev, 0x1e, 0x800c, 0x0);
550+ AIR_RTN_ERR(ret);
551+ ret = air_mii_cl45_write(phydev, 0x1e, 0x800d, 0x0);
552+ AIR_RTN_ERR(ret);
553+ ret = air_mii_cl45_write(phydev, 0x1e, 0x800e, 0x1101);
554+ AIR_RTN_ERR(ret);
555+ ret = air_mii_cl45_write(phydev, 0x1e, 0x800f, 0x0002);
556+ AIR_RTN_ERR(ret);
557+
558+ /* Serdes polarity */
559+ pbus_value = air_buckpbus_reg_read(phydev, 0xca0f8);
560+ pbus_value = (pbus_value & 0xfffffffc) | EN8811H_RX_POLARITY_NORMAL | EN8811H_TX_POLARITY_NORMAL;
561+ ret = air_buckpbus_reg_write(phydev, 0xca0f8, pbus_value);
562+ AIR_RTN_ERR(ret);
563+ pbus_value = air_buckpbus_reg_read(phydev, 0xca0f8);
564+ dev_info(dev, "0xca0f8= 0x%x\n", pbus_value);
565+ pbus_value = air_buckpbus_reg_read(phydev, 0x3b3c);
566+ dev_info(dev, "Version(0x3b3c)= %x\n", pbus_value);
567+#if defined(AIR_LED_SUPPORT)
568+ ret = en8811h_led_init(phydev);
569+ if (ret < 0)
570+ {
571+ dev_err(dev, "en8811h_led_init fail. (ret=%d)\n", ret);
572+ return ret;
573+ }
574+#endif
575+ dev_info(dev, "EN8811H initialize OK ! (%s)\n", EN8811H_FW_VERSION);
576+ return 0;
577+}
578+
579+static int en8811h_get_autonego(struct phy_device *phydev, int *an)
580+{
581+ int reg;
582+ reg = phy_read(phydev, MII_BMCR);
583+ if (reg < 0)
584+ return -EINVAL;
585+ if (reg & BMCR_ANENABLE)
586+ *an = AUTONEG_ENABLE;
587+ else
588+ *an = AUTONEG_DISABLE;
589+ return 0;
590+}
591+
592+static int en8811h_read_status(struct phy_device *phydev)
593+{
594+ int ret = 0, lpagb = 0, lpa = 0, common_adv_gb = 0, common_adv = 0, advgb = 0, adv = 0, reg = 0, an = AUTONEG_DISABLE, bmcr = 0;
595+ int old_link = phydev->link;
596+ u32 pbus_value = 0;
597+ struct device *dev = phydev_dev(phydev);
598+ ret = genphy_update_link(phydev);
599+ if (ret)
600+ {
601+ dev_err(dev, "ret %d!\n", ret);
602+ return ret;
603+ }
604+
605+ if (old_link && phydev->link)
606+ return 0;
607+
608+ phydev->speed = SPEED_UNKNOWN;
609+ phydev->duplex = DUPLEX_UNKNOWN;
610+ phydev->pause = 0;
611+ phydev->asym_pause = 0;
612+
613+ reg = phy_read(phydev, MII_BMSR);
614+ if (reg < 0)
615+ {
616+ dev_err(dev, "MII_BMSR reg %d!\n", reg);
617+ return reg;
618+ }
619+ reg = phy_read(phydev, MII_BMSR);
620+ if (reg < 0)
621+ {
622+ dev_err(dev, "MII_BMSR reg %d!\n", reg);
623+ return reg;
624+ }
625+ if(reg & BMSR_LSTATUS)
626+ {
627+ pbus_value = air_buckpbus_reg_read(phydev, 0x109D4);
628+ if (0x10 & pbus_value) {
629+ phydev->speed = SPEED_2500;
630+ phydev->duplex = DUPLEX_FULL;
631+ }
632+ else
633+ {
634+ ret = en8811h_get_autonego(phydev, &an);
635+ if ((AUTONEG_ENABLE == an) && (0 == ret))
636+ {
637+ dev_dbg(dev, "AN mode!\n");
638+ dev_dbg(dev, "SPEED 1000/100!\n");
639+ lpagb = phy_read(phydev, MII_STAT1000);
640+ if (lpagb < 0 )
641+ return lpagb;
642+ advgb = phy_read(phydev, MII_CTRL1000);
643+ if (adv < 0 )
644+ return adv;
645+ common_adv_gb = (lpagb & (advgb << 2));
646+
647+ lpa = phy_read(phydev, MII_LPA);
648+ if (lpa < 0 )
649+ return lpa;
650+ adv = phy_read(phydev, MII_ADVERTISE);
651+ if (adv < 0 )
652+ return adv;
653+ common_adv = (lpa & adv);
654+
655+ phydev->speed = SPEED_10;
656+ phydev->duplex = DUPLEX_HALF;
657+ if (common_adv_gb & (LPA_1000FULL | LPA_1000HALF))
658+ {
659+ phydev->speed = SPEED_1000;
660+ if (common_adv_gb & LPA_1000FULL)
661+
662+ phydev->duplex = DUPLEX_FULL;
663+ }
664+ else if (common_adv & (LPA_100FULL | LPA_100HALF))
665+ {
666+ phydev->speed = SPEED_100;
667+ if (common_adv & LPA_100FULL)
668+ phydev->duplex = DUPLEX_FULL;
669+ }
670+ else
671+ {
672+ if (common_adv & LPA_10FULL)
673+ phydev->duplex = DUPLEX_FULL;
674+ }
675+ }
676+ else
677+ {
678+ dev_dbg(dev, "Force mode!\n");
679+ bmcr = phy_read(phydev, MII_BMCR);
680+
681+ if (bmcr < 0)
682+ return bmcr;
683+
684+ if (bmcr & BMCR_FULLDPLX)
685+ phydev->duplex = DUPLEX_FULL;
686+ else
687+ phydev->duplex = DUPLEX_HALF;
688+
689+ if (bmcr & BMCR_SPEED1000)
690+ phydev->speed = SPEED_1000;
691+ else if (bmcr & BMCR_SPEED100)
692+ phydev->speed = SPEED_100;
693+ else
694+ phydev->speed = SPEED_UNKNOWN;
695+ }
696+ }
697+ }
698+
699+ return ret;
700+}
701+static struct phy_driver en8811h_driver[] = {
702+{
703+ .phy_id = EN8811H_PHY_ID,
704+ .name = "Airoha EN8811H",
705+ .phy_id_mask = 0x0ffffff0,
706+ .probe = en8811h_phy_probe,
707+ .read_status = en8811h_read_status,
708+#if (LINUX_VERSION_CODE > KERNEL_VERSION(4, 5, 0))
709+ .get_features = en8811h_get_features,
710+ .read_mmd = air_mii_cl45_read,
711+ .write_mmd = air_mii_cl45_write,
712+#endif
713+} };
714+
715+int __init en8811h_phy_driver_register(void)
716+{
717+ int ret;
718+#if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 5, 0))
719+ ret = phy_driver_register(en8811h_driver);
720+#else
721+ ret = phy_driver_register(en8811h_driver, THIS_MODULE);
722+#endif
723+ if (!ret)
724+ return 0;
725+
726+ phy_driver_unregister(en8811h_driver);
727+ return ret;
728+}
729+
730+void __exit en8811h_phy_driver_unregister(void)
731+{
732+ phy_driver_unregister(en8811h_driver);
733+}
734+
735+module_init(en8811h_phy_driver_register);
736+module_exit(en8811h_phy_driver_unregister);
737diff --git a/drivers/net/phy/air_en8811h.h b/drivers/net/phy/air_en8811h.h
738new file mode 100644
739index 0000000..1c91627
740--- /dev/null
741+++ b/drivers/net/phy/air_en8811h.h
742@@ -0,0 +1,151 @@
743+#ifndef __EN8811H_H
744+#define __EN8811H_H
745+
746+#define EN8811H_MD32_DM "EthMD32.dm.bin"
747+#define EN8811H_MD32_DSP "EthMD32.DSP.bin"
748+
749+#define EN8811H_PHY_ID1 0x03a2
750+#define EN8811H_PHY_ID2 0xa411
751+#define EN8811H_PHY_ID ((EN8811H_PHY_ID1 << 16) | EN8811H_PHY_ID2)
752+#define EN8811H_PHY_READY 0x02
753+#define MAX_RETRY 5
754+
755+#define EN8811H_TX_POLARITY_NORMAL 0x1
756+#define EN8811H_TX_POLARITY_REVERSE 0x0
757+
758+#define EN8811H_RX_POLARITY_REVERSE (0x1 << 1)
759+#define EN8811H_RX_POLARITY_NORMAL (0x0 << 1)
760+
761+
762+/*
763+The following led_cfg example is for reference only.
764+LED0 Link 2500/Blink 2500 TxRx (GPIO5) <-> BASE_T_LED0,
765+LED1 Link 1000/Blink 1000 TxRx (GPIO4) <-> BASE_T_LED1,
766+LED2 Link 100 /Blink 100 TxRx (GPIO3) <-> BASE_T_LED2,
767+*/
768+/* User-defined.B */
769+#define BASE_T_LED0_ON_CFG (LED_ON_EVT_LINK_2500M)
770+#define BASE_T_LED0_BLK_CFG (LED_BLK_EVT_2500M_TX_ACT | LED_BLK_EVT_2500M_RX_ACT)
771+#define BASE_T_LED1_ON_CFG (LED_ON_EVT_LINK_1000M)
772+#define BASE_T_LED1_BLK_CFG (LED_BLK_EVT_1000M_TX_ACT | LED_BLK_EVT_1000M_RX_ACT)
773+#define BASE_T_LED2_ON_CFG (LED_ON_EVT_LINK_100M)
774+#define BASE_T_LED2_BLK_CFG (LED_BLK_EVT_100M_TX_ACT | LED_BLK_EVT_100M_RX_ACT)
775+/* User-defined.E */
776+
777+/* CL45 MDIO control */
778+#define MII_MMD_ACC_CTL_REG 0x0d
779+#define MII_MMD_ADDR_DATA_REG 0x0e
780+#define MMD_OP_MODE_DATA BIT(14)
781+
782+#define EN8811H_FW_VERSION "1.1.3"
783+
784+#define LED_ON_CTRL(i) (0x024 + ((i)*2))
785+#define LED_ON_EN (1 << 15)
786+#define LED_ON_POL (1 << 14)
787+#define LED_ON_EVT_MASK (0x1ff)
788+/* LED ON Event Option.B */
789+#define LED_ON_EVT_LINK_2500M (1 << 8)
790+#define LED_ON_EVT_FORCE (1 << 6)
791+#define LED_ON_EVT_LINK_DOWN (1 << 3)
792+#define LED_ON_EVT_LINK_100M (1 << 1)
793+#define LED_ON_EVT_LINK_1000M (1 << 0)
794+/* LED ON Event Option.E */
795+
796+#define LED_BLK_CTRL(i) (0x025 + ((i)*2))
797+#define LED_BLK_EVT_MASK (0xfff)
798+/* LED Blinking Event Option.B*/
799+#define LED_BLK_EVT_2500M_RX_ACT (1 << 11)
800+#define LED_BLK_EVT_2500M_TX_ACT (1 << 10)
801+#define LED_BLK_EVT_FORCE (1 << 9)
802+#define LED_BLK_EVT_100M_RX_ACT (1 << 3)
803+#define LED_BLK_EVT_100M_TX_ACT (1 << 2)
804+#define LED_BLK_EVT_1000M_RX_ACT (1 << 1)
805+#define LED_BLK_EVT_1000M_TX_ACT (1 << 0)
806+/* LED Blinking Event Option.E*/
807+#define LED_ENABLE 1
808+#define LED_DISABLE 0
809+
810+#define EN8811H_LED_COUNT 3
811+
812+#define LED_BCR (0x021)
813+#define LED_BCR_EXT_CTRL (1 << 15)
814+#define LED_BCR_CLK_EN (1 << 3)
815+#define LED_BCR_TIME_TEST (1 << 2)
816+#define LED_BCR_MODE_MASK (3)
817+#define LED_BCR_MODE_DISABLE (0)
818+
819+#define LED_ON_DUR (0x022)
820+#define LED_ON_DUR_MASK (0xffff)
821+
822+#define LED_BLK_DUR (0x023)
823+#define LED_BLK_DUR_MASK (0xffff)
824+
825+#define UNIT_LED_BLINK_DURATION 1024
826+
827+#define AIR_RTN_ON_ERR(cond, err) \
828+ do { if ((cond)) return (err); } while(0)
829+
830+#define AIR_RTN_ERR(err) AIR_RTN_ON_ERR(err < 0, err)
831+
832+#define LED_SET_EVT(reg, cod, result, bit) do \
833+ { \
834+ if(reg & cod) { \
835+ result |= bit; \
836+ } \
837+ } while(0)
838+
839+#define LED_SET_GPIO_SEL(gpio, led, val) do \
840+ { \
841+ val |= (led << (8 * (gpio % 4))); \
842+ } while(0)
843+
844+#define INVALID_DATA 0xffff
845+#define PBUS_INVALID_DATA 0xffffffff
846+
847+typedef struct AIR_BASE_T_LED_CFG_S
848+{
849+ u16 en;
850+ u16 gpio;
851+ u16 pol;
852+ u16 on_cfg;
853+ u16 blk_cfg;
854+}AIR_BASE_T_LED_CFG_T;
855+typedef enum
856+{
857+ AIR_LED2_GPIO3 = 3,
858+ AIR_LED1_GPIO4,
859+ AIR_LED0_GPIO5,
860+ AIR_LED_LAST
861+} AIR_LED_GPIO;
862+
863+typedef enum {
864+ AIR_BASE_T_LED0,
865+ AIR_BASE_T_LED1,
866+ AIR_BASE_T_LED2,
867+ AIR_BASE_T_LED3
868+}AIR_BASE_T_LED;
869+
870+typedef enum
871+{
872+ AIR_LED_BLK_DUR_32M,
873+ AIR_LED_BLK_DUR_64M,
874+ AIR_LED_BLK_DUR_128M,
875+ AIR_LED_BLK_DUR_256M,
876+ AIR_LED_BLK_DUR_512M,
877+ AIR_LED_BLK_DUR_1024M,
878+ AIR_LED_BLK_DUR_LAST
879+} AIR_LED_BLK_DUT_T;
880+
881+typedef enum
882+{
883+ AIR_ACTIVE_LOW,
884+ AIR_ACTIVE_HIGH,
885+} AIR_LED_POLARITY;
886+typedef enum
887+{
888+ AIR_LED_MODE_DISABLE,
889+ AIR_LED_MODE_USER_DEFINE,
890+ AIR_LED_MODE_LAST
891+} AIR_LED_MODE_T;
892+
893+#endif /* End of __EN8811H_MD32_H */