| .. | .. |
|---|
| 1 | +/* SPDX-License-Identifier: GPL-2.0-only */ |
|---|
| 1 | 2 | /* |
|---|
| 2 | 3 | * linux/mdio.h: definitions for MDIO (clause 45) transceivers |
|---|
| 3 | 4 | * Copyright 2006-2009 Solarflare Communications Inc. |
|---|
| 4 | | - * |
|---|
| 5 | | - * This program is free software; you can redistribute it and/or modify it |
|---|
| 6 | | - * under the terms of the GNU General Public License version 2 as published |
|---|
| 7 | | - * by the Free Software Foundation, incorporated herein by reference. |
|---|
| 8 | 5 | */ |
|---|
| 9 | 6 | #ifndef __LINUX_MDIO_H__ |
|---|
| 10 | 7 | #define __LINUX_MDIO_H__ |
|---|
| .. | .. |
|---|
| 12 | 9 | #include <uapi/linux/mdio.h> |
|---|
| 13 | 10 | #include <linux/mod_devicetable.h> |
|---|
| 14 | 11 | |
|---|
| 12 | +/* Or MII_ADDR_C45 into regnum for read/write on mii_bus to enable the 21 bit |
|---|
| 13 | + * IEEE 802.3ae clause 45 addressing mode used by 10GIGE phy chips. |
|---|
| 14 | + */ |
|---|
| 15 | +#define MII_ADDR_C45 (1<<30) |
|---|
| 16 | +#define MII_DEVADDR_C45_SHIFT 16 |
|---|
| 17 | +#define MII_REGADDR_C45_MASK GENMASK(15, 0) |
|---|
| 18 | + |
|---|
| 15 | 19 | struct gpio_desc; |
|---|
| 16 | 20 | struct mii_bus; |
|---|
| 21 | +struct reset_control; |
|---|
| 17 | 22 | |
|---|
| 18 | 23 | /* Multiple levels of nesting are possible. However typically this is |
|---|
| 19 | 24 | * limited to nested DSA like layer, a MUX layer, and the normal |
|---|
| .. | .. |
|---|
| 39 | 44 | /* Bus address of the MDIO device (0-31) */ |
|---|
| 40 | 45 | int addr; |
|---|
| 41 | 46 | int flags; |
|---|
| 42 | | - struct gpio_desc *reset; |
|---|
| 47 | + struct gpio_desc *reset_gpio; |
|---|
| 48 | + struct reset_control *reset_ctrl; |
|---|
| 43 | 49 | unsigned int reset_assert_delay; |
|---|
| 44 | 50 | unsigned int reset_deassert_delay; |
|---|
| 45 | 51 | }; |
|---|
| .. | .. |
|---|
| 72 | 78 | }; |
|---|
| 73 | 79 | #define to_mdio_driver(d) \ |
|---|
| 74 | 80 | container_of(to_mdio_common_driver(d), struct mdio_driver, mdiodrv) |
|---|
| 81 | + |
|---|
| 82 | +/* device driver data */ |
|---|
| 83 | +static inline void mdiodev_set_drvdata(struct mdio_device *mdio, void *data) |
|---|
| 84 | +{ |
|---|
| 85 | + dev_set_drvdata(&mdio->dev, data); |
|---|
| 86 | +} |
|---|
| 87 | + |
|---|
| 88 | +static inline void *mdiodev_get_drvdata(struct mdio_device *mdio) |
|---|
| 89 | +{ |
|---|
| 90 | + return dev_get_drvdata(&mdio->dev); |
|---|
| 91 | +} |
|---|
| 75 | 92 | |
|---|
| 76 | 93 | void mdio_device_free(struct mdio_device *mdiodev); |
|---|
| 77 | 94 | struct mdio_device *mdio_device_create(struct mii_bus *bus, int addr); |
|---|
| .. | .. |
|---|
| 264 | 281 | return reg; |
|---|
| 265 | 282 | } |
|---|
| 266 | 283 | |
|---|
| 284 | +/** |
|---|
| 285 | + * linkmode_adv_to_mii_10gbt_adv_t |
|---|
| 286 | + * @advertising: the linkmode advertisement settings |
|---|
| 287 | + * |
|---|
| 288 | + * A small helper function that translates linkmode advertisement |
|---|
| 289 | + * settings to phy autonegotiation advertisements for the C45 |
|---|
| 290 | + * 10GBASE-T AN CONTROL (7.32) register. |
|---|
| 291 | + */ |
|---|
| 292 | +static inline u32 linkmode_adv_to_mii_10gbt_adv_t(unsigned long *advertising) |
|---|
| 293 | +{ |
|---|
| 294 | + u32 result = 0; |
|---|
| 295 | + |
|---|
| 296 | + if (linkmode_test_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT, |
|---|
| 297 | + advertising)) |
|---|
| 298 | + result |= MDIO_AN_10GBT_CTRL_ADV2_5G; |
|---|
| 299 | + if (linkmode_test_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT, |
|---|
| 300 | + advertising)) |
|---|
| 301 | + result |= MDIO_AN_10GBT_CTRL_ADV5G; |
|---|
| 302 | + if (linkmode_test_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT, |
|---|
| 303 | + advertising)) |
|---|
| 304 | + result |= MDIO_AN_10GBT_CTRL_ADV10G; |
|---|
| 305 | + |
|---|
| 306 | + return result; |
|---|
| 307 | +} |
|---|
| 308 | + |
|---|
| 309 | +/** |
|---|
| 310 | + * mii_10gbt_stat_mod_linkmode_lpa_t |
|---|
| 311 | + * @advertising: target the linkmode advertisement settings |
|---|
| 312 | + * @lpa: value of the C45 10GBASE-T AN STATUS register |
|---|
| 313 | + * |
|---|
| 314 | + * A small helper function that translates C45 10GBASE-T AN STATUS register bits |
|---|
| 315 | + * to linkmode advertisement settings. Other bits in advertising aren't changed. |
|---|
| 316 | + */ |
|---|
| 317 | +static inline void mii_10gbt_stat_mod_linkmode_lpa_t(unsigned long *advertising, |
|---|
| 318 | + u32 lpa) |
|---|
| 319 | +{ |
|---|
| 320 | + linkmode_mod_bit(ETHTOOL_LINK_MODE_2500baseT_Full_BIT, |
|---|
| 321 | + advertising, lpa & MDIO_AN_10GBT_STAT_LP2_5G); |
|---|
| 322 | + linkmode_mod_bit(ETHTOOL_LINK_MODE_5000baseT_Full_BIT, |
|---|
| 323 | + advertising, lpa & MDIO_AN_10GBT_STAT_LP5G); |
|---|
| 324 | + linkmode_mod_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT, |
|---|
| 325 | + advertising, lpa & MDIO_AN_10GBT_STAT_LP10G); |
|---|
| 326 | +} |
|---|
| 327 | + |
|---|
| 267 | 328 | int __mdiobus_read(struct mii_bus *bus, int addr, u32 regnum); |
|---|
| 268 | 329 | int __mdiobus_write(struct mii_bus *bus, int addr, u32 regnum, u16 val); |
|---|
| 330 | +int __mdiobus_modify_changed(struct mii_bus *bus, int addr, u32 regnum, |
|---|
| 331 | + u16 mask, u16 set); |
|---|
| 269 | 332 | |
|---|
| 270 | 333 | int mdiobus_read(struct mii_bus *bus, int addr, u32 regnum); |
|---|
| 271 | 334 | int mdiobus_read_nested(struct mii_bus *bus, int addr, u32 regnum); |
|---|
| 272 | 335 | int mdiobus_write(struct mii_bus *bus, int addr, u32 regnum, u16 val); |
|---|
| 273 | 336 | int mdiobus_write_nested(struct mii_bus *bus, int addr, u32 regnum, u16 val); |
|---|
| 337 | +int mdiobus_modify(struct mii_bus *bus, int addr, u32 regnum, u16 mask, |
|---|
| 338 | + u16 set); |
|---|
| 339 | + |
|---|
| 340 | +static inline u32 mdiobus_c45_addr(int devad, u16 regnum) |
|---|
| 341 | +{ |
|---|
| 342 | + return MII_ADDR_C45 | devad << MII_DEVADDR_C45_SHIFT | regnum; |
|---|
| 343 | +} |
|---|
| 344 | + |
|---|
| 345 | +static inline int __mdiobus_c45_read(struct mii_bus *bus, int prtad, int devad, |
|---|
| 346 | + u16 regnum) |
|---|
| 347 | +{ |
|---|
| 348 | + return __mdiobus_read(bus, prtad, mdiobus_c45_addr(devad, regnum)); |
|---|
| 349 | +} |
|---|
| 350 | + |
|---|
| 351 | +static inline int __mdiobus_c45_write(struct mii_bus *bus, int prtad, int devad, |
|---|
| 352 | + u16 regnum, u16 val) |
|---|
| 353 | +{ |
|---|
| 354 | + return __mdiobus_write(bus, prtad, mdiobus_c45_addr(devad, regnum), |
|---|
| 355 | + val); |
|---|
| 356 | +} |
|---|
| 357 | + |
|---|
| 358 | +static inline int mdiobus_c45_read(struct mii_bus *bus, int prtad, int devad, |
|---|
| 359 | + u16 regnum) |
|---|
| 360 | +{ |
|---|
| 361 | + return mdiobus_read(bus, prtad, mdiobus_c45_addr(devad, regnum)); |
|---|
| 362 | +} |
|---|
| 363 | + |
|---|
| 364 | +static inline int mdiobus_c45_write(struct mii_bus *bus, int prtad, int devad, |
|---|
| 365 | + u16 regnum, u16 val) |
|---|
| 366 | +{ |
|---|
| 367 | + return mdiobus_write(bus, prtad, mdiobus_c45_addr(devad, regnum), val); |
|---|
| 368 | +} |
|---|
| 274 | 369 | |
|---|
| 275 | 370 | int mdiobus_register_device(struct mdio_device *mdiodev); |
|---|
| 276 | 371 | int mdiobus_unregister_device(struct mdio_device *mdiodev); |
|---|
| .. | .. |
|---|
| 279 | 374 | |
|---|
| 280 | 375 | /** |
|---|
| 281 | 376 | * mdio_module_driver() - Helper macro for registering mdio drivers |
|---|
| 377 | + * @_mdio_driver: driver to register |
|---|
| 282 | 378 | * |
|---|
| 283 | 379 | * Helper macro for MDIO drivers which do not do anything special in module |
|---|
| 284 | 380 | * init/exit. Each module may only use this macro once, and calling it |
|---|