1 /*
2 * Copyright 2018 Advanced Micro Devices, Inc.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
21 *
22 * Authors: AMD
23 *
24 */
25
26 #include "reg_helper.h"
27 #include "core_types.h"
28 #include "dcn31_dccg.h"
29 #include "dcn20/dcn20_dccg.h"
30 #include "dal_asic_id.h"
31
32 #define TO_DCN_DCCG(dccg)\
33 container_of(dccg, struct dcn_dccg, base)
34
35 #define REG(reg) \
36 (dccg_dcn->regs->reg)
37
38 #undef FN
39 #define FN(reg_name, field_name) \
40 dccg_dcn->dccg_shift->field_name, dccg_dcn->dccg_mask->field_name
41
42 #define CTX \
43 dccg_dcn->base.ctx
44 #define DC_LOGGER \
45 dccg->ctx->logger
46
dccg31_update_dpp_dto(struct dccg * dccg,int dpp_inst,int req_dppclk)47 void dccg31_update_dpp_dto(struct dccg *dccg, int dpp_inst, int req_dppclk)
48 {
49 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
50
51 if (dccg->dpp_clock_gated[dpp_inst]) {
52 /*
53 * Do not update the DPPCLK DTO if the clock is stopped.
54 * It is treated the same as if the pipe itself were in PG.
55 */
56 return;
57 }
58
59 if (dccg->ref_dppclk && req_dppclk) {
60 int ref_dppclk = dccg->ref_dppclk;
61 int modulo, phase;
62
63 // phase / modulo = dpp pipe clk / dpp global clk
64 modulo = 0xff; // use FF at the end
65 phase = ((modulo * req_dppclk) + ref_dppclk - 1) / ref_dppclk;
66
67 if (phase > 0xff) {
68 ASSERT(false);
69 phase = 0xff;
70 }
71
72 REG_SET_2(DPPCLK_DTO_PARAM[dpp_inst], 0,
73 DPPCLK0_DTO_PHASE, phase,
74 DPPCLK0_DTO_MODULO, modulo);
75 REG_UPDATE(DPPCLK_DTO_CTRL,
76 DPPCLK_DTO_ENABLE[dpp_inst], 1);
77 } else {
78 REG_UPDATE(DPPCLK_DTO_CTRL,
79 DPPCLK_DTO_ENABLE[dpp_inst], 0);
80 }
81 dccg->pipe_dppclk_khz[dpp_inst] = req_dppclk;
82 }
83
get_phy_mux_symclk(struct dcn_dccg * dccg_dcn,enum phyd32clk_clock_source src)84 static enum phyd32clk_clock_source get_phy_mux_symclk(
85 struct dcn_dccg *dccg_dcn,
86 enum phyd32clk_clock_source src)
87 {
88 if (dccg_dcn->base.ctx->asic_id.chip_family == FAMILY_YELLOW_CARP &&
89 dccg_dcn->base.ctx->asic_id.hw_internal_rev == YELLOW_CARP_B0) {
90 if (src == PHYD32CLKC)
91 src = PHYD32CLKF;
92 if (src == PHYD32CLKD)
93 src = PHYD32CLKG;
94 }
95 return src;
96 }
97
dccg31_enable_dpstreamclk(struct dccg * dccg,int otg_inst)98 static void dccg31_enable_dpstreamclk(struct dccg *dccg, int otg_inst)
99 {
100 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
101
102 /* enabled to select one of the DTBCLKs for pipe */
103 switch (otg_inst) {
104 case 0:
105 REG_UPDATE(DPSTREAMCLK_CNTL,
106 DPSTREAMCLK_PIPE0_EN, 1);
107 break;
108 case 1:
109 REG_UPDATE(DPSTREAMCLK_CNTL,
110 DPSTREAMCLK_PIPE1_EN, 1);
111 break;
112 case 2:
113 REG_UPDATE(DPSTREAMCLK_CNTL,
114 DPSTREAMCLK_PIPE2_EN, 1);
115 break;
116 case 3:
117 REG_UPDATE(DPSTREAMCLK_CNTL,
118 DPSTREAMCLK_PIPE3_EN, 1);
119 break;
120 default:
121 BREAK_TO_DEBUGGER();
122 return;
123 }
124 if (dccg->ctx->dc->debug.root_clock_optimization.bits.dpstream)
125 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
126 DPSTREAMCLK_GATE_DISABLE, 1,
127 DPSTREAMCLK_ROOT_GATE_DISABLE, 1);
128 }
129
dccg31_disable_dpstreamclk(struct dccg * dccg,int otg_inst)130 static void dccg31_disable_dpstreamclk(struct dccg *dccg, int otg_inst)
131 {
132 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
133
134 if (dccg->ctx->dc->debug.root_clock_optimization.bits.dpstream)
135 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
136 DPSTREAMCLK_ROOT_GATE_DISABLE, 0,
137 DPSTREAMCLK_GATE_DISABLE, 0);
138
139 switch (otg_inst) {
140 case 0:
141 REG_UPDATE(DPSTREAMCLK_CNTL,
142 DPSTREAMCLK_PIPE0_EN, 0);
143 break;
144 case 1:
145 REG_UPDATE(DPSTREAMCLK_CNTL,
146 DPSTREAMCLK_PIPE1_EN, 0);
147 break;
148 case 2:
149 REG_UPDATE(DPSTREAMCLK_CNTL,
150 DPSTREAMCLK_PIPE2_EN, 0);
151 break;
152 case 3:
153 REG_UPDATE(DPSTREAMCLK_CNTL,
154 DPSTREAMCLK_PIPE3_EN, 0);
155 break;
156 default:
157 BREAK_TO_DEBUGGER();
158 return;
159 }
160 }
161
dccg31_set_dpstreamclk(struct dccg * dccg,enum streamclk_source src,int otg_inst,int dp_hpo_inst)162 void dccg31_set_dpstreamclk(
163 struct dccg *dccg,
164 enum streamclk_source src,
165 int otg_inst,
166 int dp_hpo_inst)
167 {
168 if (src == REFCLK)
169 dccg31_disable_dpstreamclk(dccg, otg_inst);
170 else
171 dccg31_enable_dpstreamclk(dccg, otg_inst);
172 }
173
dccg31_enable_symclk32_se(struct dccg * dccg,int hpo_se_inst,enum phyd32clk_clock_source phyd32clk)174 void dccg31_enable_symclk32_se(
175 struct dccg *dccg,
176 int hpo_se_inst,
177 enum phyd32clk_clock_source phyd32clk)
178 {
179 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
180
181 phyd32clk = get_phy_mux_symclk(dccg_dcn, phyd32clk);
182
183 /* select one of the PHYD32CLKs as the source for symclk32_se */
184 switch (hpo_se_inst) {
185 case 0:
186 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
187 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
188 SYMCLK32_SE0_GATE_DISABLE, 1,
189 SYMCLK32_ROOT_SE0_GATE_DISABLE, 1);
190 REG_UPDATE_2(SYMCLK32_SE_CNTL,
191 SYMCLK32_SE0_SRC_SEL, phyd32clk,
192 SYMCLK32_SE0_EN, 1);
193 break;
194 case 1:
195 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
196 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
197 SYMCLK32_SE1_GATE_DISABLE, 1,
198 SYMCLK32_ROOT_SE1_GATE_DISABLE, 1);
199 REG_UPDATE_2(SYMCLK32_SE_CNTL,
200 SYMCLK32_SE1_SRC_SEL, phyd32clk,
201 SYMCLK32_SE1_EN, 1);
202 break;
203 case 2:
204 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
205 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
206 SYMCLK32_SE2_GATE_DISABLE, 1,
207 SYMCLK32_ROOT_SE2_GATE_DISABLE, 1);
208 REG_UPDATE_2(SYMCLK32_SE_CNTL,
209 SYMCLK32_SE2_SRC_SEL, phyd32clk,
210 SYMCLK32_SE2_EN, 1);
211 break;
212 case 3:
213 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
214 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
215 SYMCLK32_SE3_GATE_DISABLE, 1,
216 SYMCLK32_ROOT_SE3_GATE_DISABLE, 1);
217 REG_UPDATE_2(SYMCLK32_SE_CNTL,
218 SYMCLK32_SE3_SRC_SEL, phyd32clk,
219 SYMCLK32_SE3_EN, 1);
220 break;
221 default:
222 BREAK_TO_DEBUGGER();
223 return;
224 }
225 }
226
dccg31_disable_symclk32_se(struct dccg * dccg,int hpo_se_inst)227 void dccg31_disable_symclk32_se(
228 struct dccg *dccg,
229 int hpo_se_inst)
230 {
231 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
232
233 /* set refclk as the source for symclk32_se */
234 switch (hpo_se_inst) {
235 case 0:
236 REG_UPDATE_2(SYMCLK32_SE_CNTL,
237 SYMCLK32_SE0_SRC_SEL, 0,
238 SYMCLK32_SE0_EN, 0);
239 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
240 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
241 SYMCLK32_SE0_GATE_DISABLE, 0,
242 SYMCLK32_ROOT_SE0_GATE_DISABLE, 0);
243 break;
244 case 1:
245 REG_UPDATE_2(SYMCLK32_SE_CNTL,
246 SYMCLK32_SE1_SRC_SEL, 0,
247 SYMCLK32_SE1_EN, 0);
248 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
249 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
250 SYMCLK32_SE1_GATE_DISABLE, 0,
251 SYMCLK32_ROOT_SE1_GATE_DISABLE, 0);
252 break;
253 case 2:
254 REG_UPDATE_2(SYMCLK32_SE_CNTL,
255 SYMCLK32_SE2_SRC_SEL, 0,
256 SYMCLK32_SE2_EN, 0);
257 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
258 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
259 SYMCLK32_SE2_GATE_DISABLE, 0,
260 SYMCLK32_ROOT_SE2_GATE_DISABLE, 0);
261 break;
262 case 3:
263 REG_UPDATE_2(SYMCLK32_SE_CNTL,
264 SYMCLK32_SE3_SRC_SEL, 0,
265 SYMCLK32_SE3_EN, 0);
266 if (dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_se)
267 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
268 SYMCLK32_SE3_GATE_DISABLE, 0,
269 SYMCLK32_ROOT_SE3_GATE_DISABLE, 0);
270 break;
271 default:
272 BREAK_TO_DEBUGGER();
273 return;
274 }
275 }
276
dccg31_enable_symclk32_le(struct dccg * dccg,int hpo_le_inst,enum phyd32clk_clock_source phyd32clk)277 void dccg31_enable_symclk32_le(
278 struct dccg *dccg,
279 int hpo_le_inst,
280 enum phyd32clk_clock_source phyd32clk)
281 {
282 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
283
284 phyd32clk = get_phy_mux_symclk(dccg_dcn, phyd32clk);
285
286 /* select one of the PHYD32CLKs as the source for symclk32_le */
287 switch (hpo_le_inst) {
288 case 0:
289 REG_UPDATE_2(SYMCLK32_LE_CNTL,
290 SYMCLK32_LE0_SRC_SEL, phyd32clk,
291 SYMCLK32_LE0_EN, 1);
292 break;
293 case 1:
294 REG_UPDATE_2(SYMCLK32_LE_CNTL,
295 SYMCLK32_LE1_SRC_SEL, phyd32clk,
296 SYMCLK32_LE1_EN, 1);
297 break;
298 default:
299 BREAK_TO_DEBUGGER();
300 return;
301 }
302 }
303
dccg31_disable_symclk32_le(struct dccg * dccg,int hpo_le_inst)304 void dccg31_disable_symclk32_le(
305 struct dccg *dccg,
306 int hpo_le_inst)
307 {
308 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
309
310 /* set refclk as the source for symclk32_le */
311 switch (hpo_le_inst) {
312 case 0:
313 REG_UPDATE_2(SYMCLK32_LE_CNTL,
314 SYMCLK32_LE0_SRC_SEL, 0,
315 SYMCLK32_LE0_EN, 0);
316 break;
317 case 1:
318 REG_UPDATE_2(SYMCLK32_LE_CNTL,
319 SYMCLK32_LE1_SRC_SEL, 0,
320 SYMCLK32_LE1_EN, 0);
321 break;
322 default:
323 BREAK_TO_DEBUGGER();
324 return;
325 }
326 }
327
dccg31_set_symclk32_le_root_clock_gating(struct dccg * dccg,int hpo_le_inst,bool enable)328 void dccg31_set_symclk32_le_root_clock_gating(
329 struct dccg *dccg,
330 int hpo_le_inst,
331 bool enable)
332 {
333 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
334
335 if (!dccg->ctx->dc->debug.root_clock_optimization.bits.symclk32_le)
336 return;
337
338 switch (hpo_le_inst) {
339 case 0:
340 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
341 SYMCLK32_LE0_GATE_DISABLE, enable ? 1 : 0,
342 SYMCLK32_ROOT_LE0_GATE_DISABLE, enable ? 1 : 0);
343 break;
344 case 1:
345 REG_UPDATE_2(DCCG_GATE_DISABLE_CNTL3,
346 SYMCLK32_LE1_GATE_DISABLE, enable ? 1 : 0,
347 SYMCLK32_ROOT_LE1_GATE_DISABLE, enable ? 1 : 0);
348 break;
349 default:
350 BREAK_TO_DEBUGGER();
351 return;
352 }
353 }
354
dccg31_disable_dscclk(struct dccg * dccg,int inst)355 void dccg31_disable_dscclk(struct dccg *dccg, int inst)
356 {
357 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
358
359 if (!dccg->ctx->dc->debug.root_clock_optimization.bits.dsc)
360 return;
361 //DTO must be enabled to generate a 0 Hz clock output
362 switch (inst) {
363 case 0:
364 REG_UPDATE(DSCCLK_DTO_CTRL,
365 DSCCLK0_DTO_ENABLE, 1);
366 REG_UPDATE_2(DSCCLK0_DTO_PARAM,
367 DSCCLK0_DTO_PHASE, 0,
368 DSCCLK0_DTO_MODULO, 1);
369 break;
370 case 1:
371 REG_UPDATE(DSCCLK_DTO_CTRL,
372 DSCCLK1_DTO_ENABLE, 1);
373 REG_UPDATE_2(DSCCLK1_DTO_PARAM,
374 DSCCLK1_DTO_PHASE, 0,
375 DSCCLK1_DTO_MODULO, 1);
376 break;
377 case 2:
378 REG_UPDATE(DSCCLK_DTO_CTRL,
379 DSCCLK2_DTO_ENABLE, 1);
380 REG_UPDATE_2(DSCCLK2_DTO_PARAM,
381 DSCCLK2_DTO_PHASE, 0,
382 DSCCLK2_DTO_MODULO, 1);
383 break;
384 case 3:
385 if (REG(DSCCLK3_DTO_PARAM)) {
386 REG_UPDATE(DSCCLK_DTO_CTRL,
387 DSCCLK3_DTO_ENABLE, 1);
388 REG_UPDATE_2(DSCCLK3_DTO_PARAM,
389 DSCCLK3_DTO_PHASE, 0,
390 DSCCLK3_DTO_MODULO, 1);
391 }
392 break;
393 default:
394 BREAK_TO_DEBUGGER();
395 return;
396 }
397 }
398
dccg31_enable_dscclk(struct dccg * dccg,int inst)399 void dccg31_enable_dscclk(struct dccg *dccg, int inst)
400 {
401 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
402
403 if (!dccg->ctx->dc->debug.root_clock_optimization.bits.dsc)
404 return;
405 //Disable DTO
406 switch (inst) {
407 case 0:
408 REG_UPDATE_2(DSCCLK0_DTO_PARAM,
409 DSCCLK0_DTO_PHASE, 0,
410 DSCCLK0_DTO_MODULO, 0);
411 REG_UPDATE(DSCCLK_DTO_CTRL,
412 DSCCLK0_DTO_ENABLE, 0);
413 break;
414 case 1:
415 REG_UPDATE_2(DSCCLK1_DTO_PARAM,
416 DSCCLK1_DTO_PHASE, 0,
417 DSCCLK1_DTO_MODULO, 0);
418 REG_UPDATE(DSCCLK_DTO_CTRL,
419 DSCCLK1_DTO_ENABLE, 0);
420 break;
421 case 2:
422 REG_UPDATE_2(DSCCLK2_DTO_PARAM,
423 DSCCLK2_DTO_PHASE, 0,
424 DSCCLK2_DTO_MODULO, 0);
425 REG_UPDATE(DSCCLK_DTO_CTRL,
426 DSCCLK2_DTO_ENABLE, 0);
427 break;
428 case 3:
429 if (REG(DSCCLK3_DTO_PARAM)) {
430 REG_UPDATE(DSCCLK_DTO_CTRL,
431 DSCCLK3_DTO_ENABLE, 0);
432 REG_UPDATE_2(DSCCLK3_DTO_PARAM,
433 DSCCLK3_DTO_PHASE, 0,
434 DSCCLK3_DTO_MODULO, 0);
435 }
436 break;
437 default:
438 BREAK_TO_DEBUGGER();
439 return;
440 }
441 }
442
dccg31_set_physymclk(struct dccg * dccg,int phy_inst,enum physymclk_clock_source clk_src,bool force_enable)443 void dccg31_set_physymclk(
444 struct dccg *dccg,
445 int phy_inst,
446 enum physymclk_clock_source clk_src,
447 bool force_enable)
448 {
449 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
450
451 /* Force PHYSYMCLK on and Select phyd32clk as the source of clock which is output to PHY through DCIO */
452 switch (phy_inst) {
453 case 0:
454 if (force_enable) {
455 REG_UPDATE_2(PHYASYMCLK_CLOCK_CNTL,
456 PHYASYMCLK_FORCE_EN, 1,
457 PHYASYMCLK_FORCE_SRC_SEL, clk_src);
458 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
459 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
460 PHYASYMCLK_GATE_DISABLE, 1);
461 } else {
462 REG_UPDATE_2(PHYASYMCLK_CLOCK_CNTL,
463 PHYASYMCLK_FORCE_EN, 0,
464 PHYASYMCLK_FORCE_SRC_SEL, 0);
465 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
466 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
467 PHYASYMCLK_GATE_DISABLE, 0);
468 }
469 break;
470 case 1:
471 if (force_enable) {
472 REG_UPDATE_2(PHYBSYMCLK_CLOCK_CNTL,
473 PHYBSYMCLK_FORCE_EN, 1,
474 PHYBSYMCLK_FORCE_SRC_SEL, clk_src);
475 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
476 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
477 PHYBSYMCLK_GATE_DISABLE, 1);
478 } else {
479 REG_UPDATE_2(PHYBSYMCLK_CLOCK_CNTL,
480 PHYBSYMCLK_FORCE_EN, 0,
481 PHYBSYMCLK_FORCE_SRC_SEL, 0);
482 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
483 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
484 PHYBSYMCLK_GATE_DISABLE, 0);
485 }
486 break;
487 case 2:
488 if (force_enable) {
489 REG_UPDATE_2(PHYCSYMCLK_CLOCK_CNTL,
490 PHYCSYMCLK_FORCE_EN, 1,
491 PHYCSYMCLK_FORCE_SRC_SEL, clk_src);
492 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
493 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
494 PHYCSYMCLK_GATE_DISABLE, 1);
495 } else {
496 REG_UPDATE_2(PHYCSYMCLK_CLOCK_CNTL,
497 PHYCSYMCLK_FORCE_EN, 0,
498 PHYCSYMCLK_FORCE_SRC_SEL, 0);
499 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
500 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
501 PHYCSYMCLK_GATE_DISABLE, 0);
502 }
503 break;
504 case 3:
505 if (force_enable) {
506 REG_UPDATE_2(PHYDSYMCLK_CLOCK_CNTL,
507 PHYDSYMCLK_FORCE_EN, 1,
508 PHYDSYMCLK_FORCE_SRC_SEL, clk_src);
509 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
510 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
511 PHYDSYMCLK_GATE_DISABLE, 1);
512 } else {
513 REG_UPDATE_2(PHYDSYMCLK_CLOCK_CNTL,
514 PHYDSYMCLK_FORCE_EN, 0,
515 PHYDSYMCLK_FORCE_SRC_SEL, 0);
516 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
517 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
518 PHYDSYMCLK_GATE_DISABLE, 0);
519 }
520 break;
521 case 4:
522 if (force_enable) {
523 REG_UPDATE_2(PHYESYMCLK_CLOCK_CNTL,
524 PHYESYMCLK_FORCE_EN, 1,
525 PHYESYMCLK_FORCE_SRC_SEL, clk_src);
526 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
527 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
528 PHYESYMCLK_GATE_DISABLE, 1);
529 } else {
530 REG_UPDATE_2(PHYESYMCLK_CLOCK_CNTL,
531 PHYESYMCLK_FORCE_EN, 0,
532 PHYESYMCLK_FORCE_SRC_SEL, 0);
533 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk)
534 REG_UPDATE(DCCG_GATE_DISABLE_CNTL2,
535 PHYESYMCLK_GATE_DISABLE, 0);
536 }
537 break;
538 default:
539 BREAK_TO_DEBUGGER();
540 return;
541 }
542 }
543
544 /* Controls the generation of pixel valid for OTG in (OTG -> HPO case) */
dccg31_set_dtbclk_dto(struct dccg * dccg,const struct dtbclk_dto_params * params)545 void dccg31_set_dtbclk_dto(
546 struct dccg *dccg,
547 const struct dtbclk_dto_params *params)
548 {
549 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
550 int req_dtbclk_khz = params->pixclk_khz;
551 uint32_t dtbdto_div;
552
553 /* Mode DTBDTO Rate DTBCLK_DTO<x>_DIV Register
554 * ODM 4:1 combine pixel rate/4 2
555 * ODM 2:1 combine pixel rate/2 4
556 * non-DSC 4:2:0 mode pixel rate/2 4
557 * DSC native 4:2:0 pixel rate/2 4
558 * DSC native 4:2:2 pixel rate/2 4
559 * Other modes pixel rate 8
560 */
561 if (params->num_odm_segments == 4) {
562 dtbdto_div = 2;
563 req_dtbclk_khz = params->pixclk_khz / 4;
564 } else if ((params->num_odm_segments == 2) ||
565 (params->timing->pixel_encoding == PIXEL_ENCODING_YCBCR420) ||
566 (params->timing->flags.DSC && params->timing->pixel_encoding == PIXEL_ENCODING_YCBCR422
567 && !params->timing->dsc_cfg.ycbcr422_simple)) {
568 dtbdto_div = 4;
569 req_dtbclk_khz = params->pixclk_khz / 2;
570 } else
571 dtbdto_div = 8;
572
573 if (params->ref_dtbclk_khz && req_dtbclk_khz) {
574 uint32_t modulo, phase;
575
576 // phase / modulo = dtbclk / dtbclk ref
577 modulo = params->ref_dtbclk_khz * 1000;
578 phase = div_u64((((unsigned long long)modulo * req_dtbclk_khz) + params->ref_dtbclk_khz - 1),
579 params->ref_dtbclk_khz);
580
581 REG_UPDATE(OTG_PIXEL_RATE_CNTL[params->otg_inst],
582 DTBCLK_DTO_DIV[params->otg_inst], dtbdto_div);
583
584 REG_WRITE(DTBCLK_DTO_MODULO[params->otg_inst], modulo);
585 REG_WRITE(DTBCLK_DTO_PHASE[params->otg_inst], phase);
586
587 REG_UPDATE(OTG_PIXEL_RATE_CNTL[params->otg_inst],
588 DTBCLK_DTO_ENABLE[params->otg_inst], 1);
589
590 REG_WAIT(OTG_PIXEL_RATE_CNTL[params->otg_inst],
591 DTBCLKDTO_ENABLE_STATUS[params->otg_inst], 1,
592 1, 100);
593
594 /* The recommended programming sequence to enable DTBCLK DTO to generate
595 * valid pixel HPO DPSTREAM ENCODER, specifies that DTO source select should
596 * be set only after DTO is enabled
597 */
598 REG_UPDATE(OTG_PIXEL_RATE_CNTL[params->otg_inst],
599 PIPE_DTO_SRC_SEL[params->otg_inst], 1);
600 } else {
601 REG_UPDATE_3(OTG_PIXEL_RATE_CNTL[params->otg_inst],
602 DTBCLK_DTO_ENABLE[params->otg_inst], 0,
603 PIPE_DTO_SRC_SEL[params->otg_inst], 0,
604 DTBCLK_DTO_DIV[params->otg_inst], dtbdto_div);
605
606 REG_WRITE(DTBCLK_DTO_MODULO[params->otg_inst], 0);
607 REG_WRITE(DTBCLK_DTO_PHASE[params->otg_inst], 0);
608 }
609 }
610
dccg31_set_audio_dtbclk_dto(struct dccg * dccg,const struct dtbclk_dto_params * params)611 void dccg31_set_audio_dtbclk_dto(
612 struct dccg *dccg,
613 const struct dtbclk_dto_params *params)
614 {
615 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
616
617 if (params->ref_dtbclk_khz && params->req_audio_dtbclk_khz) {
618 uint32_t modulo, phase;
619
620 // phase / modulo = dtbclk / dtbclk ref
621 modulo = params->ref_dtbclk_khz * 1000;
622 phase = div_u64((((unsigned long long)modulo * params->req_audio_dtbclk_khz) + params->ref_dtbclk_khz - 1),
623 params->ref_dtbclk_khz);
624
625
626 REG_WRITE(DCCG_AUDIO_DTBCLK_DTO_MODULO, modulo);
627 REG_WRITE(DCCG_AUDIO_DTBCLK_DTO_PHASE, phase);
628
629 //REG_UPDATE(DCCG_AUDIO_DTO_SOURCE,
630 // DCCG_AUDIO_DTBCLK_DTO_USE_512FBR_DTO, 1);
631
632 REG_UPDATE(DCCG_AUDIO_DTO_SOURCE,
633 DCCG_AUDIO_DTO_SEL, 4); // 04 - DCCG_AUDIO_DTO_SEL_AUDIO_DTO_DTBCLK
634 } else {
635 REG_WRITE(DCCG_AUDIO_DTBCLK_DTO_PHASE, 0);
636 REG_WRITE(DCCG_AUDIO_DTBCLK_DTO_MODULO, 0);
637
638 REG_UPDATE(DCCG_AUDIO_DTO_SOURCE,
639 DCCG_AUDIO_DTO_SEL, 3); // 03 - DCCG_AUDIO_DTO_SEL_NO_AUDIO_DTO
640 }
641 }
642
dccg31_get_dccg_ref_freq(struct dccg * dccg,unsigned int xtalin_freq_inKhz,unsigned int * dccg_ref_freq_inKhz)643 void dccg31_get_dccg_ref_freq(struct dccg *dccg,
644 unsigned int xtalin_freq_inKhz,
645 unsigned int *dccg_ref_freq_inKhz)
646 {
647 /*
648 * Assume refclk is sourced from xtalin
649 * expect 24MHz
650 */
651 *dccg_ref_freq_inKhz = xtalin_freq_inKhz;
652 return;
653 }
654
dccg31_set_dispclk_change_mode(struct dccg * dccg,enum dentist_dispclk_change_mode change_mode)655 void dccg31_set_dispclk_change_mode(
656 struct dccg *dccg,
657 enum dentist_dispclk_change_mode change_mode)
658 {
659 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
660
661 REG_UPDATE(DENTIST_DISPCLK_CNTL, DENTIST_DISPCLK_CHG_MODE,
662 change_mode == DISPCLK_CHANGE_MODE_RAMPING ? 2 : 0);
663 }
664
dccg31_init(struct dccg * dccg)665 void dccg31_init(struct dccg *dccg)
666 {
667 /* Set HPO stream encoder to use refclk to avoid case where PHY is
668 * disabled and SYMCLK32 for HPO SE is sourced from PHYD32CLK which
669 * will cause DCN to hang.
670 */
671 dccg31_disable_symclk32_se(dccg, 0);
672 dccg31_disable_symclk32_se(dccg, 1);
673 dccg31_disable_symclk32_se(dccg, 2);
674 dccg31_disable_symclk32_se(dccg, 3);
675
676 dccg31_set_symclk32_le_root_clock_gating(dccg, 0, false);
677 dccg31_set_symclk32_le_root_clock_gating(dccg, 1, false);
678
679 if (dccg->ctx->dc->debug.root_clock_optimization.bits.dpstream) {
680 dccg31_disable_dpstreamclk(dccg, 0);
681 dccg31_disable_dpstreamclk(dccg, 1);
682 dccg31_disable_dpstreamclk(dccg, 2);
683 dccg31_disable_dpstreamclk(dccg, 3);
684 }
685
686 if (dccg->ctx->dc->debug.root_clock_optimization.bits.physymclk) {
687 dccg31_set_physymclk(dccg, 0, PHYSYMCLK_FORCE_SRC_SYMCLK, false);
688 dccg31_set_physymclk(dccg, 1, PHYSYMCLK_FORCE_SRC_SYMCLK, false);
689 dccg31_set_physymclk(dccg, 2, PHYSYMCLK_FORCE_SRC_SYMCLK, false);
690 dccg31_set_physymclk(dccg, 3, PHYSYMCLK_FORCE_SRC_SYMCLK, false);
691 dccg31_set_physymclk(dccg, 4, PHYSYMCLK_FORCE_SRC_SYMCLK, false);
692 }
693 }
694
dccg31_otg_add_pixel(struct dccg * dccg,uint32_t otg_inst)695 void dccg31_otg_add_pixel(struct dccg *dccg,
696 uint32_t otg_inst)
697 {
698 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
699
700 REG_UPDATE(OTG_PIXEL_RATE_CNTL[otg_inst],
701 OTG_ADD_PIXEL[otg_inst], 1);
702 }
703
dccg31_otg_drop_pixel(struct dccg * dccg,uint32_t otg_inst)704 void dccg31_otg_drop_pixel(struct dccg *dccg,
705 uint32_t otg_inst)
706 {
707 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
708
709 REG_UPDATE(OTG_PIXEL_RATE_CNTL[otg_inst],
710 OTG_DROP_PIXEL[otg_inst], 1);
711 }
712
dccg31_read_reg_state(struct dccg * dccg,struct dcn_dccg_reg_state * dccg_reg_state)713 void dccg31_read_reg_state(struct dccg *dccg, struct dcn_dccg_reg_state *dccg_reg_state)
714 {
715 struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg);
716
717 dccg_reg_state->dc_mem_global_pwr_req_cntl = REG_READ(DC_MEM_GLOBAL_PWR_REQ_CNTL);
718 dccg_reg_state->dccg_audio_dtbclk_dto_modulo = REG_READ(DCCG_AUDIO_DTBCLK_DTO_MODULO);
719 dccg_reg_state->dccg_audio_dtbclk_dto_phase = REG_READ(DCCG_AUDIO_DTBCLK_DTO_PHASE);
720 dccg_reg_state->dccg_audio_dto_source = REG_READ(DCCG_AUDIO_DTO_SOURCE);
721 dccg_reg_state->dccg_audio_dto0_module = REG_READ(DCCG_AUDIO_DTO0_MODULE);
722 dccg_reg_state->dccg_audio_dto0_phase = REG_READ(DCCG_AUDIO_DTO0_PHASE);
723 dccg_reg_state->dccg_audio_dto1_module = REG_READ(DCCG_AUDIO_DTO1_MODULE);
724 dccg_reg_state->dccg_audio_dto1_phase = REG_READ(DCCG_AUDIO_DTO1_PHASE);
725 dccg_reg_state->dccg_cac_status = REG_READ(DCCG_CAC_STATUS);
726 dccg_reg_state->dccg_cac_status2 = REG_READ(DCCG_CAC_STATUS2);
727 dccg_reg_state->dccg_disp_cntl_reg = REG_READ(DCCG_DISP_CNTL_REG);
728 dccg_reg_state->dccg_ds_cntl = REG_READ(DCCG_DS_CNTL);
729 dccg_reg_state->dccg_ds_dto_incr = REG_READ(DCCG_DS_DTO_INCR);
730 dccg_reg_state->dccg_ds_dto_modulo = REG_READ(DCCG_DS_DTO_MODULO);
731 dccg_reg_state->dccg_ds_hw_cal_interval = REG_READ(DCCG_DS_HW_CAL_INTERVAL);
732 dccg_reg_state->dccg_gate_disable_cntl = REG_READ(DCCG_GATE_DISABLE_CNTL);
733 dccg_reg_state->dccg_gate_disable_cntl2 = REG_READ(DCCG_GATE_DISABLE_CNTL2);
734 dccg_reg_state->dccg_gate_disable_cntl3 = REG_READ(DCCG_GATE_DISABLE_CNTL3);
735 dccg_reg_state->dccg_gate_disable_cntl4 = REG_READ(DCCG_GATE_DISABLE_CNTL4);
736 dccg_reg_state->dccg_gate_disable_cntl5 = REG_READ(DCCG_GATE_DISABLE_CNTL5);
737 dccg_reg_state->dccg_gate_disable_cntl6 = REG_READ(DCCG_GATE_DISABLE_CNTL6);
738 dccg_reg_state->dccg_global_fgcg_rep_cntl = REG_READ(DCCG_GLOBAL_FGCG_REP_CNTL);
739 dccg_reg_state->dccg_gtc_cntl = REG_READ(DCCG_GTC_CNTL);
740 dccg_reg_state->dccg_gtc_current = REG_READ(DCCG_GTC_CURRENT);
741 dccg_reg_state->dccg_gtc_dto_incr = REG_READ(DCCG_GTC_DTO_INCR);
742 dccg_reg_state->dccg_gtc_dto_modulo = REG_READ(DCCG_GTC_DTO_MODULO);
743 dccg_reg_state->dccg_perfmon_cntl = REG_READ(DCCG_PERFMON_CNTL);
744 dccg_reg_state->dccg_perfmon_cntl2 = REG_READ(DCCG_PERFMON_CNTL2);
745 dccg_reg_state->dccg_soft_reset = REG_READ(DCCG_SOFT_RESET);
746 dccg_reg_state->dccg_test_clk_sel = REG_READ(DCCG_TEST_CLK_SEL);
747 dccg_reg_state->dccg_vsync_cnt_ctrl = REG_READ(DCCG_VSYNC_CNT_CTRL);
748 dccg_reg_state->dccg_vsync_cnt_int_ctrl = REG_READ(DCCG_VSYNC_CNT_INT_CTRL);
749 dccg_reg_state->dccg_vsync_otg0_latch_value = REG_READ(DCCG_VSYNC_OTG0_LATCH_VALUE);
750 dccg_reg_state->dccg_vsync_otg1_latch_value = REG_READ(DCCG_VSYNC_OTG1_LATCH_VALUE);
751 dccg_reg_state->dccg_vsync_otg2_latch_value = REG_READ(DCCG_VSYNC_OTG2_LATCH_VALUE);
752 dccg_reg_state->dccg_vsync_otg3_latch_value = REG_READ(DCCG_VSYNC_OTG3_LATCH_VALUE);
753 dccg_reg_state->dccg_vsync_otg4_latch_value = REG_READ(DCCG_VSYNC_OTG4_LATCH_VALUE);
754 dccg_reg_state->dccg_vsync_otg5_latch_value = REG_READ(DCCG_VSYNC_OTG5_LATCH_VALUE);
755 dccg_reg_state->dispclk_cgtt_blk_ctrl_reg = REG_READ(DISPCLK_CGTT_BLK_CTRL_REG);
756 dccg_reg_state->dispclk_freq_change_cntl = REG_READ(DISPCLK_FREQ_CHANGE_CNTL);
757 dccg_reg_state->dp_dto_dbuf_en = REG_READ(DP_DTO_DBUF_EN);
758 dccg_reg_state->dp_dto0_modulo = REG_READ(DP_DTO_MODULO[0]);
759 dccg_reg_state->dp_dto0_phase = REG_READ(DP_DTO_PHASE[0]);
760 dccg_reg_state->dp_dto1_modulo = REG_READ(DP_DTO_MODULO[1]);
761 dccg_reg_state->dp_dto1_phase = REG_READ(DP_DTO_PHASE[1]);
762 dccg_reg_state->dp_dto2_modulo = REG_READ(DP_DTO_MODULO[2]);
763 dccg_reg_state->dp_dto2_phase = REG_READ(DP_DTO_PHASE[2]);
764 dccg_reg_state->dp_dto3_modulo = REG_READ(DP_DTO_MODULO[3]);
765 dccg_reg_state->dp_dto3_phase = REG_READ(DP_DTO_PHASE[3]);
766 dccg_reg_state->dpiaclk_540m_dto_modulo = REG_READ(DPIACLK_540M_DTO_MODULO);
767 dccg_reg_state->dpiaclk_540m_dto_phase = REG_READ(DPIACLK_540M_DTO_PHASE);
768 dccg_reg_state->dpiaclk_810m_dto_modulo = REG_READ(DPIACLK_810M_DTO_MODULO);
769 dccg_reg_state->dpiaclk_810m_dto_phase = REG_READ(DPIACLK_810M_DTO_PHASE);
770 dccg_reg_state->dpiaclk_dto_cntl = REG_READ(DPIACLK_DTO_CNTL);
771 dccg_reg_state->dpiasymclk_cntl = REG_READ(DPIASYMCLK_CNTL);
772 dccg_reg_state->dppclk_cgtt_blk_ctrl_reg = REG_READ(DPPCLK_CGTT_BLK_CTRL_REG);
773 dccg_reg_state->dppclk_ctrl = REG_READ(DPPCLK_CTRL);
774 dccg_reg_state->dppclk_dto_ctrl = REG_READ(DPPCLK_DTO_CTRL);
775 dccg_reg_state->dppclk0_dto_param = REG_READ(DPPCLK_DTO_PARAM[0]);
776 dccg_reg_state->dppclk1_dto_param = REG_READ(DPPCLK_DTO_PARAM[1]);
777 dccg_reg_state->dppclk2_dto_param = REG_READ(DPPCLK_DTO_PARAM[2]);
778 dccg_reg_state->dppclk3_dto_param = REG_READ(DPPCLK_DTO_PARAM[3]);
779 dccg_reg_state->dprefclk_cgtt_blk_ctrl_reg = REG_READ(DPREFCLK_CGTT_BLK_CTRL_REG);
780 dccg_reg_state->dprefclk_cntl = REG_READ(DPREFCLK_CNTL);
781 dccg_reg_state->dpstreamclk_cntl = REG_READ(DPSTREAMCLK_CNTL);
782 dccg_reg_state->dscclk_dto_ctrl = REG_READ(DSCCLK_DTO_CTRL);
783 dccg_reg_state->dscclk0_dto_param = REG_READ(DSCCLK0_DTO_PARAM);
784 dccg_reg_state->dscclk1_dto_param = REG_READ(DSCCLK1_DTO_PARAM);
785 dccg_reg_state->dscclk2_dto_param = REG_READ(DSCCLK2_DTO_PARAM);
786 dccg_reg_state->dscclk3_dto_param = REG_READ(DSCCLK3_DTO_PARAM);
787 dccg_reg_state->dtbclk_dto_dbuf_en = REG_READ(DTBCLK_DTO_DBUF_EN);
788 dccg_reg_state->dtbclk_dto0_modulo = REG_READ(DTBCLK_DTO_MODULO[0]);
789 dccg_reg_state->dtbclk_dto0_phase = REG_READ(DTBCLK_DTO_PHASE[0]);
790 dccg_reg_state->dtbclk_dto1_modulo = REG_READ(DTBCLK_DTO_MODULO[1]);
791 dccg_reg_state->dtbclk_dto1_phase = REG_READ(DTBCLK_DTO_PHASE[1]);
792 dccg_reg_state->dtbclk_dto2_modulo = REG_READ(DTBCLK_DTO_MODULO[2]);
793 dccg_reg_state->dtbclk_dto2_phase = REG_READ(DTBCLK_DTO_PHASE[2]);
794 dccg_reg_state->dtbclk_dto3_modulo = REG_READ(DTBCLK_DTO_MODULO[3]);
795 dccg_reg_state->dtbclk_dto3_phase = REG_READ(DTBCLK_DTO_PHASE[3]);
796 dccg_reg_state->dtbclk_p_cntl = REG_READ(DTBCLK_P_CNTL);
797 dccg_reg_state->force_symclk_disable = REG_READ(FORCE_SYMCLK_DISABLE);
798 dccg_reg_state->hdmicharclk0_clock_cntl = REG_READ(HDMICHARCLK0_CLOCK_CNTL);
799 dccg_reg_state->hdmistreamclk_cntl = REG_READ(HDMISTREAMCLK_CNTL);
800 dccg_reg_state->hdmistreamclk0_dto_param = REG_READ(HDMISTREAMCLK0_DTO_PARAM);
801 dccg_reg_state->microsecond_time_base_div = REG_READ(MICROSECOND_TIME_BASE_DIV);
802 dccg_reg_state->millisecond_time_base_div = REG_READ(MILLISECOND_TIME_BASE_DIV);
803 dccg_reg_state->otg_pixel_rate_div = REG_READ(OTG_PIXEL_RATE_DIV);
804 dccg_reg_state->otg0_phypll_pixel_rate_cntl = REG_READ(OTG0_PHYPLL_PIXEL_RATE_CNTL);
805 dccg_reg_state->otg0_pixel_rate_cntl = REG_READ(OTG0_PIXEL_RATE_CNTL);
806 dccg_reg_state->otg1_phypll_pixel_rate_cntl = REG_READ(OTG1_PHYPLL_PIXEL_RATE_CNTL);
807 dccg_reg_state->otg1_pixel_rate_cntl = REG_READ(OTG1_PIXEL_RATE_CNTL);
808 dccg_reg_state->otg2_phypll_pixel_rate_cntl = REG_READ(OTG2_PHYPLL_PIXEL_RATE_CNTL);
809 dccg_reg_state->otg2_pixel_rate_cntl = REG_READ(OTG2_PIXEL_RATE_CNTL);
810 dccg_reg_state->otg3_phypll_pixel_rate_cntl = REG_READ(OTG3_PHYPLL_PIXEL_RATE_CNTL);
811 dccg_reg_state->otg3_pixel_rate_cntl = REG_READ(OTG3_PIXEL_RATE_CNTL);
812 dccg_reg_state->phyasymclk_clock_cntl = REG_READ(PHYASYMCLK_CLOCK_CNTL);
813 dccg_reg_state->phybsymclk_clock_cntl = REG_READ(PHYBSYMCLK_CLOCK_CNTL);
814 dccg_reg_state->phycsymclk_clock_cntl = REG_READ(PHYCSYMCLK_CLOCK_CNTL);
815 dccg_reg_state->phydsymclk_clock_cntl = REG_READ(PHYDSYMCLK_CLOCK_CNTL);
816 dccg_reg_state->phyesymclk_clock_cntl = REG_READ(PHYESYMCLK_CLOCK_CNTL);
817 dccg_reg_state->phyplla_pixclk_resync_cntl = REG_READ(PHYPLLA_PIXCLK_RESYNC_CNTL);
818 dccg_reg_state->phypllb_pixclk_resync_cntl = REG_READ(PHYPLLB_PIXCLK_RESYNC_CNTL);
819 dccg_reg_state->phypllc_pixclk_resync_cntl = REG_READ(PHYPLLC_PIXCLK_RESYNC_CNTL);
820 dccg_reg_state->phyplld_pixclk_resync_cntl = REG_READ(PHYPLLD_PIXCLK_RESYNC_CNTL);
821 dccg_reg_state->phyplle_pixclk_resync_cntl = REG_READ(PHYPLLE_PIXCLK_RESYNC_CNTL);
822 dccg_reg_state->refclk_cgtt_blk_ctrl_reg = REG_READ(REFCLK_CGTT_BLK_CTRL_REG);
823 dccg_reg_state->socclk_cgtt_blk_ctrl_reg = REG_READ(SOCCLK_CGTT_BLK_CTRL_REG);
824 dccg_reg_state->symclk_cgtt_blk_ctrl_reg = REG_READ(SYMCLK_CGTT_BLK_CTRL_REG);
825 dccg_reg_state->symclk_psp_cntl = REG_READ(SYMCLK_PSP_CNTL);
826 dccg_reg_state->symclk32_le_cntl = REG_READ(SYMCLK32_LE_CNTL);
827 dccg_reg_state->symclk32_se_cntl = REG_READ(SYMCLK32_SE_CNTL);
828 dccg_reg_state->symclka_clock_enable = REG_READ(SYMCLKA_CLOCK_ENABLE);
829 dccg_reg_state->symclkb_clock_enable = REG_READ(SYMCLKB_CLOCK_ENABLE);
830 dccg_reg_state->symclkc_clock_enable = REG_READ(SYMCLKC_CLOCK_ENABLE);
831 dccg_reg_state->symclkd_clock_enable = REG_READ(SYMCLKD_CLOCK_ENABLE);
832 dccg_reg_state->symclke_clock_enable = REG_READ(SYMCLKE_CLOCK_ENABLE);
833 }
834
835 static const struct dccg_funcs dccg31_funcs = {
836 .update_dpp_dto = dccg31_update_dpp_dto,
837 .get_dccg_ref_freq = dccg31_get_dccg_ref_freq,
838 .dccg_init = dccg31_init,
839 .set_dpstreamclk = dccg31_set_dpstreamclk,
840 .enable_symclk32_se = dccg31_enable_symclk32_se,
841 .disable_symclk32_se = dccg31_disable_symclk32_se,
842 .enable_symclk32_le = dccg31_enable_symclk32_le,
843 .disable_symclk32_le = dccg31_disable_symclk32_le,
844 .set_physymclk = dccg31_set_physymclk,
845 .set_dtbclk_dto = dccg31_set_dtbclk_dto,
846 .set_audio_dtbclk_dto = dccg31_set_audio_dtbclk_dto,
847 .set_fifo_errdet_ovr_en = dccg2_set_fifo_errdet_ovr_en,
848 .otg_add_pixel = dccg31_otg_add_pixel,
849 .otg_drop_pixel = dccg31_otg_drop_pixel,
850 .set_dispclk_change_mode = dccg31_set_dispclk_change_mode,
851 .disable_dsc = dccg31_disable_dscclk,
852 .enable_dsc = dccg31_enable_dscclk,
853 .dccg_read_reg_state = dccg31_read_reg_state,
854 .refclk_setup = dccg2_refclk_setup, /* Deprecated - for backward compatibility only */
855 .allow_clock_gating = dccg2_allow_clock_gating,
856 .enable_memory_low_power = dccg2_enable_memory_low_power,
857 .is_s0i3_golden_init_wa_done = dccg2_is_s0i3_golden_init_wa_done /* Deprecated - for backward compatibility only */
858 };
859
dccg31_create(struct dc_context * ctx,const struct dccg_registers * regs,const struct dccg_shift * dccg_shift,const struct dccg_mask * dccg_mask)860 struct dccg *dccg31_create(
861 struct dc_context *ctx,
862 const struct dccg_registers *regs,
863 const struct dccg_shift *dccg_shift,
864 const struct dccg_mask *dccg_mask)
865 {
866 struct dcn_dccg *dccg_dcn = kzalloc_obj(*dccg_dcn);
867 struct dccg *base;
868
869 if (dccg_dcn == NULL) {
870 BREAK_TO_DEBUGGER();
871 return NULL;
872 }
873
874 base = &dccg_dcn->base;
875 base->ctx = ctx;
876 base->funcs = &dccg31_funcs;
877
878 dccg_dcn->regs = regs;
879 dccg_dcn->dccg_shift = dccg_shift;
880 dccg_dcn->dccg_mask = dccg_mask;
881
882 return &dccg_dcn->base;
883 }
884