xref: /openbmc/linux/drivers/clk/qcom/dispcc-sc7280.c (revision 1dd0dd0b)
1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3  * Copyright (c) 2021-2022, The Linux Foundation. All rights reserved.
4  */
5 
6 #include <linux/clk-provider.h>
7 #include <linux/module.h>
8 #include <linux/platform_device.h>
9 #include <linux/regmap.h>
10 
11 #include <dt-bindings/clock/qcom,dispcc-sc7280.h>
12 
13 #include "clk-alpha-pll.h"
14 #include "clk-branch.h"
15 #include "clk-rcg.h"
16 #include "clk-regmap-divider.h"
17 #include "common.h"
18 #include "gdsc.h"
19 
20 enum {
21 	P_BI_TCXO,
22 	P_DISP_CC_PLL0_OUT_EVEN,
23 	P_DISP_CC_PLL0_OUT_MAIN,
24 	P_DP_PHY_PLL_LINK_CLK,
25 	P_DP_PHY_PLL_VCO_DIV_CLK,
26 	P_DSI0_PHY_PLL_OUT_BYTECLK,
27 	P_DSI0_PHY_PLL_OUT_DSICLK,
28 	P_EDP_PHY_PLL_LINK_CLK,
29 	P_EDP_PHY_PLL_VCO_DIV_CLK,
30 	P_GCC_DISP_GPLL0_CLK,
31 };
32 
33 static const struct pll_vco lucid_vco[] = {
34 	{ 249600000, 2000000000, 0 },
35 };
36 
37 /* 1520MHz Configuration*/
38 static const struct alpha_pll_config disp_cc_pll0_config = {
39 	.l = 0x4F,
40 	.alpha = 0x2AAA,
41 	.config_ctl_val = 0x20485699,
42 	.config_ctl_hi_val = 0x00002261,
43 	.config_ctl_hi1_val = 0x329A299C,
44 	.user_ctl_val = 0x00000001,
45 	.user_ctl_hi_val = 0x00000805,
46 	.user_ctl_hi1_val = 0x00000000,
47 };
48 
49 static struct clk_alpha_pll disp_cc_pll0 = {
50 	.offset = 0x0,
51 	.vco_table = lucid_vco,
52 	.num_vco = ARRAY_SIZE(lucid_vco),
53 	.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_LUCID],
54 	.clkr = {
55 		.hw.init = &(struct clk_init_data){
56 			.name = "disp_cc_pll0",
57 			.parent_data = &(const struct clk_parent_data){
58 				.fw_name = "bi_tcxo",
59 			},
60 			.num_parents = 1,
61 			.ops = &clk_alpha_pll_lucid_ops,
62 		},
63 	},
64 };
65 
66 static const struct parent_map disp_cc_parent_map_0[] = {
67 	{ P_BI_TCXO, 0 },
68 };
69 
70 static const struct clk_parent_data disp_cc_parent_data_0[] = {
71 	{ .fw_name = "bi_tcxo" },
72 };
73 
74 static const struct parent_map disp_cc_parent_map_1[] = {
75 	{ P_BI_TCXO, 0 },
76 	{ P_DP_PHY_PLL_LINK_CLK, 1 },
77 	{ P_DP_PHY_PLL_VCO_DIV_CLK, 2 },
78 };
79 
80 static const struct clk_parent_data disp_cc_parent_data_1[] = {
81 	{ .fw_name = "bi_tcxo" },
82 	{ .fw_name = "dp_phy_pll_link_clk" },
83 	{ .fw_name = "dp_phy_pll_vco_div_clk" },
84 };
85 
86 static const struct parent_map disp_cc_parent_map_2[] = {
87 	{ P_BI_TCXO, 0 },
88 	{ P_DSI0_PHY_PLL_OUT_BYTECLK, 1 },
89 };
90 
91 static const struct clk_parent_data disp_cc_parent_data_2[] = {
92 	{ .fw_name = "bi_tcxo" },
93 	{ .fw_name = "dsi0_phy_pll_out_byteclk" },
94 };
95 
96 static const struct parent_map disp_cc_parent_map_3[] = {
97 	{ P_BI_TCXO, 0 },
98 	{ P_EDP_PHY_PLL_LINK_CLK, 1 },
99 	{ P_EDP_PHY_PLL_VCO_DIV_CLK, 2 },
100 };
101 
102 static const struct clk_parent_data disp_cc_parent_data_3[] = {
103 	{ .fw_name = "bi_tcxo" },
104 	{ .fw_name = "edp_phy_pll_link_clk" },
105 	{ .fw_name = "edp_phy_pll_vco_div_clk" },
106 };
107 
108 static const struct parent_map disp_cc_parent_map_4[] = {
109 	{ P_BI_TCXO, 0 },
110 	{ P_DISP_CC_PLL0_OUT_MAIN, 1 },
111 	{ P_GCC_DISP_GPLL0_CLK, 4 },
112 	{ P_DISP_CC_PLL0_OUT_EVEN, 5 },
113 };
114 
115 static const struct clk_parent_data disp_cc_parent_data_4[] = {
116 	{ .fw_name = "bi_tcxo" },
117 	{ .hw = &disp_cc_pll0.clkr.hw },
118 	{ .fw_name = "gcc_disp_gpll0_clk" },
119 	{ .hw = &disp_cc_pll0.clkr.hw },
120 };
121 
122 static const struct parent_map disp_cc_parent_map_5[] = {
123 	{ P_BI_TCXO, 0 },
124 	{ P_GCC_DISP_GPLL0_CLK, 4 },
125 };
126 
127 static const struct clk_parent_data disp_cc_parent_data_5[] = {
128 	{ .fw_name = "bi_tcxo" },
129 	{ .fw_name = "gcc_disp_gpll0_clk" },
130 };
131 
132 static const struct parent_map disp_cc_parent_map_6[] = {
133 	{ P_BI_TCXO, 0 },
134 	{ P_DSI0_PHY_PLL_OUT_DSICLK, 1 },
135 };
136 
137 static const struct clk_parent_data disp_cc_parent_data_6[] = {
138 	{ .fw_name = "bi_tcxo" },
139 	{ .fw_name = "dsi0_phy_pll_out_dsiclk" },
140 };
141 
142 static const struct freq_tbl ftbl_disp_cc_mdss_ahb_clk_src[] = {
143 	F(19200000, P_BI_TCXO, 1, 0, 0),
144 	F(37500000, P_GCC_DISP_GPLL0_CLK, 16, 0, 0),
145 	F(75000000, P_GCC_DISP_GPLL0_CLK, 8, 0, 0),
146 	{ }
147 };
148 
149 static struct clk_rcg2 disp_cc_mdss_ahb_clk_src = {
150 	.cmd_rcgr = 0x1170,
151 	.mnd_width = 0,
152 	.hid_width = 5,
153 	.parent_map = disp_cc_parent_map_5,
154 	.freq_tbl = ftbl_disp_cc_mdss_ahb_clk_src,
155 	.clkr.hw.init = &(struct clk_init_data){
156 		.name = "disp_cc_mdss_ahb_clk_src",
157 		.parent_data = disp_cc_parent_data_5,
158 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_5),
159 		.ops = &clk_rcg2_shared_ops,
160 	},
161 };
162 
163 static struct clk_rcg2 disp_cc_mdss_byte0_clk_src = {
164 	.cmd_rcgr = 0x10d8,
165 	.mnd_width = 0,
166 	.hid_width = 5,
167 	.parent_map = disp_cc_parent_map_2,
168 	.clkr.hw.init = &(struct clk_init_data){
169 		.name = "disp_cc_mdss_byte0_clk_src",
170 		.parent_data = disp_cc_parent_data_2,
171 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_2),
172 		.flags = CLK_SET_RATE_PARENT,
173 		.ops = &clk_byte2_ops,
174 	},
175 };
176 
177 static const struct freq_tbl ftbl_disp_cc_mdss_dp_aux_clk_src[] = {
178 	F(19200000, P_BI_TCXO, 1, 0, 0),
179 	{ }
180 };
181 
182 static struct clk_rcg2 disp_cc_mdss_dp_aux_clk_src = {
183 	.cmd_rcgr = 0x1158,
184 	.mnd_width = 0,
185 	.hid_width = 5,
186 	.parent_map = disp_cc_parent_map_0,
187 	.freq_tbl = ftbl_disp_cc_mdss_dp_aux_clk_src,
188 	.clkr.hw.init = &(struct clk_init_data){
189 		.name = "disp_cc_mdss_dp_aux_clk_src",
190 		.parent_data = disp_cc_parent_data_0,
191 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_0),
192 		.ops = &clk_rcg2_ops,
193 	},
194 };
195 
196 static struct clk_rcg2 disp_cc_mdss_dp_crypto_clk_src = {
197 	.cmd_rcgr = 0x1128,
198 	.mnd_width = 0,
199 	.hid_width = 5,
200 	.parent_map = disp_cc_parent_map_1,
201 	.clkr.hw.init = &(struct clk_init_data){
202 		.name = "disp_cc_mdss_dp_crypto_clk_src",
203 		.parent_data = disp_cc_parent_data_1,
204 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_1),
205 		.ops = &clk_byte2_ops,
206 	},
207 };
208 
209 static struct clk_rcg2 disp_cc_mdss_dp_link_clk_src = {
210 	.cmd_rcgr = 0x110c,
211 	.mnd_width = 0,
212 	.hid_width = 5,
213 	.parent_map = disp_cc_parent_map_1,
214 	.clkr.hw.init = &(struct clk_init_data){
215 		.name = "disp_cc_mdss_dp_link_clk_src",
216 		.parent_data = disp_cc_parent_data_1,
217 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_1),
218 		.ops = &clk_byte2_ops,
219 	},
220 };
221 
222 static struct clk_rcg2 disp_cc_mdss_dp_pixel_clk_src = {
223 	.cmd_rcgr = 0x1140,
224 	.mnd_width = 16,
225 	.hid_width = 5,
226 	.parent_map = disp_cc_parent_map_1,
227 	.clkr.hw.init = &(struct clk_init_data){
228 		.name = "disp_cc_mdss_dp_pixel_clk_src",
229 		.parent_data = disp_cc_parent_data_1,
230 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_1),
231 		.ops = &clk_dp_ops,
232 	},
233 };
234 
235 static struct clk_rcg2 disp_cc_mdss_edp_aux_clk_src = {
236 	.cmd_rcgr = 0x11d0,
237 	.mnd_width = 0,
238 	.hid_width = 5,
239 	.parent_map = disp_cc_parent_map_0,
240 	.freq_tbl = ftbl_disp_cc_mdss_dp_aux_clk_src,
241 	.clkr.hw.init = &(struct clk_init_data){
242 		.name = "disp_cc_mdss_edp_aux_clk_src",
243 		.parent_data = disp_cc_parent_data_0,
244 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_0),
245 		.ops = &clk_rcg2_ops,
246 	},
247 };
248 
249 static struct clk_rcg2 disp_cc_mdss_edp_link_clk_src = {
250 	.cmd_rcgr = 0x11a0,
251 	.mnd_width = 0,
252 	.hid_width = 5,
253 	.parent_map = disp_cc_parent_map_3,
254 	.clkr.hw.init = &(struct clk_init_data){
255 		.name = "disp_cc_mdss_edp_link_clk_src",
256 		.parent_data = disp_cc_parent_data_3,
257 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
258 		.flags = CLK_SET_RATE_PARENT,
259 		.ops = &clk_byte2_ops,
260 	},
261 };
262 
263 static struct clk_rcg2 disp_cc_mdss_edp_pixel_clk_src = {
264 	.cmd_rcgr = 0x1188,
265 	.mnd_width = 16,
266 	.hid_width = 5,
267 	.parent_map = disp_cc_parent_map_3,
268 	.clkr.hw.init = &(struct clk_init_data){
269 		.name = "disp_cc_mdss_edp_pixel_clk_src",
270 		.parent_data = disp_cc_parent_data_3,
271 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
272 		.ops = &clk_dp_ops,
273 	},
274 };
275 
276 static struct clk_rcg2 disp_cc_mdss_esc0_clk_src = {
277 	.cmd_rcgr = 0x10f4,
278 	.mnd_width = 0,
279 	.hid_width = 5,
280 	.parent_map = disp_cc_parent_map_2,
281 	.freq_tbl = ftbl_disp_cc_mdss_dp_aux_clk_src,
282 	.clkr.hw.init = &(struct clk_init_data){
283 		.name = "disp_cc_mdss_esc0_clk_src",
284 		.parent_data = disp_cc_parent_data_2,
285 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_2),
286 		.ops = &clk_rcg2_ops,
287 	},
288 };
289 
290 static const struct freq_tbl ftbl_disp_cc_mdss_mdp_clk_src[] = {
291 	F(200000000, P_GCC_DISP_GPLL0_CLK, 3, 0, 0),
292 	F(300000000, P_GCC_DISP_GPLL0_CLK, 2, 0, 0),
293 	F(380000000, P_DISP_CC_PLL0_OUT_MAIN, 4, 0, 0),
294 	F(506666667, P_DISP_CC_PLL0_OUT_MAIN, 3, 0, 0),
295 	F(608000000, P_DISP_CC_PLL0_OUT_MAIN, 2.5, 0, 0),
296 	{ }
297 };
298 
299 static struct clk_rcg2 disp_cc_mdss_mdp_clk_src = {
300 	.cmd_rcgr = 0x1090,
301 	.mnd_width = 0,
302 	.hid_width = 5,
303 	.parent_map = disp_cc_parent_map_4,
304 	.freq_tbl = ftbl_disp_cc_mdss_mdp_clk_src,
305 	.clkr.hw.init = &(struct clk_init_data){
306 		.name = "disp_cc_mdss_mdp_clk_src",
307 		.parent_data = disp_cc_parent_data_4,
308 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_4),
309 		.ops = &clk_rcg2_shared_ops,
310 	},
311 };
312 
313 static struct clk_rcg2 disp_cc_mdss_pclk0_clk_src = {
314 	.cmd_rcgr = 0x1078,
315 	.mnd_width = 8,
316 	.hid_width = 5,
317 	.parent_map = disp_cc_parent_map_6,
318 	.clkr.hw.init = &(struct clk_init_data){
319 		.name = "disp_cc_mdss_pclk0_clk_src",
320 		.parent_data = disp_cc_parent_data_6,
321 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_6),
322 		.flags = CLK_SET_RATE_PARENT,
323 		.ops = &clk_pixel_ops,
324 	},
325 };
326 
327 static struct clk_rcg2 disp_cc_mdss_rot_clk_src = {
328 	.cmd_rcgr = 0x10a8,
329 	.mnd_width = 0,
330 	.hid_width = 5,
331 	.parent_map = disp_cc_parent_map_4,
332 	.freq_tbl = ftbl_disp_cc_mdss_mdp_clk_src,
333 	.clkr.hw.init = &(struct clk_init_data){
334 		.name = "disp_cc_mdss_rot_clk_src",
335 		.parent_data = disp_cc_parent_data_4,
336 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_4),
337 		.ops = &clk_rcg2_shared_ops,
338 	},
339 };
340 
341 static struct clk_rcg2 disp_cc_mdss_vsync_clk_src = {
342 	.cmd_rcgr = 0x10c0,
343 	.mnd_width = 0,
344 	.hid_width = 5,
345 	.parent_map = disp_cc_parent_map_0,
346 	.freq_tbl = ftbl_disp_cc_mdss_dp_aux_clk_src,
347 	.clkr.hw.init = &(struct clk_init_data){
348 		.name = "disp_cc_mdss_vsync_clk_src",
349 		.parent_data = disp_cc_parent_data_0,
350 		.num_parents = ARRAY_SIZE(disp_cc_parent_data_0),
351 		.ops = &clk_rcg2_ops,
352 	},
353 };
354 
355 static struct clk_regmap_div disp_cc_mdss_byte0_div_clk_src = {
356 	.reg = 0x10f0,
357 	.shift = 0,
358 	.width = 4,
359 	.clkr.hw.init = &(struct clk_init_data) {
360 		.name = "disp_cc_mdss_byte0_div_clk_src",
361 		.parent_hws = (const struct clk_hw*[]){
362 			&disp_cc_mdss_byte0_clk_src.clkr.hw,
363 		},
364 		.num_parents = 1,
365 		.ops = &clk_regmap_div_ops,
366 	},
367 };
368 
369 static struct clk_regmap_div disp_cc_mdss_dp_link_div_clk_src = {
370 	.reg = 0x1124,
371 	.shift = 0,
372 	.width = 4,
373 	.clkr.hw.init = &(struct clk_init_data) {
374 		.name = "disp_cc_mdss_dp_link_div_clk_src",
375 		.parent_hws = (const struct clk_hw*[]){
376 			&disp_cc_mdss_dp_link_clk_src.clkr.hw,
377 		},
378 		.num_parents = 1,
379 		.ops = &clk_regmap_div_ro_ops,
380 	},
381 };
382 
383 static struct clk_regmap_div disp_cc_mdss_edp_link_div_clk_src = {
384 	.reg = 0x11b8,
385 	.shift = 0,
386 	.width = 4,
387 	.clkr.hw.init = &(struct clk_init_data) {
388 		.name = "disp_cc_mdss_edp_link_div_clk_src",
389 		.parent_hws = (const struct clk_hw*[]){
390 			&disp_cc_mdss_edp_link_clk_src.clkr.hw,
391 		},
392 		.num_parents = 1,
393 		.ops = &clk_regmap_div_ro_ops,
394 	},
395 };
396 
397 static struct clk_branch disp_cc_mdss_ahb_clk = {
398 	.halt_reg = 0x1050,
399 	.halt_check = BRANCH_HALT,
400 	.clkr = {
401 		.enable_reg = 0x1050,
402 		.enable_mask = BIT(0),
403 		.hw.init = &(struct clk_init_data){
404 			.name = "disp_cc_mdss_ahb_clk",
405 			.parent_hws = (const struct clk_hw*[]){
406 				&disp_cc_mdss_ahb_clk_src.clkr.hw,
407 			},
408 			.num_parents = 1,
409 			.flags = CLK_SET_RATE_PARENT,
410 			.ops = &clk_branch2_ops,
411 		},
412 	},
413 };
414 
415 static struct clk_branch disp_cc_mdss_byte0_clk = {
416 	.halt_reg = 0x1030,
417 	.halt_check = BRANCH_HALT,
418 	.clkr = {
419 		.enable_reg = 0x1030,
420 		.enable_mask = BIT(0),
421 		.hw.init = &(struct clk_init_data){
422 			.name = "disp_cc_mdss_byte0_clk",
423 			.parent_hws = (const struct clk_hw*[]){
424 				&disp_cc_mdss_byte0_clk_src.clkr.hw,
425 			},
426 			.num_parents = 1,
427 			.flags = CLK_SET_RATE_PARENT,
428 			.ops = &clk_branch2_ops,
429 		},
430 	},
431 };
432 
433 static struct clk_branch disp_cc_mdss_byte0_intf_clk = {
434 	.halt_reg = 0x1034,
435 	.halt_check = BRANCH_HALT,
436 	.clkr = {
437 		.enable_reg = 0x1034,
438 		.enable_mask = BIT(0),
439 		.hw.init = &(struct clk_init_data){
440 			.name = "disp_cc_mdss_byte0_intf_clk",
441 			.parent_hws = (const struct clk_hw*[]){
442 				&disp_cc_mdss_byte0_div_clk_src.clkr.hw,
443 			},
444 			.num_parents = 1,
445 			.flags = CLK_SET_RATE_PARENT,
446 			.ops = &clk_branch2_ops,
447 		},
448 	},
449 };
450 
451 static struct clk_branch disp_cc_mdss_dp_aux_clk = {
452 	.halt_reg = 0x104c,
453 	.halt_check = BRANCH_HALT,
454 	.clkr = {
455 		.enable_reg = 0x104c,
456 		.enable_mask = BIT(0),
457 		.hw.init = &(struct clk_init_data){
458 			.name = "disp_cc_mdss_dp_aux_clk",
459 			.parent_hws = (const struct clk_hw*[]){
460 				&disp_cc_mdss_dp_aux_clk_src.clkr.hw,
461 			},
462 			.num_parents = 1,
463 			.flags = CLK_SET_RATE_PARENT,
464 			.ops = &clk_branch2_ops,
465 		},
466 	},
467 };
468 
469 static struct clk_branch disp_cc_mdss_dp_crypto_clk = {
470 	.halt_reg = 0x1044,
471 	.halt_check = BRANCH_HALT,
472 	.clkr = {
473 		.enable_reg = 0x1044,
474 		.enable_mask = BIT(0),
475 		.hw.init = &(struct clk_init_data){
476 			.name = "disp_cc_mdss_dp_crypto_clk",
477 			.parent_hws = (const struct clk_hw*[]){
478 				&disp_cc_mdss_dp_crypto_clk_src.clkr.hw,
479 			},
480 			.num_parents = 1,
481 			.flags = CLK_SET_RATE_PARENT,
482 			.ops = &clk_branch2_ops,
483 		},
484 	},
485 };
486 
487 static struct clk_branch disp_cc_mdss_dp_link_clk = {
488 	.halt_reg = 0x103c,
489 	.halt_check = BRANCH_HALT,
490 	.clkr = {
491 		.enable_reg = 0x103c,
492 		.enable_mask = BIT(0),
493 		.hw.init = &(struct clk_init_data){
494 			.name = "disp_cc_mdss_dp_link_clk",
495 			.parent_hws = (const struct clk_hw*[]){
496 				&disp_cc_mdss_dp_link_clk_src.clkr.hw,
497 			},
498 			.num_parents = 1,
499 			.flags = CLK_SET_RATE_PARENT,
500 			.ops = &clk_branch2_ops,
501 		},
502 	},
503 };
504 
505 static struct clk_branch disp_cc_mdss_dp_link_intf_clk = {
506 	.halt_reg = 0x1040,
507 	.halt_check = BRANCH_HALT,
508 	.clkr = {
509 		.enable_reg = 0x1040,
510 		.enable_mask = BIT(0),
511 		.hw.init = &(struct clk_init_data){
512 			.name = "disp_cc_mdss_dp_link_intf_clk",
513 			.parent_hws = (const struct clk_hw*[]){
514 				&disp_cc_mdss_dp_link_div_clk_src.clkr.hw,
515 			},
516 			.num_parents = 1,
517 			.flags = CLK_SET_RATE_PARENT,
518 			.ops = &clk_branch2_ops,
519 		},
520 	},
521 };
522 
523 static struct clk_branch disp_cc_mdss_dp_pixel_clk = {
524 	.halt_reg = 0x1048,
525 	.halt_check = BRANCH_HALT,
526 	.clkr = {
527 		.enable_reg = 0x1048,
528 		.enable_mask = BIT(0),
529 		.hw.init = &(struct clk_init_data){
530 			.name = "disp_cc_mdss_dp_pixel_clk",
531 			.parent_hws = (const struct clk_hw*[]){
532 				&disp_cc_mdss_dp_pixel_clk_src.clkr.hw,
533 			},
534 			.num_parents = 1,
535 			.flags = CLK_SET_RATE_PARENT,
536 			.ops = &clk_branch2_ops,
537 		},
538 	},
539 };
540 
541 static struct clk_branch disp_cc_mdss_edp_aux_clk = {
542 	.halt_reg = 0x1060,
543 	.halt_check = BRANCH_HALT,
544 	.clkr = {
545 		.enable_reg = 0x1060,
546 		.enable_mask = BIT(0),
547 		.hw.init = &(struct clk_init_data){
548 			.name = "disp_cc_mdss_edp_aux_clk",
549 			.parent_hws = (const struct clk_hw*[]){
550 				&disp_cc_mdss_edp_aux_clk_src.clkr.hw,
551 			},
552 			.num_parents = 1,
553 			.flags = CLK_SET_RATE_PARENT,
554 			.ops = &clk_branch2_ops,
555 		},
556 	},
557 };
558 
559 static struct clk_branch disp_cc_mdss_edp_link_clk = {
560 	.halt_reg = 0x1058,
561 	.halt_check = BRANCH_HALT,
562 	.clkr = {
563 		.enable_reg = 0x1058,
564 		.enable_mask = BIT(0),
565 		.hw.init = &(struct clk_init_data){
566 			.name = "disp_cc_mdss_edp_link_clk",
567 			.parent_hws = (const struct clk_hw*[]){
568 				&disp_cc_mdss_edp_link_clk_src.clkr.hw,
569 			},
570 			.num_parents = 1,
571 			.flags = CLK_SET_RATE_PARENT,
572 			.ops = &clk_branch2_ops,
573 		},
574 	},
575 };
576 
577 static struct clk_branch disp_cc_mdss_edp_link_intf_clk = {
578 	.halt_reg = 0x105c,
579 	.halt_check = BRANCH_HALT,
580 	.clkr = {
581 		.enable_reg = 0x105c,
582 		.enable_mask = BIT(0),
583 		.hw.init = &(struct clk_init_data){
584 			.name = "disp_cc_mdss_edp_link_intf_clk",
585 			.parent_hws = (const struct clk_hw*[]){
586 				&disp_cc_mdss_edp_link_div_clk_src.clkr.hw
587 			},
588 			.num_parents = 1,
589 			.flags = CLK_SET_RATE_PARENT,
590 			.ops = &clk_branch2_ops,
591 		},
592 	},
593 };
594 
595 static struct clk_branch disp_cc_mdss_edp_pixel_clk = {
596 	.halt_reg = 0x1054,
597 	.halt_check = BRANCH_HALT,
598 	.clkr = {
599 		.enable_reg = 0x1054,
600 		.enable_mask = BIT(0),
601 		.hw.init = &(struct clk_init_data){
602 			.name = "disp_cc_mdss_edp_pixel_clk",
603 			.parent_hws = (const struct clk_hw*[]){
604 				&disp_cc_mdss_edp_pixel_clk_src.clkr.hw,
605 			},
606 			.num_parents = 1,
607 			.flags = CLK_SET_RATE_PARENT,
608 			.ops = &clk_branch2_ops,
609 		},
610 	},
611 };
612 
613 static struct clk_branch disp_cc_mdss_esc0_clk = {
614 	.halt_reg = 0x1038,
615 	.halt_check = BRANCH_HALT,
616 	.clkr = {
617 		.enable_reg = 0x1038,
618 		.enable_mask = BIT(0),
619 		.hw.init = &(struct clk_init_data){
620 			.name = "disp_cc_mdss_esc0_clk",
621 			.parent_hws = (const struct clk_hw*[]){
622 				&disp_cc_mdss_esc0_clk_src.clkr.hw,
623 			},
624 			.num_parents = 1,
625 			.flags = CLK_SET_RATE_PARENT,
626 			.ops = &clk_branch2_ops,
627 		},
628 	},
629 };
630 
631 static struct clk_branch disp_cc_mdss_mdp_clk = {
632 	.halt_reg = 0x1014,
633 	.halt_check = BRANCH_HALT,
634 	.clkr = {
635 		.enable_reg = 0x1014,
636 		.enable_mask = BIT(0),
637 		.hw.init = &(struct clk_init_data){
638 			.name = "disp_cc_mdss_mdp_clk",
639 			.parent_hws = (const struct clk_hw*[]){
640 				&disp_cc_mdss_mdp_clk_src.clkr.hw,
641 			},
642 			.num_parents = 1,
643 			.flags = CLK_SET_RATE_PARENT,
644 			.ops = &clk_branch2_ops,
645 		},
646 	},
647 };
648 
649 static struct clk_branch disp_cc_mdss_mdp_lut_clk = {
650 	.halt_reg = 0x1024,
651 	.halt_check = BRANCH_HALT_VOTED,
652 	.clkr = {
653 		.enable_reg = 0x1024,
654 		.enable_mask = BIT(0),
655 		.hw.init = &(struct clk_init_data){
656 			.name = "disp_cc_mdss_mdp_lut_clk",
657 			.parent_hws = (const struct clk_hw*[]){
658 				&disp_cc_mdss_mdp_clk_src.clkr.hw,
659 			},
660 			.num_parents = 1,
661 			.flags = CLK_SET_RATE_PARENT,
662 			.ops = &clk_branch2_ops,
663 		},
664 	},
665 };
666 
667 static struct clk_branch disp_cc_mdss_non_gdsc_ahb_clk = {
668 	.halt_reg = 0x2004,
669 	.halt_check = BRANCH_HALT_VOTED,
670 	.clkr = {
671 		.enable_reg = 0x2004,
672 		.enable_mask = BIT(0),
673 		.hw.init = &(struct clk_init_data){
674 			.name = "disp_cc_mdss_non_gdsc_ahb_clk",
675 			.parent_hws = (const struct clk_hw*[]){
676 				&disp_cc_mdss_ahb_clk_src.clkr.hw,
677 			},
678 			.num_parents = 1,
679 			.flags = CLK_SET_RATE_PARENT,
680 			.ops = &clk_branch2_ops,
681 		},
682 	},
683 };
684 
685 static struct clk_branch disp_cc_mdss_pclk0_clk = {
686 	.halt_reg = 0x1010,
687 	.halt_check = BRANCH_HALT,
688 	.clkr = {
689 		.enable_reg = 0x1010,
690 		.enable_mask = BIT(0),
691 		.hw.init = &(struct clk_init_data){
692 			.name = "disp_cc_mdss_pclk0_clk",
693 			.parent_hws = (const struct clk_hw*[]){
694 				&disp_cc_mdss_pclk0_clk_src.clkr.hw,
695 			},
696 			.num_parents = 1,
697 			.flags = CLK_SET_RATE_PARENT,
698 			.ops = &clk_branch2_ops,
699 		},
700 	},
701 };
702 
703 static struct clk_branch disp_cc_mdss_rot_clk = {
704 	.halt_reg = 0x101c,
705 	.halt_check = BRANCH_HALT,
706 	.clkr = {
707 		.enable_reg = 0x101c,
708 		.enable_mask = BIT(0),
709 		.hw.init = &(struct clk_init_data){
710 			.name = "disp_cc_mdss_rot_clk",
711 			.parent_hws = (const struct clk_hw*[]){
712 				&disp_cc_mdss_rot_clk_src.clkr.hw,
713 			},
714 			.num_parents = 1,
715 			.flags = CLK_SET_RATE_PARENT,
716 			.ops = &clk_branch2_ops,
717 		},
718 	},
719 };
720 
721 static struct clk_branch disp_cc_mdss_rscc_ahb_clk = {
722 	.halt_reg = 0x200c,
723 	.halt_check = BRANCH_HALT,
724 	.clkr = {
725 		.enable_reg = 0x200c,
726 		.enable_mask = BIT(0),
727 		.hw.init = &(struct clk_init_data){
728 			.name = "disp_cc_mdss_rscc_ahb_clk",
729 			.parent_hws = (const struct clk_hw*[]){
730 				&disp_cc_mdss_ahb_clk_src.clkr.hw,
731 			},
732 			.num_parents = 1,
733 			.flags = CLK_SET_RATE_PARENT,
734 			.ops = &clk_branch2_ops,
735 		},
736 	},
737 };
738 
739 static struct clk_branch disp_cc_mdss_rscc_vsync_clk = {
740 	.halt_reg = 0x2008,
741 	.halt_check = BRANCH_HALT,
742 	.clkr = {
743 		.enable_reg = 0x2008,
744 		.enable_mask = BIT(0),
745 		.hw.init = &(struct clk_init_data){
746 			.name = "disp_cc_mdss_rscc_vsync_clk",
747 			.parent_hws = (const struct clk_hw*[]){
748 				&disp_cc_mdss_vsync_clk_src.clkr.hw,
749 			},
750 			.num_parents = 1,
751 			.flags = CLK_SET_RATE_PARENT,
752 			.ops = &clk_branch2_ops,
753 		},
754 	},
755 };
756 
757 static struct clk_branch disp_cc_mdss_vsync_clk = {
758 	.halt_reg = 0x102c,
759 	.halt_check = BRANCH_HALT,
760 	.clkr = {
761 		.enable_reg = 0x102c,
762 		.enable_mask = BIT(0),
763 		.hw.init = &(struct clk_init_data){
764 			.name = "disp_cc_mdss_vsync_clk",
765 			.parent_hws = (const struct clk_hw*[]){
766 				&disp_cc_mdss_vsync_clk_src.clkr.hw,
767 			},
768 			.num_parents = 1,
769 			.flags = CLK_SET_RATE_PARENT,
770 			.ops = &clk_branch2_ops,
771 		},
772 	},
773 };
774 
775 static struct clk_branch disp_cc_sleep_clk = {
776 	.halt_reg = 0x5004,
777 	.halt_check = BRANCH_HALT,
778 	.clkr = {
779 		.enable_reg = 0x5004,
780 		.enable_mask = BIT(0),
781 		.hw.init = &(struct clk_init_data){
782 			.name = "disp_cc_sleep_clk",
783 			.ops = &clk_branch2_ops,
784 		},
785 	},
786 };
787 
788 static struct gdsc disp_cc_mdss_core_gdsc = {
789 	.gdscr = 0x1004,
790 	.en_rest_wait_val = 0x2,
791 	.en_few_wait_val = 0x2,
792 	.clk_dis_wait_val = 0xf,
793 	.pd = {
794 		.name = "disp_cc_mdss_core_gdsc",
795 	},
796 	.pwrsts = PWRSTS_OFF_ON,
797 	.flags = HW_CTRL | RETAIN_FF_ENABLE,
798 };
799 
800 static struct clk_regmap *disp_cc_sc7280_clocks[] = {
801 	[DISP_CC_MDSS_AHB_CLK] = &disp_cc_mdss_ahb_clk.clkr,
802 	[DISP_CC_MDSS_AHB_CLK_SRC] = &disp_cc_mdss_ahb_clk_src.clkr,
803 	[DISP_CC_MDSS_BYTE0_CLK] = &disp_cc_mdss_byte0_clk.clkr,
804 	[DISP_CC_MDSS_BYTE0_CLK_SRC] = &disp_cc_mdss_byte0_clk_src.clkr,
805 	[DISP_CC_MDSS_BYTE0_DIV_CLK_SRC] = &disp_cc_mdss_byte0_div_clk_src.clkr,
806 	[DISP_CC_MDSS_BYTE0_INTF_CLK] = &disp_cc_mdss_byte0_intf_clk.clkr,
807 	[DISP_CC_MDSS_DP_AUX_CLK] = &disp_cc_mdss_dp_aux_clk.clkr,
808 	[DISP_CC_MDSS_DP_AUX_CLK_SRC] = &disp_cc_mdss_dp_aux_clk_src.clkr,
809 	[DISP_CC_MDSS_DP_CRYPTO_CLK] = &disp_cc_mdss_dp_crypto_clk.clkr,
810 	[DISP_CC_MDSS_DP_CRYPTO_CLK_SRC] = &disp_cc_mdss_dp_crypto_clk_src.clkr,
811 	[DISP_CC_MDSS_DP_LINK_CLK] = &disp_cc_mdss_dp_link_clk.clkr,
812 	[DISP_CC_MDSS_DP_LINK_CLK_SRC] = &disp_cc_mdss_dp_link_clk_src.clkr,
813 	[DISP_CC_MDSS_DP_LINK_DIV_CLK_SRC] =
814 		&disp_cc_mdss_dp_link_div_clk_src.clkr,
815 	[DISP_CC_MDSS_DP_LINK_INTF_CLK] = &disp_cc_mdss_dp_link_intf_clk.clkr,
816 	[DISP_CC_MDSS_DP_PIXEL_CLK] = &disp_cc_mdss_dp_pixel_clk.clkr,
817 	[DISP_CC_MDSS_DP_PIXEL_CLK_SRC] = &disp_cc_mdss_dp_pixel_clk_src.clkr,
818 	[DISP_CC_MDSS_EDP_AUX_CLK] = &disp_cc_mdss_edp_aux_clk.clkr,
819 	[DISP_CC_MDSS_EDP_AUX_CLK_SRC] = &disp_cc_mdss_edp_aux_clk_src.clkr,
820 	[DISP_CC_MDSS_EDP_LINK_CLK] = &disp_cc_mdss_edp_link_clk.clkr,
821 	[DISP_CC_MDSS_EDP_LINK_CLK_SRC] = &disp_cc_mdss_edp_link_clk_src.clkr,
822 	[DISP_CC_MDSS_EDP_LINK_DIV_CLK_SRC] =
823 		&disp_cc_mdss_edp_link_div_clk_src.clkr,
824 	[DISP_CC_MDSS_EDP_LINK_INTF_CLK] = &disp_cc_mdss_edp_link_intf_clk.clkr,
825 	[DISP_CC_MDSS_EDP_PIXEL_CLK] = &disp_cc_mdss_edp_pixel_clk.clkr,
826 	[DISP_CC_MDSS_EDP_PIXEL_CLK_SRC] = &disp_cc_mdss_edp_pixel_clk_src.clkr,
827 	[DISP_CC_MDSS_ESC0_CLK] = &disp_cc_mdss_esc0_clk.clkr,
828 	[DISP_CC_MDSS_ESC0_CLK_SRC] = &disp_cc_mdss_esc0_clk_src.clkr,
829 	[DISP_CC_MDSS_MDP_CLK] = &disp_cc_mdss_mdp_clk.clkr,
830 	[DISP_CC_MDSS_MDP_CLK_SRC] = &disp_cc_mdss_mdp_clk_src.clkr,
831 	[DISP_CC_MDSS_MDP_LUT_CLK] = &disp_cc_mdss_mdp_lut_clk.clkr,
832 	[DISP_CC_MDSS_NON_GDSC_AHB_CLK] = &disp_cc_mdss_non_gdsc_ahb_clk.clkr,
833 	[DISP_CC_MDSS_PCLK0_CLK] = &disp_cc_mdss_pclk0_clk.clkr,
834 	[DISP_CC_MDSS_PCLK0_CLK_SRC] = &disp_cc_mdss_pclk0_clk_src.clkr,
835 	[DISP_CC_MDSS_ROT_CLK] = &disp_cc_mdss_rot_clk.clkr,
836 	[DISP_CC_MDSS_ROT_CLK_SRC] = &disp_cc_mdss_rot_clk_src.clkr,
837 	[DISP_CC_MDSS_RSCC_AHB_CLK] = &disp_cc_mdss_rscc_ahb_clk.clkr,
838 	[DISP_CC_MDSS_RSCC_VSYNC_CLK] = &disp_cc_mdss_rscc_vsync_clk.clkr,
839 	[DISP_CC_MDSS_VSYNC_CLK] = &disp_cc_mdss_vsync_clk.clkr,
840 	[DISP_CC_MDSS_VSYNC_CLK_SRC] = &disp_cc_mdss_vsync_clk_src.clkr,
841 	[DISP_CC_PLL0] = &disp_cc_pll0.clkr,
842 	[DISP_CC_SLEEP_CLK] = &disp_cc_sleep_clk.clkr,
843 };
844 
845 static struct gdsc *disp_cc_sc7280_gdscs[] = {
846 	[DISP_CC_MDSS_CORE_GDSC] = &disp_cc_mdss_core_gdsc,
847 };
848 
849 static const struct regmap_config disp_cc_sc7280_regmap_config = {
850 	.reg_bits = 32,
851 	.reg_stride = 4,
852 	.val_bits = 32,
853 	.max_register = 0x10000,
854 	.fast_io = true,
855 };
856 
857 static const struct qcom_cc_desc disp_cc_sc7280_desc = {
858 	.config = &disp_cc_sc7280_regmap_config,
859 	.clks = disp_cc_sc7280_clocks,
860 	.num_clks = ARRAY_SIZE(disp_cc_sc7280_clocks),
861 	.gdscs = disp_cc_sc7280_gdscs,
862 	.num_gdscs = ARRAY_SIZE(disp_cc_sc7280_gdscs),
863 };
864 
865 static const struct of_device_id disp_cc_sc7280_match_table[] = {
866 	{ .compatible = "qcom,sc7280-dispcc" },
867 	{ }
868 };
869 MODULE_DEVICE_TABLE(of, disp_cc_sc7280_match_table);
870 
871 static int disp_cc_sc7280_probe(struct platform_device *pdev)
872 {
873 	struct regmap *regmap;
874 
875 	regmap = qcom_cc_map(pdev, &disp_cc_sc7280_desc);
876 	if (IS_ERR(regmap))
877 		return PTR_ERR(regmap);
878 
879 	clk_lucid_pll_configure(&disp_cc_pll0, regmap, &disp_cc_pll0_config);
880 
881 	/*
882 	 * Keep the clocks always-ON
883 	 * DISP_CC_XO_CLK
884 	 */
885 	regmap_update_bits(regmap, 0x5008, BIT(0), BIT(0));
886 
887 	return qcom_cc_really_probe(pdev, &disp_cc_sc7280_desc, regmap);
888 }
889 
890 static struct platform_driver disp_cc_sc7280_driver = {
891 	.probe = disp_cc_sc7280_probe,
892 	.driver = {
893 		.name = "disp_cc-sc7280",
894 		.of_match_table = disp_cc_sc7280_match_table,
895 	},
896 };
897 
898 static int __init disp_cc_sc7280_init(void)
899 {
900 	return platform_driver_register(&disp_cc_sc7280_driver);
901 }
902 subsys_initcall(disp_cc_sc7280_init);
903 
904 static void __exit disp_cc_sc7280_exit(void)
905 {
906 	platform_driver_unregister(&disp_cc_sc7280_driver);
907 }
908 module_exit(disp_cc_sc7280_exit);
909 
910 MODULE_DESCRIPTION("QTI DISP_CC sc7280 Driver");
911 MODULE_LICENSE("GPL v2");
912