1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * Rockchip USB3.0/PCIe Gen2/SATA/SGMII combphy driver 4 * 5 * Copyright (C) 2021 Rockchip Electronics Co., Ltd. 6 */ 7 8 #include <common.h> 9 #include <clk.h> 10 #include <dm.h> 11 #include <dm/lists.h> 12 #include <dt-bindings/phy/phy.h> 13 #include <generic-phy.h> 14 #include <syscon.h> 15 #include <asm/io.h> 16 #include <asm/arch/clock.h> 17 #include <regmap.h> 18 #include <reset-uclass.h> 19 20 #define BIT_WRITEABLE_SHIFT 16 21 22 struct rockchip_combphy_priv; 23 24 struct combphy_reg { 25 u32 offset; 26 u16 bitend; 27 u16 bitstart; 28 u16 disable; 29 u16 enable; 30 }; 31 32 struct rockchip_combphy_grfcfg { 33 struct combphy_reg pcie_mode_set; 34 struct combphy_reg usb_mode_set; 35 struct combphy_reg sgmii_mode_set; 36 struct combphy_reg qsgmii_mode_set; 37 struct combphy_reg pipe_rxterm_set; 38 struct combphy_reg pipe_txelec_set; 39 struct combphy_reg pipe_txcomp_set; 40 struct combphy_reg pipe_clk_24m; 41 struct combphy_reg pipe_clk_25m; 42 struct combphy_reg pipe_clk_100m; 43 struct combphy_reg pipe_phymode_sel; 44 struct combphy_reg pipe_rate_sel; 45 struct combphy_reg pipe_rxterm_sel; 46 struct combphy_reg pipe_txelec_sel; 47 struct combphy_reg pipe_txcomp_sel; 48 struct combphy_reg pipe_clk_ext; 49 struct combphy_reg pipe_sel_usb; 50 struct combphy_reg pipe_sel_qsgmii; 51 struct combphy_reg pipe_phy_status; 52 struct combphy_reg con0_for_pcie; 53 struct combphy_reg con1_for_pcie; 54 struct combphy_reg con2_for_pcie; 55 struct combphy_reg con3_for_pcie; 56 struct combphy_reg con0_for_sata; 57 struct combphy_reg con1_for_sata; 58 struct combphy_reg con2_for_sata; 59 struct combphy_reg con3_for_sata; 60 struct combphy_reg pipe_con0_for_sata; 61 struct combphy_reg pipe_con1_for_sata; 62 struct combphy_reg pipe_sgmii_mac_sel; 63 struct combphy_reg pipe_xpcs_phy_ready; 64 struct combphy_reg u3otg0_port_en; 65 struct combphy_reg u3otg1_port_en; 66 }; 67 68 struct rockchip_combphy_cfg { 69 const struct rockchip_combphy_grfcfg *grfcfg; 70 int (*combphy_cfg)(struct rockchip_combphy_priv *priv); 71 }; 72 73 struct rockchip_combphy_priv { 74 u32 mode; 75 void __iomem *mmio; 76 struct udevice *dev; 77 struct regmap *pipe_grf; 78 struct regmap *phy_grf; 79 struct phy *phy; 80 struct reset_ctl phy_rst; 81 struct clk ref_clk; 82 const struct rockchip_combphy_cfg *cfg; 83 }; 84 85 static int param_write(struct regmap *base, 86 const struct combphy_reg *reg, bool en) 87 { 88 u32 val, mask, tmp; 89 90 tmp = en ? reg->enable : reg->disable; 91 mask = GENMASK(reg->bitend, reg->bitstart); 92 val = (tmp << reg->bitstart) | (mask << BIT_WRITEABLE_SHIFT); 93 94 return regmap_write(base, reg->offset, val); 95 } 96 97 static int rockchip_combphy_pcie_init(struct rockchip_combphy_priv *priv) 98 { 99 int ret = 0; 100 101 if (priv->cfg->combphy_cfg) { 102 ret = priv->cfg->combphy_cfg(priv); 103 if (ret) { 104 dev_err(priv->dev, "failed to init phy for pcie\n"); 105 return ret; 106 } 107 } 108 109 return ret; 110 } 111 112 static int rockchip_combphy_usb3_init(struct rockchip_combphy_priv *priv) 113 { 114 int ret = 0; 115 116 if (priv->cfg->combphy_cfg) { 117 ret = priv->cfg->combphy_cfg(priv); 118 if (ret) { 119 dev_err(priv->dev, "failed to init phy for usb3\n"); 120 return ret; 121 } 122 } 123 124 return ret; 125 } 126 127 static int rockchip_combphy_sata_init(struct rockchip_combphy_priv *priv) 128 { 129 int ret = 0; 130 131 if (priv->cfg->combphy_cfg) { 132 ret = priv->cfg->combphy_cfg(priv); 133 if (ret) { 134 dev_err(priv->dev, "failed to init phy for sata\n"); 135 return ret; 136 } 137 } 138 139 return ret; 140 } 141 142 static int rockchip_combphy_sgmii_init(struct rockchip_combphy_priv *priv) 143 { 144 int ret = 0; 145 146 if (priv->cfg->combphy_cfg) { 147 ret = priv->cfg->combphy_cfg(priv); 148 if (ret) { 149 dev_err(priv->dev, "failed to init phy for sgmii\n"); 150 return ret; 151 } 152 } 153 154 return ret; 155 } 156 157 static int rockchip_combphy_set_mode(struct rockchip_combphy_priv *priv) 158 { 159 switch (priv->mode) { 160 case PHY_TYPE_PCIE: 161 rockchip_combphy_pcie_init(priv); 162 break; 163 case PHY_TYPE_USB3: 164 rockchip_combphy_usb3_init(priv); 165 break; 166 case PHY_TYPE_SATA: 167 rockchip_combphy_sata_init(priv); 168 break; 169 case PHY_TYPE_SGMII: 170 case PHY_TYPE_QSGMII: 171 return rockchip_combphy_sgmii_init(priv); 172 default: 173 dev_err(priv->dev, "incompatible PHY type\n"); 174 return -EINVAL; 175 } 176 177 return 0; 178 } 179 180 static int rockchip_combphy_init(struct phy *phy) 181 { 182 struct rockchip_combphy_priv *priv = dev_get_priv(phy->dev); 183 int ret; 184 185 ret = clk_enable(&priv->ref_clk); 186 if (ret < 0 && ret != -ENOSYS) 187 return ret; 188 189 ret = rockchip_combphy_set_mode(priv); 190 if (ret) 191 goto err_clk; 192 193 reset_deassert(&priv->phy_rst); 194 195 return 0; 196 197 err_clk: 198 clk_disable(&priv->ref_clk); 199 200 return ret; 201 } 202 203 static int rockchip_combphy_exit(struct phy *phy) 204 { 205 struct rockchip_combphy_priv *priv = dev_get_priv(phy->dev); 206 207 clk_disable(&priv->ref_clk); 208 reset_assert(&priv->phy_rst); 209 210 return 0; 211 } 212 213 static int rockchip_combphy_xlate(struct phy *phy, struct ofnode_phandle_args *args) 214 { 215 struct rockchip_combphy_priv *priv = dev_get_priv(phy->dev); 216 217 if (args->args_count != 1) { 218 pr_err("invalid number of arguments\n"); 219 return -EINVAL; 220 } 221 222 priv->mode = args->args[0]; 223 224 return 0; 225 } 226 227 static const struct phy_ops rochchip_combphy_ops = { 228 .init = rockchip_combphy_init, 229 .exit = rockchip_combphy_exit, 230 .of_xlate = rockchip_combphy_xlate, 231 }; 232 233 static int rockchip_combphy_parse_dt(struct udevice *dev, 234 struct rockchip_combphy_priv *priv) 235 { 236 struct udevice *syscon; 237 int ret; 238 u32 vals[4]; 239 240 ret = uclass_get_device_by_phandle(UCLASS_SYSCON, dev, "rockchip,pipe-grf", &syscon); 241 if (ret) { 242 dev_err(dev, "failed to find peri_ctrl pipe-grf regmap ret= %d\n", ret); 243 return ret; 244 } 245 priv->pipe_grf = syscon_get_regmap(syscon); 246 247 ret = uclass_get_device_by_phandle(UCLASS_SYSCON, dev, "rockchip,pipe-phy-grf", &syscon); 248 if (ret) { 249 dev_err(dev, "failed to find peri_ctrl pipe-phy-grf regmap\n"); 250 return ret; 251 } 252 priv->phy_grf = syscon_get_regmap(syscon); 253 254 ret = clk_get_by_index(dev, 0, &priv->ref_clk); 255 if (ret) { 256 dev_err(dev, "failed to find ref clock\n"); 257 return PTR_ERR(&priv->ref_clk); 258 } 259 260 ret = reset_get_by_name(dev, "combphy", &priv->phy_rst); 261 if (ret) { 262 dev_err(dev, "no phy reset control specified\n"); 263 return ret; 264 } 265 266 if (!dev_read_u32_array(dev, "rockchip,pcie1ln-sel-bits", 267 vals, ARRAY_SIZE(vals))) 268 regmap_write(priv->pipe_grf, vals[0], 269 (GENMASK(vals[2], vals[1]) << 16) | vals[3]); 270 271 return 0; 272 } 273 274 static int rockchip_combphy_probe(struct udevice *udev) 275 { 276 struct rockchip_combphy_priv *priv = dev_get_priv(udev); 277 const struct rockchip_combphy_cfg *phy_cfg; 278 279 priv->mmio = (void __iomem *)dev_read_addr(udev); 280 if (IS_ERR(priv->mmio)) 281 return PTR_ERR(priv->mmio); 282 283 phy_cfg = (const struct rockchip_combphy_cfg *)dev_get_driver_data(udev); 284 if (!phy_cfg) { 285 dev_err(udev, "No OF match data provided\n"); 286 return -EINVAL; 287 } 288 289 priv->dev = udev; 290 priv->mode = PHY_TYPE_SATA; 291 priv->cfg = phy_cfg; 292 293 return rockchip_combphy_parse_dt(udev, priv); 294 } 295 296 static int rk3528_combphy_cfg(struct rockchip_combphy_priv *priv) 297 { 298 const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg; 299 u32 val; 300 301 switch (priv->mode) { 302 case PHY_TYPE_PCIE: 303 /* Set SSC downward spread spectrum */ 304 val = readl(priv->mmio + 0x18); 305 val &= ~GENMASK(5, 4); 306 val |= 0x01 << 4; 307 writel(val, priv->mmio + 0x18); 308 309 param_write(priv->phy_grf, &cfg->con0_for_pcie, true); 310 param_write(priv->phy_grf, &cfg->con1_for_pcie, true); 311 param_write(priv->phy_grf, &cfg->con2_for_pcie, true); 312 param_write(priv->phy_grf, &cfg->con3_for_pcie, true); 313 break; 314 case PHY_TYPE_USB3: 315 /* Set SSC downward spread spectrum */ 316 val = readl(priv->mmio + 0x18); 317 val &= ~GENMASK(5, 4); 318 val |= 0x01 << 4; 319 writel(val, priv->mmio + 0x18); 320 321 /* Enable adaptive CTLE for USB3.0 Rx */ 322 val = readl(priv->mmio + 0x200); 323 val &= ~GENMASK(17, 17); 324 val |= 0x01; 325 writel(val, priv->mmio + 0x200); 326 327 param_write(priv->phy_grf, &cfg->pipe_txcomp_sel, false); 328 param_write(priv->phy_grf, &cfg->pipe_txelec_sel, false); 329 param_write(priv->phy_grf, &cfg->usb_mode_set, true); 330 break; 331 default: 332 dev_err(priv->dev, "incompatible PHY type\n"); 333 return -EINVAL; 334 } 335 336 param_write(priv->phy_grf, &cfg->pipe_clk_100m, true); 337 if (priv->mode == PHY_TYPE_PCIE) { 338 /* PLL KVCO tuning fine */ 339 val = readl(priv->mmio + 0x18); 340 val &= ~(0x7 << 10); 341 val |= 0x2 << 10; 342 writel(val, priv->mmio + 0x18); 343 344 /* su_trim[6:4]=111, [10:7]=1001, [2:0]=000 */ 345 val = readl(priv->mmio + 0x108); 346 val &= ~(0x7f7); 347 val |= 0x4f0; 348 writel(val, priv->mmio + 0x108); 349 } 350 351 return 0; 352 } 353 354 static const struct rockchip_combphy_grfcfg rk3528_combphy_grfcfgs = { 355 /* pipe-phy-grf */ 356 .pcie_mode_set = { 0x48000, 5, 0, 0x00, 0x11 }, 357 .usb_mode_set = { 0x48000, 5, 0, 0x00, 0x04 }, 358 .pipe_rxterm_set = { 0x48000, 12, 12, 0x00, 0x01 }, 359 .pipe_txelec_set = { 0x48004, 1, 1, 0x00, 0x01 }, 360 .pipe_txcomp_set = { 0x48004, 4, 4, 0x00, 0x01 }, 361 .pipe_clk_24m = { 0x48004, 14, 13, 0x00, 0x00 }, 362 .pipe_clk_100m = { 0x48004, 14, 13, 0x00, 0x02 }, 363 .pipe_rxterm_sel = { 0x48008, 8, 8, 0x00, 0x01 }, 364 .pipe_txelec_sel = { 0x48008, 12, 12, 0x00, 0x01 }, 365 .pipe_txcomp_sel = { 0x48008, 15, 15, 0x00, 0x01 }, 366 .pipe_clk_ext = { 0x4800c, 9, 8, 0x02, 0x01 }, 367 .pipe_phy_status = { 0x48034, 6, 6, 0x01, 0x00 }, 368 .con0_for_pcie = { 0x48000, 15, 0, 0x00, 0x110 }, 369 .con1_for_pcie = { 0x48004, 15, 0, 0x00, 0x00 }, 370 .con2_for_pcie = { 0x48008, 15, 0, 0x00, 0x101 }, 371 .con3_for_pcie = { 0x4800c, 15, 0, 0x00, 0x0200 }, 372 /* pipe-grf */ 373 .u3otg0_port_en = { 0x40044, 15, 0, 0x0181, 0x1100 }, 374 }; 375 376 static const struct rockchip_combphy_cfg rk3528_combphy_cfgs = { 377 .grfcfg = &rk3528_combphy_grfcfgs, 378 .combphy_cfg = rk3528_combphy_cfg, 379 }; 380 381 static int rk3568_combphy_cfg(struct rockchip_combphy_priv *priv) 382 { 383 const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg; 384 u32 val; 385 386 switch (priv->mode) { 387 case PHY_TYPE_PCIE: 388 /* Set SSC downward spread spectrum */ 389 val = readl(priv->mmio + (0x1f << 2)); 390 val &= ~GENMASK(5, 4); 391 val |= 0x01 << 4; 392 writel(val, priv->mmio + 0x7c); 393 394 param_write(priv->phy_grf, &cfg->con0_for_pcie, true); 395 param_write(priv->phy_grf, &cfg->con1_for_pcie, true); 396 param_write(priv->phy_grf, &cfg->con2_for_pcie, true); 397 param_write(priv->phy_grf, &cfg->con3_for_pcie, true); 398 break; 399 case PHY_TYPE_USB3: 400 /* Set SSC downward spread spectrum */ 401 val = readl(priv->mmio + (0x1f << 2)); 402 val &= ~GENMASK(5, 4); 403 val |= 0x01 << 4; 404 writel(val, priv->mmio + 0x7c); 405 406 /* Enable adaptive CTLE for USB3.0 Rx */ 407 val = readl(priv->mmio + (0x0e << 2)); 408 val &= ~GENMASK(0, 0); 409 val |= 0x01; 410 writel(val, priv->mmio + (0x0e << 2)); 411 412 /* Set PLL KVCO fine tuning signals */ 413 val = readl(priv->mmio + (0x20 << 2)); 414 val &= ~(0x7 << 2); 415 val |= 0x2 << 2; 416 writel(val, priv->mmio + (0x20 << 2)); 417 418 /* Set PLL LPF R1 to su_trim[10:7]=1001 */ 419 writel(0x4, priv->mmio + (0xb << 2)); 420 421 /* Set PLL input clock divider 1/2 */ 422 val = readl(priv->mmio + (0x5 << 2)); 423 val &= ~(0x3 << 6); 424 val |= 0x1 << 6; 425 writel(val, priv->mmio + (0x5 << 2)); 426 427 /* Set PLL loop divider */ 428 writel(0x32, priv->mmio + (0x11 << 2)); 429 430 /* Set PLL KVCO to min and set PLL charge pump current to max */ 431 writel(0xf0, priv->mmio + (0xa << 2)); 432 433 param_write(priv->phy_grf, &cfg->pipe_sel_usb, true); 434 param_write(priv->phy_grf, &cfg->pipe_txcomp_sel, false); 435 param_write(priv->phy_grf, &cfg->pipe_txelec_sel, false); 436 param_write(priv->phy_grf, &cfg->usb_mode_set, true); 437 break; 438 case PHY_TYPE_SATA: 439 writel(0x41, priv->mmio + 0x38); 440 writel(0x8F, priv->mmio + 0x18); 441 param_write(priv->phy_grf, &cfg->con0_for_sata, true); 442 param_write(priv->phy_grf, &cfg->con1_for_sata, true); 443 param_write(priv->phy_grf, &cfg->con2_for_sata, true); 444 param_write(priv->phy_grf, &cfg->con3_for_sata, true); 445 param_write(priv->pipe_grf, &cfg->pipe_con0_for_sata, true); 446 break; 447 case PHY_TYPE_SGMII: 448 param_write(priv->pipe_grf, &cfg->pipe_xpcs_phy_ready, true); 449 param_write(priv->phy_grf, &cfg->pipe_phymode_sel, true); 450 param_write(priv->phy_grf, &cfg->pipe_sel_qsgmii, true); 451 param_write(priv->phy_grf, &cfg->sgmii_mode_set, true); 452 break; 453 case PHY_TYPE_QSGMII: 454 param_write(priv->pipe_grf, &cfg->pipe_xpcs_phy_ready, true); 455 param_write(priv->phy_grf, &cfg->pipe_phymode_sel, true); 456 param_write(priv->phy_grf, &cfg->pipe_rate_sel, true); 457 param_write(priv->phy_grf, &cfg->pipe_sel_qsgmii, true); 458 param_write(priv->phy_grf, &cfg->qsgmii_mode_set, true); 459 break; 460 default: 461 pr_err("%s, phy-type %d\n", __func__, priv->mode); 462 return -EINVAL; 463 } 464 465 /* The default ref clock is 25Mhz */ 466 param_write(priv->phy_grf, &cfg->pipe_clk_25m, true); 467 468 if (dev_read_bool(priv->dev, "rockchip,enable-ssc")) { 469 val = readl(priv->mmio + (0x7 << 2)); 470 val |= BIT(4); 471 writel(val, priv->mmio + (0x7 << 2)); 472 } 473 474 return 0; 475 } 476 477 static const struct rockchip_combphy_grfcfg rk3568_combphy_grfcfgs = { 478 /* pipe-phy-grf */ 479 .pcie_mode_set = { 0x0000, 5, 0, 0x00, 0x11 }, 480 .usb_mode_set = { 0x0000, 5, 0, 0x00, 0x04 }, 481 .sgmii_mode_set = { 0x0000, 5, 0, 0x00, 0x01 }, 482 .qsgmii_mode_set = { 0x0000, 5, 0, 0x00, 0x21 }, 483 .pipe_rxterm_set = { 0x0000, 12, 12, 0x00, 0x01 }, 484 .pipe_txelec_set = { 0x0004, 1, 1, 0x00, 0x01 }, 485 .pipe_txcomp_set = { 0x0004, 4, 4, 0x00, 0x01 }, 486 .pipe_clk_25m = { 0x0004, 14, 13, 0x00, 0x01 }, 487 .pipe_clk_100m = { 0x0004, 14, 13, 0x00, 0x02 }, 488 .pipe_phymode_sel = { 0x0008, 1, 1, 0x00, 0x01 }, 489 .pipe_rate_sel = { 0x0008, 2, 2, 0x00, 0x01 }, 490 .pipe_rxterm_sel = { 0x0008, 8, 8, 0x00, 0x01 }, 491 .pipe_txelec_sel = { 0x0008, 12, 12, 0x00, 0x01 }, 492 .pipe_txcomp_sel = { 0x0008, 15, 15, 0x00, 0x01 }, 493 .pipe_clk_ext = { 0x000c, 9, 8, 0x02, 0x01 }, 494 .pipe_sel_usb = { 0x000c, 14, 13, 0x00, 0x01 }, 495 .pipe_sel_qsgmii = { 0x000c, 15, 13, 0x00, 0x07 }, 496 .pipe_phy_status = { 0x0034, 6, 6, 0x01, 0x00 }, 497 .con0_for_pcie = { 0x0000, 15, 0, 0x00, 0x1000 }, 498 .con1_for_pcie = { 0x0004, 15, 0, 0x00, 0x0000 }, 499 .con2_for_pcie = { 0x0008, 15, 0, 0x00, 0x0101 }, 500 .con3_for_pcie = { 0x000c, 15, 0, 0x00, 0x0200 }, 501 .con0_for_sata = { 0x0000, 15, 0, 0x00, 0x0119 }, 502 .con1_for_sata = { 0x0004, 15, 0, 0x00, 0x0040 }, 503 .con2_for_sata = { 0x0008, 15, 0, 0x00, 0x80c3 }, 504 .con3_for_sata = { 0x000c, 15, 0, 0x00, 0x4407 }, 505 /* pipe-grf */ 506 .pipe_con0_for_sata = { 0x0000, 15, 0, 0x00, 0x2220 }, 507 .pipe_sgmii_mac_sel = { 0x0040, 1, 1, 0x00, 0x01 }, 508 .pipe_xpcs_phy_ready = { 0x0040, 2, 2, 0x00, 0x01 }, 509 .u3otg0_port_en = { 0x0104, 15, 0, 0x0181, 0x1100 }, 510 .u3otg1_port_en = { 0x0144, 15, 0, 0x0181, 0x1100 }, 511 }; 512 513 static const struct rockchip_combphy_cfg rk3568_combphy_cfgs = { 514 .grfcfg = &rk3568_combphy_grfcfgs, 515 .combphy_cfg = rk3568_combphy_cfg, 516 }; 517 518 static int rk3588_combphy_cfg(struct rockchip_combphy_priv *priv) 519 { 520 const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg; 521 u32 val; 522 523 switch (priv->mode) { 524 case PHY_TYPE_PCIE: 525 param_write(priv->phy_grf, &cfg->con0_for_pcie, true); 526 param_write(priv->phy_grf, &cfg->con1_for_pcie, true); 527 param_write(priv->phy_grf, &cfg->con2_for_pcie, true); 528 param_write(priv->phy_grf, &cfg->con3_for_pcie, true); 529 break; 530 case PHY_TYPE_USB3: 531 /* Set SSC downward spread spectrum */ 532 val = readl(priv->mmio + (0x1f << 2)); 533 val &= ~GENMASK(5, 4); 534 val |= 0x01 << 4; 535 writel(val, priv->mmio + 0x7c); 536 537 /* Enable adaptive CTLE for USB3.0 Rx */ 538 val = readl(priv->mmio + (0x0e << 2)); 539 val &= ~GENMASK(0, 0); 540 val |= 0x01; 541 writel(val, priv->mmio + (0x0e << 2)); 542 543 /* Set PLL KVCO fine tuning signals */ 544 val = readl(priv->mmio + (0x20 << 2)); 545 val &= ~(0x7 << 2); 546 val |= 0x2 << 2; 547 writel(val, priv->mmio + (0x20 << 2)); 548 549 /* Set PLL LPF R1 to su_trim[10:7]=1001 */ 550 writel(0x4, priv->mmio + (0xb << 2)); 551 552 /* Set PLL input clock divider 1/2 */ 553 val = readl(priv->mmio + (0x5 << 2)); 554 val &= ~(0x3 << 6); 555 val |= 0x1 << 6; 556 writel(val, priv->mmio + (0x5 << 2)); 557 558 /* Set PLL loop divider */ 559 writel(0x32, priv->mmio + (0x11 << 2)); 560 561 /* Set PLL KVCO to min and set PLL charge pump current to max */ 562 writel(0xf0, priv->mmio + (0xa << 2)); 563 564 /* Set Rx squelch input filler bandwidth */ 565 writel(0x0d, priv->mmio + (0x14 << 2)); 566 567 param_write(priv->phy_grf, &cfg->pipe_txcomp_sel, false); 568 param_write(priv->phy_grf, &cfg->pipe_txelec_sel, false); 569 param_write(priv->phy_grf, &cfg->usb_mode_set, true); 570 break; 571 case PHY_TYPE_SATA: 572 /* Enable adaptive CTLE for SATA Rx */ 573 val = readl(priv->mmio + (0x0e << 2)); 574 val &= ~GENMASK(0, 0); 575 val |= 0x01; 576 writel(val, priv->mmio + (0x0e << 2)); 577 /* Set tx_rterm = 50 ohm and rx_rterm = 43.5 ohm */ 578 writel(0x8F, priv->mmio + (0x06 << 2)); 579 580 param_write(priv->phy_grf, &cfg->con0_for_sata, true); 581 param_write(priv->phy_grf, &cfg->con1_for_sata, true); 582 param_write(priv->phy_grf, &cfg->con2_for_sata, true); 583 param_write(priv->phy_grf, &cfg->con3_for_sata, true); 584 param_write(priv->pipe_grf, &cfg->pipe_con0_for_sata, true); 585 param_write(priv->pipe_grf, &cfg->pipe_con1_for_sata, true); 586 break; 587 case PHY_TYPE_SGMII: 588 case PHY_TYPE_QSGMII: 589 default: 590 dev_err(priv->dev, "incompatible PHY type\n"); 591 return -EINVAL; 592 } 593 594 /* 100MHz refclock signal is good */ 595 clk_set_rate(&priv->ref_clk, 100000000); 596 param_write(priv->phy_grf, &cfg->pipe_clk_100m, true); 597 if (priv->mode == PHY_TYPE_PCIE) { 598 /* PLL KVCO tuning fine */ 599 val = readl(priv->mmio + (0x20 << 2)); 600 val &= ~GENMASK(4, 2); 601 val |= 0x4 << 2; 602 writel(val, priv->mmio + (0x20 << 2)); 603 604 /* Set up rx_trim: PLL LPF C1 85pf R1 1.25kohm */ 605 val = 0x4c; 606 writel(val, priv->mmio + (0x1b << 2)); 607 608 /* Set up su_trim: T3 */ 609 val = 0xb0; 610 writel(val, priv->mmio + (0xa << 2)); 611 val = 0x47; 612 writel(val, priv->mmio + (0xb << 2)); 613 val = 0x57; 614 writel(val, priv->mmio + (0xd << 2)); 615 } 616 617 return 0; 618 } 619 620 static const struct rockchip_combphy_grfcfg rk3588_combphy_grfcfgs = { 621 /* pipe-phy-grf */ 622 .pcie_mode_set = { 0x0000, 5, 0, 0x00, 0x11 }, 623 .usb_mode_set = { 0x0000, 5, 0, 0x00, 0x04 }, 624 .pipe_rxterm_set = { 0x0000, 12, 12, 0x00, 0x01 }, 625 .pipe_txelec_set = { 0x0004, 1, 1, 0x00, 0x01 }, 626 .pipe_txcomp_set = { 0x0004, 4, 4, 0x00, 0x01 }, 627 .pipe_clk_25m = { 0x0004, 14, 13, 0x00, 0x01 }, 628 .pipe_clk_100m = { 0x0004, 14, 13, 0x00, 0x02 }, 629 .pipe_rxterm_sel = { 0x0008, 8, 8, 0x00, 0x01 }, 630 .pipe_txelec_sel = { 0x0008, 12, 12, 0x00, 0x01 }, 631 .pipe_txcomp_sel = { 0x0008, 15, 15, 0x00, 0x01 }, 632 .pipe_clk_ext = { 0x000c, 9, 8, 0x02, 0x01 }, 633 .pipe_phy_status = { 0x0034, 6, 6, 0x01, 0x00 }, 634 .con0_for_pcie = { 0x0000, 15, 0, 0x00, 0x1000 }, 635 .con1_for_pcie = { 0x0004, 15, 0, 0x00, 0x0000 }, 636 .con2_for_pcie = { 0x0008, 15, 0, 0x00, 0x0101 }, 637 .con3_for_pcie = { 0x000c, 15, 0, 0x00, 0x0200 }, 638 .con0_for_sata = { 0x0000, 15, 0, 0x00, 0x0129 }, 639 .con1_for_sata = { 0x0004, 15, 0, 0x00, 0x0000 }, 640 .con2_for_sata = { 0x0008, 15, 0, 0x00, 0x80c1 }, 641 .con3_for_sata = { 0x000c, 15, 0, 0x00, 0x0407 }, 642 /* pipe-grf */ 643 .pipe_con0_for_sata = { 0x0000, 11, 5, 0x00, 0x22 }, 644 .pipe_con1_for_sata = { 0x0000, 2, 0, 0x00, 0x2 }, 645 }; 646 647 static const struct rockchip_combphy_cfg rk3588_combphy_cfgs = { 648 .grfcfg = &rk3588_combphy_grfcfgs, 649 .combphy_cfg = rk3588_combphy_cfg, 650 }; 651 652 static const struct udevice_id rockchip_combphy_ids[] = { 653 { 654 .compatible = "rockchip,rk3528-naneng-combphy", 655 .data = (ulong)&rk3528_combphy_cfgs 656 }, 657 { 658 .compatible = "rockchip,rk3568-naneng-combphy", 659 .data = (ulong)&rk3568_combphy_cfgs 660 }, 661 { 662 .compatible = "rockchip,rk3588-naneng-combphy", 663 .data = (ulong)&rk3588_combphy_cfgs 664 }, 665 { } 666 }; 667 668 U_BOOT_DRIVER(rockchip_naneng_combphy) = { 669 .name = "naneng-combphy", 670 .id = UCLASS_PHY, 671 .of_match = rockchip_combphy_ids, 672 .ops = &rochchip_combphy_ops, 673 .probe = rockchip_combphy_probe, 674 .priv_auto_alloc_size = sizeof(struct rockchip_combphy_priv), 675 }; 676