Loading...
Note: File does not exist in v3.5.6.
1// SPDX-License-Identifier: GPL-2.0-only
2/*
3 * Copyright (c) 2018, The Linux Foundation. All rights reserved.
4 * Copyright (c) 2024, Danila Tikhonov <danila@jiaxyga.com>
5 * Copyright (c) 2024, David Wronek <david@mainlining.org>
6 */
7
8#include <linux/clk-provider.h>
9#include <linux/mod_devicetable.h>
10#include <linux/module.h>
11#include <linux/of.h>
12#include <linux/platform_device.h>
13#include <linux/regmap.h>
14
15#include <dt-bindings/clock/qcom,sm7150-dispcc.h>
16
17#include "clk-alpha-pll.h"
18#include "clk-branch.h"
19#include "clk-rcg.h"
20#include "clk-regmap.h"
21#include "clk-regmap-divider.h"
22#include "common.h"
23#include "gdsc.h"
24
25enum {
26 DT_BI_TCXO,
27 DT_BI_TCXO_AO,
28 DT_GCC_DISP_GPLL0_CLK,
29 DT_CHIP_SLEEP_CLK,
30 DT_DSI0_PHY_PLL_OUT_BYTECLK,
31 DT_DSI0_PHY_PLL_OUT_DSICLK,
32 DT_DSI1_PHY_PLL_OUT_BYTECLK,
33 DT_DSI1_PHY_PLL_OUT_DSICLK,
34 DT_DP_PHY_PLL_LINK_CLK,
35 DT_DP_PHY_PLL_VCO_DIV_CLK,
36};
37
38enum {
39 P_BI_TCXO,
40 P_CHIP_SLEEP_CLK,
41 P_DISPCC_PLL0_OUT_EVEN,
42 P_DISPCC_PLL0_OUT_MAIN,
43 P_DP_PHY_PLL_LINK_CLK,
44 P_DP_PHY_PLL_VCO_DIV_CLK,
45 P_DSI0_PHY_PLL_OUT_BYTECLK,
46 P_DSI0_PHY_PLL_OUT_DSICLK,
47 P_DSI1_PHY_PLL_OUT_BYTECLK,
48 P_DSI1_PHY_PLL_OUT_DSICLK,
49 P_GCC_DISP_GPLL0_CLK,
50};
51
52static const struct pll_vco fabia_vco[] = {
53 { 249600000, 2000000000, 0 },
54 { 125000000, 1000000000, 1 },
55};
56
57/* 860MHz configuration */
58static const struct alpha_pll_config dispcc_pll0_config = {
59 .l = 0x2c,
60 .alpha = 0xcaaa,
61 .test_ctl_val = 0x40000000,
62};
63
64static struct clk_alpha_pll dispcc_pll0 = {
65 .offset = 0x0,
66 .vco_table = fabia_vco,
67 .num_vco = ARRAY_SIZE(fabia_vco),
68 .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_FABIA],
69 .clkr = {
70 .hw.init = &(const struct clk_init_data) {
71 .name = "dispcc_pll0",
72 .parent_data = &(const struct clk_parent_data) {
73 .index = DT_BI_TCXO,
74 },
75 .num_parents = 1,
76 .ops = &clk_alpha_pll_fabia_ops,
77 },
78 },
79};
80
81static const struct parent_map dispcc_parent_map_0[] = {
82 { P_BI_TCXO, 0 },
83 { P_DSI0_PHY_PLL_OUT_BYTECLK, 1 },
84 { P_DSI1_PHY_PLL_OUT_BYTECLK, 2 },
85};
86
87static const struct clk_parent_data dispcc_parent_data_0[] = {
88 { .index = DT_BI_TCXO },
89 { .index = DT_DSI0_PHY_PLL_OUT_BYTECLK },
90 { .index = DT_DSI1_PHY_PLL_OUT_BYTECLK },
91};
92
93static const struct parent_map dispcc_parent_map_1[] = {
94 { P_BI_TCXO, 0 },
95 { P_DP_PHY_PLL_LINK_CLK, 1 },
96 { P_DP_PHY_PLL_VCO_DIV_CLK, 2 },
97};
98
99static const struct clk_parent_data dispcc_parent_data_1[] = {
100 { .index = DT_BI_TCXO },
101 { .index = DT_DP_PHY_PLL_LINK_CLK },
102 { .index = DT_DP_PHY_PLL_VCO_DIV_CLK },
103};
104
105static const struct parent_map dispcc_parent_map_2[] = {
106 { P_BI_TCXO, 0 },
107};
108
109static const struct clk_parent_data dispcc_parent_data_2[] = {
110 { .index = DT_BI_TCXO },
111};
112
113static const struct clk_parent_data dispcc_parent_data_2_ao[] = {
114 { .index = DT_BI_TCXO_AO },
115};
116
117static const struct parent_map dispcc_parent_map_3[] = {
118 { P_BI_TCXO, 0 },
119 { P_DISPCC_PLL0_OUT_MAIN, 1 },
120 { P_GCC_DISP_GPLL0_CLK, 4 },
121 { P_DISPCC_PLL0_OUT_EVEN, 5 },
122};
123
124static const struct clk_parent_data dispcc_parent_data_3[] = {
125 { .index = DT_BI_TCXO },
126 { .hw = &dispcc_pll0.clkr.hw },
127 { .index = DT_GCC_DISP_GPLL0_CLK },
128 { .hw = &dispcc_pll0.clkr.hw },
129};
130
131static const struct parent_map dispcc_parent_map_4[] = {
132 { P_BI_TCXO, 0 },
133 { P_DSI0_PHY_PLL_OUT_DSICLK, 1 },
134 { P_DSI1_PHY_PLL_OUT_DSICLK, 2 },
135};
136
137static const struct clk_parent_data dispcc_parent_data_4[] = {
138 { .index = DT_BI_TCXO },
139 { .index = DT_DSI0_PHY_PLL_OUT_DSICLK },
140 { .index = DT_DSI1_PHY_PLL_OUT_DSICLK },
141};
142
143static const struct parent_map dispcc_parent_map_5[] = {
144 { P_BI_TCXO, 0 },
145 { P_GCC_DISP_GPLL0_CLK, 4 },
146};
147
148static const struct clk_parent_data dispcc_parent_data_5[] = {
149 { .index = DT_BI_TCXO },
150 { .index = DT_GCC_DISP_GPLL0_CLK },
151};
152
153static const struct parent_map dispcc_parent_map_6[] = {
154 { P_CHIP_SLEEP_CLK, 0 },
155};
156
157static const struct clk_parent_data dispcc_parent_data_6[] = {
158 { .index = DT_CHIP_SLEEP_CLK },
159};
160
161static const struct freq_tbl ftbl_dispcc_mdss_ahb_clk_src[] = {
162 F(19200000, P_BI_TCXO, 1, 0, 0),
163 F(37500000, P_GCC_DISP_GPLL0_CLK, 16, 0, 0),
164 F(75000000, P_GCC_DISP_GPLL0_CLK, 8, 0, 0),
165 { }
166};
167
168static struct clk_rcg2 dispcc_mdss_ahb_clk_src = {
169 .cmd_rcgr = 0x22bc,
170 .mnd_width = 0,
171 .hid_width = 5,
172 .parent_map = dispcc_parent_map_5,
173 .freq_tbl = ftbl_dispcc_mdss_ahb_clk_src,
174 .clkr.hw.init = &(const struct clk_init_data) {
175 .name = "dispcc_mdss_ahb_clk_src",
176 .parent_data = dispcc_parent_data_5,
177 .num_parents = ARRAY_SIZE(dispcc_parent_data_5),
178 .flags = CLK_SET_RATE_PARENT,
179 .ops = &clk_rcg2_shared_ops,
180 },
181};
182
183static const struct freq_tbl ftbl_dispcc_mdss_byte0_clk_src[] = {
184 F(19200000, P_BI_TCXO, 1, 0, 0),
185 { }
186};
187
188static struct clk_rcg2 dispcc_mdss_byte0_clk_src = {
189 .cmd_rcgr = 0x2110,
190 .mnd_width = 0,
191 .hid_width = 5,
192 .parent_map = dispcc_parent_map_0,
193 .clkr.hw.init = &(const struct clk_init_data) {
194 .name = "dispcc_mdss_byte0_clk_src",
195 .parent_data = dispcc_parent_data_0,
196 .num_parents = ARRAY_SIZE(dispcc_parent_data_0),
197 .flags = CLK_SET_RATE_PARENT,
198 .ops = &clk_byte2_ops,
199 },
200};
201
202static struct clk_rcg2 dispcc_mdss_byte1_clk_src = {
203 .cmd_rcgr = 0x212c,
204 .mnd_width = 0,
205 .hid_width = 5,
206 .parent_map = dispcc_parent_map_0,
207 .clkr.hw.init = &(const struct clk_init_data) {
208 .name = "dispcc_mdss_byte1_clk_src",
209 .parent_data = dispcc_parent_data_0,
210 .num_parents = ARRAY_SIZE(dispcc_parent_data_0),
211 .flags = CLK_SET_RATE_PARENT,
212 .ops = &clk_byte2_ops,
213 },
214};
215
216static struct clk_rcg2 dispcc_mdss_dp_aux_clk_src = {
217 .cmd_rcgr = 0x21dc,
218 .mnd_width = 0,
219 .hid_width = 5,
220 .parent_map = dispcc_parent_map_2,
221 .freq_tbl = ftbl_dispcc_mdss_byte0_clk_src,
222 .clkr.hw.init = &(const struct clk_init_data) {
223 .name = "dispcc_mdss_dp_aux_clk_src",
224 .parent_data = dispcc_parent_data_2,
225 .num_parents = ARRAY_SIZE(dispcc_parent_data_2),
226 .ops = &clk_rcg2_ops,
227 },
228};
229
230static const struct freq_tbl ftbl_dispcc_mdss_dp_crypto_clk_src[] = {
231 F(108000, P_DP_PHY_PLL_LINK_CLK, 3, 0, 0),
232 F(180000, P_DP_PHY_PLL_LINK_CLK, 3, 0, 0),
233 F(360000, P_DP_PHY_PLL_LINK_CLK, 1.5, 0, 0),
234 F(540000, P_DP_PHY_PLL_LINK_CLK, 1.5, 0, 0),
235 { }
236};
237
238static struct clk_rcg2 dispcc_mdss_dp_crypto_clk_src = {
239 .cmd_rcgr = 0x2194,
240 .mnd_width = 0,
241 .hid_width = 5,
242 .parent_map = dispcc_parent_map_1,
243 .freq_tbl = ftbl_dispcc_mdss_dp_crypto_clk_src,
244 .clkr.hw.init = &(const struct clk_init_data) {
245 .name = "dispcc_mdss_dp_crypto_clk_src",
246 .parent_data = dispcc_parent_data_1,
247 .num_parents = ARRAY_SIZE(dispcc_parent_data_1),
248 .ops = &clk_rcg2_ops,
249 },
250};
251
252static struct clk_rcg2 dispcc_mdss_dp_link_clk_src = {
253 .cmd_rcgr = 0x2178,
254 .mnd_width = 0,
255 .hid_width = 5,
256 .parent_map = dispcc_parent_map_1,
257 .clkr.hw.init = &(const struct clk_init_data) {
258 .name = "dispcc_mdss_dp_link_clk_src",
259 .parent_data = dispcc_parent_data_1,
260 .num_parents = ARRAY_SIZE(dispcc_parent_data_1),
261 .flags = CLK_SET_RATE_PARENT,
262 .ops = &clk_byte2_ops,
263 },
264};
265
266static struct clk_rcg2 dispcc_mdss_dp_pixel1_clk_src = {
267 .cmd_rcgr = 0x21c4,
268 .mnd_width = 16,
269 .hid_width = 5,
270 .parent_map = dispcc_parent_map_1,
271 .clkr.hw.init = &(const struct clk_init_data) {
272 .name = "dispcc_mdss_dp_pixel1_clk_src",
273 .parent_data = dispcc_parent_data_1,
274 .num_parents = ARRAY_SIZE(dispcc_parent_data_1),
275 .flags = CLK_SET_RATE_PARENT,
276 .ops = &clk_dp_ops,
277 },
278};
279
280static struct clk_rcg2 dispcc_mdss_dp_pixel_clk_src = {
281 .cmd_rcgr = 0x21ac,
282 .mnd_width = 16,
283 .hid_width = 5,
284 .parent_map = dispcc_parent_map_1,
285 .clkr.hw.init = &(const struct clk_init_data) {
286 .name = "dispcc_mdss_dp_pixel_clk_src",
287 .parent_data = dispcc_parent_data_1,
288 .num_parents = ARRAY_SIZE(dispcc_parent_data_1),
289 .flags = CLK_SET_RATE_PARENT,
290 .ops = &clk_dp_ops,
291 },
292};
293
294static struct clk_rcg2 dispcc_mdss_esc0_clk_src = {
295 .cmd_rcgr = 0x2148,
296 .mnd_width = 0,
297 .hid_width = 5,
298 .parent_map = dispcc_parent_map_0,
299 .freq_tbl = ftbl_dispcc_mdss_byte0_clk_src,
300 .clkr.hw.init = &(const struct clk_init_data) {
301 .name = "dispcc_mdss_esc0_clk_src",
302 .parent_data = dispcc_parent_data_0,
303 .num_parents = ARRAY_SIZE(dispcc_parent_data_0),
304 .ops = &clk_rcg2_ops,
305 },
306};
307
308static struct clk_rcg2 dispcc_mdss_esc1_clk_src = {
309 .cmd_rcgr = 0x2160,
310 .mnd_width = 0,
311 .hid_width = 5,
312 .parent_map = dispcc_parent_map_0,
313 .freq_tbl = ftbl_dispcc_mdss_byte0_clk_src,
314 .clkr.hw.init = &(const struct clk_init_data) {
315 .name = "dispcc_mdss_esc1_clk_src",
316 .parent_data = dispcc_parent_data_0,
317 .num_parents = ARRAY_SIZE(dispcc_parent_data_0),
318 .ops = &clk_rcg2_ops,
319 },
320};
321
322static const struct freq_tbl ftbl_dispcc_mdss_mdp_clk_src[] = {
323 F(19200000, P_BI_TCXO, 1, 0, 0),
324 F(85714286, P_GCC_DISP_GPLL0_CLK, 7, 0, 0),
325 F(100000000, P_GCC_DISP_GPLL0_CLK, 6, 0, 0),
326 F(150000000, P_GCC_DISP_GPLL0_CLK, 4, 0, 0),
327 F(172000000, P_DISPCC_PLL0_OUT_MAIN, 5, 0, 0),
328 F(200000000, P_GCC_DISP_GPLL0_CLK, 3, 0, 0),
329 F(286666667, P_DISPCC_PLL0_OUT_MAIN, 3, 0, 0),
330 F(300000000, P_GCC_DISP_GPLL0_CLK, 2, 0, 0),
331 F(344000000, P_DISPCC_PLL0_OUT_MAIN, 2.5, 0, 0),
332 F(430000000, P_DISPCC_PLL0_OUT_MAIN, 2, 0, 0),
333 { }
334};
335
336static struct clk_rcg2 dispcc_mdss_mdp_clk_src = {
337 .cmd_rcgr = 0x20c8,
338 .mnd_width = 0,
339 .hid_width = 5,
340 .parent_map = dispcc_parent_map_3,
341 .freq_tbl = ftbl_dispcc_mdss_mdp_clk_src,
342 .clkr.hw.init = &(const struct clk_init_data) {
343 .name = "dispcc_mdss_mdp_clk_src",
344 .parent_data = dispcc_parent_data_3,
345 .num_parents = ARRAY_SIZE(dispcc_parent_data_3),
346 .flags = CLK_SET_RATE_PARENT,
347 .ops = &clk_rcg2_shared_ops,
348 },
349};
350
351static struct clk_rcg2 dispcc_mdss_pclk0_clk_src = {
352 .cmd_rcgr = 0x2098,
353 .mnd_width = 8,
354 .hid_width = 5,
355 .parent_map = dispcc_parent_map_4,
356 .clkr.hw.init = &(const struct clk_init_data) {
357 .name = "dispcc_mdss_pclk0_clk_src",
358 .parent_data = dispcc_parent_data_4,
359 .num_parents = ARRAY_SIZE(dispcc_parent_data_4),
360 .flags = CLK_SET_RATE_PARENT,
361 .ops = &clk_pixel_ops,
362 },
363};
364
365static struct clk_rcg2 dispcc_mdss_pclk1_clk_src = {
366 .cmd_rcgr = 0x20b0,
367 .mnd_width = 8,
368 .hid_width = 5,
369 .parent_map = dispcc_parent_map_4,
370 .clkr.hw.init = &(const struct clk_init_data) {
371 .name = "dispcc_mdss_pclk1_clk_src",
372 .parent_data = dispcc_parent_data_4,
373 .num_parents = ARRAY_SIZE(dispcc_parent_data_4),
374 .flags = CLK_SET_RATE_PARENT,
375 .ops = &clk_pixel_ops,
376 },
377};
378
379static const struct freq_tbl ftbl_dispcc_mdss_rot_clk_src[] = {
380 F(19200000, P_BI_TCXO, 1, 0, 0),
381 F(171428571, P_GCC_DISP_GPLL0_CLK, 3.5, 0, 0),
382 F(200000000, P_GCC_DISP_GPLL0_CLK, 3, 0, 0),
383 F(300000000, P_GCC_DISP_GPLL0_CLK, 2, 0, 0),
384 F(344000000, P_DISPCC_PLL0_OUT_MAIN, 2.5, 0, 0),
385 F(430000000, P_DISPCC_PLL0_OUT_MAIN, 2, 0, 0),
386 { }
387};
388
389static struct clk_rcg2 dispcc_mdss_rot_clk_src = {
390 .cmd_rcgr = 0x20e0,
391 .mnd_width = 0,
392 .hid_width = 5,
393 .parent_map = dispcc_parent_map_3,
394 .freq_tbl = ftbl_dispcc_mdss_rot_clk_src,
395 .clkr.hw.init = &(const struct clk_init_data) {
396 .name = "dispcc_mdss_rot_clk_src",
397 .parent_data = dispcc_parent_data_3,
398 .num_parents = ARRAY_SIZE(dispcc_parent_data_3),
399 .ops = &clk_rcg2_shared_ops,
400 },
401};
402
403static struct clk_rcg2 dispcc_mdss_vsync_clk_src = {
404 .cmd_rcgr = 0x20f8,
405 .mnd_width = 0,
406 .hid_width = 5,
407 .parent_map = dispcc_parent_map_2,
408 .freq_tbl = ftbl_dispcc_mdss_byte0_clk_src,
409 .clkr.hw.init = &(const struct clk_init_data) {
410 .name = "dispcc_mdss_vsync_clk_src",
411 .parent_data = dispcc_parent_data_2,
412 .num_parents = ARRAY_SIZE(dispcc_parent_data_2),
413 .ops = &clk_rcg2_ops,
414 },
415};
416
417static const struct freq_tbl ftbl_dispcc_sleep_clk_src[] = {
418 F(32000, P_CHIP_SLEEP_CLK, 1, 0, 0),
419 { }
420};
421
422static struct clk_rcg2 dispcc_sleep_clk_src = {
423 .cmd_rcgr = 0x6060,
424 .mnd_width = 0,
425 .hid_width = 5,
426 .parent_map = dispcc_parent_map_6,
427 .freq_tbl = ftbl_dispcc_sleep_clk_src,
428 .clkr.hw.init = &(const struct clk_init_data) {
429 .name = "dispcc_sleep_clk_src",
430 .parent_data = dispcc_parent_data_6,
431 .num_parents = ARRAY_SIZE(dispcc_parent_data_6),
432 .ops = &clk_rcg2_ops,
433 },
434};
435
436static struct clk_rcg2 dispcc_xo_clk_src = {
437 .cmd_rcgr = 0x6044,
438 .mnd_width = 0,
439 .hid_width = 5,
440 .parent_map = dispcc_parent_map_2,
441 .freq_tbl = ftbl_dispcc_mdss_byte0_clk_src,
442 .clkr.hw.init = &(const struct clk_init_data) {
443 .name = "dispcc_xo_clk_src",
444 .parent_data = dispcc_parent_data_2_ao,
445 .num_parents = ARRAY_SIZE(dispcc_parent_data_2_ao),
446 .ops = &clk_rcg2_ops,
447 },
448};
449
450static struct clk_branch dispcc_mdss_ahb_clk = {
451 .halt_reg = 0x2080,
452 .halt_check = BRANCH_HALT,
453 .clkr = {
454 .enable_reg = 0x2080,
455 .enable_mask = BIT(0),
456 .hw.init = &(const struct clk_init_data) {
457 .name = "dispcc_mdss_ahb_clk",
458 .parent_hws = (const struct clk_hw*[]) {
459 &dispcc_mdss_ahb_clk_src.clkr.hw,
460 },
461 .num_parents = 1,
462 .flags = CLK_SET_RATE_PARENT,
463 .ops = &clk_branch2_ops,
464 },
465 },
466};
467
468static struct clk_branch dispcc_mdss_byte0_clk = {
469 .halt_reg = 0x2028,
470 .halt_check = BRANCH_HALT,
471 .clkr = {
472 .enable_reg = 0x2028,
473 .enable_mask = BIT(0),
474 .hw.init = &(const struct clk_init_data) {
475 .name = "dispcc_mdss_byte0_clk",
476 .parent_hws = (const struct clk_hw*[]) {
477 &dispcc_mdss_byte0_clk_src.clkr.hw,
478 },
479 .num_parents = 1,
480 .flags = CLK_SET_RATE_PARENT,
481 .ops = &clk_branch2_ops,
482 },
483 },
484};
485
486static struct clk_regmap_div dispcc_mdss_byte0_div_clk_src = {
487 .reg = 0x2128,
488 .shift = 0,
489 .width = 2,
490 .clkr = {
491 .hw.init = &(const struct clk_init_data) {
492 .name = "dispcc_mdss_byte0_div_clk_src",
493 .parent_hws = (const struct clk_hw*[]) {
494 &dispcc_mdss_byte0_clk_src.clkr.hw,
495 },
496 .num_parents = 1,
497 .ops = &clk_regmap_div_ops,
498 },
499 },
500};
501
502static struct clk_branch dispcc_mdss_byte0_intf_clk = {
503 .halt_reg = 0x202c,
504 .halt_check = BRANCH_HALT,
505 .clkr = {
506 .enable_reg = 0x202c,
507 .enable_mask = BIT(0),
508 .hw.init = &(const struct clk_init_data) {
509 .name = "dispcc_mdss_byte0_intf_clk",
510 .parent_hws = (const struct clk_hw*[]) {
511 &dispcc_mdss_byte0_div_clk_src.clkr.hw,
512 },
513 .num_parents = 1,
514 .ops = &clk_branch2_ops,
515 },
516 },
517};
518
519static struct clk_branch dispcc_mdss_byte1_clk = {
520 .halt_reg = 0x2030,
521 .halt_check = BRANCH_HALT,
522 .clkr = {
523 .enable_reg = 0x2030,
524 .enable_mask = BIT(0),
525 .hw.init = &(const struct clk_init_data) {
526 .name = "dispcc_mdss_byte1_clk",
527 .parent_hws = (const struct clk_hw*[]) {
528 &dispcc_mdss_byte1_clk_src.clkr.hw,
529 },
530 .num_parents = 1,
531 .flags = CLK_SET_RATE_PARENT,
532 .ops = &clk_branch2_ops,
533 },
534 },
535};
536
537static struct clk_regmap_div dispcc_mdss_byte1_div_clk_src = {
538 .reg = 0x2144,
539 .shift = 0,
540 .width = 2,
541 .clkr = {
542 .hw.init = &(const struct clk_init_data) {
543 .name = "dispcc_mdss_byte1_div_clk_src",
544 .parent_hws = (const struct clk_hw*[]) {
545 &dispcc_mdss_byte1_clk_src.clkr.hw,
546 },
547 .num_parents = 1,
548 .ops = &clk_regmap_div_ops,
549 },
550 },
551};
552
553static struct clk_branch dispcc_mdss_byte1_intf_clk = {
554 .halt_reg = 0x2034,
555 .halt_check = BRANCH_HALT,
556 .clkr = {
557 .enable_reg = 0x2034,
558 .enable_mask = BIT(0),
559 .hw.init = &(const struct clk_init_data) {
560 .name = "dispcc_mdss_byte1_intf_clk",
561 .parent_hws = (const struct clk_hw*[]) {
562 &dispcc_mdss_byte1_div_clk_src.clkr.hw,
563 },
564 .num_parents = 1,
565 .flags = CLK_SET_RATE_PARENT,
566 .ops = &clk_branch2_ops,
567 },
568 },
569};
570
571static struct clk_branch dispcc_mdss_dp_aux_clk = {
572 .halt_reg = 0x2054,
573 .halt_check = BRANCH_HALT,
574 .clkr = {
575 .enable_reg = 0x2054,
576 .enable_mask = BIT(0),
577 .hw.init = &(const struct clk_init_data) {
578 .name = "dispcc_mdss_dp_aux_clk",
579 .parent_hws = (const struct clk_hw*[]) {
580 &dispcc_mdss_dp_aux_clk_src.clkr.hw,
581 },
582 .num_parents = 1,
583 .flags = CLK_SET_RATE_PARENT,
584 .ops = &clk_branch2_ops,
585 },
586 },
587};
588
589static struct clk_branch dispcc_mdss_dp_crypto_clk = {
590 .halt_reg = 0x2048,
591 .halt_check = BRANCH_HALT,
592 .clkr = {
593 .enable_reg = 0x2048,
594 .enable_mask = BIT(0),
595 .hw.init = &(const struct clk_init_data) {
596 .name = "dispcc_mdss_dp_crypto_clk",
597 .parent_hws = (const struct clk_hw*[]) {
598 &dispcc_mdss_dp_crypto_clk_src.clkr.hw,
599 },
600 .num_parents = 1,
601 .flags = CLK_SET_RATE_PARENT,
602 .ops = &clk_branch2_ops,
603 },
604 },
605};
606
607static struct clk_branch dispcc_mdss_dp_link_clk = {
608 .halt_reg = 0x2040,
609 .halt_check = BRANCH_HALT,
610 .clkr = {
611 .enable_reg = 0x2040,
612 .enable_mask = BIT(0),
613 .hw.init = &(const struct clk_init_data) {
614 .name = "dispcc_mdss_dp_link_clk",
615 .parent_hws = (const struct clk_hw*[]) {
616 &dispcc_mdss_dp_link_clk_src.clkr.hw,
617 },
618 .num_parents = 1,
619 .flags = CLK_SET_RATE_PARENT,
620 .ops = &clk_branch2_ops,
621 },
622 },
623};
624
625static struct clk_branch dispcc_mdss_dp_link_intf_clk = {
626 .halt_reg = 0x2044,
627 .halt_check = BRANCH_HALT,
628 .clkr = {
629 .enable_reg = 0x2044,
630 .enable_mask = BIT(0),
631 .hw.init = &(const struct clk_init_data) {
632 .name = "dispcc_mdss_dp_link_intf_clk",
633 .parent_hws = (const struct clk_hw*[]) {
634 &dispcc_mdss_dp_link_clk_src.clkr.hw,
635 },
636 .num_parents = 1,
637 .ops = &clk_branch2_ops,
638 },
639 },
640};
641
642static struct clk_branch dispcc_mdss_dp_pixel1_clk = {
643 .halt_reg = 0x2050,
644 .halt_check = BRANCH_HALT,
645 .clkr = {
646 .enable_reg = 0x2050,
647 .enable_mask = BIT(0),
648 .hw.init = &(const struct clk_init_data) {
649 .name = "dispcc_mdss_dp_pixel1_clk",
650 .parent_hws = (const struct clk_hw*[]) {
651 &dispcc_mdss_dp_pixel1_clk_src.clkr.hw,
652 },
653 .num_parents = 1,
654 .flags = CLK_SET_RATE_PARENT,
655 .ops = &clk_branch2_ops,
656 },
657 },
658};
659
660static struct clk_branch dispcc_mdss_dp_pixel_clk = {
661 .halt_reg = 0x204c,
662 .halt_check = BRANCH_HALT,
663 .clkr = {
664 .enable_reg = 0x204c,
665 .enable_mask = BIT(0),
666 .hw.init = &(const struct clk_init_data) {
667 .name = "dispcc_mdss_dp_pixel_clk",
668 .parent_hws = (const struct clk_hw*[]) {
669 &dispcc_mdss_dp_pixel_clk_src.clkr.hw,
670 },
671 .num_parents = 1,
672 .flags = CLK_SET_RATE_PARENT,
673 .ops = &clk_branch2_ops,
674 },
675 },
676};
677
678static struct clk_branch dispcc_mdss_esc0_clk = {
679 .halt_reg = 0x2038,
680 .halt_check = BRANCH_HALT,
681 .clkr = {
682 .enable_reg = 0x2038,
683 .enable_mask = BIT(0),
684 .hw.init = &(const struct clk_init_data) {
685 .name = "dispcc_mdss_esc0_clk",
686 .parent_hws = (const struct clk_hw*[]) {
687 &dispcc_mdss_esc0_clk_src.clkr.hw,
688 },
689 .num_parents = 1,
690 .flags = CLK_SET_RATE_PARENT,
691 .ops = &clk_branch2_ops,
692 },
693 },
694};
695
696static struct clk_branch dispcc_mdss_esc1_clk = {
697 .halt_reg = 0x203c,
698 .halt_check = BRANCH_HALT,
699 .clkr = {
700 .enable_reg = 0x203c,
701 .enable_mask = BIT(0),
702 .hw.init = &(const struct clk_init_data) {
703 .name = "dispcc_mdss_esc1_clk",
704 .parent_hws = (const struct clk_hw*[]) {
705 &dispcc_mdss_esc1_clk_src.clkr.hw,
706 },
707 .num_parents = 1,
708 .flags = CLK_SET_RATE_PARENT,
709 .ops = &clk_branch2_ops,
710 },
711 },
712};
713
714static struct clk_branch dispcc_mdss_mdp_clk = {
715 .halt_reg = 0x200c,
716 .halt_check = BRANCH_HALT,
717 .clkr = {
718 .enable_reg = 0x200c,
719 .enable_mask = BIT(0),
720 .hw.init = &(const struct clk_init_data) {
721 .name = "dispcc_mdss_mdp_clk",
722 .parent_hws = (const struct clk_hw*[]) {
723 &dispcc_mdss_mdp_clk_src.clkr.hw,
724 },
725 .num_parents = 1,
726 .flags = CLK_SET_RATE_PARENT,
727 .ops = &clk_branch2_ops,
728 },
729 },
730};
731
732static struct clk_branch dispcc_mdss_mdp_lut_clk = {
733 .halt_reg = 0x201c,
734 .halt_check = BRANCH_VOTED,
735 .clkr = {
736 .enable_reg = 0x201c,
737 .enable_mask = BIT(0),
738 .hw.init = &(const struct clk_init_data) {
739 .name = "dispcc_mdss_mdp_lut_clk",
740 .parent_hws = (const struct clk_hw*[]) {
741 &dispcc_mdss_mdp_clk_src.clkr.hw,
742 },
743 .num_parents = 1,
744 .ops = &clk_branch2_ops,
745 },
746 },
747};
748
749static struct clk_branch dispcc_mdss_non_gdsc_ahb_clk = {
750 .halt_reg = 0x4004,
751 .halt_check = BRANCH_VOTED,
752 .clkr = {
753 .enable_reg = 0x4004,
754 .enable_mask = BIT(0),
755 .hw.init = &(const struct clk_init_data) {
756 .name = "dispcc_mdss_non_gdsc_ahb_clk",
757 .parent_hws = (const struct clk_hw*[]) {
758 &dispcc_mdss_ahb_clk_src.clkr.hw,
759 },
760 .num_parents = 1,
761 .flags = CLK_SET_RATE_PARENT,
762 .ops = &clk_branch2_ops,
763 },
764 },
765};
766
767static struct clk_branch dispcc_mdss_pclk0_clk = {
768 .halt_reg = 0x2004,
769 .halt_check = BRANCH_HALT,
770 .clkr = {
771 .enable_reg = 0x2004,
772 .enable_mask = BIT(0),
773 .hw.init = &(const struct clk_init_data) {
774 .name = "dispcc_mdss_pclk0_clk",
775 .parent_hws = (const struct clk_hw*[]) {
776 &dispcc_mdss_pclk0_clk_src.clkr.hw,
777 },
778 .num_parents = 1,
779 .flags = CLK_SET_RATE_PARENT,
780 .ops = &clk_branch2_ops,
781 },
782 },
783};
784
785static struct clk_branch dispcc_mdss_pclk1_clk = {
786 .halt_reg = 0x2008,
787 .halt_check = BRANCH_HALT,
788 .clkr = {
789 .enable_reg = 0x2008,
790 .enable_mask = BIT(0),
791 .hw.init = &(const struct clk_init_data) {
792 .name = "dispcc_mdss_pclk1_clk",
793 .parent_hws = (const struct clk_hw*[]) {
794 &dispcc_mdss_pclk1_clk_src.clkr.hw,
795 },
796 .num_parents = 1,
797 .flags = CLK_SET_RATE_PARENT,
798 .ops = &clk_branch2_ops,
799 },
800 },
801};
802
803static struct clk_branch dispcc_mdss_rot_clk = {
804 .halt_reg = 0x2014,
805 .halt_check = BRANCH_HALT,
806 .clkr = {
807 .enable_reg = 0x2014,
808 .enable_mask = BIT(0),
809 .hw.init = &(const struct clk_init_data) {
810 .name = "dispcc_mdss_rot_clk",
811 .parent_hws = (const struct clk_hw*[]) {
812 &dispcc_mdss_rot_clk_src.clkr.hw,
813 },
814 .num_parents = 1,
815 .flags = CLK_SET_RATE_PARENT,
816 .ops = &clk_branch2_ops,
817 },
818 },
819};
820
821static struct clk_branch dispcc_mdss_rscc_ahb_clk = {
822 .halt_reg = 0x400c,
823 .halt_check = BRANCH_HALT,
824 .clkr = {
825 .enable_reg = 0x400c,
826 .enable_mask = BIT(0),
827 .hw.init = &(const struct clk_init_data) {
828 .name = "dispcc_mdss_rscc_ahb_clk",
829 .parent_names = (const char *[]) {
830 "dispcc_mdss_ahb_clk_src",
831 },
832 .num_parents = 1,
833 .flags = CLK_SET_RATE_PARENT,
834 .ops = &clk_branch2_ops,
835 },
836 },
837};
838
839static struct clk_branch dispcc_mdss_rscc_vsync_clk = {
840 .halt_reg = 0x4008,
841 .halt_check = BRANCH_HALT,
842 .clkr = {
843 .enable_reg = 0x4008,
844 .enable_mask = BIT(0),
845 .hw.init = &(const struct clk_init_data) {
846 .name = "dispcc_mdss_rscc_vsync_clk",
847 .parent_hws = (const struct clk_hw*[]) {
848 &dispcc_mdss_vsync_clk_src.clkr.hw,
849 },
850 .num_parents = 1,
851 .flags = CLK_SET_RATE_PARENT,
852 .ops = &clk_branch2_ops,
853 },
854 },
855};
856
857static struct clk_branch dispcc_mdss_vsync_clk = {
858 .halt_reg = 0x2024,
859 .halt_check = BRANCH_HALT,
860 .clkr = {
861 .enable_reg = 0x2024,
862 .enable_mask = BIT(0),
863 .hw.init = &(const struct clk_init_data) {
864 .name = "dispcc_mdss_vsync_clk",
865 .parent_hws = (const struct clk_hw*[]) {
866 &dispcc_mdss_vsync_clk_src.clkr.hw,
867 },
868 .num_parents = 1,
869 .flags = CLK_SET_RATE_PARENT,
870 .ops = &clk_branch2_ops,
871 },
872 },
873};
874
875static struct clk_branch dispcc_sleep_clk = {
876 .halt_reg = 0x6078,
877 .halt_check = BRANCH_HALT,
878 .clkr = {
879 .enable_reg = 0x6078,
880 .enable_mask = BIT(0),
881 .hw.init = &(const struct clk_init_data) {
882 .name = "dispcc_sleep_clk",
883 .parent_names = (const char *[]) {
884 "dispcc_sleep_clk_src",
885 },
886 .num_parents = 1,
887 .flags = CLK_SET_RATE_PARENT,
888 .ops = &clk_branch2_ops,
889 },
890 },
891};
892
893static struct gdsc mdss_gdsc = {
894 .gdscr = 0x3000,
895 .en_rest_wait_val = 0x2,
896 .en_few_wait_val = 0x2,
897 .clk_dis_wait_val = 0xf,
898 .pd = {
899 .name = "mdss_gdsc",
900 },
901 .pwrsts = PWRSTS_OFF_ON,
902 .flags = HW_CTRL,
903};
904
905static struct clk_regmap *dispcc_sm7150_clocks[] = {
906 [DISPCC_MDSS_AHB_CLK] = &dispcc_mdss_ahb_clk.clkr,
907 [DISPCC_MDSS_AHB_CLK_SRC] = &dispcc_mdss_ahb_clk_src.clkr,
908 [DISPCC_MDSS_BYTE0_CLK] = &dispcc_mdss_byte0_clk.clkr,
909 [DISPCC_MDSS_BYTE0_CLK_SRC] = &dispcc_mdss_byte0_clk_src.clkr,
910 [DISPCC_MDSS_BYTE0_DIV_CLK_SRC] = &dispcc_mdss_byte0_div_clk_src.clkr,
911 [DISPCC_MDSS_BYTE0_INTF_CLK] = &dispcc_mdss_byte0_intf_clk.clkr,
912 [DISPCC_MDSS_BYTE1_CLK] = &dispcc_mdss_byte1_clk.clkr,
913 [DISPCC_MDSS_BYTE1_CLK_SRC] = &dispcc_mdss_byte1_clk_src.clkr,
914 [DISPCC_MDSS_BYTE1_DIV_CLK_SRC] = &dispcc_mdss_byte1_div_clk_src.clkr,
915 [DISPCC_MDSS_BYTE1_INTF_CLK] = &dispcc_mdss_byte1_intf_clk.clkr,
916 [DISPCC_MDSS_DP_AUX_CLK] = &dispcc_mdss_dp_aux_clk.clkr,
917 [DISPCC_MDSS_DP_AUX_CLK_SRC] = &dispcc_mdss_dp_aux_clk_src.clkr,
918 [DISPCC_MDSS_DP_CRYPTO_CLK] = &dispcc_mdss_dp_crypto_clk.clkr,
919 [DISPCC_MDSS_DP_CRYPTO_CLK_SRC] = &dispcc_mdss_dp_crypto_clk_src.clkr,
920 [DISPCC_MDSS_DP_LINK_CLK] = &dispcc_mdss_dp_link_clk.clkr,
921 [DISPCC_MDSS_DP_LINK_CLK_SRC] = &dispcc_mdss_dp_link_clk_src.clkr,
922 [DISPCC_MDSS_DP_LINK_INTF_CLK] = &dispcc_mdss_dp_link_intf_clk.clkr,
923 [DISPCC_MDSS_DP_PIXEL1_CLK] = &dispcc_mdss_dp_pixel1_clk.clkr,
924 [DISPCC_MDSS_DP_PIXEL1_CLK_SRC] = &dispcc_mdss_dp_pixel1_clk_src.clkr,
925 [DISPCC_MDSS_DP_PIXEL_CLK] = &dispcc_mdss_dp_pixel_clk.clkr,
926 [DISPCC_MDSS_DP_PIXEL_CLK_SRC] = &dispcc_mdss_dp_pixel_clk_src.clkr,
927 [DISPCC_MDSS_ESC0_CLK] = &dispcc_mdss_esc0_clk.clkr,
928 [DISPCC_MDSS_ESC0_CLK_SRC] = &dispcc_mdss_esc0_clk_src.clkr,
929 [DISPCC_MDSS_ESC1_CLK] = &dispcc_mdss_esc1_clk.clkr,
930 [DISPCC_MDSS_ESC1_CLK_SRC] = &dispcc_mdss_esc1_clk_src.clkr,
931 [DISPCC_MDSS_MDP_CLK] = &dispcc_mdss_mdp_clk.clkr,
932 [DISPCC_MDSS_MDP_CLK_SRC] = &dispcc_mdss_mdp_clk_src.clkr,
933 [DISPCC_MDSS_MDP_LUT_CLK] = &dispcc_mdss_mdp_lut_clk.clkr,
934 [DISPCC_MDSS_NON_GDSC_AHB_CLK] = &dispcc_mdss_non_gdsc_ahb_clk.clkr,
935 [DISPCC_MDSS_PCLK0_CLK] = &dispcc_mdss_pclk0_clk.clkr,
936 [DISPCC_MDSS_PCLK0_CLK_SRC] = &dispcc_mdss_pclk0_clk_src.clkr,
937 [DISPCC_MDSS_PCLK1_CLK] = &dispcc_mdss_pclk1_clk.clkr,
938 [DISPCC_MDSS_PCLK1_CLK_SRC] = &dispcc_mdss_pclk1_clk_src.clkr,
939 [DISPCC_MDSS_ROT_CLK] = &dispcc_mdss_rot_clk.clkr,
940 [DISPCC_MDSS_ROT_CLK_SRC] = &dispcc_mdss_rot_clk_src.clkr,
941 [DISPCC_MDSS_RSCC_AHB_CLK] = &dispcc_mdss_rscc_ahb_clk.clkr,
942 [DISPCC_MDSS_RSCC_VSYNC_CLK] = &dispcc_mdss_rscc_vsync_clk.clkr,
943 [DISPCC_MDSS_VSYNC_CLK] = &dispcc_mdss_vsync_clk.clkr,
944 [DISPCC_MDSS_VSYNC_CLK_SRC] = &dispcc_mdss_vsync_clk_src.clkr,
945 [DISPCC_PLL0] = &dispcc_pll0.clkr,
946 [DISPCC_SLEEP_CLK] = &dispcc_sleep_clk.clkr,
947 [DISPCC_SLEEP_CLK_SRC] = &dispcc_sleep_clk_src.clkr,
948 [DISPCC_XO_CLK_SRC] = &dispcc_xo_clk_src.clkr,
949};
950
951static struct gdsc *dispcc_sm7150_gdscs[] = {
952 [MDSS_GDSC] = &mdss_gdsc,
953};
954
955static const struct regmap_config dispcc_sm7150_regmap_config = {
956 .reg_bits = 32,
957 .reg_stride = 4,
958 .val_bits = 32,
959 .max_register = 0x10000,
960 .fast_io = true,
961};
962
963static const struct qcom_cc_desc dispcc_sm7150_desc = {
964 .config = &dispcc_sm7150_regmap_config,
965 .clks = dispcc_sm7150_clocks,
966 .num_clks = ARRAY_SIZE(dispcc_sm7150_clocks),
967 .gdscs = dispcc_sm7150_gdscs,
968 .num_gdscs = ARRAY_SIZE(dispcc_sm7150_gdscs),
969};
970
971static const struct of_device_id dispcc_sm7150_match_table[] = {
972 { .compatible = "qcom,sm7150-dispcc" },
973 { }
974};
975MODULE_DEVICE_TABLE(of, dispcc_sm7150_match_table);
976
977static int dispcc_sm7150_probe(struct platform_device *pdev)
978{
979 struct regmap *regmap;
980
981 regmap = qcom_cc_map(pdev, &dispcc_sm7150_desc);
982 if (IS_ERR(regmap))
983 return PTR_ERR(regmap);
984
985 clk_fabia_pll_configure(&dispcc_pll0, regmap, &dispcc_pll0_config);
986 /* Enable clock gating for DSI and MDP clocks */
987 regmap_update_bits(regmap, 0x8000, 0x7f0, 0x7f0);
988
989 /* Keep some clocks always-on */
990 qcom_branch_set_clk_en(regmap, 0x605c); /* DISPCC_XO_CLK */
991
992 return qcom_cc_really_probe(&pdev->dev, &dispcc_sm7150_desc, regmap);
993}
994
995static struct platform_driver dispcc_sm7150_driver = {
996 .probe = dispcc_sm7150_probe,
997 .driver = {
998 .name = "dispcc-sm7150",
999 .of_match_table = dispcc_sm7150_match_table,
1000 },
1001};
1002
1003module_platform_driver(dispcc_sm7150_driver);
1004
1005MODULE_DESCRIPTION("Qualcomm SM7150 Display Clock Controller");
1006MODULE_LICENSE("GPL");