1 // SPDX-License-Identifier: GPL-2.0 2 /* Renesas Ethernet SERDES device driver 3 * 4 * Copyright (C) 2022-2025 Renesas Electronics Corporation 5 */ 6 7 #include <linux/delay.h> 8 #include <linux/err.h> 9 #include <linux/iopoll.h> 10 #include <linux/kernel.h> 11 #include <linux/of.h> 12 #include <linux/phy.h> 13 #include <linux/phy/phy.h> 14 #include <linux/platform_device.h> 15 #include <linux/reset.h> 16 17 #define R8A779F0_ETH_SERDES_NUM 3 18 #define R8A779F0_ETH_SERDES_OFFSET 0x0400 19 #define R8A779F0_ETH_SERDES_BANK_SELECT 0x03fc 20 #define R8A779F0_ETH_SERDES_TIMEOUT_US 100000 21 #define R8A779F0_ETH_SERDES_NUM_RETRY_LINKUP 3 22 23 struct r8a779f0_eth_serdes_drv_data; 24 struct r8a779f0_eth_serdes_channel { 25 struct r8a779f0_eth_serdes_drv_data *dd; 26 struct phy *phy; 27 void __iomem *addr; 28 phy_interface_t phy_interface; 29 int speed; 30 int index; 31 }; 32 33 struct r8a779f0_eth_serdes_drv_data { 34 void __iomem *addr; 35 struct platform_device *pdev; 36 struct reset_control *reset; 37 struct r8a779f0_eth_serdes_channel channel[R8A779F0_ETH_SERDES_NUM]; 38 bool initialized; 39 }; 40 41 /* 42 * The datasheet describes initialization procedure without any information 43 * about registers' name/bits. So, this is all black magic to initialize 44 * the hardware. 45 */ 46 static void r8a779f0_eth_serdes_write32(void __iomem *addr, u32 offs, u32 bank, u32 data) 47 { 48 iowrite32(bank, addr + R8A779F0_ETH_SERDES_BANK_SELECT); 49 iowrite32(data, addr + offs); 50 } 51 52 static u32 r8a779f0_eth_serdes_read32(void __iomem *addr, u32 offs, u32 bank) 53 { 54 iowrite32(bank, addr + R8A779F0_ETH_SERDES_BANK_SELECT); 55 56 return ioread32(addr + offs); 57 } 58 59 static int 60 r8a779f0_eth_serdes_reg_wait(struct r8a779f0_eth_serdes_channel *channel, 61 u32 offs, u32 bank, u32 mask, u32 expected) 62 { 63 int ret; 64 u32 val; 65 66 iowrite32(bank, channel->addr + R8A779F0_ETH_SERDES_BANK_SELECT); 67 68 ret = readl_poll_timeout_atomic(channel->addr + offs, val, 69 (val & mask) == expected, 70 1, R8A779F0_ETH_SERDES_TIMEOUT_US); 71 if (ret) 72 dev_dbg(&channel->phy->dev, 73 "%s: index %d, offs %x, bank %x, mask %x, expected %x\n", 74 __func__, channel->index, offs, bank, mask, expected); 75 76 return ret; 77 } 78 79 static int 80 r8a779f0_eth_serdes_common_init_ram(struct r8a779f0_eth_serdes_drv_data *dd) 81 { 82 struct r8a779f0_eth_serdes_channel *channel; 83 int i, ret; 84 85 for (i = 0; i < R8A779F0_ETH_SERDES_NUM; i++) { 86 channel = &dd->channel[i]; 87 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x026c, 0x180, BIT(0), 0x01); 88 if (ret) 89 return ret; 90 } 91 92 r8a779f0_eth_serdes_write32(dd->addr, 0x026c, 0x180, 0x03); 93 94 return ret; 95 } 96 97 static int 98 r8a779f0_eth_serdes_common_setting(struct r8a779f0_eth_serdes_channel *channel) 99 { 100 struct r8a779f0_eth_serdes_drv_data *dd = channel->dd; 101 102 /* Set combination mode */ 103 r8a779f0_eth_serdes_write32(dd->addr, 0x0244, 0x180, 0x00d7); 104 r8a779f0_eth_serdes_write32(dd->addr, 0x01cc, 0x180, 0xc200); 105 r8a779f0_eth_serdes_write32(dd->addr, 0x01c4, 0x180, 0x0042); 106 r8a779f0_eth_serdes_write32(dd->addr, 0x01c8, 0x180, 0x0000); 107 r8a779f0_eth_serdes_write32(dd->addr, 0x01dc, 0x180, 0x002f); 108 r8a779f0_eth_serdes_write32(dd->addr, 0x01d0, 0x180, 0x0060); 109 r8a779f0_eth_serdes_write32(dd->addr, 0x01d8, 0x180, 0x2200); 110 r8a779f0_eth_serdes_write32(dd->addr, 0x01d4, 0x180, 0x0000); 111 r8a779f0_eth_serdes_write32(dd->addr, 0x01e0, 0x180, 0x003d); 112 113 return 0; 114 } 115 116 static int 117 r8a779f0_eth_serdes_chan_setting(struct r8a779f0_eth_serdes_channel *channel) 118 { 119 int ret; 120 121 switch (channel->phy_interface) { 122 case PHY_INTERFACE_MODE_SGMII: 123 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x380, 0x2000); 124 r8a779f0_eth_serdes_write32(channel->addr, 0x01c0, 0x180, 0x0011); 125 r8a779f0_eth_serdes_write32(channel->addr, 0x0248, 0x180, 0x0540); 126 r8a779f0_eth_serdes_write32(channel->addr, 0x0258, 0x180, 0x0015); 127 r8a779f0_eth_serdes_write32(channel->addr, 0x0144, 0x180, 0x0100); 128 r8a779f0_eth_serdes_write32(channel->addr, 0x01a0, 0x180, 0x0000); 129 r8a779f0_eth_serdes_write32(channel->addr, 0x00d0, 0x180, 0x0002); 130 r8a779f0_eth_serdes_write32(channel->addr, 0x0150, 0x180, 0x0003); 131 r8a779f0_eth_serdes_write32(channel->addr, 0x00c8, 0x180, 0x0100); 132 r8a779f0_eth_serdes_write32(channel->addr, 0x0148, 0x180, 0x0100); 133 r8a779f0_eth_serdes_write32(channel->addr, 0x0174, 0x180, 0x0000); 134 r8a779f0_eth_serdes_write32(channel->addr, 0x0160, 0x180, 0x0007); 135 r8a779f0_eth_serdes_write32(channel->addr, 0x01ac, 0x180, 0x0000); 136 r8a779f0_eth_serdes_write32(channel->addr, 0x00c4, 0x180, 0x0310); 137 r8a779f0_eth_serdes_write32(channel->addr, 0x00c8, 0x180, 0x0101); 138 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x00c8, 0x0180, BIT(0), 0); 139 if (ret) 140 return ret; 141 142 r8a779f0_eth_serdes_write32(channel->addr, 0x0148, 0x180, 0x0101); 143 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0148, 0x0180, BIT(0), 0); 144 if (ret) 145 return ret; 146 147 r8a779f0_eth_serdes_write32(channel->addr, 0x00c4, 0x180, 0x1310); 148 r8a779f0_eth_serdes_write32(channel->addr, 0x00d8, 0x180, 0x1800); 149 r8a779f0_eth_serdes_write32(channel->addr, 0x00dc, 0x180, 0x0000); 150 r8a779f0_eth_serdes_write32(channel->addr, 0x001c, 0x300, 0x0001); 151 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x380, 0x2100); 152 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0000, 0x0380, BIT(8), 0); 153 if (ret) 154 return ret; 155 156 if (channel->speed == 1000) 157 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x1f00, 0x0140); 158 else if (channel->speed == 100) 159 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x1f00, 0x2100); 160 161 /* For AN_ON */ 162 r8a779f0_eth_serdes_write32(channel->addr, 0x0004, 0x1f80, 0x0005); 163 r8a779f0_eth_serdes_write32(channel->addr, 0x0028, 0x1f80, 0x07a1); 164 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x1f80, 0x0208); 165 break; 166 167 case PHY_INTERFACE_MODE_USXGMII: 168 r8a779f0_eth_serdes_write32(channel->addr, 0x001c, 0x300, 0x0000); 169 r8a779f0_eth_serdes_write32(channel->addr, 0x0014, 0x380, 0x0050); 170 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x380, 0x2200); 171 r8a779f0_eth_serdes_write32(channel->addr, 0x001c, 0x380, 0x0400); 172 r8a779f0_eth_serdes_write32(channel->addr, 0x01c0, 0x180, 0x0001); 173 r8a779f0_eth_serdes_write32(channel->addr, 0x0248, 0x180, 0x056a); 174 r8a779f0_eth_serdes_write32(channel->addr, 0x0258, 0x180, 0x0015); 175 r8a779f0_eth_serdes_write32(channel->addr, 0x0144, 0x180, 0x1100); 176 r8a779f0_eth_serdes_write32(channel->addr, 0x01a0, 0x180, 0x0001); 177 r8a779f0_eth_serdes_write32(channel->addr, 0x00d0, 0x180, 0x0001); 178 r8a779f0_eth_serdes_write32(channel->addr, 0x0150, 0x180, 0x0001); 179 r8a779f0_eth_serdes_write32(channel->addr, 0x00c8, 0x180, 0x0300); 180 r8a779f0_eth_serdes_write32(channel->addr, 0x0148, 0x180, 0x0300); 181 r8a779f0_eth_serdes_write32(channel->addr, 0x0174, 0x180, 0x0000); 182 r8a779f0_eth_serdes_write32(channel->addr, 0x0160, 0x180, 0x0004); 183 r8a779f0_eth_serdes_write32(channel->addr, 0x01ac, 0x180, 0x0000); 184 r8a779f0_eth_serdes_write32(channel->addr, 0x00c4, 0x180, 0x0310); 185 r8a779f0_eth_serdes_write32(channel->addr, 0x00c8, 0x180, 0x0301); 186 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x00c8, 0x180, BIT(0), 0); 187 if (ret) 188 return ret; 189 r8a779f0_eth_serdes_write32(channel->addr, 0x0148, 0x180, 0x0301); 190 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0148, 0x180, BIT(0), 0); 191 if (ret) 192 return ret; 193 r8a779f0_eth_serdes_write32(channel->addr, 0x00c4, 0x180, 0x1310); 194 r8a779f0_eth_serdes_write32(channel->addr, 0x00d8, 0x180, 0x1800); 195 r8a779f0_eth_serdes_write32(channel->addr, 0x00dc, 0x180, 0x0000); 196 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x380, 0x2300); 197 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0000, 0x380, BIT(8), 0); 198 if (ret) 199 return ret; 200 break; 201 202 default: 203 return -EOPNOTSUPP; 204 } 205 206 return 0; 207 } 208 209 static int 210 r8a779f0_eth_serdes_chan_speed(struct r8a779f0_eth_serdes_channel *channel) 211 { 212 int ret; 213 214 switch (channel->phy_interface) { 215 case PHY_INTERFACE_MODE_SGMII: 216 /* For AN_ON */ 217 if (channel->speed == 1000) 218 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x1f00, 0x1140); 219 else if (channel->speed == 100) 220 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x1f00, 0x3100); 221 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0008, 0x1f80, BIT(0), 1); 222 if (ret) 223 return ret; 224 r8a779f0_eth_serdes_write32(channel->addr, 0x0008, 0x1f80, 0x0000); 225 break; 226 case PHY_INTERFACE_MODE_USXGMII: 227 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x1f00, 0x0120); 228 usleep_range(10, 20); 229 r8a779f0_eth_serdes_write32(channel->addr, 0x0000, 0x380, 0x2600); 230 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0000, 0x380, BIT(10), 0); 231 if (ret) 232 return ret; 233 break; 234 default: 235 return -EOPNOTSUPP; 236 } 237 238 return 0; 239 } 240 241 242 static int r8a779f0_eth_serdes_monitor_linkup(struct r8a779f0_eth_serdes_channel *channel) 243 { 244 int i, ret; 245 246 for (i = 0; i < R8A779F0_ETH_SERDES_NUM_RETRY_LINKUP; i++) { 247 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0004, 0x300, 248 BIT(2), BIT(2)); 249 if (!ret) 250 break; 251 252 /* restart */ 253 r8a779f0_eth_serdes_write32(channel->addr, 0x0144, 0x180, 0x0100); 254 udelay(1); 255 r8a779f0_eth_serdes_write32(channel->addr, 0x0144, 0x180, 0x0000); 256 } 257 258 return ret; 259 } 260 261 static int r8a779f0_eth_serdes_hw_init(struct r8a779f0_eth_serdes_channel *channel) 262 { 263 struct r8a779f0_eth_serdes_drv_data *dd = channel->dd; 264 int i, ret; 265 266 if (dd->initialized) 267 return 0; 268 269 reset_control_reset(dd->reset); 270 271 usleep_range(1000, 2000); 272 273 ret = r8a779f0_eth_serdes_common_init_ram(dd); 274 if (ret) 275 return ret; 276 277 for (i = 0; i < R8A779F0_ETH_SERDES_NUM; i++) { 278 ret = r8a779f0_eth_serdes_reg_wait(&dd->channel[i], 0x0000, 279 0x300, BIT(15), 0); 280 if (ret) 281 return ret; 282 } 283 284 for (i = 0; i < R8A779F0_ETH_SERDES_NUM; i++) 285 r8a779f0_eth_serdes_write32(dd->channel[i].addr, 0x03d4, 0x380, 0x0443); 286 287 ret = r8a779f0_eth_serdes_common_setting(channel); 288 if (ret) 289 return ret; 290 291 for (i = 0; i < R8A779F0_ETH_SERDES_NUM; i++) 292 r8a779f0_eth_serdes_write32(dd->channel[i].addr, 0x03d0, 0x380, 0x0001); 293 294 295 r8a779f0_eth_serdes_write32(dd->addr, 0x0000, 0x380, 0x8000); 296 297 ret = r8a779f0_eth_serdes_common_init_ram(dd); 298 if (ret) 299 return ret; 300 301 return r8a779f0_eth_serdes_reg_wait(&dd->channel[0], 0x0000, 0x380, BIT(15), 0); 302 } 303 304 static int r8a779f0_eth_serdes_init(struct phy *p) 305 { 306 struct r8a779f0_eth_serdes_channel *channel = phy_get_drvdata(p); 307 int ret; 308 309 ret = r8a779f0_eth_serdes_hw_init(channel); 310 if (!ret) 311 channel->dd->initialized = true; 312 313 return ret; 314 } 315 316 static int r8a779f0_eth_serdes_exit(struct phy *p) 317 { 318 struct r8a779f0_eth_serdes_channel *channel = phy_get_drvdata(p); 319 320 channel->dd->initialized = false; 321 322 return 0; 323 } 324 325 static int r8a779f0_eth_serdes_hw_init_late(struct r8a779f0_eth_serdes_channel 326 *channel) 327 { 328 int ret; 329 u32 val; 330 331 ret = r8a779f0_eth_serdes_chan_setting(channel); 332 if (ret) 333 return ret; 334 335 ret = r8a779f0_eth_serdes_chan_speed(channel); 336 if (ret) 337 return ret; 338 339 r8a779f0_eth_serdes_write32(channel->addr, 0x03c0, 0x380, 0x0000); 340 341 r8a779f0_eth_serdes_write32(channel->addr, 0x03d0, 0x380, 0x0000); 342 343 val = r8a779f0_eth_serdes_read32(channel->addr, 0x00c0, 0x180); 344 r8a779f0_eth_serdes_write32(channel->addr, 0x00c0, 0x180, val | BIT(8)); 345 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0100, 0x180, BIT(0), 1); 346 if (ret) 347 return ret; 348 r8a779f0_eth_serdes_write32(channel->addr, 0x00c0, 0x180, val & ~BIT(8)); 349 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0100, 0x180, BIT(0), 0); 350 if (ret) 351 return ret; 352 353 val = r8a779f0_eth_serdes_read32(channel->addr, 0x0144, 0x180); 354 r8a779f0_eth_serdes_write32(channel->addr, 0x0144, 0x180, val | BIT(4)); 355 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0180, 0x180, BIT(0), 1); 356 if (ret) 357 return ret; 358 r8a779f0_eth_serdes_write32(channel->addr, 0x0144, 0x180, val & ~BIT(4)); 359 ret = r8a779f0_eth_serdes_reg_wait(channel, 0x0180, 0x180, BIT(0), 0); 360 if (ret) 361 return ret; 362 363 return r8a779f0_eth_serdes_monitor_linkup(channel); 364 } 365 366 static int r8a779f0_eth_serdes_power_on(struct phy *p) 367 { 368 struct r8a779f0_eth_serdes_channel *channel = phy_get_drvdata(p); 369 370 return r8a779f0_eth_serdes_hw_init_late(channel); 371 } 372 373 static int r8a779f0_eth_serdes_set_mode(struct phy *p, enum phy_mode mode, 374 int submode) 375 { 376 struct r8a779f0_eth_serdes_channel *channel = phy_get_drvdata(p); 377 378 if (mode != PHY_MODE_ETHERNET) 379 return -EOPNOTSUPP; 380 381 switch (submode) { 382 case PHY_INTERFACE_MODE_GMII: 383 case PHY_INTERFACE_MODE_SGMII: 384 case PHY_INTERFACE_MODE_USXGMII: 385 channel->phy_interface = submode; 386 return 0; 387 default: 388 return -EOPNOTSUPP; 389 } 390 } 391 392 static int r8a779f0_eth_serdes_set_speed(struct phy *p, int speed) 393 { 394 struct r8a779f0_eth_serdes_channel *channel = phy_get_drvdata(p); 395 396 channel->speed = speed; 397 398 return 0; 399 } 400 401 static const struct phy_ops r8a779f0_eth_serdes_ops = { 402 .init = r8a779f0_eth_serdes_init, 403 .exit = r8a779f0_eth_serdes_exit, 404 .power_on = r8a779f0_eth_serdes_power_on, 405 .set_mode = r8a779f0_eth_serdes_set_mode, 406 .set_speed = r8a779f0_eth_serdes_set_speed, 407 }; 408 409 static struct phy *r8a779f0_eth_serdes_xlate(struct device *dev, 410 const struct of_phandle_args *args) 411 { 412 struct r8a779f0_eth_serdes_drv_data *dd = dev_get_drvdata(dev); 413 414 if (args->args[0] >= R8A779F0_ETH_SERDES_NUM) 415 return ERR_PTR(-ENODEV); 416 417 return dd->channel[args->args[0]].phy; 418 } 419 420 static const struct of_device_id r8a779f0_eth_serdes_of_table[] = { 421 { .compatible = "renesas,r8a779f0-ether-serdes", }, 422 { } 423 }; 424 MODULE_DEVICE_TABLE(of, r8a779f0_eth_serdes_of_table); 425 426 static int r8a779f0_eth_serdes_probe(struct platform_device *pdev) 427 { 428 struct r8a779f0_eth_serdes_drv_data *dd; 429 struct phy_provider *provider; 430 int i; 431 432 dd = devm_kzalloc(&pdev->dev, sizeof(*dd), GFP_KERNEL); 433 if (!dd) 434 return -ENOMEM; 435 436 platform_set_drvdata(pdev, dd); 437 dd->pdev = pdev; 438 dd->addr = devm_platform_ioremap_resource(pdev, 0); 439 if (IS_ERR(dd->addr)) 440 return PTR_ERR(dd->addr); 441 442 dd->reset = devm_reset_control_get(&pdev->dev, NULL); 443 if (IS_ERR(dd->reset)) 444 return PTR_ERR(dd->reset); 445 446 for (i = 0; i < R8A779F0_ETH_SERDES_NUM; i++) { 447 struct r8a779f0_eth_serdes_channel *channel = &dd->channel[i]; 448 449 channel->phy = devm_phy_create(&pdev->dev, NULL, 450 &r8a779f0_eth_serdes_ops); 451 if (IS_ERR(channel->phy)) 452 return PTR_ERR(channel->phy); 453 channel->addr = dd->addr + R8A779F0_ETH_SERDES_OFFSET * i; 454 channel->dd = dd; 455 channel->index = i; 456 phy_set_drvdata(channel->phy, channel); 457 } 458 459 provider = devm_of_phy_provider_register(&pdev->dev, 460 r8a779f0_eth_serdes_xlate); 461 if (IS_ERR(provider)) 462 return PTR_ERR(provider); 463 464 pm_runtime_enable(&pdev->dev); 465 pm_runtime_get_sync(&pdev->dev); 466 467 return 0; 468 } 469 470 static void r8a779f0_eth_serdes_remove(struct platform_device *pdev) 471 { 472 pm_runtime_put(&pdev->dev); 473 pm_runtime_disable(&pdev->dev); 474 475 platform_set_drvdata(pdev, NULL); 476 } 477 478 static struct platform_driver r8a779f0_eth_serdes_driver_platform = { 479 .probe = r8a779f0_eth_serdes_probe, 480 .remove = r8a779f0_eth_serdes_remove, 481 .driver = { 482 .name = "r8a779f0_eth_serdes", 483 .of_match_table = r8a779f0_eth_serdes_of_table, 484 } 485 }; 486 module_platform_driver(r8a779f0_eth_serdes_driver_platform); 487 MODULE_AUTHOR("Yoshihiro Shimoda"); 488 MODULE_DESCRIPTION("Renesas Ethernet SERDES device driver"); 489 MODULE_LICENSE("GPL"); 490