1 /* 2 * Marvell PHY drivers 3 * 4 * SPDX-License-Identifier: GPL-2.0+ 5 * 6 * Copyright 2010-2011 Freescale Semiconductor, Inc. 7 * author Andy Fleming 8 */ 9 #include <config.h> 10 #include <common.h> 11 #include <phy.h> 12 13 #define PHY_AUTONEGOTIATE_TIMEOUT 5000 14 15 /* 88E1011 PHY Status Register */ 16 #define MIIM_88E1xxx_PHY_STATUS 0x11 17 #define MIIM_88E1xxx_PHYSTAT_SPEED 0xc000 18 #define MIIM_88E1xxx_PHYSTAT_GBIT 0x8000 19 #define MIIM_88E1xxx_PHYSTAT_100 0x4000 20 #define MIIM_88E1xxx_PHYSTAT_DUPLEX 0x2000 21 #define MIIM_88E1xxx_PHYSTAT_SPDDONE 0x0800 22 #define MIIM_88E1xxx_PHYSTAT_LINK 0x0400 23 24 #define MIIM_88E1xxx_PHY_SCR 0x10 25 #define MIIM_88E1xxx_PHY_MDI_X_AUTO 0x0060 26 27 /* 88E1111 PHY LED Control Register */ 28 #define MIIM_88E1111_PHY_LED_CONTROL 24 29 #define MIIM_88E1111_PHY_LED_DIRECT 0x4100 30 #define MIIM_88E1111_PHY_LED_COMBINE 0x411C 31 32 /* 88E1111 Extended PHY Specific Control Register */ 33 #define MIIM_88E1111_PHY_EXT_CR 0x14 34 #define MIIM_88E1111_RX_DELAY 0x80 35 #define MIIM_88E1111_TX_DELAY 0x2 36 37 /* 88E1111 Extended PHY Specific Status Register */ 38 #define MIIM_88E1111_PHY_EXT_SR 0x1b 39 #define MIIM_88E1111_HWCFG_MODE_MASK 0xf 40 #define MIIM_88E1111_HWCFG_MODE_COPPER_RGMII 0xb 41 #define MIIM_88E1111_HWCFG_MODE_FIBER_RGMII 0x3 42 #define MIIM_88E1111_HWCFG_MODE_SGMII_NO_CLK 0x4 43 #define MIIM_88E1111_HWCFG_MODE_COPPER_RTBI 0x9 44 #define MIIM_88E1111_HWCFG_FIBER_COPPER_AUTO 0x8000 45 #define MIIM_88E1111_HWCFG_FIBER_COPPER_RES 0x2000 46 47 #define MIIM_88E1111_COPPER 0 48 #define MIIM_88E1111_FIBER 1 49 50 /* 88E1118 PHY defines */ 51 #define MIIM_88E1118_PHY_PAGE 22 52 #define MIIM_88E1118_PHY_LED_PAGE 3 53 54 /* 88E1121 PHY LED Control Register */ 55 #define MIIM_88E1121_PHY_LED_CTRL 16 56 #define MIIM_88E1121_PHY_LED_PAGE 3 57 #define MIIM_88E1121_PHY_LED_DEF 0x0030 58 59 /* 88E1121 PHY IRQ Enable/Status Register */ 60 #define MIIM_88E1121_PHY_IRQ_EN 18 61 #define MIIM_88E1121_PHY_IRQ_STATUS 19 62 63 #define MIIM_88E1121_PHY_PAGE 22 64 65 /* 88E1145 Extended PHY Specific Control Register */ 66 #define MIIM_88E1145_PHY_EXT_CR 20 67 #define MIIM_M88E1145_RGMII_RX_DELAY 0x0080 68 #define MIIM_M88E1145_RGMII_TX_DELAY 0x0002 69 70 #define MIIM_88E1145_PHY_LED_CONTROL 24 71 #define MIIM_88E1145_PHY_LED_DIRECT 0x4100 72 73 #define MIIM_88E1145_PHY_PAGE 29 74 #define MIIM_88E1145_PHY_CAL_OV 30 75 76 #define MIIM_88E1149_PHY_PAGE 29 77 78 /* 88E1310 PHY defines */ 79 #define MIIM_88E1310_PHY_LED_CTRL 16 80 #define MIIM_88E1310_PHY_IRQ_EN 18 81 #define MIIM_88E1310_PHY_RGMII_CTRL 21 82 #define MIIM_88E1310_PHY_PAGE 22 83 84 /* Marvell 88E1011S */ 85 static int m88e1011s_config(struct phy_device *phydev) 86 { 87 /* Reset and configure the PHY */ 88 phy_write(phydev, MDIO_DEVAD_NONE, MII_BMCR, BMCR_RESET); 89 90 phy_write(phydev, MDIO_DEVAD_NONE, 0x1d, 0x1f); 91 phy_write(phydev, MDIO_DEVAD_NONE, 0x1e, 0x200c); 92 phy_write(phydev, MDIO_DEVAD_NONE, 0x1d, 0x5); 93 phy_write(phydev, MDIO_DEVAD_NONE, 0x1e, 0); 94 phy_write(phydev, MDIO_DEVAD_NONE, 0x1e, 0x100); 95 96 phy_write(phydev, MDIO_DEVAD_NONE, MII_BMCR, BMCR_RESET); 97 98 genphy_config_aneg(phydev); 99 100 return 0; 101 } 102 103 /* Parse the 88E1011's status register for speed and duplex 104 * information 105 */ 106 static uint m88e1xxx_parse_status(struct phy_device *phydev) 107 { 108 unsigned int speed; 109 unsigned int mii_reg; 110 111 mii_reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_88E1xxx_PHY_STATUS); 112 113 if ((mii_reg & MIIM_88E1xxx_PHYSTAT_LINK) && 114 !(mii_reg & MIIM_88E1xxx_PHYSTAT_SPDDONE)) { 115 int i = 0; 116 117 puts("Waiting for PHY realtime link"); 118 while (!(mii_reg & MIIM_88E1xxx_PHYSTAT_SPDDONE)) { 119 /* Timeout reached ? */ 120 if (i > PHY_AUTONEGOTIATE_TIMEOUT) { 121 puts(" TIMEOUT !\n"); 122 phydev->link = 0; 123 break; 124 } 125 126 if ((i++ % 1000) == 0) 127 putc('.'); 128 udelay(1000); 129 mii_reg = phy_read(phydev, MDIO_DEVAD_NONE, 130 MIIM_88E1xxx_PHY_STATUS); 131 } 132 puts(" done\n"); 133 udelay(500000); /* another 500 ms (results in faster booting) */ 134 } else { 135 if (mii_reg & MIIM_88E1xxx_PHYSTAT_LINK) 136 phydev->link = 1; 137 else 138 phydev->link = 0; 139 } 140 141 if (mii_reg & MIIM_88E1xxx_PHYSTAT_DUPLEX) 142 phydev->duplex = DUPLEX_FULL; 143 else 144 phydev->duplex = DUPLEX_HALF; 145 146 speed = mii_reg & MIIM_88E1xxx_PHYSTAT_SPEED; 147 148 switch (speed) { 149 case MIIM_88E1xxx_PHYSTAT_GBIT: 150 phydev->speed = SPEED_1000; 151 break; 152 case MIIM_88E1xxx_PHYSTAT_100: 153 phydev->speed = SPEED_100; 154 break; 155 default: 156 phydev->speed = SPEED_10; 157 break; 158 } 159 160 return 0; 161 } 162 163 static int m88e1011s_startup(struct phy_device *phydev) 164 { 165 genphy_update_link(phydev); 166 m88e1xxx_parse_status(phydev); 167 168 return 0; 169 } 170 171 /* Marvell 88E1111S */ 172 static int m88e1111s_config(struct phy_device *phydev) 173 { 174 int reg; 175 int timeout; 176 177 if ((phydev->interface == PHY_INTERFACE_MODE_RGMII) || 178 (phydev->interface == PHY_INTERFACE_MODE_RGMII_ID) || 179 (phydev->interface == PHY_INTERFACE_MODE_RGMII_RXID) || 180 (phydev->interface == PHY_INTERFACE_MODE_RGMII_TXID)) { 181 reg = phy_read(phydev, 182 MDIO_DEVAD_NONE, MIIM_88E1111_PHY_EXT_CR); 183 if ((phydev->interface == PHY_INTERFACE_MODE_RGMII) || 184 (phydev->interface == PHY_INTERFACE_MODE_RGMII_ID)) { 185 reg |= (MIIM_88E1111_RX_DELAY | MIIM_88E1111_TX_DELAY); 186 } else if (phydev->interface == PHY_INTERFACE_MODE_RGMII_RXID) { 187 reg &= ~MIIM_88E1111_TX_DELAY; 188 reg |= MIIM_88E1111_RX_DELAY; 189 } else if (phydev->interface == PHY_INTERFACE_MODE_RGMII_TXID) { 190 reg &= ~MIIM_88E1111_RX_DELAY; 191 reg |= MIIM_88E1111_TX_DELAY; 192 } 193 194 phy_write(phydev, 195 MDIO_DEVAD_NONE, MIIM_88E1111_PHY_EXT_CR, reg); 196 197 reg = phy_read(phydev, 198 MDIO_DEVAD_NONE, MIIM_88E1111_PHY_EXT_SR); 199 200 reg &= ~(MIIM_88E1111_HWCFG_MODE_MASK); 201 202 if (reg & MIIM_88E1111_HWCFG_FIBER_COPPER_RES) 203 reg |= MIIM_88E1111_HWCFG_MODE_FIBER_RGMII; 204 else 205 reg |= MIIM_88E1111_HWCFG_MODE_COPPER_RGMII; 206 207 phy_write(phydev, 208 MDIO_DEVAD_NONE, MIIM_88E1111_PHY_EXT_SR, reg); 209 } 210 211 if (phydev->interface == PHY_INTERFACE_MODE_SGMII) { 212 reg = phy_read(phydev, 213 MDIO_DEVAD_NONE, MIIM_88E1111_PHY_EXT_SR); 214 215 reg &= ~(MIIM_88E1111_HWCFG_MODE_MASK); 216 reg |= MIIM_88E1111_HWCFG_MODE_SGMII_NO_CLK; 217 reg |= MIIM_88E1111_HWCFG_FIBER_COPPER_AUTO; 218 219 phy_write(phydev, MDIO_DEVAD_NONE, 220 MIIM_88E1111_PHY_EXT_SR, reg); 221 } 222 223 if (phydev->interface == PHY_INTERFACE_MODE_RTBI) { 224 reg = phy_read(phydev, 225 MDIO_DEVAD_NONE, MIIM_88E1111_PHY_EXT_CR); 226 reg |= (MIIM_88E1111_RX_DELAY | MIIM_88E1111_TX_DELAY); 227 phy_write(phydev, 228 MDIO_DEVAD_NONE, MIIM_88E1111_PHY_EXT_CR, reg); 229 230 reg = phy_read(phydev, MDIO_DEVAD_NONE, 231 MIIM_88E1111_PHY_EXT_SR); 232 reg &= ~(MIIM_88E1111_HWCFG_MODE_MASK | 233 MIIM_88E1111_HWCFG_FIBER_COPPER_RES); 234 reg |= 0x7 | MIIM_88E1111_HWCFG_FIBER_COPPER_AUTO; 235 phy_write(phydev, MDIO_DEVAD_NONE, 236 MIIM_88E1111_PHY_EXT_SR, reg); 237 238 /* soft reset */ 239 timeout = 1000; 240 phy_write(phydev, MDIO_DEVAD_NONE, MII_BMCR, BMCR_RESET); 241 udelay(1000); 242 reg = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR); 243 while ((reg & BMCR_RESET) && --timeout) { 244 udelay(1000); 245 reg = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR); 246 } 247 if (!timeout) 248 printf("%s: phy soft reset timeout\n", __func__); 249 250 reg = phy_read(phydev, MDIO_DEVAD_NONE, 251 MIIM_88E1111_PHY_EXT_SR); 252 reg &= ~(MIIM_88E1111_HWCFG_MODE_MASK | 253 MIIM_88E1111_HWCFG_FIBER_COPPER_RES); 254 reg |= MIIM_88E1111_HWCFG_MODE_COPPER_RTBI | 255 MIIM_88E1111_HWCFG_FIBER_COPPER_AUTO; 256 phy_write(phydev, MDIO_DEVAD_NONE, 257 MIIM_88E1111_PHY_EXT_SR, reg); 258 } 259 260 /* soft reset */ 261 timeout = 1000; 262 phy_write(phydev, MDIO_DEVAD_NONE, MII_BMCR, BMCR_RESET); 263 udelay(1000); 264 reg = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR); 265 while ((reg & BMCR_RESET) && --timeout) { 266 udelay(1000); 267 reg = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR); 268 } 269 if (!timeout) 270 printf("%s: phy soft reset timeout\n", __func__); 271 272 genphy_config_aneg(phydev); 273 274 phy_reset(phydev); 275 276 return 0; 277 } 278 279 /** 280 * m88e1518_phy_writebits - write bits to a register 281 */ 282 void m88e1518_phy_writebits(struct phy_device *phydev, 283 u8 reg_num, u16 offset, u16 len, u16 data) 284 { 285 u16 reg, mask; 286 287 if ((len + offset) >= 16) 288 mask = 0 - (1 << offset); 289 else 290 mask = (1 << (len + offset)) - (1 << offset); 291 292 reg = phy_read(phydev, MDIO_DEVAD_NONE, reg_num); 293 294 reg &= ~mask; 295 reg |= data << offset; 296 297 phy_write(phydev, MDIO_DEVAD_NONE, reg_num, reg); 298 } 299 300 static int m88e1518_config(struct phy_device *phydev) 301 { 302 /* 303 * As per Marvell Release Notes - Alaska 88E1510/88E1518/88E1512 304 * /88E1514 Rev A0, Errata Section 3.1 305 */ 306 if (phydev->interface == PHY_INTERFACE_MODE_SGMII) { 307 phy_write(phydev, MDIO_DEVAD_NONE, 22, 0x00ff); /* page 0xff */ 308 phy_write(phydev, MDIO_DEVAD_NONE, 17, 0x214B); 309 phy_write(phydev, MDIO_DEVAD_NONE, 16, 0x2144); 310 phy_write(phydev, MDIO_DEVAD_NONE, 17, 0x0C28); 311 phy_write(phydev, MDIO_DEVAD_NONE, 16, 0x2146); 312 phy_write(phydev, MDIO_DEVAD_NONE, 17, 0xB233); 313 phy_write(phydev, MDIO_DEVAD_NONE, 16, 0x214D); 314 phy_write(phydev, MDIO_DEVAD_NONE, 17, 0xCC0C); 315 phy_write(phydev, MDIO_DEVAD_NONE, 16, 0x2159); 316 phy_write(phydev, MDIO_DEVAD_NONE, 22, 0x0000); /* reg page 0 */ 317 phy_write(phydev, MDIO_DEVAD_NONE, 22, 18); /* reg page 18 */ 318 /* Write HWCFG_MODE = SGMII to Copper */ 319 m88e1518_phy_writebits(phydev, 20, 0, 3, 1); 320 321 /* Phy reset */ 322 m88e1518_phy_writebits(phydev, 20, 15, 1, 1); 323 phy_write(phydev, MDIO_DEVAD_NONE, 22, 0); /* reg page 18 */ 324 udelay(100); 325 } 326 327 return m88e1111s_config(phydev); 328 } 329 330 /* Marvell 88E1118 */ 331 static int m88e1118_config(struct phy_device *phydev) 332 { 333 /* Change Page Number */ 334 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1118_PHY_PAGE, 0x0002); 335 /* Delay RGMII TX and RX */ 336 phy_write(phydev, MDIO_DEVAD_NONE, 0x15, 0x1070); 337 /* Change Page Number */ 338 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1118_PHY_PAGE, 0x0003); 339 /* Adjust LED control */ 340 phy_write(phydev, MDIO_DEVAD_NONE, 0x10, 0x021e); 341 /* Change Page Number */ 342 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1118_PHY_PAGE, 0x0000); 343 344 genphy_config_aneg(phydev); 345 346 phy_reset(phydev); 347 348 return 0; 349 } 350 351 static int m88e1118_startup(struct phy_device *phydev) 352 { 353 /* Change Page Number */ 354 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1118_PHY_PAGE, 0x0000); 355 356 genphy_update_link(phydev); 357 m88e1xxx_parse_status(phydev); 358 359 return 0; 360 } 361 362 /* Marvell 88E1121R */ 363 static int m88e1121_config(struct phy_device *phydev) 364 { 365 int pg; 366 367 /* Configure the PHY */ 368 genphy_config_aneg(phydev); 369 370 /* Switch the page to access the led register */ 371 pg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_88E1121_PHY_PAGE); 372 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1121_PHY_PAGE, 373 MIIM_88E1121_PHY_LED_PAGE); 374 /* Configure leds */ 375 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1121_PHY_LED_CTRL, 376 MIIM_88E1121_PHY_LED_DEF); 377 /* Restore the page pointer */ 378 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1121_PHY_PAGE, pg); 379 380 /* Disable IRQs and de-assert interrupt */ 381 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1121_PHY_IRQ_EN, 0); 382 phy_read(phydev, MDIO_DEVAD_NONE, MIIM_88E1121_PHY_IRQ_STATUS); 383 384 return 0; 385 } 386 387 /* Marvell 88E1145 */ 388 static int m88e1145_config(struct phy_device *phydev) 389 { 390 int reg; 391 392 /* Errata E0, E1 */ 393 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1145_PHY_PAGE, 0x001b); 394 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1145_PHY_CAL_OV, 0x418f); 395 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1145_PHY_PAGE, 0x0016); 396 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1145_PHY_CAL_OV, 0xa2da); 397 398 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1xxx_PHY_SCR, 399 MIIM_88E1xxx_PHY_MDI_X_AUTO); 400 401 reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_88E1145_PHY_EXT_CR); 402 if (phydev->interface == PHY_INTERFACE_MODE_RGMII_ID) 403 reg |= MIIM_M88E1145_RGMII_RX_DELAY | 404 MIIM_M88E1145_RGMII_TX_DELAY; 405 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1145_PHY_EXT_CR, reg); 406 407 genphy_config_aneg(phydev); 408 409 phy_reset(phydev); 410 411 return 0; 412 } 413 414 static int m88e1145_startup(struct phy_device *phydev) 415 { 416 genphy_update_link(phydev); 417 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1145_PHY_LED_CONTROL, 418 MIIM_88E1145_PHY_LED_DIRECT); 419 m88e1xxx_parse_status(phydev); 420 421 return 0; 422 } 423 424 /* Marvell 88E1149S */ 425 static int m88e1149_config(struct phy_device *phydev) 426 { 427 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1149_PHY_PAGE, 0x1f); 428 phy_write(phydev, MDIO_DEVAD_NONE, 0x1e, 0x200c); 429 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1149_PHY_PAGE, 0x5); 430 phy_write(phydev, MDIO_DEVAD_NONE, 0x1e, 0x0); 431 phy_write(phydev, MDIO_DEVAD_NONE, 0x1e, 0x100); 432 433 genphy_config_aneg(phydev); 434 435 phy_reset(phydev); 436 437 return 0; 438 } 439 440 /* Marvell 88E1310 */ 441 static int m88e1310_config(struct phy_device *phydev) 442 { 443 u16 reg; 444 445 /* LED link and activity */ 446 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_PAGE, 0x0003); 447 reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_LED_CTRL); 448 reg = (reg & ~0xf) | 0x1; 449 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_LED_CTRL, reg); 450 451 /* Set LED2/INT to INT mode, low active */ 452 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_PAGE, 0x0003); 453 reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_IRQ_EN); 454 reg = (reg & 0x77ff) | 0x0880; 455 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_IRQ_EN, reg); 456 457 /* Set RGMII delay */ 458 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_PAGE, 0x0002); 459 reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_RGMII_CTRL); 460 reg |= 0x0030; 461 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_RGMII_CTRL, reg); 462 463 /* Ensure to return to page 0 */ 464 phy_write(phydev, MDIO_DEVAD_NONE, MIIM_88E1310_PHY_PAGE, 0x0000); 465 466 genphy_config_aneg(phydev); 467 phy_reset(phydev); 468 469 return 0; 470 } 471 472 static struct phy_driver M88E1011S_driver = { 473 .name = "Marvell 88E1011S", 474 .uid = 0x1410c60, 475 .mask = 0xffffff0, 476 .features = PHY_GBIT_FEATURES, 477 .config = &m88e1011s_config, 478 .startup = &m88e1011s_startup, 479 .shutdown = &genphy_shutdown, 480 }; 481 482 static struct phy_driver M88E1111S_driver = { 483 .name = "Marvell 88E1111S", 484 .uid = 0x1410cc0, 485 .mask = 0xffffff0, 486 .features = PHY_GBIT_FEATURES, 487 .config = &m88e1111s_config, 488 .startup = &m88e1011s_startup, 489 .shutdown = &genphy_shutdown, 490 }; 491 492 static struct phy_driver M88E1118_driver = { 493 .name = "Marvell 88E1118", 494 .uid = 0x1410e10, 495 .mask = 0xffffff0, 496 .features = PHY_GBIT_FEATURES, 497 .config = &m88e1118_config, 498 .startup = &m88e1118_startup, 499 .shutdown = &genphy_shutdown, 500 }; 501 502 static struct phy_driver M88E1118R_driver = { 503 .name = "Marvell 88E1118R", 504 .uid = 0x1410e40, 505 .mask = 0xffffff0, 506 .features = PHY_GBIT_FEATURES, 507 .config = &m88e1118_config, 508 .startup = &m88e1118_startup, 509 .shutdown = &genphy_shutdown, 510 }; 511 512 static struct phy_driver M88E1121R_driver = { 513 .name = "Marvell 88E1121R", 514 .uid = 0x1410cb0, 515 .mask = 0xffffff0, 516 .features = PHY_GBIT_FEATURES, 517 .config = &m88e1121_config, 518 .startup = &genphy_startup, 519 .shutdown = &genphy_shutdown, 520 }; 521 522 static struct phy_driver M88E1145_driver = { 523 .name = "Marvell 88E1145", 524 .uid = 0x1410cd0, 525 .mask = 0xffffff0, 526 .features = PHY_GBIT_FEATURES, 527 .config = &m88e1145_config, 528 .startup = &m88e1145_startup, 529 .shutdown = &genphy_shutdown, 530 }; 531 532 static struct phy_driver M88E1149S_driver = { 533 .name = "Marvell 88E1149S", 534 .uid = 0x1410ca0, 535 .mask = 0xffffff0, 536 .features = PHY_GBIT_FEATURES, 537 .config = &m88e1149_config, 538 .startup = &m88e1011s_startup, 539 .shutdown = &genphy_shutdown, 540 }; 541 542 static struct phy_driver M88E1518_driver = { 543 .name = "Marvell 88E1518", 544 .uid = 0x1410dd1, 545 .mask = 0xffffff0, 546 .features = PHY_GBIT_FEATURES, 547 .config = &m88e1518_config, 548 .startup = &m88e1011s_startup, 549 .shutdown = &genphy_shutdown, 550 }; 551 552 static struct phy_driver M88E1310_driver = { 553 .name = "Marvell 88E1310", 554 .uid = 0x01410e90, 555 .mask = 0xffffff0, 556 .features = PHY_GBIT_FEATURES, 557 .config = &m88e1310_config, 558 .startup = &m88e1011s_startup, 559 .shutdown = &genphy_shutdown, 560 }; 561 562 int phy_marvell_init(void) 563 { 564 phy_register(&M88E1310_driver); 565 phy_register(&M88E1149S_driver); 566 phy_register(&M88E1145_driver); 567 phy_register(&M88E1121R_driver); 568 phy_register(&M88E1118_driver); 569 phy_register(&M88E1118R_driver); 570 phy_register(&M88E1111S_driver); 571 phy_register(&M88E1011S_driver); 572 phy_register(&M88E1518_driver); 573 574 return 0; 575 } 576