1 // SPDX-License-Identifier: GPL-2.0
4 #include <linux/module.h>
6 #include <linux/netdevice.h>
7 #include <linux/etherdevice.h>
8 #include <linux/ethtool_netlink.h>
12 MODULE_DESCRIPTION("Qualcomm PHY driver Common Functions");
13 MODULE_AUTHOR("Matus Ujhelyi");
15 MODULE_LICENSE("GPL");
17 int at803x_debug_reg_read(struct phy_device *phydev, u16 reg)
21 ret = phy_write(phydev, AT803X_DEBUG_ADDR, reg);
25 return phy_read(phydev, AT803X_DEBUG_DATA);
27 EXPORT_SYMBOL_GPL(at803x_debug_reg_read);
29 int at803x_debug_reg_mask(struct phy_device *phydev, u16 reg,
35 ret = at803x_debug_reg_read(phydev, reg);
43 return phy_write(phydev, AT803X_DEBUG_DATA, val);
45 EXPORT_SYMBOL_GPL(at803x_debug_reg_mask);
47 int at803x_debug_reg_write(struct phy_device *phydev, u16 reg, u16 data)
51 ret = phy_write(phydev, AT803X_DEBUG_ADDR, reg);
55 return phy_write(phydev, AT803X_DEBUG_DATA, data);
57 EXPORT_SYMBOL_GPL(at803x_debug_reg_write);
59 int at803x_set_wol(struct phy_device *phydev,
60 struct ethtool_wolinfo *wol)
64 if (wol->wolopts & WAKE_MAGIC) {
65 struct net_device *ndev = phydev->attached_dev;
68 static const unsigned int offsets[] = {
69 AT803X_LOC_MAC_ADDR_32_47_OFFSET,
70 AT803X_LOC_MAC_ADDR_16_31_OFFSET,
71 AT803X_LOC_MAC_ADDR_0_15_OFFSET,
77 mac = (const u8 *)ndev->dev_addr;
79 if (!is_valid_ether_addr(mac))
82 for (i = 0; i < 3; i++)
83 phy_write_mmd(phydev, MDIO_MMD_PCS, offsets[i],
84 mac[(i * 2) + 1] | (mac[(i * 2)] << 8));
86 /* Enable WOL interrupt */
87 ret = phy_modify(phydev, AT803X_INTR_ENABLE, 0, AT803X_INTR_ENABLE_WOL);
91 /* Disable WOL interrupt */
92 ret = phy_modify(phydev, AT803X_INTR_ENABLE, AT803X_INTR_ENABLE_WOL, 0);
97 /* Clear WOL status */
98 ret = phy_read(phydev, AT803X_INTR_STATUS);
102 /* Check if there are other interrupts except for WOL triggered when PHY is
103 * in interrupt mode, only the interrupts enabled by AT803X_INTR_ENABLE can
104 * be passed up to the interrupt PIN.
106 irq_enabled = phy_read(phydev, AT803X_INTR_ENABLE);
110 irq_enabled &= ~AT803X_INTR_ENABLE_WOL;
111 if (ret & irq_enabled && !phy_polling_mode(phydev))
112 phy_trigger_machine(phydev);
116 EXPORT_SYMBOL_GPL(at803x_set_wol);
118 void at803x_get_wol(struct phy_device *phydev,
119 struct ethtool_wolinfo *wol)
123 wol->supported = WAKE_MAGIC;
126 value = phy_read(phydev, AT803X_INTR_ENABLE);
130 if (value & AT803X_INTR_ENABLE_WOL)
131 wol->wolopts |= WAKE_MAGIC;
133 EXPORT_SYMBOL_GPL(at803x_get_wol);
135 int at803x_ack_interrupt(struct phy_device *phydev)
139 err = phy_read(phydev, AT803X_INTR_STATUS);
141 return (err < 0) ? err : 0;
143 EXPORT_SYMBOL_GPL(at803x_ack_interrupt);
145 int at803x_config_intr(struct phy_device *phydev)
150 value = phy_read(phydev, AT803X_INTR_ENABLE);
152 if (phydev->interrupts == PHY_INTERRUPT_ENABLED) {
153 /* Clear any pending interrupts */
154 err = at803x_ack_interrupt(phydev);
158 value |= AT803X_INTR_ENABLE_AUTONEG_ERR;
159 value |= AT803X_INTR_ENABLE_SPEED_CHANGED;
160 value |= AT803X_INTR_ENABLE_DUPLEX_CHANGED;
161 value |= AT803X_INTR_ENABLE_LINK_FAIL;
162 value |= AT803X_INTR_ENABLE_LINK_SUCCESS;
164 err = phy_write(phydev, AT803X_INTR_ENABLE, value);
166 err = phy_write(phydev, AT803X_INTR_ENABLE, 0);
170 /* Clear any pending interrupts */
171 err = at803x_ack_interrupt(phydev);
176 EXPORT_SYMBOL_GPL(at803x_config_intr);
178 irqreturn_t at803x_handle_interrupt(struct phy_device *phydev)
180 int irq_status, int_enabled;
182 irq_status = phy_read(phydev, AT803X_INTR_STATUS);
183 if (irq_status < 0) {
188 /* Read the current enabled interrupts */
189 int_enabled = phy_read(phydev, AT803X_INTR_ENABLE);
190 if (int_enabled < 0) {
195 /* See if this was one of our enabled interrupts */
196 if (!(irq_status & int_enabled))
199 phy_trigger_machine(phydev);
203 EXPORT_SYMBOL_GPL(at803x_handle_interrupt);
205 int at803x_read_specific_status(struct phy_device *phydev,
206 struct at803x_ss_mask ss_mask)
210 /* Read the AT8035 PHY-Specific Status register, which indicates the
211 * speed and duplex that the PHY is actually using, irrespective of
212 * whether we are in autoneg mode or not.
214 ss = phy_read(phydev, AT803X_SPECIFIC_STATUS);
218 if (ss & AT803X_SS_SPEED_DUPLEX_RESOLVED) {
221 sfc = phy_read(phydev, AT803X_SPECIFIC_FUNCTION_CONTROL);
225 speed = ss & ss_mask.speed_mask;
226 speed >>= ss_mask.speed_shift;
229 case AT803X_SS_SPEED_10:
230 phydev->speed = SPEED_10;
232 case AT803X_SS_SPEED_100:
233 phydev->speed = SPEED_100;
235 case AT803X_SS_SPEED_1000:
236 phydev->speed = SPEED_1000;
238 case QCA808X_SS_SPEED_2500:
239 phydev->speed = SPEED_2500;
242 if (ss & AT803X_SS_DUPLEX)
243 phydev->duplex = DUPLEX_FULL;
245 phydev->duplex = DUPLEX_HALF;
247 if (ss & AT803X_SS_MDIX)
248 phydev->mdix = ETH_TP_MDI_X;
250 phydev->mdix = ETH_TP_MDI;
252 switch (FIELD_GET(AT803X_SFC_MDI_CROSSOVER_MODE_M, sfc)) {
253 case AT803X_SFC_MANUAL_MDI:
254 phydev->mdix_ctrl = ETH_TP_MDI;
256 case AT803X_SFC_MANUAL_MDIX:
257 phydev->mdix_ctrl = ETH_TP_MDI_X;
259 case AT803X_SFC_AUTOMATIC_CROSSOVER:
260 phydev->mdix_ctrl = ETH_TP_MDI_AUTO;
267 EXPORT_SYMBOL_GPL(at803x_read_specific_status);
269 int at803x_config_mdix(struct phy_device *phydev, u8 ctrl)
275 val = AT803X_SFC_MANUAL_MDI;
278 val = AT803X_SFC_MANUAL_MDIX;
280 case ETH_TP_MDI_AUTO:
281 val = AT803X_SFC_AUTOMATIC_CROSSOVER;
287 return phy_modify_changed(phydev, AT803X_SPECIFIC_FUNCTION_CONTROL,
288 AT803X_SFC_MDI_CROSSOVER_MODE_M,
289 FIELD_PREP(AT803X_SFC_MDI_CROSSOVER_MODE_M, val));
291 EXPORT_SYMBOL_GPL(at803x_config_mdix);
293 int at803x_prepare_config_aneg(struct phy_device *phydev)
297 ret = at803x_config_mdix(phydev, phydev->mdix_ctrl);
301 /* Changes of the midx bits are disruptive to the normal operation;
302 * therefore any changes to these registers must be followed by a
303 * software reset to take effect.
306 ret = genphy_soft_reset(phydev);
313 EXPORT_SYMBOL_GPL(at803x_prepare_config_aneg);
315 int at803x_read_status(struct phy_device *phydev)
317 struct at803x_ss_mask ss_mask = { 0 };
318 int err, old_link = phydev->link;
320 /* Update the link, but return if there was an error */
321 err = genphy_update_link(phydev);
325 /* why bother the PHY if nothing can have changed */
326 if (phydev->autoneg == AUTONEG_ENABLE && old_link && phydev->link)
329 phydev->speed = SPEED_UNKNOWN;
330 phydev->duplex = DUPLEX_UNKNOWN;
332 phydev->asym_pause = 0;
334 err = genphy_read_lpa(phydev);
338 ss_mask.speed_mask = AT803X_SS_SPEED_MASK;
339 ss_mask.speed_shift = __bf_shf(AT803X_SS_SPEED_MASK);
340 err = at803x_read_specific_status(phydev, ss_mask);
344 if (phydev->autoneg == AUTONEG_ENABLE && phydev->autoneg_complete)
345 phy_resolve_aneg_pause(phydev);
349 EXPORT_SYMBOL_GPL(at803x_read_status);
351 static int at803x_get_downshift(struct phy_device *phydev, u8 *d)
355 val = phy_read(phydev, AT803X_SMART_SPEED);
359 if (val & AT803X_SMART_SPEED_ENABLE)
360 *d = FIELD_GET(AT803X_SMART_SPEED_RETRY_LIMIT_MASK, val) + 2;
362 *d = DOWNSHIFT_DEV_DISABLE;
367 static int at803x_set_downshift(struct phy_device *phydev, u8 cnt)
373 case DOWNSHIFT_DEV_DEFAULT_COUNT:
374 cnt = AT803X_DEFAULT_DOWNSHIFT;
376 case AT803X_MIN_DOWNSHIFT ... AT803X_MAX_DOWNSHIFT:
377 set = AT803X_SMART_SPEED_ENABLE |
378 AT803X_SMART_SPEED_BYPASS_TIMER |
379 FIELD_PREP(AT803X_SMART_SPEED_RETRY_LIMIT_MASK, cnt - 2);
380 mask = AT803X_SMART_SPEED_RETRY_LIMIT_MASK;
382 case DOWNSHIFT_DEV_DISABLE:
384 mask = AT803X_SMART_SPEED_ENABLE |
385 AT803X_SMART_SPEED_BYPASS_TIMER;
391 ret = phy_modify_changed(phydev, AT803X_SMART_SPEED, mask, set);
393 /* After changing the smart speed settings, we need to perform a
394 * software reset, use phy_init_hw() to make sure we set the
395 * reapply any values which might got lost during software reset.
398 ret = phy_init_hw(phydev);
403 int at803x_get_tunable(struct phy_device *phydev,
404 struct ethtool_tunable *tuna, void *data)
407 case ETHTOOL_PHY_DOWNSHIFT:
408 return at803x_get_downshift(phydev, data);
413 EXPORT_SYMBOL_GPL(at803x_get_tunable);
415 int at803x_set_tunable(struct phy_device *phydev,
416 struct ethtool_tunable *tuna, const void *data)
419 case ETHTOOL_PHY_DOWNSHIFT:
420 return at803x_set_downshift(phydev, *(const u8 *)data);
425 EXPORT_SYMBOL_GPL(at803x_set_tunable);
427 int at803x_cdt_fault_length(int dt)
429 /* According to the datasheet the distance to the fault is
430 * DELTA_TIME * 0.824 meters.
432 * The author suspect the correct formula is:
434 * fault_distance = DELTA_TIME * (c * VF) / 125MHz / 2
436 * where c is the speed of light, VF is the velocity factor of
437 * the twisted pair cable, 125MHz the counter frequency and
438 * we need to divide by 2 because the hardware will measure the
439 * round trip time to the fault and back to the PHY.
441 * With a VF of 0.69 we get the factor 0.824 mentioned in the
444 return (dt * 824) / 10;
446 EXPORT_SYMBOL_GPL(at803x_cdt_fault_length);
448 int at803x_cdt_start(struct phy_device *phydev, u32 cdt_start)
450 return phy_write(phydev, AT803X_CDT, cdt_start);
452 EXPORT_SYMBOL_GPL(at803x_cdt_start);
454 int at803x_cdt_wait_for_completion(struct phy_device *phydev,
459 /* One test run takes about 25ms */
460 ret = phy_read_poll_timeout(phydev, AT803X_CDT, val,
462 30000, 100000, true);
464 return ret < 0 ? ret : 0;
466 EXPORT_SYMBOL_GPL(at803x_cdt_wait_for_completion);
468 static bool qca808x_cdt_fault_length_valid(int cdt_code)
471 case QCA808X_CDT_STATUS_STAT_SAME_SHORT:
472 case QCA808X_CDT_STATUS_STAT_SAME_OPEN:
473 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI1_SAME_NORMAL:
474 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI1_SAME_OPEN:
475 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI1_SAME_SHORT:
476 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI2_SAME_NORMAL:
477 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI2_SAME_OPEN:
478 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI2_SAME_SHORT:
479 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI3_SAME_NORMAL:
480 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI3_SAME_OPEN:
481 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI3_SAME_SHORT:
488 static int qca808x_cable_test_result_trans(int cdt_code)
491 case QCA808X_CDT_STATUS_STAT_NORMAL:
492 return ETHTOOL_A_CABLE_RESULT_CODE_OK;
493 case QCA808X_CDT_STATUS_STAT_SAME_SHORT:
494 return ETHTOOL_A_CABLE_RESULT_CODE_SAME_SHORT;
495 case QCA808X_CDT_STATUS_STAT_SAME_OPEN:
496 return ETHTOOL_A_CABLE_RESULT_CODE_OPEN;
497 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI1_SAME_NORMAL:
498 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI1_SAME_OPEN:
499 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI1_SAME_SHORT:
500 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI2_SAME_NORMAL:
501 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI2_SAME_OPEN:
502 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI2_SAME_SHORT:
503 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI3_SAME_NORMAL:
504 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI3_SAME_OPEN:
505 case QCA808X_CDT_STATUS_STAT_CROSS_SHORT_WITH_MDI3_SAME_SHORT:
506 return ETHTOOL_A_CABLE_RESULT_CODE_CROSS_SHORT;
507 case QCA808X_CDT_STATUS_STAT_FAIL:
509 return ETHTOOL_A_CABLE_RESULT_CODE_UNSPEC;
513 static int qca808x_cdt_fault_length(struct phy_device *phydev, int pair,
517 u32 cdt_length_reg = 0;
520 case ETHTOOL_A_CABLE_PAIR_A:
521 cdt_length_reg = QCA808X_MMD3_CDT_DIAG_PAIR_A;
523 case ETHTOOL_A_CABLE_PAIR_B:
524 cdt_length_reg = QCA808X_MMD3_CDT_DIAG_PAIR_B;
526 case ETHTOOL_A_CABLE_PAIR_C:
527 cdt_length_reg = QCA808X_MMD3_CDT_DIAG_PAIR_C;
529 case ETHTOOL_A_CABLE_PAIR_D:
530 cdt_length_reg = QCA808X_MMD3_CDT_DIAG_PAIR_D;
536 val = phy_read_mmd(phydev, MDIO_MMD_PCS, cdt_length_reg);
540 if (result == ETHTOOL_A_CABLE_RESULT_CODE_SAME_SHORT)
541 val = FIELD_GET(QCA808X_CDT_DIAG_LENGTH_SAME_SHORT, val);
543 val = FIELD_GET(QCA808X_CDT_DIAG_LENGTH_CROSS_SHORT, val);
545 return at803x_cdt_fault_length(val);
548 static int qca808x_cable_test_get_pair_status(struct phy_device *phydev, u8 pair,
555 case ETHTOOL_A_CABLE_PAIR_A:
556 pair_code = FIELD_GET(QCA808X_CDT_CODE_PAIR_A, status);
558 case ETHTOOL_A_CABLE_PAIR_B:
559 pair_code = FIELD_GET(QCA808X_CDT_CODE_PAIR_B, status);
561 case ETHTOOL_A_CABLE_PAIR_C:
562 pair_code = FIELD_GET(QCA808X_CDT_CODE_PAIR_C, status);
564 case ETHTOOL_A_CABLE_PAIR_D:
565 pair_code = FIELD_GET(QCA808X_CDT_CODE_PAIR_D, status);
571 result = qca808x_cable_test_result_trans(pair_code);
572 ethnl_cable_test_result(phydev, pair, result);
574 if (qca808x_cdt_fault_length_valid(pair_code)) {
575 length = qca808x_cdt_fault_length(phydev, pair, result);
576 ethnl_cable_test_fault_length(phydev, pair, length);
582 int qca808x_cable_test_get_status(struct phy_device *phydev, bool *finished)
588 val = QCA808X_CDT_ENABLE_TEST |
589 QCA808X_CDT_LENGTH_UNIT;
590 ret = at803x_cdt_start(phydev, val);
594 ret = at803x_cdt_wait_for_completion(phydev, QCA808X_CDT_ENABLE_TEST);
598 val = phy_read_mmd(phydev, MDIO_MMD_PCS, QCA808X_MMD3_CDT_STATUS);
602 ret = qca808x_cable_test_get_pair_status(phydev, ETHTOOL_A_CABLE_PAIR_A, val);
606 ret = qca808x_cable_test_get_pair_status(phydev, ETHTOOL_A_CABLE_PAIR_B, val);
610 ret = qca808x_cable_test_get_pair_status(phydev, ETHTOOL_A_CABLE_PAIR_C, val);
614 ret = qca808x_cable_test_get_pair_status(phydev, ETHTOOL_A_CABLE_PAIR_D, val);
622 EXPORT_SYMBOL_GPL(qca808x_cable_test_get_status);
624 int qca808x_led_reg_hw_control_enable(struct phy_device *phydev, u16 reg)
626 return phy_clear_bits_mmd(phydev, MDIO_MMD_AN, reg,
627 QCA808X_LED_FORCE_EN);
629 EXPORT_SYMBOL_GPL(qca808x_led_reg_hw_control_enable);
631 bool qca808x_led_reg_hw_control_status(struct phy_device *phydev, u16 reg)
635 val = phy_read_mmd(phydev, MDIO_MMD_AN, reg);
636 return !(val & QCA808X_LED_FORCE_EN);
638 EXPORT_SYMBOL_GPL(qca808x_led_reg_hw_control_status);
640 int qca808x_led_reg_brightness_set(struct phy_device *phydev,
641 u16 reg, enum led_brightness value)
643 return phy_modify_mmd(phydev, MDIO_MMD_AN, reg,
644 QCA808X_LED_FORCE_EN | QCA808X_LED_FORCE_MODE_MASK,
645 QCA808X_LED_FORCE_EN | (value ? QCA808X_LED_FORCE_ON :
646 QCA808X_LED_FORCE_OFF));
648 EXPORT_SYMBOL_GPL(qca808x_led_reg_brightness_set);
650 int qca808x_led_reg_blink_set(struct phy_device *phydev, u16 reg,
651 unsigned long *delay_on,
652 unsigned long *delay_off)
656 /* Set blink to 50% off, 50% on at 4Hz by default */
657 ret = phy_modify_mmd(phydev, MDIO_MMD_AN, QCA808X_MMD7_LED_GLOBAL,
658 QCA808X_LED_BLINK_FREQ_MASK | QCA808X_LED_BLINK_DUTY_MASK,
659 QCA808X_LED_BLINK_FREQ_4HZ | QCA808X_LED_BLINK_DUTY_50_50);
663 /* We use BLINK_1 for normal blinking */
664 ret = phy_modify_mmd(phydev, MDIO_MMD_AN, reg,
665 QCA808X_LED_FORCE_EN | QCA808X_LED_FORCE_MODE_MASK,
666 QCA808X_LED_FORCE_EN | QCA808X_LED_FORCE_BLINK_1);
670 /* We set blink to 4Hz, aka 250ms */
672 *delay_off = 250 / 2;
676 EXPORT_SYMBOL_GPL(qca808x_led_reg_blink_set);