2 * Copyright 2014 Advanced Micro Devices, Inc.
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:
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
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.
24 #include <linux/firmware.h>
25 #include <linux/seq_file.h>
28 #include "amdgpu_pm.h"
29 #include "amdgpu_atombios.h"
32 #include "amdgpu_dpm.h"
37 #include "smu/smu_8_0_d.h"
38 #include "smu/smu_8_0_sh_mask.h"
39 #include "gca/gfx_8_0_d.h"
40 #include "gca/gfx_8_0_sh_mask.h"
41 #include "gmc/gmc_8_1_d.h"
42 #include "bif/bif_5_1_d.h"
45 static void cz_dpm_powergate_uvd(struct amdgpu_device
*adev
, bool gate
);
46 static void cz_dpm_powergate_vce(struct amdgpu_device
*adev
, bool gate
);
48 static struct cz_ps
*cz_get_ps(struct amdgpu_ps
*rps
)
50 struct cz_ps
*ps
= rps
->ps_priv
;
55 static struct cz_power_info
*cz_get_pi(struct amdgpu_device
*adev
)
57 struct cz_power_info
*pi
= adev
->pm
.dpm
.priv
;
62 static uint16_t cz_convert_8bit_index_to_voltage(struct amdgpu_device
*adev
,
65 uint16_t tmp
= 6200 - voltage
* 25;
70 static void cz_construct_max_power_limits_table(struct amdgpu_device
*adev
,
71 struct amdgpu_clock_and_voltage_limits
*table
)
73 struct cz_power_info
*pi
= cz_get_pi(adev
);
74 struct amdgpu_clock_voltage_dependency_table
*dep_table
=
75 &adev
->pm
.dpm
.dyn_state
.vddc_dependency_on_sclk
;
77 if (dep_table
->count
> 0) {
78 table
->sclk
= dep_table
->entries
[dep_table
->count
- 1].clk
;
79 table
->vddc
= cz_convert_8bit_index_to_voltage(adev
,
80 dep_table
->entries
[dep_table
->count
- 1].v
);
83 table
->mclk
= pi
->sys_info
.nbp_memory_clock
[0];
88 struct _ATOM_INTEGRATED_SYSTEM_INFO info
;
89 struct _ATOM_INTEGRATED_SYSTEM_INFO_V1_7 info_7
;
90 struct _ATOM_INTEGRATED_SYSTEM_INFO_V1_8 info_8
;
91 struct _ATOM_INTEGRATED_SYSTEM_INFO_V1_9 info_9
;
94 static int cz_parse_sys_info_table(struct amdgpu_device
*adev
)
96 struct cz_power_info
*pi
= cz_get_pi(adev
);
97 struct amdgpu_mode_info
*mode_info
= &adev
->mode_info
;
98 int index
= GetIndexIntoMasterTable(DATA
, IntegratedSystemInfo
);
99 union igp_info
*igp_info
;
104 if (amdgpu_atom_parse_data_header(mode_info
->atom_context
, index
, NULL
,
105 &frev
, &crev
, &data_offset
)) {
106 igp_info
= (union igp_info
*)(mode_info
->atom_context
->bios
+
110 DRM_ERROR("Unsupported IGP table: %d %d\n", frev
, crev
);
113 pi
->sys_info
.bootup_sclk
=
114 le32_to_cpu(igp_info
->info_9
.ulBootUpEngineClock
);
115 pi
->sys_info
.bootup_uma_clk
=
116 le32_to_cpu(igp_info
->info_9
.ulBootUpUMAClock
);
117 pi
->sys_info
.dentist_vco_freq
=
118 le32_to_cpu(igp_info
->info_9
.ulDentistVCOFreq
);
119 pi
->sys_info
.bootup_nb_voltage_index
=
120 le16_to_cpu(igp_info
->info_9
.usBootUpNBVoltage
);
122 if (igp_info
->info_9
.ucHtcTmpLmt
== 0)
123 pi
->sys_info
.htc_tmp_lmt
= 203;
125 pi
->sys_info
.htc_tmp_lmt
= igp_info
->info_9
.ucHtcTmpLmt
;
127 if (igp_info
->info_9
.ucHtcHystLmt
== 0)
128 pi
->sys_info
.htc_hyst_lmt
= 5;
130 pi
->sys_info
.htc_hyst_lmt
= igp_info
->info_9
.ucHtcHystLmt
;
132 if (pi
->sys_info
.htc_tmp_lmt
<= pi
->sys_info
.htc_hyst_lmt
) {
133 DRM_ERROR("The htcTmpLmt should be larger than htcHystLmt.\n");
137 if (le32_to_cpu(igp_info
->info_9
.ulSystemConfig
) & (1 << 3) &&
138 pi
->enable_nb_ps_policy
)
139 pi
->sys_info
.nb_dpm_enable
= true;
141 pi
->sys_info
.nb_dpm_enable
= false;
143 for (i
= 0; i
< CZ_NUM_NBPSTATES
; i
++) {
144 if (i
< CZ_NUM_NBPMEMORY_CLOCK
)
145 pi
->sys_info
.nbp_memory_clock
[i
] =
146 le32_to_cpu(igp_info
->info_9
.ulNbpStateMemclkFreq
[i
]);
147 pi
->sys_info
.nbp_n_clock
[i
] =
148 le32_to_cpu(igp_info
->info_9
.ulNbpStateNClkFreq
[i
]);
151 for (i
= 0; i
< CZ_MAX_DISPLAY_CLOCK_LEVEL
; i
++)
152 pi
->sys_info
.display_clock
[i
] =
153 le32_to_cpu(igp_info
->info_9
.sDispClkVoltageMapping
[i
].ulMaximumSupportedCLK
);
155 for (i
= 0; i
< CZ_NUM_NBPSTATES
; i
++)
156 pi
->sys_info
.nbp_voltage_index
[i
] =
157 le32_to_cpu(igp_info
->info_9
.usNBPStateVoltage
[i
]);
159 if (le32_to_cpu(igp_info
->info_9
.ulGPUCapInfo
) &
160 SYS_INFO_GPUCAPS__ENABEL_DFS_BYPASS
)
161 pi
->caps_enable_dfs_bypass
= true;
163 pi
->sys_info
.uma_channel_number
=
164 igp_info
->info_9
.ucUMAChannelNumber
;
166 cz_construct_max_power_limits_table(adev
,
167 &adev
->pm
.dpm
.dyn_state
.max_clock_voltage_on_ac
);
173 static void cz_patch_voltage_values(struct amdgpu_device
*adev
)
176 struct amdgpu_uvd_clock_voltage_dependency_table
*uvd_table
=
177 &adev
->pm
.dpm
.dyn_state
.uvd_clock_voltage_dependency_table
;
178 struct amdgpu_vce_clock_voltage_dependency_table
*vce_table
=
179 &adev
->pm
.dpm
.dyn_state
.vce_clock_voltage_dependency_table
;
180 struct amdgpu_clock_voltage_dependency_table
*acp_table
=
181 &adev
->pm
.dpm
.dyn_state
.acp_clock_voltage_dependency_table
;
183 if (uvd_table
->count
) {
184 for (i
= 0; i
< uvd_table
->count
; i
++)
185 uvd_table
->entries
[i
].v
=
186 cz_convert_8bit_index_to_voltage(adev
,
187 uvd_table
->entries
[i
].v
);
190 if (vce_table
->count
) {
191 for (i
= 0; i
< vce_table
->count
; i
++)
192 vce_table
->entries
[i
].v
=
193 cz_convert_8bit_index_to_voltage(adev
,
194 vce_table
->entries
[i
].v
);
197 if (acp_table
->count
) {
198 for (i
= 0; i
< acp_table
->count
; i
++)
199 acp_table
->entries
[i
].v
=
200 cz_convert_8bit_index_to_voltage(adev
,
201 acp_table
->entries
[i
].v
);
206 static void cz_construct_boot_state(struct amdgpu_device
*adev
)
208 struct cz_power_info
*pi
= cz_get_pi(adev
);
210 pi
->boot_pl
.sclk
= pi
->sys_info
.bootup_sclk
;
211 pi
->boot_pl
.vddc_index
= pi
->sys_info
.bootup_nb_voltage_index
;
212 pi
->boot_pl
.ds_divider_index
= 0;
213 pi
->boot_pl
.ss_divider_index
= 0;
214 pi
->boot_pl
.allow_gnb_slow
= 1;
215 pi
->boot_pl
.force_nbp_state
= 0;
216 pi
->boot_pl
.display_wm
= 0;
217 pi
->boot_pl
.vce_wm
= 0;
221 static void cz_patch_boot_state(struct amdgpu_device
*adev
,
224 struct cz_power_info
*pi
= cz_get_pi(adev
);
227 ps
->levels
[0] = pi
->boot_pl
;
230 union pplib_clock_info
{
231 struct _ATOM_PPLIB_EVERGREEN_CLOCK_INFO evergreen
;
232 struct _ATOM_PPLIB_SUMO_CLOCK_INFO sumo
;
233 struct _ATOM_PPLIB_CZ_CLOCK_INFO carrizo
;
236 static void cz_parse_pplib_clock_info(struct amdgpu_device
*adev
,
237 struct amdgpu_ps
*rps
, int index
,
238 union pplib_clock_info
*clock_info
)
240 struct cz_power_info
*pi
= cz_get_pi(adev
);
241 struct cz_ps
*ps
= cz_get_ps(rps
);
242 struct cz_pl
*pl
= &ps
->levels
[index
];
243 struct amdgpu_clock_voltage_dependency_table
*table
=
244 &adev
->pm
.dpm
.dyn_state
.vddc_dependency_on_sclk
;
246 pl
->sclk
= table
->entries
[clock_info
->carrizo
.index
].clk
;
247 pl
->vddc_index
= table
->entries
[clock_info
->carrizo
.index
].v
;
249 ps
->num_levels
= index
+ 1;
251 if (pi
->caps_sclk_ds
) {
252 pl
->ds_divider_index
= 5;
253 pl
->ss_divider_index
= 5;
258 static void cz_parse_pplib_non_clock_info(struct amdgpu_device
*adev
,
259 struct amdgpu_ps
*rps
,
260 struct _ATOM_PPLIB_NONCLOCK_INFO
*non_clock_info
,
263 struct cz_ps
*ps
= cz_get_ps(rps
);
265 rps
->caps
= le32_to_cpu(non_clock_info
->ulCapsAndSettings
);
266 rps
->class = le16_to_cpu(non_clock_info
->usClassification
);
267 rps
->class2
= le16_to_cpu(non_clock_info
->usClassification2
);
269 if (ATOM_PPLIB_NONCLOCKINFO_VER1
< table_rev
) {
270 rps
->vclk
= le32_to_cpu(non_clock_info
->ulVCLK
);
271 rps
->dclk
= le32_to_cpu(non_clock_info
->ulDCLK
);
277 if (rps
->class & ATOM_PPLIB_CLASSIFICATION_BOOT
) {
278 adev
->pm
.dpm
.boot_ps
= rps
;
279 cz_patch_boot_state(adev
, ps
);
281 if (rps
->class & ATOM_PPLIB_CLASSIFICATION_UVDSTATE
)
282 adev
->pm
.dpm
.uvd_ps
= rps
;
287 struct _ATOM_PPLIB_POWERPLAYTABLE pplib
;
288 struct _ATOM_PPLIB_POWERPLAYTABLE2 pplib2
;
289 struct _ATOM_PPLIB_POWERPLAYTABLE3 pplib3
;
290 struct _ATOM_PPLIB_POWERPLAYTABLE4 pplib4
;
291 struct _ATOM_PPLIB_POWERPLAYTABLE5 pplib5
;
294 union pplib_power_state
{
295 struct _ATOM_PPLIB_STATE v1
;
296 struct _ATOM_PPLIB_STATE_V2 v2
;
299 static int cz_parse_power_table(struct amdgpu_device
*adev
)
301 struct amdgpu_mode_info
*mode_info
= &adev
->mode_info
;
302 struct _ATOM_PPLIB_NONCLOCK_INFO
*non_clock_info
;
303 union pplib_power_state
*power_state
;
304 int i
, j
, k
, non_clock_array_index
, clock_array_index
;
305 union pplib_clock_info
*clock_info
;
306 struct _StateArray
*state_array
;
307 struct _ClockInfoArray
*clock_info_array
;
308 struct _NonClockInfoArray
*non_clock_info_array
;
309 union power_info
*power_info
;
310 int index
= GetIndexIntoMasterTable(DATA
, PowerPlayInfo
);
313 u8
*power_state_offset
;
316 if (!amdgpu_atom_parse_data_header(mode_info
->atom_context
, index
, NULL
,
317 &frev
, &crev
, &data_offset
))
319 power_info
= (union power_info
*)(mode_info
->atom_context
->bios
+ data_offset
);
321 state_array
= (struct _StateArray
*)
322 (mode_info
->atom_context
->bios
+ data_offset
+
323 le16_to_cpu(power_info
->pplib
.usStateArrayOffset
));
324 clock_info_array
= (struct _ClockInfoArray
*)
325 (mode_info
->atom_context
->bios
+ data_offset
+
326 le16_to_cpu(power_info
->pplib
.usClockInfoArrayOffset
));
327 non_clock_info_array
= (struct _NonClockInfoArray
*)
328 (mode_info
->atom_context
->bios
+ data_offset
+
329 le16_to_cpu(power_info
->pplib
.usNonClockInfoArrayOffset
));
331 adev
->pm
.dpm
.ps
= kzalloc(sizeof(struct amdgpu_ps
) *
332 state_array
->ucNumEntries
, GFP_KERNEL
);
334 if (!adev
->pm
.dpm
.ps
)
337 power_state_offset
= (u8
*)state_array
->states
;
338 adev
->pm
.dpm
.platform_caps
=
339 le32_to_cpu(power_info
->pplib
.ulPlatformCaps
);
340 adev
->pm
.dpm
.backbias_response_time
=
341 le16_to_cpu(power_info
->pplib
.usBackbiasTime
);
342 adev
->pm
.dpm
.voltage_response_time
=
343 le16_to_cpu(power_info
->pplib
.usVoltageTime
);
345 for (i
= 0; i
< state_array
->ucNumEntries
; i
++) {
346 power_state
= (union pplib_power_state
*)power_state_offset
;
347 non_clock_array_index
= power_state
->v2
.nonClockInfoIndex
;
348 non_clock_info
= (struct _ATOM_PPLIB_NONCLOCK_INFO
*)
349 &non_clock_info_array
->nonClockInfo
[non_clock_array_index
];
351 ps
= kzalloc(sizeof(struct cz_ps
), GFP_KERNEL
);
353 kfree(adev
->pm
.dpm
.ps
);
357 adev
->pm
.dpm
.ps
[i
].ps_priv
= ps
;
359 for (j
= 0; j
< power_state
->v2
.ucNumDPMLevels
; j
++) {
360 clock_array_index
= power_state
->v2
.clockInfoIndex
[j
];
361 if (clock_array_index
>= clock_info_array
->ucNumEntries
)
363 if (k
>= CZ_MAX_HARDWARE_POWERLEVELS
)
365 clock_info
= (union pplib_clock_info
*)
366 &clock_info_array
->clockInfo
[clock_array_index
*
367 clock_info_array
->ucEntrySize
];
368 cz_parse_pplib_clock_info(adev
, &adev
->pm
.dpm
.ps
[i
],
372 cz_parse_pplib_non_clock_info(adev
, &adev
->pm
.dpm
.ps
[i
],
374 non_clock_info_array
->ucEntrySize
);
375 power_state_offset
+= 2 + power_state
->v2
.ucNumDPMLevels
;
377 adev
->pm
.dpm
.num_ps
= state_array
->ucNumEntries
;
382 static int cz_process_firmware_header(struct amdgpu_device
*adev
)
384 struct cz_power_info
*pi
= cz_get_pi(adev
);
388 ret
= cz_read_smc_sram_dword(adev
, SMU8_FIRMWARE_HEADER_LOCATION
+
389 offsetof(struct SMU8_Firmware_Header
,
394 pi
->dpm_table_start
= tmp
;
399 static int cz_dpm_init(struct amdgpu_device
*adev
)
401 struct cz_power_info
*pi
;
404 pi
= kzalloc(sizeof(struct cz_power_info
), GFP_KERNEL
);
408 adev
->pm
.dpm
.priv
= pi
;
410 ret
= amdgpu_get_platform_caps(adev
);
414 ret
= amdgpu_parse_extended_power_table(adev
);
418 pi
->sram_end
= SMC_RAM_END
;
420 /* set up DPM defaults */
421 for (i
= 0; i
< CZ_MAX_HARDWARE_POWERLEVELS
; i
++)
422 pi
->active_target
[i
] = CZ_AT_DFLT
;
424 pi
->mgcg_cgtt_local0
= 0x0;
425 pi
->mgcg_cgtt_local1
= 0x0;
426 pi
->clock_slow_down_step
= 25000;
427 pi
->skip_clock_slow_down
= 1;
428 pi
->enable_nb_ps_policy
= 0;
429 pi
->caps_power_containment
= true;
431 pi
->didt_enabled
= false;
432 if (pi
->didt_enabled
) {
433 pi
->caps_sq_ramping
= true;
434 pi
->caps_db_ramping
= true;
435 pi
->caps_td_ramping
= true;
436 pi
->caps_tcp_ramping
= true;
438 pi
->caps_sclk_ds
= true;
439 pi
->voting_clients
= 0x00c00033;
440 pi
->auto_thermal_throttling_enabled
= true;
441 pi
->bapm_enabled
= false;
442 pi
->disable_nb_ps3_in_battery
= false;
443 pi
->voltage_drop_threshold
= 0;
444 pi
->caps_sclk_throttle_low_notification
= false;
445 pi
->gfx_pg_threshold
= 500;
448 pi
->caps_uvd_pg
= (adev
->pg_flags
& AMDGPU_PG_SUPPORT_UVD
) ? true : false;
449 pi
->caps_uvd_dpm
= true;
451 pi
->caps_vce_pg
= (adev
->pg_flags
& AMDGPU_PG_SUPPORT_VCE
) ? true : false;
452 pi
->caps_vce_dpm
= true;
454 pi
->caps_acp_pg
= (adev
->pg_flags
& AMDGPU_PG_SUPPORT_ACP
) ? true : false;
455 pi
->caps_acp_dpm
= true;
457 pi
->caps_stable_power_state
= false;
458 pi
->nb_dpm_enabled_by_driver
= true;
459 pi
->nb_dpm_enabled
= false;
460 pi
->caps_voltage_island
= false;
461 /* flags which indicate need to upload pptable */
462 pi
->need_pptable_upload
= true;
464 ret
= cz_parse_sys_info_table(adev
);
468 cz_patch_voltage_values(adev
);
469 cz_construct_boot_state(adev
);
471 ret
= cz_parse_power_table(adev
);
475 ret
= cz_process_firmware_header(adev
);
479 pi
->dpm_enabled
= true;
480 pi
->uvd_dynamic_pg
= false;
485 static void cz_dpm_fini(struct amdgpu_device
*adev
)
489 for (i
= 0; i
< adev
->pm
.dpm
.num_ps
; i
++)
490 kfree(adev
->pm
.dpm
.ps
[i
].ps_priv
);
492 kfree(adev
->pm
.dpm
.ps
);
493 kfree(adev
->pm
.dpm
.priv
);
494 amdgpu_free_extended_power_table(adev
);
497 #define ixSMUSVI_NB_CURRENTVID 0xD8230044
498 #define CURRENT_NB_VID_MASK 0xff000000
499 #define CURRENT_NB_VID__SHIFT 24
500 #define ixSMUSVI_GFX_CURRENTVID 0xD8230048
501 #define CURRENT_GFX_VID_MASK 0xff000000
502 #define CURRENT_GFX_VID__SHIFT 24
505 cz_dpm_debugfs_print_current_performance_level(struct amdgpu_device
*adev
,
508 struct cz_power_info
*pi
= cz_get_pi(adev
);
509 struct amdgpu_clock_voltage_dependency_table
*table
=
510 &adev
->pm
.dpm
.dyn_state
.vddc_dependency_on_sclk
;
511 struct amdgpu_uvd_clock_voltage_dependency_table
*uvd_table
=
512 &adev
->pm
.dpm
.dyn_state
.uvd_clock_voltage_dependency_table
;
513 struct amdgpu_vce_clock_voltage_dependency_table
*vce_table
=
514 &adev
->pm
.dpm
.dyn_state
.vce_clock_voltage_dependency_table
;
515 u32 sclk_index
= REG_GET_FIELD(RREG32_SMC(ixTARGET_AND_CURRENT_PROFILE_INDEX
),
516 TARGET_AND_CURRENT_PROFILE_INDEX
, CURR_SCLK_INDEX
);
517 u32 uvd_index
= REG_GET_FIELD(RREG32_SMC(ixTARGET_AND_CURRENT_PROFILE_INDEX_2
),
518 TARGET_AND_CURRENT_PROFILE_INDEX_2
, CURR_UVD_INDEX
);
519 u32 vce_index
= REG_GET_FIELD(RREG32_SMC(ixTARGET_AND_CURRENT_PROFILE_INDEX_2
),
520 TARGET_AND_CURRENT_PROFILE_INDEX_2
, CURR_VCE_INDEX
);
521 u32 sclk
, vclk
, dclk
, ecclk
, tmp
;
524 if (sclk_index
>= NUM_SCLK_LEVELS
) {
525 seq_printf(m
, "invalid sclk dpm profile %d\n", sclk_index
);
527 sclk
= table
->entries
[sclk_index
].clk
;
528 seq_printf(m
, "%u sclk: %u\n", sclk_index
, sclk
);
531 tmp
= (RREG32_SMC(ixSMUSVI_NB_CURRENTVID
) &
532 CURRENT_NB_VID_MASK
) >> CURRENT_NB_VID__SHIFT
;
533 vddnb
= cz_convert_8bit_index_to_voltage(adev
, (u16
)tmp
);
534 tmp
= (RREG32_SMC(ixSMUSVI_GFX_CURRENTVID
) &
535 CURRENT_GFX_VID_MASK
) >> CURRENT_GFX_VID__SHIFT
;
536 vddgfx
= cz_convert_8bit_index_to_voltage(adev
, (u16
)tmp
);
537 seq_printf(m
, "vddnb: %u vddgfx: %u\n", vddnb
, vddgfx
);
539 seq_printf(m
, "uvd %sabled\n", pi
->uvd_power_gated
? "dis" : "en");
540 if (!pi
->uvd_power_gated
) {
541 if (uvd_index
>= CZ_MAX_HARDWARE_POWERLEVELS
) {
542 seq_printf(m
, "invalid uvd dpm level %d\n", uvd_index
);
544 vclk
= uvd_table
->entries
[uvd_index
].vclk
;
545 dclk
= uvd_table
->entries
[uvd_index
].dclk
;
546 seq_printf(m
, "%u uvd vclk: %u dclk: %u\n", uvd_index
, vclk
, dclk
);
550 seq_printf(m
, "vce %sabled\n", pi
->vce_power_gated
? "dis" : "en");
551 if (!pi
->vce_power_gated
) {
552 if (vce_index
>= CZ_MAX_HARDWARE_POWERLEVELS
) {
553 seq_printf(m
, "invalid vce dpm level %d\n", vce_index
);
555 ecclk
= vce_table
->entries
[vce_index
].ecclk
;
556 seq_printf(m
, "%u vce ecclk: %u\n", vce_index
, ecclk
);
561 static void cz_dpm_print_power_state(struct amdgpu_device
*adev
,
562 struct amdgpu_ps
*rps
)
565 struct cz_ps
*ps
= cz_get_ps(rps
);
567 amdgpu_dpm_print_class_info(rps
->class, rps
->class2
);
568 amdgpu_dpm_print_cap_info(rps
->caps
);
570 DRM_INFO("\tuvd vclk: %d dclk: %d\n", rps
->vclk
, rps
->dclk
);
571 for (i
= 0; i
< ps
->num_levels
; i
++) {
572 struct cz_pl
*pl
= &ps
->levels
[i
];
574 DRM_INFO("\t\tpower level %d sclk: %u vddc: %u\n",
576 cz_convert_8bit_index_to_voltage(adev
, pl
->vddc_index
));
579 amdgpu_dpm_print_ps_status(adev
, rps
);
582 static void cz_dpm_set_funcs(struct amdgpu_device
*adev
);
584 static int cz_dpm_early_init(void *handle
)
586 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
588 cz_dpm_set_funcs(adev
);
594 static int cz_dpm_late_init(void *handle
)
596 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
600 /* init the sysfs and debugfs files late */
601 ret
= amdgpu_pm_sysfs_init(adev
);
605 /* powerdown unused blocks for now */
606 cz_dpm_powergate_uvd(adev
, true);
607 cz_dpm_powergate_vce(adev
, true);
613 static int cz_dpm_sw_init(void *handle
)
615 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
617 /* fix me to add thermal support TODO */
619 /* default to balanced state */
620 adev
->pm
.dpm
.state
= POWER_STATE_TYPE_BALANCED
;
621 adev
->pm
.dpm
.user_state
= POWER_STATE_TYPE_BALANCED
;
622 adev
->pm
.dpm
.forced_level
= AMDGPU_DPM_FORCED_LEVEL_AUTO
;
623 adev
->pm
.default_sclk
= adev
->clock
.default_sclk
;
624 adev
->pm
.default_mclk
= adev
->clock
.default_mclk
;
625 adev
->pm
.current_sclk
= adev
->clock
.default_sclk
;
626 adev
->pm
.current_mclk
= adev
->clock
.default_mclk
;
627 adev
->pm
.int_thermal_type
= THERMAL_TYPE_NONE
;
632 mutex_lock(&adev
->pm
.mutex
);
633 ret
= cz_dpm_init(adev
);
635 goto dpm_init_failed
;
637 adev
->pm
.dpm
.current_ps
= adev
->pm
.dpm
.requested_ps
= adev
->pm
.dpm
.boot_ps
;
639 amdgpu_pm_print_power_states(adev
);
641 mutex_unlock(&adev
->pm
.mutex
);
642 DRM_INFO("amdgpu: dpm initialized\n");
648 mutex_unlock(&adev
->pm
.mutex
);
649 DRM_ERROR("amdgpu: dpm initialization failed\n");
654 static int cz_dpm_sw_fini(void *handle
)
656 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
658 mutex_lock(&adev
->pm
.mutex
);
659 amdgpu_pm_sysfs_fini(adev
);
661 mutex_unlock(&adev
->pm
.mutex
);
666 static void cz_reset_ap_mask(struct amdgpu_device
*adev
)
668 struct cz_power_info
*pi
= cz_get_pi(adev
);
670 pi
->active_process_mask
= 0;
674 static int cz_dpm_download_pptable_from_smu(struct amdgpu_device
*adev
,
679 ret
= cz_smu_download_pptable(adev
, table
);
684 static int cz_dpm_upload_pptable_to_smu(struct amdgpu_device
*adev
)
686 struct cz_power_info
*pi
= cz_get_pi(adev
);
687 struct SMU8_Fusion_ClkTable
*clock_table
;
688 struct atom_clock_dividers dividers
;
693 struct amdgpu_clock_voltage_dependency_table
*vddc_table
=
694 &adev
->pm
.dpm
.dyn_state
.vddc_dependency_on_sclk
;
695 struct amdgpu_clock_voltage_dependency_table
*vddgfx_table
=
696 &adev
->pm
.dpm
.dyn_state
.vddgfx_dependency_on_sclk
;
697 struct amdgpu_uvd_clock_voltage_dependency_table
*uvd_table
=
698 &adev
->pm
.dpm
.dyn_state
.uvd_clock_voltage_dependency_table
;
699 struct amdgpu_vce_clock_voltage_dependency_table
*vce_table
=
700 &adev
->pm
.dpm
.dyn_state
.vce_clock_voltage_dependency_table
;
701 struct amdgpu_clock_voltage_dependency_table
*acp_table
=
702 &adev
->pm
.dpm
.dyn_state
.acp_clock_voltage_dependency_table
;
704 if (!pi
->need_pptable_upload
)
707 ret
= cz_dpm_download_pptable_from_smu(adev
, &table
);
709 DRM_ERROR("amdgpu: Failed to get power play table from SMU!\n");
713 clock_table
= (struct SMU8_Fusion_ClkTable
*)table
;
714 /* patch clock table */
715 if (vddc_table
->count
> CZ_MAX_HARDWARE_POWERLEVELS
||
716 vddgfx_table
->count
> CZ_MAX_HARDWARE_POWERLEVELS
||
717 uvd_table
->count
> CZ_MAX_HARDWARE_POWERLEVELS
||
718 vce_table
->count
> CZ_MAX_HARDWARE_POWERLEVELS
||
719 acp_table
->count
> CZ_MAX_HARDWARE_POWERLEVELS
) {
720 DRM_ERROR("amdgpu: Invalid Clock Voltage Dependency Table!\n");
724 for (i
= 0; i
< CZ_MAX_HARDWARE_POWERLEVELS
; i
++) {
727 clock_table
->SclkBreakdownTable
.ClkLevel
[i
].GnbVid
=
728 (i
< vddc_table
->count
) ? (uint8_t)vddc_table
->entries
[i
].v
: 0;
729 clock_table
->SclkBreakdownTable
.ClkLevel
[i
].Frequency
=
730 (i
< vddc_table
->count
) ? vddc_table
->entries
[i
].clk
: 0;
731 ret
= amdgpu_atombios_get_clock_dividers(adev
, COMPUTE_GPUCLK_INPUT_FLAG_DEFAULT_GPUCLK
,
732 clock_table
->SclkBreakdownTable
.ClkLevel
[i
].Frequency
,
736 clock_table
->SclkBreakdownTable
.ClkLevel
[i
].DfsDid
=
737 (uint8_t)dividers
.post_divider
;
740 clock_table
->SclkBreakdownTable
.ClkLevel
[i
].GfxVid
=
741 (i
< vddgfx_table
->count
) ? (uint8_t)vddgfx_table
->entries
[i
].v
: 0;
744 clock_table
->AclkBreakdownTable
.ClkLevel
[i
].GfxVid
=
745 (i
< acp_table
->count
) ? (uint8_t)acp_table
->entries
[i
].v
: 0;
746 clock_table
->AclkBreakdownTable
.ClkLevel
[i
].Frequency
=
747 (i
< acp_table
->count
) ? acp_table
->entries
[i
].clk
: 0;
748 ret
= amdgpu_atombios_get_clock_dividers(adev
, COMPUTE_GPUCLK_INPUT_FLAG_DEFAULT_GPUCLK
,
749 clock_table
->SclkBreakdownTable
.ClkLevel
[i
].Frequency
,
753 clock_table
->AclkBreakdownTable
.ClkLevel
[i
].DfsDid
=
754 (uint8_t)dividers
.post_divider
;
757 clock_table
->VclkBreakdownTable
.ClkLevel
[i
].GfxVid
=
758 (i
< uvd_table
->count
) ? (uint8_t)uvd_table
->entries
[i
].v
: 0;
759 clock_table
->VclkBreakdownTable
.ClkLevel
[i
].Frequency
=
760 (i
< uvd_table
->count
) ? uvd_table
->entries
[i
].vclk
: 0;
761 ret
= amdgpu_atombios_get_clock_dividers(adev
, COMPUTE_GPUCLK_INPUT_FLAG_DEFAULT_GPUCLK
,
762 clock_table
->VclkBreakdownTable
.ClkLevel
[i
].Frequency
,
766 clock_table
->VclkBreakdownTable
.ClkLevel
[i
].DfsDid
=
767 (uint8_t)dividers
.post_divider
;
769 clock_table
->DclkBreakdownTable
.ClkLevel
[i
].GfxVid
=
770 (i
< uvd_table
->count
) ? (uint8_t)uvd_table
->entries
[i
].v
: 0;
771 clock_table
->DclkBreakdownTable
.ClkLevel
[i
].Frequency
=
772 (i
< uvd_table
->count
) ? uvd_table
->entries
[i
].dclk
: 0;
773 ret
= amdgpu_atombios_get_clock_dividers(adev
, COMPUTE_GPUCLK_INPUT_FLAG_DEFAULT_GPUCLK
,
774 clock_table
->DclkBreakdownTable
.ClkLevel
[i
].Frequency
,
778 clock_table
->DclkBreakdownTable
.ClkLevel
[i
].DfsDid
=
779 (uint8_t)dividers
.post_divider
;
782 clock_table
->EclkBreakdownTable
.ClkLevel
[i
].GfxVid
=
783 (i
< vce_table
->count
) ? (uint8_t)vce_table
->entries
[i
].v
: 0;
784 clock_table
->EclkBreakdownTable
.ClkLevel
[i
].Frequency
=
785 (i
< vce_table
->count
) ? vce_table
->entries
[i
].ecclk
: 0;
786 ret
= amdgpu_atombios_get_clock_dividers(adev
, COMPUTE_GPUCLK_INPUT_FLAG_DEFAULT_GPUCLK
,
787 clock_table
->EclkBreakdownTable
.ClkLevel
[i
].Frequency
,
791 clock_table
->EclkBreakdownTable
.ClkLevel
[i
].DfsDid
=
792 (uint8_t)dividers
.post_divider
;
795 /* its time to upload to SMU */
796 ret
= cz_smu_upload_pptable(adev
);
798 DRM_ERROR("amdgpu: Failed to put power play table to SMU!\n");
805 static void cz_init_sclk_limit(struct amdgpu_device
*adev
)
807 struct cz_power_info
*pi
= cz_get_pi(adev
);
808 struct amdgpu_clock_voltage_dependency_table
*table
=
809 &adev
->pm
.dpm
.dyn_state
.vddc_dependency_on_sclk
;
810 uint32_t clock
= 0, level
;
812 if (!table
|| !table
->count
) {
813 DRM_ERROR("Invalid Voltage Dependency table.\n");
817 pi
->sclk_dpm
.soft_min_clk
= 0;
818 pi
->sclk_dpm
.hard_min_clk
= 0;
819 cz_send_msg_to_smc(adev
, PPSMC_MSG_GetMaxSclkLevel
);
820 level
= cz_get_argument(adev
);
821 if (level
< table
->count
)
822 clock
= table
->entries
[level
].clk
;
824 DRM_ERROR("Invalid SLCK Voltage Dependency table entry.\n");
825 clock
= table
->entries
[table
->count
- 1].clk
;
828 pi
->sclk_dpm
.soft_max_clk
= clock
;
829 pi
->sclk_dpm
.hard_max_clk
= clock
;
833 static void cz_init_uvd_limit(struct amdgpu_device
*adev
)
835 struct cz_power_info
*pi
= cz_get_pi(adev
);
836 struct amdgpu_uvd_clock_voltage_dependency_table
*table
=
837 &adev
->pm
.dpm
.dyn_state
.uvd_clock_voltage_dependency_table
;
838 uint32_t clock
= 0, level
;
840 if (!table
|| !table
->count
) {
841 DRM_ERROR("Invalid Voltage Dependency table.\n");
845 pi
->uvd_dpm
.soft_min_clk
= 0;
846 pi
->uvd_dpm
.hard_min_clk
= 0;
847 cz_send_msg_to_smc(adev
, PPSMC_MSG_GetMaxUvdLevel
);
848 level
= cz_get_argument(adev
);
849 if (level
< table
->count
)
850 clock
= table
->entries
[level
].vclk
;
852 DRM_ERROR("Invalid UVD Voltage Dependency table entry.\n");
853 clock
= table
->entries
[table
->count
- 1].vclk
;
856 pi
->uvd_dpm
.soft_max_clk
= clock
;
857 pi
->uvd_dpm
.hard_max_clk
= clock
;
861 static void cz_init_vce_limit(struct amdgpu_device
*adev
)
863 struct cz_power_info
*pi
= cz_get_pi(adev
);
864 struct amdgpu_vce_clock_voltage_dependency_table
*table
=
865 &adev
->pm
.dpm
.dyn_state
.vce_clock_voltage_dependency_table
;
866 uint32_t clock
= 0, level
;
868 if (!table
|| !table
->count
) {
869 DRM_ERROR("Invalid Voltage Dependency table.\n");
873 pi
->vce_dpm
.soft_min_clk
= table
->entries
[0].ecclk
;
874 pi
->vce_dpm
.hard_min_clk
= table
->entries
[0].ecclk
;
875 cz_send_msg_to_smc(adev
, PPSMC_MSG_GetMaxEclkLevel
);
876 level
= cz_get_argument(adev
);
877 if (level
< table
->count
)
878 clock
= table
->entries
[level
].ecclk
;
880 /* future BIOS would fix this error */
881 DRM_ERROR("Invalid VCE Voltage Dependency table entry.\n");
882 clock
= table
->entries
[table
->count
- 1].ecclk
;
885 pi
->vce_dpm
.soft_max_clk
= clock
;
886 pi
->vce_dpm
.hard_max_clk
= clock
;
890 static void cz_init_acp_limit(struct amdgpu_device
*adev
)
892 struct cz_power_info
*pi
= cz_get_pi(adev
);
893 struct amdgpu_clock_voltage_dependency_table
*table
=
894 &adev
->pm
.dpm
.dyn_state
.acp_clock_voltage_dependency_table
;
895 uint32_t clock
= 0, level
;
897 if (!table
|| !table
->count
) {
898 DRM_ERROR("Invalid Voltage Dependency table.\n");
902 pi
->acp_dpm
.soft_min_clk
= 0;
903 pi
->acp_dpm
.hard_min_clk
= 0;
904 cz_send_msg_to_smc(adev
, PPSMC_MSG_GetMaxAclkLevel
);
905 level
= cz_get_argument(adev
);
906 if (level
< table
->count
)
907 clock
= table
->entries
[level
].clk
;
909 DRM_ERROR("Invalid ACP Voltage Dependency table entry.\n");
910 clock
= table
->entries
[table
->count
- 1].clk
;
913 pi
->acp_dpm
.soft_max_clk
= clock
;
914 pi
->acp_dpm
.hard_max_clk
= clock
;
918 static void cz_init_pg_state(struct amdgpu_device
*adev
)
920 struct cz_power_info
*pi
= cz_get_pi(adev
);
922 pi
->uvd_power_gated
= false;
923 pi
->vce_power_gated
= false;
924 pi
->acp_power_gated
= false;
928 static void cz_init_sclk_threshold(struct amdgpu_device
*adev
)
930 struct cz_power_info
*pi
= cz_get_pi(adev
);
932 pi
->low_sclk_interrupt_threshold
= 0;
936 static void cz_dpm_setup_asic(struct amdgpu_device
*adev
)
938 cz_reset_ap_mask(adev
);
939 cz_dpm_upload_pptable_to_smu(adev
);
940 cz_init_sclk_limit(adev
);
941 cz_init_uvd_limit(adev
);
942 cz_init_vce_limit(adev
);
943 cz_init_acp_limit(adev
);
944 cz_init_pg_state(adev
);
945 cz_init_sclk_threshold(adev
);
949 static bool cz_check_smu_feature(struct amdgpu_device
*adev
,
952 uint32_t smu_feature
= 0;
955 ret
= cz_send_msg_to_smc_with_parameter(adev
,
956 PPSMC_MSG_GetFeatureStatus
, 0);
958 DRM_ERROR("Failed to get SMU features from SMC.\n");
961 smu_feature
= cz_get_argument(adev
);
962 if (feature
& smu_feature
)
969 static bool cz_check_for_dpm_enabled(struct amdgpu_device
*adev
)
971 if (cz_check_smu_feature(adev
,
972 SMU_EnabledFeatureScoreboard_SclkDpmOn
))
978 static void cz_program_voting_clients(struct amdgpu_device
*adev
)
980 WREG32_SMC(ixCG_FREQ_TRAN_VOTING_0
, PPCZ_VOTINGRIGHTSCLIENTS_DFLT0
);
983 static void cz_clear_voting_clients(struct amdgpu_device
*adev
)
985 WREG32_SMC(ixCG_FREQ_TRAN_VOTING_0
, 0);
988 static int cz_start_dpm(struct amdgpu_device
*adev
)
993 ret
= cz_send_msg_to_smc_with_parameter(adev
,
994 PPSMC_MSG_EnableAllSmuFeatures
, SCLK_DPM_MASK
);
996 DRM_ERROR("SMU feature: SCLK_DPM enable failed\n");
1004 static int cz_stop_dpm(struct amdgpu_device
*adev
)
1008 if (amdgpu_dpm
&& adev
->pm
.dpm_enabled
) {
1009 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1010 PPSMC_MSG_DisableAllSmuFeatures
, SCLK_DPM_MASK
);
1012 DRM_ERROR("SMU feature: SCLK_DPM disable failed\n");
1020 static uint32_t cz_get_sclk_level(struct amdgpu_device
*adev
,
1021 uint32_t clock
, uint16_t msg
)
1024 struct amdgpu_clock_voltage_dependency_table
*table
=
1025 &adev
->pm
.dpm
.dyn_state
.vddc_dependency_on_sclk
;
1028 case PPSMC_MSG_SetSclkSoftMin
:
1029 case PPSMC_MSG_SetSclkHardMin
:
1030 for (i
= 0; i
< table
->count
; i
++)
1031 if (clock
<= table
->entries
[i
].clk
)
1033 if (i
== table
->count
)
1034 i
= table
->count
- 1;
1036 case PPSMC_MSG_SetSclkSoftMax
:
1037 case PPSMC_MSG_SetSclkHardMax
:
1038 for (i
= table
->count
- 1; i
>= 0; i
--)
1039 if (clock
>= table
->entries
[i
].clk
)
1051 static uint32_t cz_get_eclk_level(struct amdgpu_device
*adev
,
1052 uint32_t clock
, uint16_t msg
)
1055 struct amdgpu_vce_clock_voltage_dependency_table
*table
=
1056 &adev
->pm
.dpm
.dyn_state
.vce_clock_voltage_dependency_table
;
1058 if (table
->count
== 0)
1062 case PPSMC_MSG_SetEclkSoftMin
:
1063 case PPSMC_MSG_SetEclkHardMin
:
1064 for (i
= 0; i
< table
->count
-1; i
++)
1065 if (clock
<= table
->entries
[i
].ecclk
)
1068 case PPSMC_MSG_SetEclkSoftMax
:
1069 case PPSMC_MSG_SetEclkHardMax
:
1070 for (i
= table
->count
- 1; i
> 0; i
--)
1071 if (clock
>= table
->entries
[i
].ecclk
)
1081 static int cz_program_bootup_state(struct amdgpu_device
*adev
)
1083 struct cz_power_info
*pi
= cz_get_pi(adev
);
1084 uint32_t soft_min_clk
= 0;
1085 uint32_t soft_max_clk
= 0;
1088 pi
->sclk_dpm
.soft_min_clk
= pi
->sys_info
.bootup_sclk
;
1089 pi
->sclk_dpm
.soft_max_clk
= pi
->sys_info
.bootup_sclk
;
1091 soft_min_clk
= cz_get_sclk_level(adev
,
1092 pi
->sclk_dpm
.soft_min_clk
,
1093 PPSMC_MSG_SetSclkSoftMin
);
1094 soft_max_clk
= cz_get_sclk_level(adev
,
1095 pi
->sclk_dpm
.soft_max_clk
,
1096 PPSMC_MSG_SetSclkSoftMax
);
1098 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1099 PPSMC_MSG_SetSclkSoftMin
, soft_min_clk
);
1103 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1104 PPSMC_MSG_SetSclkSoftMax
, soft_max_clk
);
1112 static int cz_disable_cgpg(struct amdgpu_device
*adev
)
1118 static int cz_enable_cgpg(struct amdgpu_device
*adev
)
1124 static int cz_program_pt_config_registers(struct amdgpu_device
*adev
)
1129 static void cz_do_enable_didt(struct amdgpu_device
*adev
, bool enable
)
1131 struct cz_power_info
*pi
= cz_get_pi(adev
);
1134 if (pi
->caps_sq_ramping
) {
1135 reg
= RREG32_DIDT(ixDIDT_SQ_CTRL0
);
1137 reg
= REG_SET_FIELD(reg
, DIDT_SQ_CTRL0
, DIDT_CTRL_EN
, 1);
1139 reg
= REG_SET_FIELD(reg
, DIDT_SQ_CTRL0
, DIDT_CTRL_EN
, 0);
1140 WREG32_DIDT(ixDIDT_SQ_CTRL0
, reg
);
1142 if (pi
->caps_db_ramping
) {
1143 reg
= RREG32_DIDT(ixDIDT_DB_CTRL0
);
1145 reg
= REG_SET_FIELD(reg
, DIDT_DB_CTRL0
, DIDT_CTRL_EN
, 1);
1147 reg
= REG_SET_FIELD(reg
, DIDT_DB_CTRL0
, DIDT_CTRL_EN
, 0);
1148 WREG32_DIDT(ixDIDT_DB_CTRL0
, reg
);
1150 if (pi
->caps_td_ramping
) {
1151 reg
= RREG32_DIDT(ixDIDT_TD_CTRL0
);
1153 reg
= REG_SET_FIELD(reg
, DIDT_TD_CTRL0
, DIDT_CTRL_EN
, 1);
1155 reg
= REG_SET_FIELD(reg
, DIDT_TD_CTRL0
, DIDT_CTRL_EN
, 0);
1156 WREG32_DIDT(ixDIDT_TD_CTRL0
, reg
);
1158 if (pi
->caps_tcp_ramping
) {
1159 reg
= RREG32_DIDT(ixDIDT_TCP_CTRL0
);
1161 reg
= REG_SET_FIELD(reg
, DIDT_SQ_CTRL0
, DIDT_CTRL_EN
, 1);
1163 reg
= REG_SET_FIELD(reg
, DIDT_SQ_CTRL0
, DIDT_CTRL_EN
, 0);
1164 WREG32_DIDT(ixDIDT_TCP_CTRL0
, reg
);
1169 static int cz_enable_didt(struct amdgpu_device
*adev
, bool enable
)
1171 struct cz_power_info
*pi
= cz_get_pi(adev
);
1174 if (pi
->caps_sq_ramping
|| pi
->caps_db_ramping
||
1175 pi
->caps_td_ramping
|| pi
->caps_tcp_ramping
) {
1176 if (adev
->gfx
.gfx_current_status
!= AMDGPU_GFX_SAFE_MODE
) {
1177 ret
= cz_disable_cgpg(adev
);
1179 DRM_ERROR("Pre Di/Dt disable cg/pg failed\n");
1182 adev
->gfx
.gfx_current_status
= AMDGPU_GFX_SAFE_MODE
;
1185 ret
= cz_program_pt_config_registers(adev
);
1187 DRM_ERROR("Di/Dt config failed\n");
1190 cz_do_enable_didt(adev
, enable
);
1192 if (adev
->gfx
.gfx_current_status
== AMDGPU_GFX_SAFE_MODE
) {
1193 ret
= cz_enable_cgpg(adev
);
1195 DRM_ERROR("Post Di/Dt enable cg/pg failed\n");
1198 adev
->gfx
.gfx_current_status
= AMDGPU_GFX_NORMAL_MODE
;
1206 static void cz_reset_acp_boot_level(struct amdgpu_device
*adev
)
1210 static void cz_update_current_ps(struct amdgpu_device
*adev
,
1211 struct amdgpu_ps
*rps
)
1213 struct cz_power_info
*pi
= cz_get_pi(adev
);
1214 struct cz_ps
*ps
= cz_get_ps(rps
);
1216 pi
->current_ps
= *ps
;
1217 pi
->current_rps
= *rps
;
1218 pi
->current_rps
.ps_priv
= ps
;
1222 static void cz_update_requested_ps(struct amdgpu_device
*adev
,
1223 struct amdgpu_ps
*rps
)
1225 struct cz_power_info
*pi
= cz_get_pi(adev
);
1226 struct cz_ps
*ps
= cz_get_ps(rps
);
1228 pi
->requested_ps
= *ps
;
1229 pi
->requested_rps
= *rps
;
1230 pi
->requested_rps
.ps_priv
= ps
;
1234 /* PP arbiter support needed TODO */
1235 static void cz_apply_state_adjust_rules(struct amdgpu_device
*adev
,
1236 struct amdgpu_ps
*new_rps
,
1237 struct amdgpu_ps
*old_rps
)
1239 struct cz_ps
*ps
= cz_get_ps(new_rps
);
1240 struct cz_power_info
*pi
= cz_get_pi(adev
);
1241 struct amdgpu_clock_and_voltage_limits
*limits
=
1242 &adev
->pm
.dpm
.dyn_state
.max_clock_voltage_on_ac
;
1243 /* 10kHz memory clock */
1246 ps
->force_high
= false;
1247 ps
->need_dfs_bypass
= true;
1248 pi
->video_start
= new_rps
->dclk
|| new_rps
->vclk
||
1249 new_rps
->evclk
|| new_rps
->ecclk
;
1251 if ((new_rps
->class & ATOM_PPLIB_CLASSIFICATION_UI_MASK
) ==
1252 ATOM_PPLIB_CLASSIFICATION_UI_BATTERY
)
1253 pi
->battery_state
= true;
1255 pi
->battery_state
= false;
1257 if (pi
->caps_stable_power_state
)
1258 mclk
= limits
->mclk
;
1260 if (mclk
> pi
->sys_info
.nbp_memory_clock
[CZ_NUM_NBPMEMORY_CLOCK
- 1])
1261 ps
->force_high
= true;
1265 static int cz_dpm_enable(struct amdgpu_device
*adev
)
1269 /* renable will hang up SMU, so check first */
1270 if (cz_check_for_dpm_enabled(adev
))
1273 cz_program_voting_clients(adev
);
1275 ret
= cz_start_dpm(adev
);
1277 DRM_ERROR("Carrizo DPM enable failed\n");
1281 ret
= cz_program_bootup_state(adev
);
1283 DRM_ERROR("Carrizo bootup state program failed\n");
1287 ret
= cz_enable_didt(adev
, true);
1289 DRM_ERROR("Carrizo enable di/dt failed\n");
1293 cz_reset_acp_boot_level(adev
);
1295 cz_update_current_ps(adev
, adev
->pm
.dpm
.boot_ps
);
1300 static int cz_dpm_hw_init(void *handle
)
1302 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
1305 mutex_lock(&adev
->pm
.mutex
);
1307 /* smu init only needs to be called at startup, not resume.
1308 * It should be in sw_init, but requires the fw info gathered
1309 * in sw_init from other IP modules.
1311 ret
= cz_smu_init(adev
);
1313 DRM_ERROR("amdgpu: smc initialization failed\n");
1314 mutex_unlock(&adev
->pm
.mutex
);
1318 /* do the actual fw loading */
1319 ret
= cz_smu_start(adev
);
1321 DRM_ERROR("amdgpu: smc start failed\n");
1322 mutex_unlock(&adev
->pm
.mutex
);
1327 adev
->pm
.dpm_enabled
= false;
1328 mutex_unlock(&adev
->pm
.mutex
);
1332 /* cz dpm setup asic */
1333 cz_dpm_setup_asic(adev
);
1336 ret
= cz_dpm_enable(adev
);
1338 adev
->pm
.dpm_enabled
= false;
1340 adev
->pm
.dpm_enabled
= true;
1342 mutex_unlock(&adev
->pm
.mutex
);
1347 static int cz_dpm_disable(struct amdgpu_device
*adev
)
1351 if (!cz_check_for_dpm_enabled(adev
))
1354 ret
= cz_enable_didt(adev
, false);
1356 DRM_ERROR("Carrizo disable di/dt failed\n");
1360 /* powerup blocks */
1361 cz_dpm_powergate_uvd(adev
, false);
1362 cz_dpm_powergate_vce(adev
, false);
1364 cz_clear_voting_clients(adev
);
1366 cz_update_current_ps(adev
, adev
->pm
.dpm
.boot_ps
);
1371 static int cz_dpm_hw_fini(void *handle
)
1374 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
1376 mutex_lock(&adev
->pm
.mutex
);
1378 /* smu fini only needs to be called at teardown, not suspend.
1379 * It should be in sw_fini, but we put it here for symmetry
1384 if (adev
->pm
.dpm_enabled
) {
1385 ret
= cz_dpm_disable(adev
);
1387 adev
->pm
.dpm
.current_ps
=
1388 adev
->pm
.dpm
.requested_ps
=
1389 adev
->pm
.dpm
.boot_ps
;
1392 adev
->pm
.dpm_enabled
= false;
1394 mutex_unlock(&adev
->pm
.mutex
);
1399 static int cz_dpm_suspend(void *handle
)
1402 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
1404 if (adev
->pm
.dpm_enabled
) {
1405 mutex_lock(&adev
->pm
.mutex
);
1407 ret
= cz_dpm_disable(adev
);
1409 adev
->pm
.dpm
.current_ps
=
1410 adev
->pm
.dpm
.requested_ps
=
1411 adev
->pm
.dpm
.boot_ps
;
1413 mutex_unlock(&adev
->pm
.mutex
);
1419 static int cz_dpm_resume(void *handle
)
1422 struct amdgpu_device
*adev
= (struct amdgpu_device
*)handle
;
1424 mutex_lock(&adev
->pm
.mutex
);
1426 /* do the actual fw loading */
1427 ret
= cz_smu_start(adev
);
1429 DRM_ERROR("amdgpu: smc start failed\n");
1430 mutex_unlock(&adev
->pm
.mutex
);
1435 adev
->pm
.dpm_enabled
= false;
1436 mutex_unlock(&adev
->pm
.mutex
);
1440 /* cz dpm setup asic */
1441 cz_dpm_setup_asic(adev
);
1444 ret
= cz_dpm_enable(adev
);
1446 adev
->pm
.dpm_enabled
= false;
1448 adev
->pm
.dpm_enabled
= true;
1450 mutex_unlock(&adev
->pm
.mutex
);
1451 /* upon resume, re-compute the clocks */
1452 if (adev
->pm
.dpm_enabled
)
1453 amdgpu_pm_compute_clocks(adev
);
1458 static int cz_dpm_set_clockgating_state(void *handle
,
1459 enum amd_clockgating_state state
)
1464 static int cz_dpm_set_powergating_state(void *handle
,
1465 enum amd_powergating_state state
)
1470 /* borrowed from KV, need future unify */
1471 static int cz_dpm_get_temperature(struct amdgpu_device
*adev
)
1473 int actual_temp
= 0;
1474 uint32_t temp
= RREG32_SMC(0xC0300E0C);
1477 actual_temp
= 1000 * ((temp
/ 8) - 49);
1482 static int cz_dpm_pre_set_power_state(struct amdgpu_device
*adev
)
1484 struct cz_power_info
*pi
= cz_get_pi(adev
);
1485 struct amdgpu_ps requested_ps
= *adev
->pm
.dpm
.requested_ps
;
1486 struct amdgpu_ps
*new_ps
= &requested_ps
;
1488 cz_update_requested_ps(adev
, new_ps
);
1489 cz_apply_state_adjust_rules(adev
, &pi
->requested_rps
,
1495 static int cz_dpm_update_sclk_limit(struct amdgpu_device
*adev
)
1497 struct cz_power_info
*pi
= cz_get_pi(adev
);
1498 struct amdgpu_clock_and_voltage_limits
*limits
=
1499 &adev
->pm
.dpm
.dyn_state
.max_clock_voltage_on_ac
;
1500 uint32_t clock
, stable_ps_clock
= 0;
1502 clock
= pi
->sclk_dpm
.soft_min_clk
;
1504 if (pi
->caps_stable_power_state
) {
1505 stable_ps_clock
= limits
->sclk
* 75 / 100;
1506 if (clock
< stable_ps_clock
)
1507 clock
= stable_ps_clock
;
1510 if (clock
!= pi
->sclk_dpm
.soft_min_clk
) {
1511 pi
->sclk_dpm
.soft_min_clk
= clock
;
1512 cz_send_msg_to_smc_with_parameter(adev
,
1513 PPSMC_MSG_SetSclkSoftMin
,
1514 cz_get_sclk_level(adev
, clock
,
1515 PPSMC_MSG_SetSclkSoftMin
));
1518 if (pi
->caps_stable_power_state
&&
1519 pi
->sclk_dpm
.soft_max_clk
!= clock
) {
1520 pi
->sclk_dpm
.soft_max_clk
= clock
;
1521 cz_send_msg_to_smc_with_parameter(adev
,
1522 PPSMC_MSG_SetSclkSoftMax
,
1523 cz_get_sclk_level(adev
, clock
,
1524 PPSMC_MSG_SetSclkSoftMax
));
1526 cz_send_msg_to_smc_with_parameter(adev
,
1527 PPSMC_MSG_SetSclkSoftMax
,
1528 cz_get_sclk_level(adev
,
1529 pi
->sclk_dpm
.soft_max_clk
,
1530 PPSMC_MSG_SetSclkSoftMax
));
1536 static int cz_dpm_set_deep_sleep_sclk_threshold(struct amdgpu_device
*adev
)
1539 struct cz_power_info
*pi
= cz_get_pi(adev
);
1541 if (pi
->caps_sclk_ds
) {
1542 cz_send_msg_to_smc_with_parameter(adev
,
1543 PPSMC_MSG_SetMinDeepSleepSclk
,
1544 CZ_MIN_DEEP_SLEEP_SCLK
);
1550 /* ?? without dal support, is this still needed in setpowerstate list*/
1551 static int cz_dpm_set_watermark_threshold(struct amdgpu_device
*adev
)
1554 struct cz_power_info
*pi
= cz_get_pi(adev
);
1556 cz_send_msg_to_smc_with_parameter(adev
,
1557 PPSMC_MSG_SetWatermarkFrequency
,
1558 pi
->sclk_dpm
.soft_max_clk
);
1563 static int cz_dpm_enable_nbdpm(struct amdgpu_device
*adev
)
1566 struct cz_power_info
*pi
= cz_get_pi(adev
);
1568 /* also depend on dal NBPStateDisableRequired */
1569 if (pi
->nb_dpm_enabled_by_driver
&& !pi
->nb_dpm_enabled
) {
1570 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1571 PPSMC_MSG_EnableAllSmuFeatures
,
1574 DRM_ERROR("amdgpu: nb dpm enable failed\n");
1577 pi
->nb_dpm_enabled
= true;
1583 static void cz_dpm_nbdpm_lm_pstate_enable(struct amdgpu_device
*adev
,
1587 cz_send_msg_to_smc(adev
, PPSMC_MSG_EnableLowMemoryPstate
);
1589 cz_send_msg_to_smc(adev
, PPSMC_MSG_DisableLowMemoryPstate
);
1593 static int cz_dpm_update_low_memory_pstate(struct amdgpu_device
*adev
)
1596 struct cz_power_info
*pi
= cz_get_pi(adev
);
1597 struct cz_ps
*ps
= &pi
->requested_ps
;
1599 if (pi
->sys_info
.nb_dpm_enable
) {
1601 cz_dpm_nbdpm_lm_pstate_enable(adev
, false);
1603 cz_dpm_nbdpm_lm_pstate_enable(adev
, true);
1609 /* with dpm enabled */
1610 static int cz_dpm_set_power_state(struct amdgpu_device
*adev
)
1614 cz_dpm_update_sclk_limit(adev
);
1615 cz_dpm_set_deep_sleep_sclk_threshold(adev
);
1616 cz_dpm_set_watermark_threshold(adev
);
1617 cz_dpm_enable_nbdpm(adev
);
1618 cz_dpm_update_low_memory_pstate(adev
);
1623 static void cz_dpm_post_set_power_state(struct amdgpu_device
*adev
)
1625 struct cz_power_info
*pi
= cz_get_pi(adev
);
1626 struct amdgpu_ps
*ps
= &pi
->requested_rps
;
1628 cz_update_current_ps(adev
, ps
);
1632 static int cz_dpm_force_highest(struct amdgpu_device
*adev
)
1634 struct cz_power_info
*pi
= cz_get_pi(adev
);
1637 if (pi
->sclk_dpm
.soft_min_clk
!= pi
->sclk_dpm
.soft_max_clk
) {
1638 pi
->sclk_dpm
.soft_min_clk
=
1639 pi
->sclk_dpm
.soft_max_clk
;
1640 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1641 PPSMC_MSG_SetSclkSoftMin
,
1642 cz_get_sclk_level(adev
,
1643 pi
->sclk_dpm
.soft_min_clk
,
1644 PPSMC_MSG_SetSclkSoftMin
));
1652 static int cz_dpm_force_lowest(struct amdgpu_device
*adev
)
1654 struct cz_power_info
*pi
= cz_get_pi(adev
);
1657 if (pi
->sclk_dpm
.soft_max_clk
!= pi
->sclk_dpm
.soft_min_clk
) {
1658 pi
->sclk_dpm
.soft_max_clk
= pi
->sclk_dpm
.soft_min_clk
;
1659 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1660 PPSMC_MSG_SetSclkSoftMax
,
1661 cz_get_sclk_level(adev
,
1662 pi
->sclk_dpm
.soft_max_clk
,
1663 PPSMC_MSG_SetSclkSoftMax
));
1671 static uint32_t cz_dpm_get_max_sclk_level(struct amdgpu_device
*adev
)
1673 struct cz_power_info
*pi
= cz_get_pi(adev
);
1675 if (!pi
->max_sclk_level
) {
1676 cz_send_msg_to_smc(adev
, PPSMC_MSG_GetMaxSclkLevel
);
1677 pi
->max_sclk_level
= cz_get_argument(adev
) + 1;
1680 if (pi
->max_sclk_level
> CZ_MAX_HARDWARE_POWERLEVELS
) {
1681 DRM_ERROR("Invalid max sclk level!\n");
1685 return pi
->max_sclk_level
;
1688 static int cz_dpm_unforce_dpm_levels(struct amdgpu_device
*adev
)
1690 struct cz_power_info
*pi
= cz_get_pi(adev
);
1691 struct amdgpu_clock_voltage_dependency_table
*dep_table
=
1692 &adev
->pm
.dpm
.dyn_state
.vddc_dependency_on_sclk
;
1696 pi
->sclk_dpm
.soft_min_clk
= dep_table
->entries
[0].clk
;
1697 level
= cz_dpm_get_max_sclk_level(adev
) - 1;
1698 if (level
< dep_table
->count
)
1699 pi
->sclk_dpm
.soft_max_clk
= dep_table
->entries
[level
].clk
;
1701 pi
->sclk_dpm
.soft_max_clk
=
1702 dep_table
->entries
[dep_table
->count
- 1].clk
;
1704 /* get min/max sclk soft value
1705 * notify SMU to execute */
1706 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1707 PPSMC_MSG_SetSclkSoftMin
,
1708 cz_get_sclk_level(adev
,
1709 pi
->sclk_dpm
.soft_min_clk
,
1710 PPSMC_MSG_SetSclkSoftMin
));
1714 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1715 PPSMC_MSG_SetSclkSoftMax
,
1716 cz_get_sclk_level(adev
,
1717 pi
->sclk_dpm
.soft_max_clk
,
1718 PPSMC_MSG_SetSclkSoftMax
));
1722 DRM_DEBUG("DPM unforce state min=%d, max=%d.\n",
1723 pi
->sclk_dpm
.soft_min_clk
,
1724 pi
->sclk_dpm
.soft_max_clk
);
1729 static int cz_dpm_force_dpm_level(struct amdgpu_device
*adev
,
1730 enum amdgpu_dpm_forced_level level
)
1735 case AMDGPU_DPM_FORCED_LEVEL_HIGH
:
1736 ret
= cz_dpm_unforce_dpm_levels(adev
);
1739 ret
= cz_dpm_force_highest(adev
);
1743 case AMDGPU_DPM_FORCED_LEVEL_LOW
:
1744 ret
= cz_dpm_unforce_dpm_levels(adev
);
1747 ret
= cz_dpm_force_lowest(adev
);
1751 case AMDGPU_DPM_FORCED_LEVEL_AUTO
:
1752 ret
= cz_dpm_unforce_dpm_levels(adev
);
1760 adev
->pm
.dpm
.forced_level
= level
;
1765 /* fix me, display configuration change lists here
1766 * mostly dal related*/
1767 static void cz_dpm_display_configuration_changed(struct amdgpu_device
*adev
)
1771 static uint32_t cz_dpm_get_sclk(struct amdgpu_device
*adev
, bool low
)
1773 struct cz_power_info
*pi
= cz_get_pi(adev
);
1774 struct cz_ps
*requested_state
= cz_get_ps(&pi
->requested_rps
);
1777 return requested_state
->levels
[0].sclk
;
1779 return requested_state
->levels
[requested_state
->num_levels
- 1].sclk
;
1783 static uint32_t cz_dpm_get_mclk(struct amdgpu_device
*adev
, bool low
)
1785 struct cz_power_info
*pi
= cz_get_pi(adev
);
1787 return pi
->sys_info
.bootup_uma_clk
;
1790 static int cz_enable_uvd_dpm(struct amdgpu_device
*adev
, bool enable
)
1792 struct cz_power_info
*pi
= cz_get_pi(adev
);
1795 if (enable
&& pi
->caps_uvd_dpm
) {
1796 pi
->dpm_flags
|= DPMFlags_UVD_Enabled
;
1797 DRM_DEBUG("UVD DPM Enabled.\n");
1799 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1800 PPSMC_MSG_EnableAllSmuFeatures
, UVD_DPM_MASK
);
1802 pi
->dpm_flags
&= ~DPMFlags_UVD_Enabled
;
1803 DRM_DEBUG("UVD DPM Stopped\n");
1805 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1806 PPSMC_MSG_DisableAllSmuFeatures
, UVD_DPM_MASK
);
1812 static int cz_update_uvd_dpm(struct amdgpu_device
*adev
, bool gate
)
1814 return cz_enable_uvd_dpm(adev
, !gate
);
1818 static void cz_dpm_powergate_uvd(struct amdgpu_device
*adev
, bool gate
)
1820 struct cz_power_info
*pi
= cz_get_pi(adev
);
1823 if (pi
->uvd_power_gated
== gate
)
1826 pi
->uvd_power_gated
= gate
;
1829 if (pi
->caps_uvd_pg
) {
1830 /* disable clockgating so we can properly shut down the block */
1831 ret
= amdgpu_set_clockgating_state(adev
, AMD_IP_BLOCK_TYPE_UVD
,
1832 AMD_CG_STATE_UNGATE
);
1833 /* shutdown the UVD block */
1834 ret
= amdgpu_set_powergating_state(adev
, AMD_IP_BLOCK_TYPE_UVD
,
1836 /* XXX: check for errors */
1838 cz_update_uvd_dpm(adev
, gate
);
1839 if (pi
->caps_uvd_pg
)
1840 /* power off the UVD block */
1841 cz_send_msg_to_smc(adev
, PPSMC_MSG_UVDPowerOFF
);
1843 if (pi
->caps_uvd_pg
) {
1844 /* power on the UVD block */
1845 if (pi
->uvd_dynamic_pg
)
1846 cz_send_msg_to_smc_with_parameter(adev
, PPSMC_MSG_UVDPowerON
, 1);
1848 cz_send_msg_to_smc_with_parameter(adev
, PPSMC_MSG_UVDPowerON
, 0);
1849 /* re-init the UVD block */
1850 ret
= amdgpu_set_powergating_state(adev
, AMD_IP_BLOCK_TYPE_UVD
,
1851 AMD_PG_STATE_UNGATE
);
1852 /* enable clockgating. hw will dynamically gate/ungate clocks on the fly */
1853 ret
= amdgpu_set_clockgating_state(adev
, AMD_IP_BLOCK_TYPE_UVD
,
1855 /* XXX: check for errors */
1857 cz_update_uvd_dpm(adev
, gate
);
1861 static int cz_enable_vce_dpm(struct amdgpu_device
*adev
, bool enable
)
1863 struct cz_power_info
*pi
= cz_get_pi(adev
);
1866 if (enable
&& pi
->caps_vce_dpm
) {
1867 pi
->dpm_flags
|= DPMFlags_VCE_Enabled
;
1868 DRM_DEBUG("VCE DPM Enabled.\n");
1870 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1871 PPSMC_MSG_EnableAllSmuFeatures
, VCE_DPM_MASK
);
1874 pi
->dpm_flags
&= ~DPMFlags_VCE_Enabled
;
1875 DRM_DEBUG("VCE DPM Stopped\n");
1877 ret
= cz_send_msg_to_smc_with_parameter(adev
,
1878 PPSMC_MSG_DisableAllSmuFeatures
, VCE_DPM_MASK
);
1884 static int cz_update_vce_dpm(struct amdgpu_device
*adev
)
1886 struct cz_power_info
*pi
= cz_get_pi(adev
);
1887 struct amdgpu_vce_clock_voltage_dependency_table
*table
=
1888 &adev
->pm
.dpm
.dyn_state
.vce_clock_voltage_dependency_table
;
1890 /* Stable Pstate is enabled and we need to set the VCE DPM to highest level */
1891 if (pi
->caps_stable_power_state
) {
1892 pi
->vce_dpm
.hard_min_clk
= table
->entries
[table
->count
-1].ecclk
;
1894 } else { /* non-stable p-state cases. without vce.Arbiter.EcclkHardMin */
1895 pi
->vce_dpm
.hard_min_clk
= table
->entries
[0].ecclk
;
1898 cz_send_msg_to_smc_with_parameter(adev
,
1899 PPSMC_MSG_SetEclkHardMin
,
1900 cz_get_eclk_level(adev
,
1901 pi
->vce_dpm
.hard_min_clk
,
1902 PPSMC_MSG_SetEclkHardMin
));
1906 static void cz_dpm_powergate_vce(struct amdgpu_device
*adev
, bool gate
)
1908 struct cz_power_info
*pi
= cz_get_pi(adev
);
1910 if (pi
->caps_vce_pg
) {
1911 if (pi
->vce_power_gated
!= gate
) {
1913 /* disable clockgating so we can properly shut down the block */
1914 amdgpu_set_clockgating_state(adev
, AMD_IP_BLOCK_TYPE_VCE
,
1915 AMD_CG_STATE_UNGATE
);
1916 /* shutdown the VCE block */
1917 amdgpu_set_powergating_state(adev
, AMD_IP_BLOCK_TYPE_VCE
,
1920 cz_enable_vce_dpm(adev
, false);
1921 /* TODO: to figure out why vce can't be poweroff. */
1922 /* cz_send_msg_to_smc(adev, PPSMC_MSG_VCEPowerOFF); */
1923 pi
->vce_power_gated
= true;
1925 cz_send_msg_to_smc(adev
, PPSMC_MSG_VCEPowerON
);
1926 pi
->vce_power_gated
= false;
1928 /* re-init the VCE block */
1929 amdgpu_set_powergating_state(adev
, AMD_IP_BLOCK_TYPE_VCE
,
1930 AMD_PG_STATE_UNGATE
);
1931 /* enable clockgating. hw will dynamically gate/ungate clocks on the fly */
1932 amdgpu_set_clockgating_state(adev
, AMD_IP_BLOCK_TYPE_VCE
,
1935 cz_update_vce_dpm(adev
);
1936 cz_enable_vce_dpm(adev
, true);
1939 if (! pi
->vce_power_gated
) {
1940 cz_update_vce_dpm(adev
);
1943 } else { /*pi->caps_vce_pg*/
1944 cz_update_vce_dpm(adev
);
1945 cz_enable_vce_dpm(adev
, true);
1951 const struct amd_ip_funcs cz_dpm_ip_funcs
= {
1952 .early_init
= cz_dpm_early_init
,
1953 .late_init
= cz_dpm_late_init
,
1954 .sw_init
= cz_dpm_sw_init
,
1955 .sw_fini
= cz_dpm_sw_fini
,
1956 .hw_init
= cz_dpm_hw_init
,
1957 .hw_fini
= cz_dpm_hw_fini
,
1958 .suspend
= cz_dpm_suspend
,
1959 .resume
= cz_dpm_resume
,
1961 .wait_for_idle
= NULL
,
1963 .print_status
= NULL
,
1964 .set_clockgating_state
= cz_dpm_set_clockgating_state
,
1965 .set_powergating_state
= cz_dpm_set_powergating_state
,
1968 static const struct amdgpu_dpm_funcs cz_dpm_funcs
= {
1969 .get_temperature
= cz_dpm_get_temperature
,
1970 .pre_set_power_state
= cz_dpm_pre_set_power_state
,
1971 .set_power_state
= cz_dpm_set_power_state
,
1972 .post_set_power_state
= cz_dpm_post_set_power_state
,
1973 .display_configuration_changed
= cz_dpm_display_configuration_changed
,
1974 .get_sclk
= cz_dpm_get_sclk
,
1975 .get_mclk
= cz_dpm_get_mclk
,
1976 .print_power_state
= cz_dpm_print_power_state
,
1977 .debugfs_print_current_performance_level
=
1978 cz_dpm_debugfs_print_current_performance_level
,
1979 .force_performance_level
= cz_dpm_force_dpm_level
,
1980 .vblank_too_short
= NULL
,
1981 .powergate_uvd
= cz_dpm_powergate_uvd
,
1982 .powergate_vce
= cz_dpm_powergate_vce
,
1985 static void cz_dpm_set_funcs(struct amdgpu_device
*adev
)
1987 if (NULL
== adev
->pm
.funcs
)
1988 adev
->pm
.funcs
= &cz_dpm_funcs
;