xref: /linux/drivers/phy/rockchip/phy-rockchip-naneng-combphy.c (revision c909a49128a31bced8cfbd2dfb0a4fe56e01a6d0)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Rockchip PIPE USB3.0 PCIE SATA Combo Phy driver
4  *
5  * Copyright (C) 2021 Rockchip Electronics Co., Ltd.
6  */
7 
8 #include <dt-bindings/phy/phy.h>
9 #include <linux/clk.h>
10 #include <linux/mfd/syscon.h>
11 #include <linux/of.h>
12 #include <linux/phy/phy.h>
13 #include <linux/platform_device.h>
14 #include <linux/regmap.h>
15 #include <linux/reset.h>
16 #include <linux/units.h>
17 
18 #define BIT_WRITEABLE_SHIFT		16
19 #define REF_CLOCK_24MHz			(24 * HZ_PER_MHZ)
20 #define REF_CLOCK_25MHz			(25 * HZ_PER_MHZ)
21 #define REF_CLOCK_100MHz		(100 * HZ_PER_MHZ)
22 
23 /* COMBO PHY REG */
24 #define PHYREG6				0x14
25 #define PHYREG6_PLL_DIV_MASK		GENMASK(7, 6)
26 #define PHYREG6_PLL_DIV_SHIFT		6
27 #define PHYREG6_PLL_DIV_2		1
28 
29 #define PHYREG7				0x18
30 #define PHYREG7_TX_RTERM_MASK		GENMASK(7, 4)
31 #define PHYREG7_TX_RTERM_SHIFT		4
32 #define PHYREG7_TX_RTERM_50OHM		8
33 #define PHYREG7_RX_RTERM_MASK		GENMASK(3, 0)
34 #define PHYREG7_RX_RTERM_SHIFT		0
35 #define PHYREG7_RX_RTERM_44OHM		15
36 
37 #define PHYREG8				0x1C
38 #define PHYREG8_SSC_EN			BIT(4)
39 
40 #define PHYREG10			0x24
41 #define PHYREG10_SSC_PCM_MASK		GENMASK(3, 0)
42 #define PHYREG10_SSC_PCM_3500PPM	7
43 
44 #define PHYREG11			0x28
45 #define PHYREG11_SU_TRIM_0_7		0xF0
46 
47 #define PHYREG12			0x2C
48 #define PHYREG12_PLL_LPF_ADJ_VALUE	4
49 
50 #define PHYREG13			0x30
51 #define PHYREG13_RESISTER_MASK		GENMASK(5, 4)
52 #define PHYREG13_RESISTER_SHIFT		0x4
53 #define PHYREG13_RESISTER_HIGH_Z	3
54 #define PHYREG13_CKRCV_AMP0		BIT(7)
55 
56 #define PHYREG14			0x34
57 #define PHYREG14_CKRCV_AMP1		BIT(0)
58 
59 #define PHYREG15			0x38
60 #define PHYREG15_CTLE_EN		BIT(0)
61 #define PHYREG15_SSC_CNT_MASK		GENMASK(7, 6)
62 #define PHYREG15_SSC_CNT_SHIFT		6
63 #define PHYREG15_SSC_CNT_VALUE		1
64 
65 #define PHYREG16			0x3C
66 #define PHYREG16_SSC_CNT_VALUE		0x5f
67 
68 #define PHYREG17			0x40
69 
70 #define PHYREG18			0x44
71 #define PHYREG18_PLL_LOOP		0x32
72 
73 #define PHYREG21			0x50
74 #define PHYREG21_RX_SQUELCH_VAL		0x0D
75 
76 #define PHYREG27			0x6C
77 #define PHYREG27_RX_TRIM_RK3588		0x4C
78 
79 #define PHYREG30			0x74
80 
81 #define PHYREG32			0x7C
82 #define PHYREG32_SSC_MASK		GENMASK(7, 4)
83 #define PHYREG32_SSC_DIR_MASK		GENMASK(5, 4)
84 #define PHYREG32_SSC_DIR_SHIFT		4
85 #define PHYREG32_SSC_UPWARD		0
86 #define PHYREG32_SSC_DOWNWARD		1
87 #define PHYREG32_SSC_OFFSET_MASK	GENMASK(7, 6)
88 #define PHYREG32_SSC_OFFSET_SHIFT	6
89 #define PHYREG32_SSC_OFFSET_500PPM	1
90 
91 #define PHYREG33			0x80
92 #define PHYREG33_PLL_KVCO_MASK		GENMASK(4, 2)
93 #define PHYREG33_PLL_KVCO_SHIFT		2
94 #define PHYREG33_PLL_KVCO_VALUE		2
95 #define PHYREG33_PLL_KVCO_VALUE_RK3576	4
96 
97 struct rockchip_combphy_priv;
98 
99 struct combphy_reg {
100 	u16 offset;
101 	u16 bitend;
102 	u16 bitstart;
103 	u16 disable;
104 	u16 enable;
105 };
106 
107 struct rockchip_combphy_grfcfg {
108 	struct combphy_reg pcie_mode_set;
109 	struct combphy_reg usb_mode_set;
110 	struct combphy_reg sgmii_mode_set;
111 	struct combphy_reg qsgmii_mode_set;
112 	struct combphy_reg pipe_rxterm_set;
113 	struct combphy_reg pipe_txelec_set;
114 	struct combphy_reg pipe_txcomp_set;
115 	struct combphy_reg pipe_clk_24m;
116 	struct combphy_reg pipe_clk_25m;
117 	struct combphy_reg pipe_clk_100m;
118 	struct combphy_reg pipe_phymode_sel;
119 	struct combphy_reg pipe_rate_sel;
120 	struct combphy_reg pipe_rxterm_sel;
121 	struct combphy_reg pipe_txelec_sel;
122 	struct combphy_reg pipe_txcomp_sel;
123 	struct combphy_reg pipe_clk_ext;
124 	struct combphy_reg pipe_sel_usb;
125 	struct combphy_reg pipe_sel_qsgmii;
126 	struct combphy_reg pipe_phy_status;
127 	struct combphy_reg con0_for_pcie;
128 	struct combphy_reg con1_for_pcie;
129 	struct combphy_reg con2_for_pcie;
130 	struct combphy_reg con3_for_pcie;
131 	struct combphy_reg con0_for_sata;
132 	struct combphy_reg con1_for_sata;
133 	struct combphy_reg con2_for_sata;
134 	struct combphy_reg con3_for_sata;
135 	struct combphy_reg pipe_con0_for_sata;
136 	struct combphy_reg pipe_con1_for_sata;
137 	struct combphy_reg pipe_xpcs_phy_ready;
138 	struct combphy_reg pipe_pcie1l0_sel;
139 	struct combphy_reg pipe_pcie1l1_sel;
140 };
141 
142 struct rockchip_combphy_cfg {
143 	unsigned int num_phys;
144 	unsigned int phy_ids[3];
145 	const struct rockchip_combphy_grfcfg *grfcfg;
146 	int (*combphy_cfg)(struct rockchip_combphy_priv *priv);
147 };
148 
149 struct rockchip_combphy_priv {
150 	u8 type;
151 	int id;
152 	void __iomem *mmio;
153 	int num_clks;
154 	struct clk_bulk_data *clks;
155 	struct device *dev;
156 	struct regmap *pipe_grf;
157 	struct regmap *phy_grf;
158 	struct phy *phy;
159 	struct reset_control *phy_rst;
160 	const struct rockchip_combphy_cfg *cfg;
161 	bool enable_ssc;
162 	bool ext_refclk;
163 	struct clk *refclk;
164 };
165 
166 static void rockchip_combphy_updatel(struct rockchip_combphy_priv *priv,
167 				     int mask, int val, int reg)
168 {
169 	unsigned int temp;
170 
171 	temp = readl(priv->mmio + reg);
172 	temp = (temp & ~(mask)) | val;
173 	writel(temp, priv->mmio + reg);
174 }
175 
176 static int rockchip_combphy_param_write(struct regmap *base,
177 					const struct combphy_reg *reg, bool en)
178 {
179 	u32 val, mask, tmp;
180 
181 	tmp = en ? reg->enable : reg->disable;
182 	mask = GENMASK(reg->bitend, reg->bitstart);
183 	val = (tmp << reg->bitstart) | (mask << BIT_WRITEABLE_SHIFT);
184 
185 	return regmap_write(base, reg->offset, val);
186 }
187 
188 static u32 rockchip_combphy_is_ready(struct rockchip_combphy_priv *priv)
189 {
190 	const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg;
191 	u32 mask, val;
192 
193 	mask = GENMASK(cfg->pipe_phy_status.bitend,
194 		       cfg->pipe_phy_status.bitstart);
195 
196 	regmap_read(priv->phy_grf, cfg->pipe_phy_status.offset, &val);
197 	val = (val & mask) >> cfg->pipe_phy_status.bitstart;
198 
199 	return val;
200 }
201 
202 static int rockchip_combphy_init(struct phy *phy)
203 {
204 	struct rockchip_combphy_priv *priv = phy_get_drvdata(phy);
205 	const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg;
206 	u32 val;
207 	int ret;
208 
209 	ret = clk_bulk_prepare_enable(priv->num_clks, priv->clks);
210 	if (ret) {
211 		dev_err(priv->dev, "failed to enable clks\n");
212 		return ret;
213 	}
214 
215 	switch (priv->type) {
216 	case PHY_TYPE_PCIE:
217 	case PHY_TYPE_USB3:
218 	case PHY_TYPE_SATA:
219 	case PHY_TYPE_SGMII:
220 	case PHY_TYPE_QSGMII:
221 		if (priv->cfg->combphy_cfg)
222 			ret = priv->cfg->combphy_cfg(priv);
223 		break;
224 	default:
225 		dev_err(priv->dev, "incompatible PHY type\n");
226 		ret = -EINVAL;
227 		break;
228 	}
229 
230 	if (ret) {
231 		dev_err(priv->dev, "failed to init phy for phy type %x\n", priv->type);
232 		goto err_clk;
233 	}
234 
235 	ret = reset_control_deassert(priv->phy_rst);
236 	if (ret)
237 		goto err_clk;
238 
239 	if (priv->type == PHY_TYPE_USB3) {
240 		ret = readx_poll_timeout_atomic(rockchip_combphy_is_ready,
241 						priv, val,
242 						val == cfg->pipe_phy_status.enable,
243 						10, 1000);
244 		if (ret)
245 			dev_warn(priv->dev, "wait phy status ready timeout\n");
246 	}
247 
248 	return 0;
249 
250 err_clk:
251 	clk_bulk_disable_unprepare(priv->num_clks, priv->clks);
252 
253 	return ret;
254 }
255 
256 static int rockchip_combphy_exit(struct phy *phy)
257 {
258 	struct rockchip_combphy_priv *priv = phy_get_drvdata(phy);
259 
260 	clk_bulk_disable_unprepare(priv->num_clks, priv->clks);
261 	reset_control_assert(priv->phy_rst);
262 
263 	return 0;
264 }
265 
266 static const struct phy_ops rockchip_combphy_ops = {
267 	.init = rockchip_combphy_init,
268 	.exit = rockchip_combphy_exit,
269 	.owner = THIS_MODULE,
270 };
271 
272 static struct phy *rockchip_combphy_xlate(struct device *dev, const struct of_phandle_args *args)
273 {
274 	struct rockchip_combphy_priv *priv = dev_get_drvdata(dev);
275 
276 	if (args->args_count != 1) {
277 		dev_err(dev, "invalid number of arguments\n");
278 		return ERR_PTR(-EINVAL);
279 	}
280 
281 	if (priv->type != PHY_NONE && priv->type != args->args[0])
282 		dev_warn(dev, "phy type select %d overwriting type %d\n",
283 			 args->args[0], priv->type);
284 
285 	priv->type = args->args[0];
286 
287 	return priv->phy;
288 }
289 
290 static int rockchip_combphy_parse_dt(struct device *dev, struct rockchip_combphy_priv *priv)
291 {
292 	int i;
293 
294 	priv->num_clks = devm_clk_bulk_get_all(dev, &priv->clks);
295 	if (priv->num_clks < 1)
296 		return -EINVAL;
297 
298 	priv->refclk = NULL;
299 	for (i = 0; i < priv->num_clks; i++) {
300 		if (!strncmp(priv->clks[i].id, "ref", 3)) {
301 			priv->refclk = priv->clks[i].clk;
302 			break;
303 		}
304 	}
305 
306 	if (!priv->refclk) {
307 		dev_err(dev, "no refclk found\n");
308 		return -EINVAL;
309 	}
310 
311 	priv->pipe_grf = syscon_regmap_lookup_by_phandle(dev->of_node, "rockchip,pipe-grf");
312 	if (IS_ERR(priv->pipe_grf)) {
313 		dev_err(dev, "failed to find peri_ctrl pipe-grf regmap\n");
314 		return PTR_ERR(priv->pipe_grf);
315 	}
316 
317 	priv->phy_grf = syscon_regmap_lookup_by_phandle(dev->of_node, "rockchip,pipe-phy-grf");
318 	if (IS_ERR(priv->phy_grf)) {
319 		dev_err(dev, "failed to find peri_ctrl pipe-phy-grf regmap\n");
320 		return PTR_ERR(priv->phy_grf);
321 	}
322 
323 	priv->enable_ssc = device_property_present(dev, "rockchip,enable-ssc");
324 
325 	priv->ext_refclk = device_property_present(dev, "rockchip,ext-refclk");
326 
327 	priv->phy_rst = devm_reset_control_get(dev, "phy");
328 	if (IS_ERR(priv->phy_rst))
329 		return dev_err_probe(dev, PTR_ERR(priv->phy_rst), "failed to get phy reset\n");
330 
331 	return 0;
332 }
333 
334 static int rockchip_combphy_probe(struct platform_device *pdev)
335 {
336 	struct phy_provider *phy_provider;
337 	struct device *dev = &pdev->dev;
338 	struct rockchip_combphy_priv *priv;
339 	const struct rockchip_combphy_cfg *phy_cfg;
340 	struct resource *res;
341 	int ret, id;
342 
343 	phy_cfg = of_device_get_match_data(dev);
344 	if (!phy_cfg) {
345 		dev_err(dev, "no OF match data provided\n");
346 		return -EINVAL;
347 	}
348 
349 	priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
350 	if (!priv)
351 		return -ENOMEM;
352 
353 	priv->mmio = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
354 	if (IS_ERR(priv->mmio)) {
355 		ret = PTR_ERR(priv->mmio);
356 		return ret;
357 	}
358 
359 	/* find the phy-id from the io address */
360 	priv->id = -ENODEV;
361 	for (id = 0; id < phy_cfg->num_phys; id++) {
362 		if (res->start == phy_cfg->phy_ids[id]) {
363 			priv->id = id;
364 			break;
365 		}
366 	}
367 
368 	priv->dev = dev;
369 	priv->type = PHY_NONE;
370 	priv->cfg = phy_cfg;
371 
372 	ret = rockchip_combphy_parse_dt(dev, priv);
373 	if (ret)
374 		return ret;
375 
376 	ret = reset_control_assert(priv->phy_rst);
377 	if (ret) {
378 		dev_err(dev, "failed to reset phy\n");
379 		return ret;
380 	}
381 
382 	priv->phy = devm_phy_create(dev, NULL, &rockchip_combphy_ops);
383 	if (IS_ERR(priv->phy)) {
384 		dev_err(dev, "failed to create combphy\n");
385 		return PTR_ERR(priv->phy);
386 	}
387 
388 	dev_set_drvdata(dev, priv);
389 	phy_set_drvdata(priv->phy, priv);
390 
391 	phy_provider = devm_of_phy_provider_register(dev, rockchip_combphy_xlate);
392 
393 	return PTR_ERR_OR_ZERO(phy_provider);
394 }
395 
396 static int rk3568_combphy_cfg(struct rockchip_combphy_priv *priv)
397 {
398 	const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg;
399 	unsigned long rate;
400 	u32 val;
401 
402 	switch (priv->type) {
403 	case PHY_TYPE_PCIE:
404 		/* Set SSC downward spread spectrum. */
405 		rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK,
406 					 PHYREG32_SSC_DOWNWARD << PHYREG32_SSC_DIR_SHIFT,
407 					 PHYREG32);
408 
409 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con0_for_pcie, true);
410 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con1_for_pcie, true);
411 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con2_for_pcie, true);
412 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con3_for_pcie, true);
413 		break;
414 
415 	case PHY_TYPE_USB3:
416 		/* Set SSC downward spread spectrum. */
417 		rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK,
418 					 PHYREG32_SSC_DOWNWARD << PHYREG32_SSC_DIR_SHIFT,
419 					 PHYREG32);
420 
421 		/* Enable adaptive CTLE for USB3.0 Rx. */
422 		val = readl(priv->mmio + PHYREG15);
423 		val |= PHYREG15_CTLE_EN;
424 		writel(val, priv->mmio + PHYREG15);
425 
426 		/* Set PLL KVCO fine tuning signals. */
427 		rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK,
428 					 PHYREG33_PLL_KVCO_VALUE << PHYREG33_PLL_KVCO_SHIFT,
429 					 PHYREG33);
430 
431 		/* Enable controlling random jitter. */
432 		writel(PHYREG12_PLL_LPF_ADJ_VALUE, priv->mmio + PHYREG12);
433 
434 		/* Set PLL input clock divider 1/2. */
435 		rockchip_combphy_updatel(priv, PHYREG6_PLL_DIV_MASK,
436 					 PHYREG6_PLL_DIV_2 << PHYREG6_PLL_DIV_SHIFT,
437 					 PHYREG6);
438 
439 		writel(PHYREG18_PLL_LOOP, priv->mmio + PHYREG18);
440 		writel(PHYREG11_SU_TRIM_0_7, priv->mmio + PHYREG11);
441 
442 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_sel_usb, true);
443 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_txcomp_sel, false);
444 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_txelec_sel, false);
445 		rockchip_combphy_param_write(priv->phy_grf, &cfg->usb_mode_set, true);
446 		break;
447 
448 	case PHY_TYPE_SATA:
449 		/* Enable adaptive CTLE for SATA Rx. */
450 		val = readl(priv->mmio + PHYREG15);
451 		val |= PHYREG15_CTLE_EN;
452 		writel(val, priv->mmio + PHYREG15);
453 		/*
454 		 * Set tx_rterm=50ohm and rx_rterm=44ohm for SATA.
455 		 * 0: 60ohm, 8: 50ohm 15: 44ohm (by step abort 1ohm)
456 		 */
457 		val = PHYREG7_TX_RTERM_50OHM << PHYREG7_TX_RTERM_SHIFT;
458 		val |= PHYREG7_RX_RTERM_44OHM << PHYREG7_RX_RTERM_SHIFT;
459 		writel(val, priv->mmio + PHYREG7);
460 
461 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con0_for_sata, true);
462 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con1_for_sata, true);
463 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con2_for_sata, true);
464 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con3_for_sata, true);
465 		rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_con0_for_sata, true);
466 		break;
467 
468 	case PHY_TYPE_SGMII:
469 		rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_xpcs_phy_ready, true);
470 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_phymode_sel, true);
471 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_sel_qsgmii, true);
472 		rockchip_combphy_param_write(priv->phy_grf, &cfg->sgmii_mode_set, true);
473 		break;
474 
475 	case PHY_TYPE_QSGMII:
476 		rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_xpcs_phy_ready, true);
477 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_phymode_sel, true);
478 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_rate_sel, true);
479 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_sel_qsgmii, true);
480 		rockchip_combphy_param_write(priv->phy_grf, &cfg->qsgmii_mode_set, true);
481 		break;
482 
483 	default:
484 		dev_err(priv->dev, "incompatible PHY type\n");
485 		return -EINVAL;
486 	}
487 
488 	rate = clk_get_rate(priv->refclk);
489 
490 	switch (rate) {
491 	case REF_CLOCK_24MHz:
492 		if (priv->type == PHY_TYPE_USB3 || priv->type == PHY_TYPE_SATA) {
493 			/* Set ssc_cnt[9:0]=0101111101 & 31.5KHz. */
494 			val = PHYREG15_SSC_CNT_VALUE << PHYREG15_SSC_CNT_SHIFT;
495 			rockchip_combphy_updatel(priv, PHYREG15_SSC_CNT_MASK,
496 						 val, PHYREG15);
497 
498 			writel(PHYREG16_SSC_CNT_VALUE, priv->mmio + PHYREG16);
499 		}
500 		break;
501 
502 	case REF_CLOCK_25MHz:
503 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_25m, true);
504 		break;
505 
506 	case REF_CLOCK_100MHz:
507 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_100m, true);
508 		if (priv->type == PHY_TYPE_PCIE) {
509 			/* PLL KVCO  fine tuning. */
510 			val = PHYREG33_PLL_KVCO_VALUE << PHYREG33_PLL_KVCO_SHIFT;
511 			rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK,
512 						 val, PHYREG33);
513 
514 			/* Enable controlling random jitter. */
515 			writel(PHYREG12_PLL_LPF_ADJ_VALUE, priv->mmio + PHYREG12);
516 
517 			val = PHYREG6_PLL_DIV_2 << PHYREG6_PLL_DIV_SHIFT;
518 			rockchip_combphy_updatel(priv, PHYREG6_PLL_DIV_MASK,
519 						 val, PHYREG6);
520 
521 			writel(PHYREG18_PLL_LOOP, priv->mmio + PHYREG18);
522 			writel(PHYREG11_SU_TRIM_0_7, priv->mmio + PHYREG11);
523 		} else if (priv->type == PHY_TYPE_SATA) {
524 			/* downward spread spectrum +500ppm */
525 			val = PHYREG32_SSC_DOWNWARD << PHYREG32_SSC_DIR_SHIFT;
526 			val |= PHYREG32_SSC_OFFSET_500PPM << PHYREG32_SSC_OFFSET_SHIFT;
527 			rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK, val, PHYREG32);
528 		}
529 		break;
530 
531 	default:
532 		dev_err(priv->dev, "unsupported rate: %lu\n", rate);
533 		return -EINVAL;
534 	}
535 
536 	if (priv->ext_refclk) {
537 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_ext, true);
538 		if (priv->type == PHY_TYPE_PCIE && rate == REF_CLOCK_100MHz) {
539 			val = PHYREG13_RESISTER_HIGH_Z << PHYREG13_RESISTER_SHIFT;
540 			val |= PHYREG13_CKRCV_AMP0;
541 			rockchip_combphy_updatel(priv, PHYREG13_RESISTER_MASK, val, PHYREG13);
542 
543 			val = readl(priv->mmio + PHYREG14);
544 			val |= PHYREG14_CKRCV_AMP1;
545 			writel(val, priv->mmio + PHYREG14);
546 		}
547 	}
548 
549 	if (priv->enable_ssc) {
550 		val = readl(priv->mmio + PHYREG8);
551 		val |= PHYREG8_SSC_EN;
552 		writel(val, priv->mmio + PHYREG8);
553 	}
554 
555 	return 0;
556 }
557 
558 static const struct rockchip_combphy_grfcfg rk3568_combphy_grfcfgs = {
559 	/* pipe-phy-grf */
560 	.pcie_mode_set		= { 0x0000, 5, 0, 0x00, 0x11 },
561 	.usb_mode_set		= { 0x0000, 5, 0, 0x00, 0x04 },
562 	.sgmii_mode_set		= { 0x0000, 5, 0, 0x00, 0x01 },
563 	.qsgmii_mode_set	= { 0x0000, 5, 0, 0x00, 0x21 },
564 	.pipe_rxterm_set	= { 0x0000, 12, 12, 0x00, 0x01 },
565 	.pipe_txelec_set	= { 0x0004, 1, 1, 0x00, 0x01 },
566 	.pipe_txcomp_set	= { 0x0004, 4, 4, 0x00, 0x01 },
567 	.pipe_clk_25m		= { 0x0004, 14, 13, 0x00, 0x01 },
568 	.pipe_clk_100m		= { 0x0004, 14, 13, 0x00, 0x02 },
569 	.pipe_phymode_sel	= { 0x0008, 1, 1, 0x00, 0x01 },
570 	.pipe_rate_sel		= { 0x0008, 2, 2, 0x00, 0x01 },
571 	.pipe_rxterm_sel	= { 0x0008, 8, 8, 0x00, 0x01 },
572 	.pipe_txelec_sel	= { 0x0008, 12, 12, 0x00, 0x01 },
573 	.pipe_txcomp_sel	= { 0x0008, 15, 15, 0x00, 0x01 },
574 	.pipe_clk_ext		= { 0x000c, 9, 8, 0x02, 0x01 },
575 	.pipe_sel_usb		= { 0x000c, 14, 13, 0x00, 0x01 },
576 	.pipe_sel_qsgmii	= { 0x000c, 15, 13, 0x00, 0x07 },
577 	.pipe_phy_status	= { 0x0034, 6, 6, 0x01, 0x00 },
578 	.con0_for_pcie		= { 0x0000, 15, 0, 0x00, 0x1000 },
579 	.con1_for_pcie		= { 0x0004, 15, 0, 0x00, 0x0000 },
580 	.con2_for_pcie		= { 0x0008, 15, 0, 0x00, 0x0101 },
581 	.con3_for_pcie		= { 0x000c, 15, 0, 0x00, 0x0200 },
582 	.con0_for_sata		= { 0x0000, 15, 0, 0x00, 0x0119 },
583 	.con1_for_sata		= { 0x0004, 15, 0, 0x00, 0x0040 },
584 	.con2_for_sata		= { 0x0008, 15, 0, 0x00, 0x80c3 },
585 	.con3_for_sata		= { 0x000c, 15, 0, 0x00, 0x4407 },
586 	/* pipe-grf */
587 	.pipe_con0_for_sata	= { 0x0000, 15, 0, 0x00, 0x2220 },
588 	.pipe_xpcs_phy_ready	= { 0x0040, 2, 2, 0x00, 0x01 },
589 };
590 
591 static const struct rockchip_combphy_cfg rk3568_combphy_cfgs = {
592 	.num_phys = 3,
593 	.phy_ids = {
594 		0xfe820000,
595 		0xfe830000,
596 		0xfe840000,
597 	},
598 	.grfcfg		= &rk3568_combphy_grfcfgs,
599 	.combphy_cfg	= rk3568_combphy_cfg,
600 };
601 
602 static int rk3576_combphy_cfg(struct rockchip_combphy_priv *priv)
603 {
604 	const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg;
605 	unsigned long rate;
606 	u32 val;
607 
608 	switch (priv->type) {
609 	case PHY_TYPE_PCIE:
610 		/* Set SSC downward spread spectrum */
611 		val = FIELD_PREP(PHYREG32_SSC_MASK, PHYREG32_SSC_DOWNWARD);
612 		rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK, val, PHYREG32);
613 
614 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con0_for_pcie, true);
615 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con1_for_pcie, true);
616 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con2_for_pcie, true);
617 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con3_for_pcie, true);
618 		break;
619 
620 	case PHY_TYPE_USB3:
621 		/* Set SSC downward spread spectrum */
622 		val = FIELD_PREP(PHYREG32_SSC_MASK, PHYREG32_SSC_DOWNWARD);
623 		rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK, val, PHYREG32);
624 
625 		/* Enable adaptive CTLE for USB3.0 Rx */
626 		val = readl(priv->mmio + PHYREG15);
627 		val |= PHYREG15_CTLE_EN;
628 		writel(val, priv->mmio + PHYREG15);
629 
630 		/* Set PLL KVCO fine tuning signals */
631 		rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK, BIT(3), PHYREG33);
632 
633 		/* Set PLL LPF R1 to su_trim[10:7]=1001 */
634 		writel(PHYREG12_PLL_LPF_ADJ_VALUE, priv->mmio + PHYREG12);
635 
636 		/* Set PLL input clock divider 1/2 */
637 		val = FIELD_PREP(PHYREG6_PLL_DIV_MASK, PHYREG6_PLL_DIV_2);
638 		rockchip_combphy_updatel(priv, PHYREG6_PLL_DIV_MASK, val, PHYREG6);
639 
640 		/* Set PLL loop divider */
641 		writel(PHYREG18_PLL_LOOP, priv->mmio + PHYREG18);
642 
643 		/* Set PLL KVCO to min and set PLL charge pump current to max */
644 		writel(PHYREG11_SU_TRIM_0_7, priv->mmio + PHYREG11);
645 
646 		/* Set Rx squelch input filler bandwidth */
647 		writel(PHYREG21_RX_SQUELCH_VAL, priv->mmio + PHYREG21);
648 
649 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_txcomp_sel, false);
650 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_txelec_sel, false);
651 		rockchip_combphy_param_write(priv->phy_grf, &cfg->usb_mode_set, true);
652 		break;
653 
654 	case PHY_TYPE_SATA:
655 		/* Enable adaptive CTLE for SATA Rx */
656 		val = readl(priv->mmio + PHYREG15);
657 		val |= PHYREG15_CTLE_EN;
658 		writel(val, priv->mmio + PHYREG15);
659 
660 		/* Set tx_rterm = 50 ohm and rx_rterm = 43.5 ohm */
661 		val = PHYREG7_TX_RTERM_50OHM << PHYREG7_TX_RTERM_SHIFT;
662 		val |= PHYREG7_RX_RTERM_44OHM << PHYREG7_RX_RTERM_SHIFT;
663 		writel(val, priv->mmio + PHYREG7);
664 
665 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con0_for_sata, true);
666 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con1_for_sata, true);
667 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con2_for_sata, true);
668 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con3_for_sata, true);
669 		rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_con0_for_sata, true);
670 		rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_con1_for_sata, true);
671 		break;
672 
673 	default:
674 		dev_err(priv->dev, "incompatible PHY type\n");
675 		return -EINVAL;
676 	}
677 
678 	rate = clk_get_rate(priv->refclk);
679 
680 	switch (rate) {
681 	case REF_CLOCK_24MHz:
682 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_24m, true);
683 		if (priv->type == PHY_TYPE_USB3 || priv->type == PHY_TYPE_SATA) {
684 			/* Set ssc_cnt[9:0]=0101111101 & 31.5KHz */
685 			val = FIELD_PREP(PHYREG15_SSC_CNT_MASK, PHYREG15_SSC_CNT_VALUE);
686 			rockchip_combphy_updatel(priv, PHYREG15_SSC_CNT_MASK,
687 						 val, PHYREG15);
688 
689 			writel(PHYREG16_SSC_CNT_VALUE, priv->mmio + PHYREG16);
690 		} else if (priv->type == PHY_TYPE_PCIE) {
691 			/* PLL KVCO tuning fine */
692 			val = FIELD_PREP(PHYREG33_PLL_KVCO_MASK, PHYREG33_PLL_KVCO_VALUE_RK3576);
693 			rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK,
694 						 val, PHYREG33);
695 
696 			/* Set up rx_pck invert and rx msb to disable */
697 			writel(0x00, priv->mmio + PHYREG27);
698 
699 			/*
700 			 * Set up SU adjust signal:
701 			 * su_trim[7:0],   PLL KVCO adjust bits[2:0] to min
702 			 * su_trim[15:8],  PLL LPF R1 adujst bits[9:7]=3'b011
703 			 * su_trim[31:24], CKDRV adjust
704 			 */
705 			writel(0x90, priv->mmio + PHYREG11);
706 			writel(0x02, priv->mmio + PHYREG12);
707 			writel(0x57, priv->mmio + PHYREG14);
708 
709 			writel(PHYREG16_SSC_CNT_VALUE, priv->mmio + PHYREG16);
710 		}
711 		break;
712 
713 	case REF_CLOCK_25MHz:
714 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_25m, true);
715 		break;
716 
717 	case REF_CLOCK_100MHz:
718 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_100m, true);
719 		if (priv->type == PHY_TYPE_PCIE) {
720 			/* gate_tx_pck_sel length select work for L1SS */
721 			writel(0xc0, priv->mmio + PHYREG30);
722 
723 			/* PLL KVCO tuning fine */
724 			val = FIELD_PREP(PHYREG33_PLL_KVCO_MASK, PHYREG33_PLL_KVCO_VALUE_RK3576);
725 			rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK,
726 						 val, PHYREG33);
727 
728 			/* Set up rx_trim: PLL LPF C1 85pf R1 1.25kohm */
729 			writel(0x4c, priv->mmio + PHYREG27);
730 
731 			/*
732 			 * Set up SU adjust signal:
733 			 * su_trim[7:0],   PLL KVCO adjust bits[2:0] to min
734 			 * su_trim[15:8],  bypass PLL loop divider code, and
735 			 *                 PLL LPF R1 adujst bits[9:7]=3'b101
736 			 * su_trim[23:16], CKRCV adjust
737 			 * su_trim[31:24], CKDRV adjust
738 			 */
739 			writel(0x90, priv->mmio + PHYREG11);
740 			writel(0x43, priv->mmio + PHYREG12);
741 			writel(0x88, priv->mmio + PHYREG13);
742 			writel(0x56, priv->mmio + PHYREG14);
743 		} else if (priv->type == PHY_TYPE_SATA) {
744 			/* downward spread spectrum +500ppm */
745 			val = FIELD_PREP(PHYREG32_SSC_DIR_MASK, PHYREG32_SSC_DOWNWARD);
746 			val |= FIELD_PREP(PHYREG32_SSC_OFFSET_MASK, PHYREG32_SSC_OFFSET_500PPM);
747 			rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK, val, PHYREG32);
748 
749 			/* ssc ppm adjust to 3500ppm */
750 			rockchip_combphy_updatel(priv, PHYREG10_SSC_PCM_MASK,
751 						 PHYREG10_SSC_PCM_3500PPM,
752 						 PHYREG10);
753 		}
754 		break;
755 
756 	default:
757 		dev_err(priv->dev, "Unsupported rate: %lu\n", rate);
758 		return -EINVAL;
759 	}
760 
761 	if (priv->ext_refclk) {
762 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_ext, true);
763 		if (priv->type == PHY_TYPE_PCIE && rate == REF_CLOCK_100MHz) {
764 			val = FIELD_PREP(PHYREG33_PLL_KVCO_MASK, PHYREG33_PLL_KVCO_VALUE_RK3576);
765 			rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK,
766 						 val, PHYREG33);
767 
768 			/* Set up rx_trim: PLL LPF C1 85pf R1 2.5kohm */
769 			writel(0x0c, priv->mmio + PHYREG27);
770 
771 			/*
772 			 * Set up SU adjust signal:
773 			 * su_trim[7:0],   PLL KVCO adjust bits[2:0] to min
774 			 * su_trim[15:8],  bypass PLL loop divider code, and
775 			 *                 PLL LPF R1 adujst bits[9:7]=3'b101.
776 			 * su_trim[23:16], CKRCV adjust
777 			 * su_trim[31:24], CKDRV adjust
778 			 */
779 			writel(0x90, priv->mmio + PHYREG11);
780 			writel(0x43, priv->mmio + PHYREG12);
781 			writel(0x88, priv->mmio + PHYREG13);
782 			writel(0x56, priv->mmio + PHYREG14);
783 		}
784 	}
785 
786 	if (priv->enable_ssc) {
787 		val = readl(priv->mmio + PHYREG8);
788 		val |= PHYREG8_SSC_EN;
789 		writel(val, priv->mmio + PHYREG8);
790 
791 		if (priv->type == PHY_TYPE_PCIE && rate == REF_CLOCK_24MHz) {
792 			/* Set PLL loop divider */
793 			writel(0x00, priv->mmio + PHYREG17);
794 			writel(PHYREG18_PLL_LOOP, priv->mmio + PHYREG18);
795 
796 			/* Set up rx_pck invert and rx msb to disable */
797 			writel(0x00, priv->mmio + PHYREG27);
798 
799 			/*
800 			 * Set up SU adjust signal:
801 			 * su_trim[7:0],   PLL KVCO adjust bits[2:0] to min
802 			 * su_trim[15:8],  PLL LPF R1 adujst bits[9:7]=3'b101
803 			 * su_trim[23:16], CKRCV adjust
804 			 * su_trim[31:24], CKDRV adjust
805 			 */
806 			writel(0x90, priv->mmio + PHYREG11);
807 			writel(0x02, priv->mmio + PHYREG12);
808 			writel(0x08, priv->mmio + PHYREG13);
809 			writel(0x57, priv->mmio + PHYREG14);
810 			writel(0x40, priv->mmio + PHYREG15);
811 
812 			writel(PHYREG16_SSC_CNT_VALUE, priv->mmio + PHYREG16);
813 
814 			val = FIELD_PREP(PHYREG33_PLL_KVCO_MASK, PHYREG33_PLL_KVCO_VALUE_RK3576);
815 			writel(val, priv->mmio + PHYREG33);
816 		}
817 	}
818 
819 	return 0;
820 }
821 
822 static const struct rockchip_combphy_grfcfg rk3576_combphy_grfcfgs = {
823 	/* pipe-phy-grf */
824 	.pcie_mode_set		= { 0x0000, 5, 0, 0x00, 0x11 },
825 	.usb_mode_set		= { 0x0000, 5, 0, 0x00, 0x04 },
826 	.pipe_rxterm_set	= { 0x0000, 12, 12, 0x00, 0x01 },
827 	.pipe_txelec_set	= { 0x0004, 1, 1, 0x00, 0x01 },
828 	.pipe_txcomp_set	= { 0x0004, 4, 4, 0x00, 0x01 },
829 	.pipe_clk_24m		= { 0x0004, 14, 13, 0x00, 0x00 },
830 	.pipe_clk_25m		= { 0x0004, 14, 13, 0x00, 0x01 },
831 	.pipe_clk_100m		= { 0x0004, 14, 13, 0x00, 0x02 },
832 	.pipe_phymode_sel	= { 0x0008, 1, 1, 0x00, 0x01 },
833 	.pipe_rate_sel		= { 0x0008, 2, 2, 0x00, 0x01 },
834 	.pipe_rxterm_sel	= { 0x0008, 8, 8, 0x00, 0x01 },
835 	.pipe_txelec_sel	= { 0x0008, 12, 12, 0x00, 0x01 },
836 	.pipe_txcomp_sel	= { 0x0008, 15, 15, 0x00, 0x01 },
837 	.pipe_clk_ext		= { 0x000c, 9, 8, 0x02, 0x01 },
838 	.pipe_phy_status	= { 0x0034, 6, 6, 0x01, 0x00 },
839 	.con0_for_pcie		= { 0x0000, 15, 0, 0x00, 0x1000 },
840 	.con1_for_pcie		= { 0x0004, 15, 0, 0x00, 0x0000 },
841 	.con2_for_pcie		= { 0x0008, 15, 0, 0x00, 0x0101 },
842 	.con3_for_pcie		= { 0x000c, 15, 0, 0x00, 0x0200 },
843 	.con0_for_sata		= { 0x0000, 15, 0, 0x00, 0x0129 },
844 	.con1_for_sata		= { 0x0004, 15, 0, 0x00, 0x0000 },
845 	.con2_for_sata		= { 0x0008, 15, 0, 0x00, 0x80c1 },
846 	.con3_for_sata		= { 0x000c, 15, 0, 0x00, 0x0407 },
847 	/* php-grf */
848 	.pipe_con0_for_sata	= { 0x001C, 2, 0, 0x00, 0x2 },
849 	.pipe_con1_for_sata	= { 0x0020, 2, 0, 0x00, 0x2 },
850 };
851 
852 static const struct rockchip_combphy_cfg rk3576_combphy_cfgs = {
853 	.num_phys = 2,
854 	.phy_ids = {
855 		0x2b050000,
856 		0x2b060000
857 	},
858 	.grfcfg		= &rk3576_combphy_grfcfgs,
859 	.combphy_cfg	= rk3576_combphy_cfg,
860 };
861 
862 static int rk3588_combphy_cfg(struct rockchip_combphy_priv *priv)
863 {
864 	const struct rockchip_combphy_grfcfg *cfg = priv->cfg->grfcfg;
865 	unsigned long rate;
866 	u32 val;
867 
868 	switch (priv->type) {
869 	case PHY_TYPE_PCIE:
870 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con0_for_pcie, true);
871 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con1_for_pcie, true);
872 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con2_for_pcie, true);
873 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con3_for_pcie, true);
874 		switch (priv->id) {
875 		case 1:
876 			rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_pcie1l0_sel, true);
877 			break;
878 		case 2:
879 			rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_pcie1l1_sel, true);
880 			break;
881 		}
882 		break;
883 	case PHY_TYPE_USB3:
884 		/* Set SSC downward spread spectrum */
885 		rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK,
886 					 PHYREG32_SSC_DOWNWARD << PHYREG32_SSC_DIR_SHIFT,
887 					 PHYREG32);
888 
889 		/* Enable adaptive CTLE for USB3.0 Rx. */
890 		val = readl(priv->mmio + PHYREG15);
891 		val |= PHYREG15_CTLE_EN;
892 		writel(val, priv->mmio + PHYREG15);
893 
894 		/* Set PLL KVCO fine tuning signals. */
895 		rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK,
896 					 PHYREG33_PLL_KVCO_VALUE << PHYREG33_PLL_KVCO_SHIFT,
897 					 PHYREG33);
898 
899 		/* Enable controlling random jitter. */
900 		writel(PHYREG12_PLL_LPF_ADJ_VALUE, priv->mmio + PHYREG12);
901 
902 		/* Set PLL input clock divider 1/2. */
903 		rockchip_combphy_updatel(priv, PHYREG6_PLL_DIV_MASK,
904 					 PHYREG6_PLL_DIV_2 << PHYREG6_PLL_DIV_SHIFT,
905 					 PHYREG6);
906 
907 		writel(PHYREG18_PLL_LOOP, priv->mmio + PHYREG18);
908 		writel(PHYREG11_SU_TRIM_0_7, priv->mmio + PHYREG11);
909 
910 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_txcomp_sel, false);
911 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_txelec_sel, false);
912 		rockchip_combphy_param_write(priv->phy_grf, &cfg->usb_mode_set, true);
913 		break;
914 	case PHY_TYPE_SATA:
915 		/* Enable adaptive CTLE for SATA Rx. */
916 		val = readl(priv->mmio + PHYREG15);
917 		val |= PHYREG15_CTLE_EN;
918 		writel(val, priv->mmio + PHYREG15);
919 		/*
920 		 * Set tx_rterm=50ohm and rx_rterm=44ohm for SATA.
921 		 * 0: 60ohm, 8: 50ohm 15: 44ohm (by step abort 1ohm)
922 		 */
923 		val = PHYREG7_TX_RTERM_50OHM << PHYREG7_TX_RTERM_SHIFT;
924 		val |= PHYREG7_RX_RTERM_44OHM << PHYREG7_RX_RTERM_SHIFT;
925 		writel(val, priv->mmio + PHYREG7);
926 
927 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con0_for_sata, true);
928 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con1_for_sata, true);
929 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con2_for_sata, true);
930 		rockchip_combphy_param_write(priv->phy_grf, &cfg->con3_for_sata, true);
931 		rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_con0_for_sata, true);
932 		rockchip_combphy_param_write(priv->pipe_grf, &cfg->pipe_con1_for_sata, true);
933 		break;
934 	case PHY_TYPE_SGMII:
935 	case PHY_TYPE_QSGMII:
936 	default:
937 		dev_err(priv->dev, "incompatible PHY type\n");
938 		return -EINVAL;
939 	}
940 
941 	rate = clk_get_rate(priv->refclk);
942 
943 	switch (rate) {
944 	case REF_CLOCK_24MHz:
945 		if (priv->type == PHY_TYPE_USB3 || priv->type == PHY_TYPE_SATA) {
946 			/* Set ssc_cnt[9:0]=0101111101 & 31.5KHz. */
947 			val = PHYREG15_SSC_CNT_VALUE << PHYREG15_SSC_CNT_SHIFT;
948 			rockchip_combphy_updatel(priv, PHYREG15_SSC_CNT_MASK,
949 						 val, PHYREG15);
950 
951 			writel(PHYREG16_SSC_CNT_VALUE, priv->mmio + PHYREG16);
952 		}
953 		break;
954 
955 	case REF_CLOCK_25MHz:
956 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_25m, true);
957 		break;
958 	case REF_CLOCK_100MHz:
959 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_100m, true);
960 		if (priv->type == PHY_TYPE_PCIE) {
961 			/* PLL KVCO fine tuning. */
962 			val = 4 << PHYREG33_PLL_KVCO_SHIFT;
963 			rockchip_combphy_updatel(priv, PHYREG33_PLL_KVCO_MASK,
964 						 val, PHYREG33);
965 
966 			/* Enable controlling random jitter. */
967 			writel(PHYREG12_PLL_LPF_ADJ_VALUE, priv->mmio + PHYREG12);
968 
969 			/* Set up rx_trim: PLL LPF C1 85pf R1 1.25kohm */
970 			writel(PHYREG27_RX_TRIM_RK3588, priv->mmio + PHYREG27);
971 
972 			/* Set up su_trim:  */
973 			writel(PHYREG11_SU_TRIM_0_7, priv->mmio + PHYREG11);
974 		} else if (priv->type == PHY_TYPE_SATA) {
975 			/* downward spread spectrum +500ppm */
976 			val = PHYREG32_SSC_DOWNWARD << PHYREG32_SSC_DIR_SHIFT;
977 			val |= PHYREG32_SSC_OFFSET_500PPM << PHYREG32_SSC_OFFSET_SHIFT;
978 			rockchip_combphy_updatel(priv, PHYREG32_SSC_MASK, val, PHYREG32);
979 		}
980 		break;
981 	default:
982 		dev_err(priv->dev, "Unsupported rate: %lu\n", rate);
983 		return -EINVAL;
984 	}
985 
986 	if (priv->ext_refclk) {
987 		rockchip_combphy_param_write(priv->phy_grf, &cfg->pipe_clk_ext, true);
988 		if (priv->type == PHY_TYPE_PCIE && rate == REF_CLOCK_100MHz) {
989 			val = PHYREG13_RESISTER_HIGH_Z << PHYREG13_RESISTER_SHIFT;
990 			val |= PHYREG13_CKRCV_AMP0;
991 			rockchip_combphy_updatel(priv, PHYREG13_RESISTER_MASK, val, PHYREG13);
992 
993 			val = readl(priv->mmio + PHYREG14);
994 			val |= PHYREG14_CKRCV_AMP1;
995 			writel(val, priv->mmio + PHYREG14);
996 		}
997 	}
998 
999 	if (priv->enable_ssc) {
1000 		val = readl(priv->mmio + PHYREG8);
1001 		val |= PHYREG8_SSC_EN;
1002 		writel(val, priv->mmio + PHYREG8);
1003 	}
1004 
1005 	return 0;
1006 }
1007 
1008 static const struct rockchip_combphy_grfcfg rk3588_combphy_grfcfgs = {
1009 	/* pipe-phy-grf */
1010 	.pcie_mode_set		= { 0x0000, 5, 0, 0x00, 0x11 },
1011 	.usb_mode_set		= { 0x0000, 5, 0, 0x00, 0x04 },
1012 	.pipe_rxterm_set	= { 0x0000, 12, 12, 0x00, 0x01 },
1013 	.pipe_txelec_set	= { 0x0004, 1, 1, 0x00, 0x01 },
1014 	.pipe_txcomp_set	= { 0x0004, 4, 4, 0x00, 0x01 },
1015 	.pipe_clk_25m		= { 0x0004, 14, 13, 0x00, 0x01 },
1016 	.pipe_clk_100m		= { 0x0004, 14, 13, 0x00, 0x02 },
1017 	.pipe_rxterm_sel	= { 0x0008, 8, 8, 0x00, 0x01 },
1018 	.pipe_txelec_sel	= { 0x0008, 12, 12, 0x00, 0x01 },
1019 	.pipe_txcomp_sel	= { 0x0008, 15, 15, 0x00, 0x01 },
1020 	.pipe_clk_ext		= { 0x000c, 9, 8, 0x02, 0x01 },
1021 	.pipe_phy_status	= { 0x0034, 6, 6, 0x01, 0x00 },
1022 	.con0_for_pcie		= { 0x0000, 15, 0, 0x00, 0x1000 },
1023 	.con1_for_pcie		= { 0x0004, 15, 0, 0x00, 0x0000 },
1024 	.con2_for_pcie		= { 0x0008, 15, 0, 0x00, 0x0101 },
1025 	.con3_for_pcie		= { 0x000c, 15, 0, 0x00, 0x0200 },
1026 	.con0_for_sata		= { 0x0000, 15, 0, 0x00, 0x0129 },
1027 	.con1_for_sata		= { 0x0004, 15, 0, 0x00, 0x0000 },
1028 	.con2_for_sata		= { 0x0008, 15, 0, 0x00, 0x80c1 },
1029 	.con3_for_sata		= { 0x000c, 15, 0, 0x00, 0x0407 },
1030 	/* pipe-grf */
1031 	.pipe_con0_for_sata	= { 0x0000, 11, 5, 0x00, 0x22 },
1032 	.pipe_con1_for_sata	= { 0x0000, 2, 0, 0x00, 0x2 },
1033 	.pipe_pcie1l0_sel	= { 0x0100, 0, 0, 0x01, 0x0 },
1034 	.pipe_pcie1l1_sel	= { 0x0100, 1, 1, 0x01, 0x0 },
1035 };
1036 
1037 static const struct rockchip_combphy_cfg rk3588_combphy_cfgs = {
1038 	.num_phys = 3,
1039 	.phy_ids = {
1040 		0xfee00000,
1041 		0xfee10000,
1042 		0xfee20000,
1043 	},
1044 	.grfcfg		= &rk3588_combphy_grfcfgs,
1045 	.combphy_cfg	= rk3588_combphy_cfg,
1046 };
1047 
1048 static const struct of_device_id rockchip_combphy_of_match[] = {
1049 	{
1050 		.compatible = "rockchip,rk3568-naneng-combphy",
1051 		.data = &rk3568_combphy_cfgs,
1052 	},
1053 	{
1054 		.compatible = "rockchip,rk3576-naneng-combphy",
1055 		.data = &rk3576_combphy_cfgs,
1056 	},
1057 	{
1058 		.compatible = "rockchip,rk3588-naneng-combphy",
1059 		.data = &rk3588_combphy_cfgs,
1060 	},
1061 	{ },
1062 };
1063 MODULE_DEVICE_TABLE(of, rockchip_combphy_of_match);
1064 
1065 static struct platform_driver rockchip_combphy_driver = {
1066 	.probe	= rockchip_combphy_probe,
1067 	.driver = {
1068 		.name = "rockchip-naneng-combphy",
1069 		.of_match_table = rockchip_combphy_of_match,
1070 	},
1071 };
1072 module_platform_driver(rockchip_combphy_driver);
1073 
1074 MODULE_DESCRIPTION("Rockchip NANENG COMBPHY driver");
1075 MODULE_LICENSE("GPL v2");
1076