drm/amdgpu: enable gfxoff for sienna_cichlid
[linux-2.6-microblaze.git] / drivers / gpu / drm / amd / powerplay / sienna_cichlid_ppt.c
1 /*
2  * Copyright 2019 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  */
23
24 #include "pp_debug.h"
25 #include <linux/firmware.h>
26 #include <linux/pci.h>
27 #include "amdgpu.h"
28 #include "amdgpu_smu.h"
29 #include "smu_internal.h"
30 #include "atomfirmware.h"
31 #include "amdgpu_atomfirmware.h"
32 #include "smu_v11_0.h"
33 #include "smu11_driver_if_sienna_cichlid.h"
34 #include "soc15_common.h"
35 #include "atom.h"
36 #include "sienna_cichlid_ppt.h"
37 #include "smu_v11_0_pptable.h"
38 #include "smu_v11_0_7_ppsmc.h"
39
40 #include "nbio/nbio_2_3_sh_mask.h"
41 #include "asic_reg/mp/mp_11_0_sh_mask.h"
42
43 #define FEATURE_MASK(feature) (1ULL << feature)
44 #define SMC_DPM_FEATURE ( \
45         FEATURE_MASK(FEATURE_DPM_PREFETCHER_BIT) | \
46         FEATURE_MASK(FEATURE_DPM_GFXCLK_BIT)     | \
47         FEATURE_MASK(FEATURE_DPM_UCLK_BIT)       | \
48         FEATURE_MASK(FEATURE_DPM_LINK_BIT)       | \
49         FEATURE_MASK(FEATURE_DPM_SOCCLK_BIT)     | \
50         FEATURE_MASK(FEATURE_DPM_FCLK_BIT)       | \
51         FEATURE_MASK(FEATURE_DPM_DCEFCLK_BIT))
52
53 #define MSG_MAP(msg, index) \
54         [SMU_MSG_##msg] = {1, (index)}
55
56 static struct smu_11_0_cmn2aisc_mapping sienna_cichlid_message_map[SMU_MSG_MAX_COUNT] = {
57         MSG_MAP(TestMessage,                    PPSMC_MSG_TestMessage),
58         MSG_MAP(GetSmuVersion,                  PPSMC_MSG_GetSmuVersion),
59         MSG_MAP(GetDriverIfVersion,             PPSMC_MSG_GetDriverIfVersion),
60         MSG_MAP(SetAllowedFeaturesMaskLow,      PPSMC_MSG_SetAllowedFeaturesMaskLow),
61         MSG_MAP(SetAllowedFeaturesMaskHigh,     PPSMC_MSG_SetAllowedFeaturesMaskHigh),
62         MSG_MAP(EnableAllSmuFeatures,           PPSMC_MSG_EnableAllSmuFeatures),
63         MSG_MAP(DisableAllSmuFeatures,          PPSMC_MSG_DisableAllSmuFeatures),
64         MSG_MAP(EnableSmuFeaturesLow,           PPSMC_MSG_EnableSmuFeaturesLow),
65         MSG_MAP(EnableSmuFeaturesHigh,          PPSMC_MSG_EnableSmuFeaturesHigh),
66         MSG_MAP(DisableSmuFeaturesLow,          PPSMC_MSG_DisableSmuFeaturesLow),
67         MSG_MAP(DisableSmuFeaturesHigh,         PPSMC_MSG_DisableSmuFeaturesHigh),
68         MSG_MAP(GetEnabledSmuFeaturesLow,       PPSMC_MSG_GetRunningSmuFeaturesLow),
69         MSG_MAP(GetEnabledSmuFeaturesHigh,      PPSMC_MSG_GetRunningSmuFeaturesHigh),
70         MSG_MAP(SetWorkloadMask,                PPSMC_MSG_SetWorkloadMask),
71         MSG_MAP(SetPptLimit,                    PPSMC_MSG_SetPptLimit),
72         MSG_MAP(SetDriverDramAddrHigh,          PPSMC_MSG_SetDriverDramAddrHigh),
73         MSG_MAP(SetDriverDramAddrLow,           PPSMC_MSG_SetDriverDramAddrLow),
74         MSG_MAP(SetToolsDramAddrHigh,           PPSMC_MSG_SetToolsDramAddrHigh),
75         MSG_MAP(SetToolsDramAddrLow,            PPSMC_MSG_SetToolsDramAddrLow),
76         MSG_MAP(TransferTableSmu2Dram,          PPSMC_MSG_TransferTableSmu2Dram),
77         MSG_MAP(TransferTableDram2Smu,          PPSMC_MSG_TransferTableDram2Smu),
78         MSG_MAP(UseDefaultPPTable,              PPSMC_MSG_UseDefaultPPTable),
79         MSG_MAP(EnterBaco,                      PPSMC_MSG_EnterBaco),
80         MSG_MAP(SetSoftMinByFreq,               PPSMC_MSG_SetSoftMinByFreq),
81         MSG_MAP(SetSoftMaxByFreq,               PPSMC_MSG_SetSoftMaxByFreq),
82         MSG_MAP(SetHardMinByFreq,               PPSMC_MSG_SetHardMinByFreq),
83         MSG_MAP(SetHardMaxByFreq,               PPSMC_MSG_SetHardMaxByFreq),
84         MSG_MAP(GetMinDpmFreq,                  PPSMC_MSG_GetMinDpmFreq),
85         MSG_MAP(GetMaxDpmFreq,                  PPSMC_MSG_GetMaxDpmFreq),
86         MSG_MAP(GetDpmFreqByIndex,              PPSMC_MSG_GetDpmFreqByIndex),
87         MSG_MAP(SetGeminiMode,                  PPSMC_MSG_SetGeminiMode),
88         MSG_MAP(SetGeminiApertureHigh,          PPSMC_MSG_SetGeminiApertureHigh),
89         MSG_MAP(SetGeminiApertureLow,           PPSMC_MSG_SetGeminiApertureLow),
90         MSG_MAP(OverridePcieParameters,         PPSMC_MSG_OverridePcieParameters),
91         MSG_MAP(ReenableAcDcInterrupt,          PPSMC_MSG_ReenableAcDcInterrupt),
92         MSG_MAP(NotifyPowerSource,              PPSMC_MSG_NotifyPowerSource),
93         MSG_MAP(SetUclkFastSwitch,              PPSMC_MSG_SetUclkFastSwitch),
94         MSG_MAP(SetVideoFps,                    PPSMC_MSG_SetVideoFps),
95         MSG_MAP(PrepareMp1ForUnload,            PPSMC_MSG_PrepareMp1ForUnload),
96         MSG_MAP(AllowGfxOff,                    PPSMC_MSG_AllowGfxOff),
97         MSG_MAP(DisallowGfxOff,                 PPSMC_MSG_DisallowGfxOff),
98         MSG_MAP(GetPptLimit,                    PPSMC_MSG_GetPptLimit),
99         MSG_MAP(GetDcModeMaxDpmFreq,            PPSMC_MSG_GetDcModeMaxDpmFreq),
100         MSG_MAP(ExitBaco,                       PPSMC_MSG_ExitBaco),
101         MSG_MAP(PowerUpVcn,                     PPSMC_MSG_PowerUpVcn),
102         MSG_MAP(PowerDownVcn,                   PPSMC_MSG_PowerDownVcn),
103         MSG_MAP(PowerUpJpeg,                    PPSMC_MSG_PowerUpJpeg),
104         MSG_MAP(PowerDownJpeg,                  PPSMC_MSG_PowerDownJpeg),
105         MSG_MAP(BacoAudioD3PME,                 PPSMC_MSG_BacoAudioD3PME),
106         MSG_MAP(ArmD3,                          PPSMC_MSG_ArmD3),
107 };
108
109 static struct smu_11_0_cmn2aisc_mapping sienna_cichlid_clk_map[SMU_CLK_COUNT] = {
110         CLK_MAP(GFXCLK,         PPCLK_GFXCLK),
111         CLK_MAP(SCLK,           PPCLK_GFXCLK),
112         CLK_MAP(SOCCLK,         PPCLK_SOCCLK),
113         CLK_MAP(FCLK,           PPCLK_FCLK),
114         CLK_MAP(UCLK,           PPCLK_UCLK),
115         CLK_MAP(MCLK,           PPCLK_UCLK),
116         CLK_MAP(DCLK,           PPCLK_DCLK_0),
117         CLK_MAP(DCLK1,          PPCLK_DCLK_0),
118         CLK_MAP(VCLK,           PPCLK_VCLK_1),
119         CLK_MAP(VCLK1,          PPCLK_VCLK_1),
120         CLK_MAP(DCEFCLK,        PPCLK_DCEFCLK),
121         CLK_MAP(DISPCLK,        PPCLK_DISPCLK),
122         CLK_MAP(PIXCLK,         PPCLK_PIXCLK),
123         CLK_MAP(PHYCLK,         PPCLK_PHYCLK),
124 };
125
126 static struct smu_11_0_cmn2aisc_mapping sienna_cichlid_feature_mask_map[SMU_FEATURE_COUNT] = {
127         FEA_MAP(DPM_PREFETCHER),
128         FEA_MAP(DPM_GFXCLK),
129         FEA_MAP(DPM_GFX_GPO),
130         FEA_MAP(DPM_UCLK),
131         FEA_MAP(DPM_SOCCLK),
132         FEA_MAP(DPM_MP0CLK),
133         FEA_MAP(DPM_LINK),
134         FEA_MAP(DPM_DCEFCLK),
135         FEA_MAP(MEM_VDDCI_SCALING),
136         FEA_MAP(MEM_MVDD_SCALING),
137         FEA_MAP(DS_GFXCLK),
138         FEA_MAP(DS_SOCCLK),
139         FEA_MAP(DS_LCLK),
140         FEA_MAP(DS_DCEFCLK),
141         FEA_MAP(DS_UCLK),
142         FEA_MAP(GFX_ULV),
143         FEA_MAP(FW_DSTATE),
144         FEA_MAP(GFXOFF),
145         FEA_MAP(BACO),
146         FEA_MAP(MM_DPM_PG),
147         FEA_MAP(RSMU_SMN_CG),
148         FEA_MAP(PPT),
149         FEA_MAP(TDC),
150         FEA_MAP(APCC_PLUS),
151         FEA_MAP(GTHR),
152         FEA_MAP(ACDC),
153         FEA_MAP(VR0HOT),
154         FEA_MAP(VR1HOT),
155         FEA_MAP(FW_CTF),
156         FEA_MAP(FAN_CONTROL),
157         FEA_MAP(THERMAL),
158         FEA_MAP(GFX_DCS),
159         FEA_MAP(RM),
160         FEA_MAP(LED_DISPLAY),
161         FEA_MAP(GFX_SS),
162         FEA_MAP(OUT_OF_BAND_MONITOR),
163         FEA_MAP(TEMP_DEPENDENT_VMIN),
164         FEA_MAP(MMHUB_PG),
165         FEA_MAP(ATHUB_PG),
166         FEA_MAP(APCC_DFLL),
167 };
168
169 static struct smu_11_0_cmn2aisc_mapping sienna_cichlid_table_map[SMU_TABLE_COUNT] = {
170         TAB_MAP(PPTABLE),
171         TAB_MAP(WATERMARKS),
172         TAB_MAP(AVFS_PSM_DEBUG),
173         TAB_MAP(AVFS_FUSE_OVERRIDE),
174         TAB_MAP(PMSTATUSLOG),
175         TAB_MAP(SMU_METRICS),
176         TAB_MAP(DRIVER_SMU_CONFIG),
177         TAB_MAP(ACTIVITY_MONITOR_COEFF),
178         TAB_MAP(OVERDRIVE),
179         TAB_MAP(I2C_COMMANDS),
180         TAB_MAP(PACE),
181 };
182
183 static struct smu_11_0_cmn2aisc_mapping sienna_cichlid_pwr_src_map[SMU_POWER_SOURCE_COUNT] = {
184         PWR_MAP(AC),
185         PWR_MAP(DC),
186 };
187
188 static struct smu_11_0_cmn2aisc_mapping sienna_cichlid_workload_map[PP_SMC_POWER_PROFILE_COUNT] = {
189         WORKLOAD_MAP(PP_SMC_POWER_PROFILE_BOOTUP_DEFAULT,       WORKLOAD_PPLIB_DEFAULT_BIT),
190         WORKLOAD_MAP(PP_SMC_POWER_PROFILE_FULLSCREEN3D,         WORKLOAD_PPLIB_FULL_SCREEN_3D_BIT),
191         WORKLOAD_MAP(PP_SMC_POWER_PROFILE_POWERSAVING,          WORKLOAD_PPLIB_POWER_SAVING_BIT),
192         WORKLOAD_MAP(PP_SMC_POWER_PROFILE_VIDEO,                WORKLOAD_PPLIB_VIDEO_BIT),
193         WORKLOAD_MAP(PP_SMC_POWER_PROFILE_VR,                   WORKLOAD_PPLIB_VR_BIT),
194         WORKLOAD_MAP(PP_SMC_POWER_PROFILE_COMPUTE,              WORKLOAD_PPLIB_CUSTOM_BIT),
195         WORKLOAD_MAP(PP_SMC_POWER_PROFILE_CUSTOM,               WORKLOAD_PPLIB_CUSTOM_BIT),
196 };
197
198 static int sienna_cichlid_get_smu_msg_index(struct smu_context *smc, uint32_t index)
199 {
200         struct smu_11_0_cmn2aisc_mapping mapping;
201
202         if (index >= SMU_MSG_MAX_COUNT)
203                 return -EINVAL;
204
205         mapping = sienna_cichlid_message_map[index];
206         if (!(mapping.valid_mapping)) {
207                 return -EINVAL;
208         }
209
210         return mapping.map_to;
211 }
212
213 static int sienna_cichlid_get_smu_clk_index(struct smu_context *smc, uint32_t index)
214 {
215         struct smu_11_0_cmn2aisc_mapping mapping;
216
217         if (index >= SMU_CLK_COUNT)
218                 return -EINVAL;
219
220         mapping = sienna_cichlid_clk_map[index];
221         if (!(mapping.valid_mapping)) {
222                 return -EINVAL;
223         }
224
225         return mapping.map_to;
226 }
227
228 static int sienna_cichlid_get_smu_feature_index(struct smu_context *smc, uint32_t index)
229 {
230         struct smu_11_0_cmn2aisc_mapping mapping;
231
232         if (index >= SMU_FEATURE_COUNT)
233                 return -EINVAL;
234
235         mapping = sienna_cichlid_feature_mask_map[index];
236         if (!(mapping.valid_mapping)) {
237                 return -EINVAL;
238         }
239
240         return mapping.map_to;
241 }
242
243 static int sienna_cichlid_get_smu_table_index(struct smu_context *smc, uint32_t index)
244 {
245         struct smu_11_0_cmn2aisc_mapping mapping;
246
247         if (index >= SMU_TABLE_COUNT)
248                 return -EINVAL;
249
250         mapping = sienna_cichlid_table_map[index];
251         if (!(mapping.valid_mapping)) {
252                 return -EINVAL;
253         }
254
255         return mapping.map_to;
256 }
257
258 static int sienna_cichlid_get_pwr_src_index(struct smu_context *smc, uint32_t index)
259 {
260         struct smu_11_0_cmn2aisc_mapping mapping;
261
262         if (index >= SMU_POWER_SOURCE_COUNT)
263                 return -EINVAL;
264
265         mapping = sienna_cichlid_pwr_src_map[index];
266         if (!(mapping.valid_mapping)) {
267                 return -EINVAL;
268         }
269
270         return mapping.map_to;
271 }
272
273 static int sienna_cichlid_get_workload_type(struct smu_context *smu, enum PP_SMC_POWER_PROFILE profile)
274 {
275         struct smu_11_0_cmn2aisc_mapping mapping;
276
277         if (profile > PP_SMC_POWER_PROFILE_CUSTOM)
278                 return -EINVAL;
279
280         mapping = sienna_cichlid_workload_map[profile];
281         if (!(mapping.valid_mapping)) {
282                 return -EINVAL;
283         }
284
285         return mapping.map_to;
286 }
287
288 static int
289 sienna_cichlid_get_allowed_feature_mask(struct smu_context *smu,
290                                   uint32_t *feature_mask, uint32_t num)
291 {
292         struct amdgpu_device *adev = smu->adev;
293
294         if (num > 2)
295                 return -EINVAL;
296
297         memset(feature_mask, 0, sizeof(uint32_t) * num);
298
299         *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DPM_PREFETCHER_BIT)
300                                 | FEATURE_MASK(FEATURE_DPM_FCLK_BIT)
301                                 | FEATURE_MASK(FEATURE_DS_SOCCLK_BIT)
302                                 | FEATURE_MASK(FEATURE_DS_DCEFCLK_BIT)
303                                 | FEATURE_MASK(FEATURE_DS_FCLK_BIT)
304                                 | FEATURE_MASK(FEATURE_DS_UCLK_BIT)
305                                 | FEATURE_MASK(FEATURE_FW_DSTATE_BIT)
306                                 | FEATURE_MASK(FEATURE_DF_CSTATE_BIT)
307                                 | FEATURE_MASK(FEATURE_RSMU_SMN_CG_BIT)
308                                 | FEATURE_MASK(FEATURE_GFX_SS_BIT)
309                                 | FEATURE_MASK(FEATURE_VR0HOT_BIT)
310                                 | FEATURE_MASK(FEATURE_PPT_BIT)
311                                 | FEATURE_MASK(FEATURE_TDC_BIT)
312                                 | FEATURE_MASK(FEATURE_BACO_BIT)
313                                 | FEATURE_MASK(FEATURE_APCC_DFLL_BIT)
314                                 | FEATURE_MASK(FEATURE_FW_CTF_BIT)
315                                 | FEATURE_MASK(FEATURE_FAN_CONTROL_BIT)
316                                 | FEATURE_MASK(FEATURE_THERMAL_BIT)
317                                 | FEATURE_MASK(FEATURE_OUT_OF_BAND_MONITOR_BIT);
318
319         if (adev->pm.pp_feature & PP_SCLK_DPM_MASK) {
320                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DPM_GFXCLK_BIT);
321                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DPM_GFX_GPO_BIT);
322         }
323
324         if (adev->pm.pp_feature & PP_MCLK_DPM_MASK)
325                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DPM_UCLK_BIT)
326                                         | FEATURE_MASK(FEATURE_MEM_VDDCI_SCALING_BIT)
327                                         | FEATURE_MASK(FEATURE_MEM_MVDD_SCALING_BIT);
328
329         if (adev->pm.pp_feature & PP_PCIE_DPM_MASK)
330                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DPM_LINK_BIT);
331
332         if (adev->pm.pp_feature & PP_DCEFCLK_DPM_MASK)
333                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DPM_DCEFCLK_BIT);
334
335         if (adev->pm.pp_feature & PP_SOCCLK_DPM_MASK)
336                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DPM_SOCCLK_BIT);
337
338         if (adev->pm.pp_feature & PP_ULV_MASK)
339                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_GFX_ULV_BIT);
340
341         if (adev->pm.pp_feature & PP_SCLK_DEEP_SLEEP_MASK)
342                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_DS_GFXCLK_BIT);
343
344         if (adev->pm.pp_feature & PP_GFXOFF_MASK)
345                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_GFXOFF_BIT);
346
347         if (smu->adev->pg_flags & AMD_PG_SUPPORT_ATHUB)
348                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_ATHUB_PG_BIT);
349
350         if (smu->adev->pg_flags & AMD_PG_SUPPORT_MMHUB)
351                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_MMHUB_PG_BIT);
352
353         if (smu->adev->pg_flags & AMD_PG_SUPPORT_VCN ||
354             smu->adev->pg_flags & AMD_PG_SUPPORT_JPEG)
355                 *(uint64_t *)feature_mask |= FEATURE_MASK(FEATURE_MM_DPM_PG_BIT);
356
357         return 0;
358 }
359
360 static int sienna_cichlid_check_powerplay_table(struct smu_context *smu)
361 {
362         return 0;
363 }
364
365 static int sienna_cichlid_append_powerplay_table(struct smu_context *smu)
366 {
367         struct smu_table_context *table_context = &smu->smu_table;
368         PPTable_t *smc_pptable = table_context->driver_pptable;
369         struct atom_smc_dpm_info_v4_9 *smc_dpm_table;
370         int index, ret;
371         int i;
372
373         index = get_index_into_master_table(atom_master_list_of_data_tables_v2_1,
374                                             smc_dpm_info);
375
376         ret = smu_get_atom_data_table(smu, index, NULL, NULL, NULL,
377                                       (uint8_t **)&smc_dpm_table);
378         if (ret)
379                 return ret;
380
381         memcpy(smc_pptable->I2cControllers, smc_dpm_table->I2cControllers,
382                sizeof(I2cControllerConfig_t) * NUM_I2C_CONTROLLERS);
383
384         /* SVI2 Board Parameters */
385         smc_pptable->VddGfxVrMapping = smc_dpm_table->VddGfxVrMapping;
386         smc_pptable->VddSocVrMapping = smc_dpm_table->VddSocVrMapping;
387         smc_pptable->VddMem0VrMapping = smc_dpm_table->VddMem0VrMapping;
388         smc_pptable->VddMem1VrMapping = smc_dpm_table->VddMem1VrMapping;
389         smc_pptable->GfxUlvPhaseSheddingMask = smc_dpm_table->GfxUlvPhaseSheddingMask;
390         smc_pptable->SocUlvPhaseSheddingMask = smc_dpm_table->SocUlvPhaseSheddingMask;
391         smc_pptable->VddciUlvPhaseSheddingMask = smc_dpm_table->VddciUlvPhaseSheddingMask;
392         smc_pptable->MvddUlvPhaseSheddingMask = smc_dpm_table->MvddUlvPhaseSheddingMask;
393
394         /* Telemetry Settings */
395         smc_pptable->GfxMaxCurrent = smc_dpm_table->GfxMaxCurrent;
396         smc_pptable->GfxOffset = smc_dpm_table->GfxOffset;
397         smc_pptable->Padding_TelemetryGfx = smc_dpm_table->Padding_TelemetryGfx;
398         smc_pptable->SocMaxCurrent = smc_dpm_table->SocMaxCurrent;
399         smc_pptable->SocOffset = smc_dpm_table->SocOffset;
400         smc_pptable->Padding_TelemetrySoc = smc_dpm_table->Padding_TelemetrySoc;
401         smc_pptable->Mem0MaxCurrent = smc_dpm_table->Mem0MaxCurrent;
402         smc_pptable->Mem0Offset = smc_dpm_table->Mem0Offset;
403         smc_pptable->Padding_TelemetryMem0 = smc_dpm_table->Padding_TelemetryMem0;
404         smc_pptable->Mem1MaxCurrent = smc_dpm_table->Mem1MaxCurrent;
405         smc_pptable->Mem1Offset = smc_dpm_table->Mem1Offset;
406         smc_pptable->Padding_TelemetryMem1 = smc_dpm_table->Padding_TelemetryMem1;
407         smc_pptable->MvddRatio = smc_dpm_table->MvddRatio;
408
409         /* GPIO Settings */
410         smc_pptable->AcDcGpio = smc_dpm_table->AcDcGpio;
411         smc_pptable->AcDcPolarity = smc_dpm_table->AcDcPolarity;
412         smc_pptable->VR0HotGpio = smc_dpm_table->VR0HotGpio;
413         smc_pptable->VR0HotPolarity = smc_dpm_table->VR0HotPolarity;
414         smc_pptable->VR1HotGpio = smc_dpm_table->VR1HotGpio;
415         smc_pptable->VR1HotPolarity = smc_dpm_table->VR1HotPolarity;
416         smc_pptable->GthrGpio = smc_dpm_table->GthrGpio;
417         smc_pptable->GthrPolarity = smc_dpm_table->GthrPolarity;
418
419         /* LED Display Settings */
420         smc_pptable->LedPin0 = smc_dpm_table->LedPin0;
421         smc_pptable->LedPin1 = smc_dpm_table->LedPin1;
422         smc_pptable->LedPin2 = smc_dpm_table->LedPin2;
423         smc_pptable->LedEnableMask = smc_dpm_table->LedEnableMask;
424         smc_pptable->LedPcie = smc_dpm_table->LedPcie;
425         smc_pptable->LedError = smc_dpm_table->LedError;
426         smc_pptable->LedSpare1[0] = smc_dpm_table->LedSpare1[0];
427         smc_pptable->LedSpare1[1] = smc_dpm_table->LedSpare1[1];
428
429         /* GFXCLK PLL Spread Spectrum */
430         smc_pptable->PllGfxclkSpreadEnabled = smc_dpm_table->PllGfxclkSpreadEnabled;
431         smc_pptable->PllGfxclkSpreadPercent = smc_dpm_table->PllGfxclkSpreadPercent;
432         smc_pptable->PllGfxclkSpreadFreq = smc_dpm_table->PllGfxclkSpreadFreq;
433
434         /* GFXCLK DFLL Spread Spectrum */
435         smc_pptable->DfllGfxclkSpreadEnabled = smc_dpm_table->DfllGfxclkSpreadEnabled;
436         smc_pptable->DfllGfxclkSpreadPercent = smc_dpm_table->DfllGfxclkSpreadPercent;
437         smc_pptable->DfllGfxclkSpreadFreq = smc_dpm_table->DfllGfxclkSpreadFreq;
438
439         /* UCLK Spread Spectrum */
440         smc_pptable->UclkSpreadEnabled = smc_dpm_table->UclkSpreadEnabled;
441         smc_pptable->UclkSpreadPercent = smc_dpm_table->UclkSpreadPercent;
442         smc_pptable->UclkSpreadFreq = smc_dpm_table->UclkSpreadFreq;
443
444         /* FCLK Spred Spectrum */
445         smc_pptable->FclkSpreadEnabled = smc_dpm_table->FclkSpreadEnabled;
446         smc_pptable->FclkSpreadPercent = smc_dpm_table->FclkSpreadPercent;
447         smc_pptable->FclkSpreadFreq = smc_dpm_table->FclkSpreadFreq;
448
449         /* Memory Config */
450         smc_pptable->MemoryChannelEnabled = smc_dpm_table->MemoryChannelEnabled;
451         smc_pptable->DramBitWidth = smc_dpm_table->DramBitWidth;
452         smc_pptable->PaddingMem1[0] = smc_dpm_table->PaddingMem1[0];
453         smc_pptable->PaddingMem1[1] = smc_dpm_table->PaddingMem1[1];
454         smc_pptable->PaddingMem1[2] = smc_dpm_table->PaddingMem1[2];
455
456         /* Total board power */
457         smc_pptable->TotalBoardPower = smc_dpm_table->TotalBoardPower;
458         smc_pptable->BoardPowerPadding = smc_dpm_table->BoardPowerPadding;
459
460         /* XGMI Training */
461         for (i = 0; i < NUM_XGMI_PSTATE_LEVELS; i++) {
462                 smc_pptable->XgmiLinkSpeed[i] = smc_dpm_table->XgmiLinkSpeed[i];
463                 smc_pptable->XgmiLinkWidth[i] = smc_dpm_table->XgmiLinkWidth[i];
464                 smc_pptable->XgmiFclkFreq[i] = smc_dpm_table->XgmiFclkFreq[i];
465                 smc_pptable->XgmiSocVoltage[i] = smc_dpm_table->XgmiSocVoltage[i];
466         }
467
468         return 0;
469 }
470
471 static int sienna_cichlid_store_powerplay_table(struct smu_context *smu)
472 {
473         struct smu_11_0_powerplay_table *powerplay_table = NULL;
474         struct smu_table_context *table_context = &smu->smu_table;
475         struct smu_baco_context *smu_baco = &smu->smu_baco;
476
477         if (!table_context->power_play_table)
478                 return -EINVAL;
479
480         powerplay_table = table_context->power_play_table;
481
482         memcpy(table_context->driver_pptable, &powerplay_table->smc_pptable,
483                sizeof(PPTable_t));
484
485         table_context->thermal_controller_type = powerplay_table->thermal_controller_type;
486
487         mutex_lock(&smu_baco->mutex);
488         if (powerplay_table->platform_caps & SMU_11_0_PP_PLATFORM_CAP_BACO ||
489             powerplay_table->platform_caps & SMU_11_0_PP_PLATFORM_CAP_MACO)
490                 smu_baco->platform_support = true;
491         mutex_unlock(&smu_baco->mutex);
492
493         return 0;
494 }
495
496 static int sienna_cichlid_tables_init(struct smu_context *smu, struct smu_table *tables)
497 {
498         struct smu_table_context *smu_table = &smu->smu_table;
499
500         SMU_TABLE_INIT(tables, SMU_TABLE_PPTABLE, sizeof(PPTable_t),
501                        PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);
502         SMU_TABLE_INIT(tables, SMU_TABLE_WATERMARKS, sizeof(Watermarks_t),
503                        PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);
504         SMU_TABLE_INIT(tables, SMU_TABLE_SMU_METRICS, sizeof(SmuMetrics_t),
505                        PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);
506         SMU_TABLE_INIT(tables, SMU_TABLE_OVERDRIVE, sizeof(OverDriveTable_t),
507                        PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);
508         SMU_TABLE_INIT(tables, SMU_TABLE_PMSTATUSLOG, SMU11_TOOL_SIZE,
509                        PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);
510         SMU_TABLE_INIT(tables, SMU_TABLE_ACTIVITY_MONITOR_COEFF,
511                        sizeof(DpmActivityMonitorCoeffInt_t), PAGE_SIZE,
512                        AMDGPU_GEM_DOMAIN_VRAM);
513
514         smu_table->metrics_table = kzalloc(sizeof(SmuMetrics_t), GFP_KERNEL);
515         if (!smu_table->metrics_table)
516                 return -ENOMEM;
517         smu_table->metrics_time = 0;
518
519         return 0;
520 }
521
522 static int sienna_cichlid_get_metrics_table(struct smu_context *smu,
523                                     SmuMetrics_t *metrics_table)
524 {
525         struct smu_table_context *smu_table= &smu->smu_table;
526         int ret = 0;
527
528         mutex_lock(&smu->metrics_lock);
529         if (!smu_table->metrics_time || time_after(jiffies, smu_table->metrics_time + msecs_to_jiffies(100))) {
530                 ret = smu_update_table(smu, SMU_TABLE_SMU_METRICS, 0,
531                                 (void *)smu_table->metrics_table, false);
532                 if (ret) {
533                         pr_info("Failed to export SMU metrics table!\n");
534                         mutex_unlock(&smu->metrics_lock);
535                         return ret;
536                 }
537                 smu_table->metrics_time = jiffies;
538         }
539
540         memcpy(metrics_table, smu_table->metrics_table, sizeof(SmuMetrics_t));
541         mutex_unlock(&smu->metrics_lock);
542
543         return ret;
544 }
545
546 static int sienna_cichlid_allocate_dpm_context(struct smu_context *smu)
547 {
548         struct smu_dpm_context *smu_dpm = &smu->smu_dpm;
549
550         if (smu_dpm->dpm_context)
551                 return -EINVAL;
552
553         smu_dpm->dpm_context = kzalloc(sizeof(struct smu_11_0_dpm_context),
554                                        GFP_KERNEL);
555         if (!smu_dpm->dpm_context)
556                 return -ENOMEM;
557
558         smu_dpm->dpm_context_size = sizeof(struct smu_11_0_dpm_context);
559
560         return 0;
561 }
562
563 static int sienna_cichlid_set_default_dpm_table(struct smu_context *smu)
564 {
565         struct smu_dpm_context *smu_dpm = &smu->smu_dpm;
566         struct smu_table_context *table_context = &smu->smu_table;
567         struct smu_11_0_dpm_context *dpm_context = smu_dpm->dpm_context;
568         PPTable_t *driver_ppt = NULL;
569         int i;
570
571         driver_ppt = table_context->driver_pptable;
572
573         dpm_context->dpm_tables.soc_table.min = driver_ppt->FreqTableSocclk[0];
574         dpm_context->dpm_tables.soc_table.max = driver_ppt->FreqTableSocclk[NUM_SOCCLK_DPM_LEVELS - 1];
575
576         dpm_context->dpm_tables.gfx_table.min = driver_ppt->FreqTableGfx[0];
577         dpm_context->dpm_tables.gfx_table.max = driver_ppt->FreqTableGfx[NUM_GFXCLK_DPM_LEVELS - 1];
578
579         dpm_context->dpm_tables.uclk_table.min = driver_ppt->FreqTableUclk[0];
580         dpm_context->dpm_tables.uclk_table.max = driver_ppt->FreqTableUclk[NUM_UCLK_DPM_LEVELS - 1];
581
582         dpm_context->dpm_tables.vclk_table.min = driver_ppt->FreqTableVclk[0];
583         dpm_context->dpm_tables.vclk_table.max = driver_ppt->FreqTableVclk[NUM_VCLK_DPM_LEVELS - 1];
584
585         dpm_context->dpm_tables.dclk_table.min = driver_ppt->FreqTableDclk[0];
586         dpm_context->dpm_tables.dclk_table.max = driver_ppt->FreqTableDclk[NUM_DCLK_DPM_LEVELS - 1];
587
588         dpm_context->dpm_tables.dcef_table.min = driver_ppt->FreqTableDcefclk[0];
589         dpm_context->dpm_tables.dcef_table.max = driver_ppt->FreqTableDcefclk[NUM_DCEFCLK_DPM_LEVELS - 1];
590
591         dpm_context->dpm_tables.pixel_table.min = driver_ppt->FreqTablePixclk[0];
592         dpm_context->dpm_tables.pixel_table.max = driver_ppt->FreqTablePixclk[NUM_PIXCLK_DPM_LEVELS - 1];
593
594         dpm_context->dpm_tables.display_table.min = driver_ppt->FreqTableDispclk[0];
595         dpm_context->dpm_tables.display_table.max = driver_ppt->FreqTableDispclk[NUM_DISPCLK_DPM_LEVELS - 1];
596
597         dpm_context->dpm_tables.phy_table.min = driver_ppt->FreqTablePhyclk[0];
598         dpm_context->dpm_tables.phy_table.max = driver_ppt->FreqTablePhyclk[NUM_PHYCLK_DPM_LEVELS - 1];
599
600         for (i = 0; i < MAX_PCIE_CONF; i++) {
601                 dpm_context->dpm_tables.pcie_table.pcie_gen[i] = driver_ppt->PcieGenSpeed[i];
602                 dpm_context->dpm_tables.pcie_table.pcie_lane[i] = driver_ppt->PcieLaneCount[i];
603         }
604
605         return 0;
606 }
607
608 static int sienna_cichlid_dpm_set_uvd_enable(struct smu_context *smu, bool enable)
609 {
610         struct smu_power_context *smu_power = &smu->smu_power;
611         struct smu_power_gate *power_gate = &smu_power->power_gate;
612         int ret = 0;
613
614         if (enable) {
615                 /* vcn dpm on is a prerequisite for vcn power gate messages */
616                 if (smu_feature_is_enabled(smu, SMU_FEATURE_MM_DPM_PG_BIT)) {
617                         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_PowerUpVcn, 0, NULL);
618                         if (ret)
619                                 return ret;
620                         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_PowerUpVcn, 0x10000, NULL);
621                         if (ret)
622                                 return ret;
623                 }
624                 power_gate->vcn_gated = false;
625         } else {
626                 if (smu_feature_is_enabled(smu, SMU_FEATURE_MM_DPM_PG_BIT)) {
627                         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_PowerDownVcn, 0, NULL);
628                         if (ret)
629                                 return ret;
630                         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_PowerDownVcn, 0x10000, NULL);
631                         if (ret)
632                                 return ret;
633                 }
634                 power_gate->vcn_gated = true;
635         }
636
637         return ret;
638 }
639
640 static int sienna_cichlid_dpm_set_jpeg_enable(struct smu_context *smu, bool enable)
641 {
642         struct smu_power_context *smu_power = &smu->smu_power;
643         struct smu_power_gate *power_gate = &smu_power->power_gate;
644         int ret = 0;
645
646         if (enable) {
647                 if (smu_feature_is_enabled(smu, SMU_FEATURE_MM_DPM_PG_BIT)) {
648                         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_PowerUpJpeg, 0, NULL);
649                         if (ret)
650                                 return ret;
651                 }
652                 power_gate->jpeg_gated = false;
653         } else {
654                 if (smu_feature_is_enabled(smu, SMU_FEATURE_MM_DPM_PG_BIT)) {
655                         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_PowerDownJpeg, 0, NULL);
656                         if (ret)
657                                 return ret;
658                 }
659                 power_gate->jpeg_gated = true;
660         }
661
662         return ret;
663 }
664
665 static int sienna_cichlid_get_current_clk_freq_by_table(struct smu_context *smu,
666                                        enum smu_clk_type clk_type,
667                                        uint32_t *value)
668 {
669         int ret = 0, clk_id = 0;
670         SmuMetrics_t metrics;
671
672         ret = sienna_cichlid_get_metrics_table(smu, &metrics);
673         if (ret)
674                 return ret;
675
676         clk_id = smu_clk_get_index(smu, clk_type);
677         if (clk_id < 0)
678                 return clk_id;
679
680         *value = metrics.CurrClock[clk_id];
681
682         return ret;
683 }
684
685 static bool sienna_cichlid_is_support_fine_grained_dpm(struct smu_context *smu, enum smu_clk_type clk_type)
686 {
687         PPTable_t *pptable = smu->smu_table.driver_pptable;
688         DpmDescriptor_t *dpm_desc = NULL;
689         uint32_t clk_index = 0;
690
691         clk_index = smu_clk_get_index(smu, clk_type);
692         dpm_desc = &pptable->DpmDescriptor[clk_index];
693
694         /* 0 - Fine grained DPM, 1 - Discrete DPM */
695         return dpm_desc->SnapToDiscrete == 0 ? true : false;
696 }
697
698 static int sienna_cichlid_print_clk_levels(struct smu_context *smu,
699                         enum smu_clk_type clk_type, char *buf)
700 {
701         struct amdgpu_device *adev = smu->adev;
702         struct smu_table_context *table_context = &smu->smu_table;
703         struct smu_dpm_context *smu_dpm = &smu->smu_dpm;
704         struct smu_11_0_dpm_context *dpm_context = smu_dpm->dpm_context;
705         PPTable_t *pptable = (PPTable_t *)table_context->driver_pptable;
706         int i, size = 0, ret = 0;
707         uint32_t cur_value = 0, value = 0, count = 0;
708         uint32_t freq_values[3] = {0};
709         uint32_t mark_index = 0;
710         uint32_t gen_speed, lane_width;
711
712         if ((clk_type == SMU_GFXCLK) || (clk_type == SMU_SCLK))
713                 amdgpu_gfx_off_ctrl(adev, false);
714
715         switch (clk_type) {
716         case SMU_GFXCLK:
717         case SMU_SCLK:
718         case SMU_SOCCLK:
719         case SMU_MCLK:
720         case SMU_UCLK:
721         case SMU_FCLK:
722         case SMU_DCEFCLK:
723                 ret = smu_get_current_clk_freq(smu, clk_type, &cur_value);
724                 if (ret)
725                         goto print_clk_out;
726
727                 /* 10KHz -> MHz */
728                 cur_value = cur_value / 100;
729
730                 ret = smu_get_dpm_level_count(smu, clk_type, &count);
731                 if (ret)
732                         goto print_clk_out;
733
734                 if (!sienna_cichlid_is_support_fine_grained_dpm(smu, clk_type)) {
735                         for (i = 0; i < count; i++) {
736                                 ret = smu_get_dpm_freq_by_index(smu, clk_type, i, &value);
737                                 if (ret)
738                                         goto print_clk_out;
739
740                                 size += sprintf(buf + size, "%d: %uMhz %s\n", i, value,
741                                                 cur_value == value ? "*" : "");
742                         }
743                 } else {
744                         ret = smu_get_dpm_freq_by_index(smu, clk_type, 0, &freq_values[0]);
745                         if (ret)
746                                 goto print_clk_out;
747                         ret = smu_get_dpm_freq_by_index(smu, clk_type, count - 1, &freq_values[2]);
748                         if (ret)
749                                 goto print_clk_out;
750
751                         freq_values[1] = cur_value;
752                         mark_index = cur_value == freq_values[0] ? 0 :
753                                      cur_value == freq_values[2] ? 2 : 1;
754                         if (mark_index != 1)
755                                 freq_values[1] = (freq_values[0] + freq_values[2]) / 2;
756
757                         for (i = 0; i < 3; i++) {
758                                 size += sprintf(buf + size, "%d: %uMhz %s\n", i, freq_values[i],
759                                                 i == mark_index ? "*" : "");
760                         }
761
762                 }
763                 break;
764         case SMU_PCIE:
765                 gen_speed = (RREG32_PCIE(smnPCIE_LC_SPEED_CNTL) &
766                              PSWUSP0_PCIE_LC_SPEED_CNTL__LC_CURRENT_DATA_RATE_MASK)
767                         >> PSWUSP0_PCIE_LC_SPEED_CNTL__LC_CURRENT_DATA_RATE__SHIFT;
768                 lane_width = (RREG32_PCIE(smnPCIE_LC_LINK_WIDTH_CNTL) &
769                               PCIE_LC_LINK_WIDTH_CNTL__LC_LINK_WIDTH_RD_MASK)
770                         >> PCIE_LC_LINK_WIDTH_CNTL__LC_LINK_WIDTH_RD__SHIFT;
771                 for (i = 0; i < NUM_LINK_LEVELS; i++)
772                         size += sprintf(buf + size, "%d: %s %s %dMhz %s\n", i,
773                                         (dpm_context->dpm_tables.pcie_table.pcie_gen[i] == 0) ? "2.5GT/s," :
774                                         (dpm_context->dpm_tables.pcie_table.pcie_gen[i] == 1) ? "5.0GT/s," :
775                                         (dpm_context->dpm_tables.pcie_table.pcie_gen[i] == 2) ? "8.0GT/s," :
776                                         (dpm_context->dpm_tables.pcie_table.pcie_gen[i] == 3) ? "16.0GT/s," : "",
777                                         (dpm_context->dpm_tables.pcie_table.pcie_lane[i] == 1) ? "x1" :
778                                         (dpm_context->dpm_tables.pcie_table.pcie_lane[i] == 2) ? "x2" :
779                                         (dpm_context->dpm_tables.pcie_table.pcie_lane[i] == 3) ? "x4" :
780                                         (dpm_context->dpm_tables.pcie_table.pcie_lane[i] == 4) ? "x8" :
781                                         (dpm_context->dpm_tables.pcie_table.pcie_lane[i] == 5) ? "x12" :
782                                         (dpm_context->dpm_tables.pcie_table.pcie_lane[i] == 6) ? "x16" : "",
783                                         pptable->LclkFreq[i],
784                                         (gen_speed == dpm_context->dpm_tables.pcie_table.pcie_gen[i]) &&
785                                         (lane_width == dpm_context->dpm_tables.pcie_table.pcie_lane[i]) ?
786                                         "*" : "");
787                 break;
788         default:
789                 break;
790         }
791
792 print_clk_out:
793         if ((clk_type == SMU_GFXCLK) || (clk_type == SMU_SCLK))
794                 amdgpu_gfx_off_ctrl(adev, true);
795
796         return size;
797 }
798
799 static int sienna_cichlid_force_clk_levels(struct smu_context *smu,
800                                    enum smu_clk_type clk_type, uint32_t mask)
801 {
802         struct amdgpu_device *adev = smu->adev;
803         int ret = 0, size = 0;
804         uint32_t soft_min_level = 0, soft_max_level = 0, min_freq = 0, max_freq = 0;
805
806         soft_min_level = mask ? (ffs(mask) - 1) : 0;
807         soft_max_level = mask ? (fls(mask) - 1) : 0;
808
809         if ((clk_type == SMU_GFXCLK) || (clk_type == SMU_SCLK))
810                 amdgpu_gfx_off_ctrl(adev, false);
811
812         switch (clk_type) {
813         case SMU_GFXCLK:
814         case SMU_SCLK:
815         case SMU_SOCCLK:
816         case SMU_MCLK:
817         case SMU_UCLK:
818         case SMU_DCEFCLK:
819         case SMU_FCLK:
820                 /* There is only 2 levels for fine grained DPM */
821                 if (sienna_cichlid_is_support_fine_grained_dpm(smu, clk_type)) {
822                         soft_max_level = (soft_max_level >= 1 ? 1 : 0);
823                         soft_min_level = (soft_min_level >= 1 ? 1 : 0);
824                 }
825
826                 ret = smu_get_dpm_freq_by_index(smu, clk_type, soft_min_level, &min_freq);
827                 if (ret)
828                         goto forec_level_out;
829
830                 ret = smu_get_dpm_freq_by_index(smu, clk_type, soft_max_level, &max_freq);
831                 if (ret)
832                         goto forec_level_out;
833
834                 ret = smu_set_soft_freq_range(smu, clk_type, min_freq, max_freq, false);
835                 if (ret)
836                         goto forec_level_out;
837                 break;
838         default:
839                 break;
840         }
841
842 forec_level_out:
843         if ((clk_type == SMU_GFXCLK) || (clk_type == SMU_SCLK))
844                 amdgpu_gfx_off_ctrl(adev, true);
845
846         return size;
847 }
848
849 static int sienna_cichlid_populate_umd_state_clk(struct smu_context *smu)
850 {
851         int ret = 0;
852         uint32_t min_sclk_freq = 0, min_mclk_freq = 0;
853
854         ret = smu_get_dpm_freq_range(smu, SMU_SCLK, &min_sclk_freq, NULL, false);
855         if (ret)
856                 return ret;
857
858         smu->pstate_sclk = min_sclk_freq * 100;
859
860         ret = smu_get_dpm_freq_range(smu, SMU_MCLK, &min_mclk_freq, NULL, false);
861         if (ret)
862                 return ret;
863
864         smu->pstate_mclk = min_mclk_freq * 100;
865
866         return ret;
867 }
868
869 static int sienna_cichlid_get_clock_by_type_with_latency(struct smu_context *smu,
870                                                  enum smu_clk_type clk_type,
871                                                  struct pp_clock_levels_with_latency *clocks)
872 {
873         int ret = 0, i = 0;
874         uint32_t level_count = 0, freq = 0;
875
876         switch (clk_type) {
877         case SMU_GFXCLK:
878         case SMU_DCEFCLK:
879         case SMU_SOCCLK:
880                 ret = smu_get_dpm_level_count(smu, clk_type, &level_count);
881                 if (ret)
882                         return ret;
883
884                 level_count = min(level_count, (uint32_t)MAX_NUM_CLOCKS);
885                 clocks->num_levels = level_count;
886
887                 for (i = 0; i < level_count; i++) {
888                         ret = smu_get_dpm_freq_by_index(smu, clk_type, i, &freq);
889                         if (ret)
890                                 return ret;
891
892                         clocks->data[i].clocks_in_khz = freq * 1000;
893                         clocks->data[i].latency_in_us = 0;
894                 }
895                 break;
896         default:
897                 break;
898         }
899
900         return ret;
901 }
902
903 static int sienna_cichlid_pre_display_config_changed(struct smu_context *smu)
904 {
905         int ret = 0;
906         uint32_t max_freq = 0;
907
908         /* Sienna_Cichlid do not support to change display num currently */
909         return 0;
910 #if 0
911         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_NumOfDisplays, 0, NULL);
912         if (ret)
913                 return ret;
914 #endif
915
916         if (smu_feature_is_enabled(smu, SMU_FEATURE_DPM_UCLK_BIT)) {
917                 ret = smu_get_dpm_freq_range(smu, SMU_UCLK, NULL, &max_freq, false);
918                 if (ret)
919                         return ret;
920                 ret = smu_set_hard_freq_range(smu, SMU_UCLK, 0, max_freq);
921                 if (ret)
922                         return ret;
923         }
924
925         return ret;
926 }
927
928 static int sienna_cichlid_display_config_changed(struct smu_context *smu)
929 {
930         int ret = 0;
931
932         if ((smu->watermarks_bitmap & WATERMARKS_EXIST) &&
933             !(smu->watermarks_bitmap & WATERMARKS_LOADED)) {
934                 ret = smu_write_watermarks_table(smu);
935                 if (ret)
936                         return ret;
937
938                 smu->watermarks_bitmap |= WATERMARKS_LOADED;
939         }
940
941         if ((smu->watermarks_bitmap & WATERMARKS_EXIST) &&
942             smu_feature_is_supported(smu, SMU_FEATURE_DPM_DCEFCLK_BIT) &&
943             smu_feature_is_supported(smu, SMU_FEATURE_DPM_SOCCLK_BIT)) {
944                 /* Sienna_Cichlid do not support to change display num currently */
945                 ret = 0;
946 #if 0
947                 ret = smu_send_smc_msg_with_param(smu, SMU_MSG_NumOfDisplays,
948                                                   smu->display_config->num_display, NULL);
949 #endif
950                 if (ret)
951                         return ret;
952         }
953
954         return ret;
955 }
956
957 static int sienna_cichlid_force_dpm_limit_value(struct smu_context *smu, bool highest)
958 {
959         int ret = 0, i = 0;
960         uint32_t min_freq, max_freq, force_freq;
961         enum smu_clk_type clk_type;
962
963         enum smu_clk_type clks[] = {
964                 SMU_GFXCLK,
965                 SMU_MCLK,
966                 SMU_SOCCLK,
967         };
968
969         for (i = 0; i < ARRAY_SIZE(clks); i++) {
970                 clk_type = clks[i];
971                 ret = smu_get_dpm_freq_range(smu, clk_type, &min_freq, &max_freq, false);
972                 if (ret)
973                         return ret;
974
975                 force_freq = highest ? max_freq : min_freq;
976                 ret = smu_set_soft_freq_range(smu, clk_type, force_freq, force_freq, false);
977                 if (ret)
978                         return ret;
979         }
980
981         return ret;
982 }
983
984 static int sienna_cichlid_unforce_dpm_levels(struct smu_context *smu)
985 {
986         int ret = 0, i = 0;
987         uint32_t min_freq, max_freq;
988         enum smu_clk_type clk_type;
989
990         enum smu_clk_type clks[] = {
991                 SMU_GFXCLK,
992                 SMU_MCLK,
993                 SMU_SOCCLK,
994         };
995
996         for (i = 0; i < ARRAY_SIZE(clks); i++) {
997                 clk_type = clks[i];
998                 ret = smu_get_dpm_freq_range(smu, clk_type, &min_freq, &max_freq, false);
999                 if (ret)
1000                         return ret;
1001
1002                 ret = smu_set_soft_freq_range(smu, clk_type, min_freq, max_freq, false);
1003                 if (ret)
1004                         return ret;
1005         }
1006
1007         return ret;
1008 }
1009
1010 static int sienna_cichlid_get_gpu_power(struct smu_context *smu, uint32_t *value)
1011 {
1012         int ret = 0;
1013         SmuMetrics_t metrics;
1014
1015         if (!value)
1016                 return -EINVAL;
1017
1018         ret = sienna_cichlid_get_metrics_table(smu, &metrics);
1019         if (ret)
1020                 return ret;
1021
1022         *value = metrics.AverageSocketPower << 8;
1023
1024         return 0;
1025 }
1026
1027 static int sienna_cichlid_get_current_activity_percent(struct smu_context *smu,
1028                                                enum amd_pp_sensors sensor,
1029                                                uint32_t *value)
1030 {
1031         int ret = 0;
1032         SmuMetrics_t metrics;
1033
1034         if (!value)
1035                 return -EINVAL;
1036
1037         ret = sienna_cichlid_get_metrics_table(smu, &metrics);
1038         if (ret)
1039                 return ret;
1040
1041         switch (sensor) {
1042         case AMDGPU_PP_SENSOR_GPU_LOAD:
1043                 *value = metrics.AverageGfxActivity;
1044                 break;
1045         case AMDGPU_PP_SENSOR_MEM_LOAD:
1046                 *value = metrics.AverageUclkActivity;
1047                 break;
1048         default:
1049                 pr_err("Invalid sensor for retrieving clock activity\n");
1050                 return -EINVAL;
1051         }
1052
1053         return 0;
1054 }
1055
1056 static bool sienna_cichlid_is_dpm_running(struct smu_context *smu)
1057 {
1058         int ret = 0;
1059         uint32_t feature_mask[2];
1060         unsigned long feature_enabled;
1061         ret = smu_feature_get_enabled_mask(smu, feature_mask, 2);
1062         feature_enabled = (unsigned long)((uint64_t)feature_mask[0] |
1063                            ((uint64_t)feature_mask[1] << 32));
1064         return !!(feature_enabled & SMC_DPM_FEATURE);
1065 }
1066
1067 static int sienna_cichlid_get_fan_speed_rpm(struct smu_context *smu,
1068                                     uint32_t *speed)
1069 {
1070         SmuMetrics_t metrics;
1071         int ret = 0;
1072
1073         if (!speed)
1074                 return -EINVAL;
1075
1076         ret = sienna_cichlid_get_metrics_table(smu, &metrics);
1077         if (ret)
1078                 return ret;
1079
1080         *speed = metrics.CurrFanSpeed;
1081
1082         return ret;
1083 }
1084
1085 static int sienna_cichlid_get_fan_speed_percent(struct smu_context *smu,
1086                                         uint32_t *speed)
1087 {
1088         int ret = 0;
1089         uint32_t percent = 0;
1090         uint32_t current_rpm;
1091         PPTable_t *pptable = smu->smu_table.driver_pptable;
1092
1093         ret = sienna_cichlid_get_fan_speed_rpm(smu, &current_rpm);
1094         if (ret)
1095                 return ret;
1096
1097         percent = current_rpm * 100 / pptable->FanMaximumRpm;
1098         *speed = percent > 100 ? 100 : percent;
1099
1100         return ret;
1101 }
1102
1103 static int sienna_cichlid_get_power_profile_mode(struct smu_context *smu, char *buf)
1104 {
1105         DpmActivityMonitorCoeffInt_t activity_monitor;
1106         uint32_t i, size = 0;
1107         int16_t workload_type = 0;
1108         static const char *profile_name[] = {
1109                                         "BOOTUP_DEFAULT",
1110                                         "3D_FULL_SCREEN",
1111                                         "POWER_SAVING",
1112                                         "VIDEO",
1113                                         "VR",
1114                                         "COMPUTE",
1115                                         "CUSTOM"};
1116         static const char *title[] = {
1117                         "PROFILE_INDEX(NAME)",
1118                         "CLOCK_TYPE(NAME)",
1119                         "FPS",
1120                         "MinFreqType",
1121                         "MinActiveFreqType",
1122                         "MinActiveFreq",
1123                         "BoosterFreqType",
1124                         "BoosterFreq",
1125                         "PD_Data_limit_c",
1126                         "PD_Data_error_coeff",
1127                         "PD_Data_error_rate_coeff"};
1128         int result = 0;
1129
1130         if (!buf)
1131                 return -EINVAL;
1132
1133         size += sprintf(buf + size, "%16s %s %s %s %s %s %s %s %s %s %s\n",
1134                         title[0], title[1], title[2], title[3], title[4], title[5],
1135                         title[6], title[7], title[8], title[9], title[10]);
1136
1137         for (i = 0; i <= PP_SMC_POWER_PROFILE_CUSTOM; i++) {
1138                 /* conv PP_SMC_POWER_PROFILE* to WORKLOAD_PPLIB_*_BIT */
1139                 workload_type = smu_workload_get_type(smu, i);
1140                 if (workload_type < 0)
1141                         return -EINVAL;
1142
1143                 result = smu_update_table(smu,
1144                                           SMU_TABLE_ACTIVITY_MONITOR_COEFF, workload_type,
1145                                           (void *)(&activity_monitor), false);
1146                 if (result) {
1147                         pr_err("[%s] Failed to get activity monitor!", __func__);
1148                         return result;
1149                 }
1150
1151                 size += sprintf(buf + size, "%2d %14s%s:\n",
1152                         i, profile_name[i], (i == smu->power_profile_mode) ? "*" : " ");
1153
1154                 size += sprintf(buf + size, "%19s %d(%13s) %7d %7d %7d %7d %7d %7d %7d %7d %7d\n",
1155                         " ",
1156                         0,
1157                         "GFXCLK",
1158                         activity_monitor.Gfx_FPS,
1159                         activity_monitor.Gfx_MinFreqStep,
1160                         activity_monitor.Gfx_MinActiveFreqType,
1161                         activity_monitor.Gfx_MinActiveFreq,
1162                         activity_monitor.Gfx_BoosterFreqType,
1163                         activity_monitor.Gfx_BoosterFreq,
1164                         activity_monitor.Gfx_PD_Data_limit_c,
1165                         activity_monitor.Gfx_PD_Data_error_coeff,
1166                         activity_monitor.Gfx_PD_Data_error_rate_coeff);
1167
1168                 size += sprintf(buf + size, "%19s %d(%13s) %7d %7d %7d %7d %7d %7d %7d %7d %7d\n",
1169                         " ",
1170                         1,
1171                         "SOCCLK",
1172                         activity_monitor.Fclk_FPS,
1173                         activity_monitor.Fclk_MinFreqStep,
1174                         activity_monitor.Fclk_MinActiveFreqType,
1175                         activity_monitor.Fclk_MinActiveFreq,
1176                         activity_monitor.Fclk_BoosterFreqType,
1177                         activity_monitor.Fclk_BoosterFreq,
1178                         activity_monitor.Fclk_PD_Data_limit_c,
1179                         activity_monitor.Fclk_PD_Data_error_coeff,
1180                         activity_monitor.Fclk_PD_Data_error_rate_coeff);
1181
1182                 size += sprintf(buf + size, "%19s %d(%13s) %7d %7d %7d %7d %7d %7d %7d %7d %7d\n",
1183                         " ",
1184                         2,
1185                         "MEMLK",
1186                         activity_monitor.Mem_FPS,
1187                         activity_monitor.Mem_MinFreqStep,
1188                         activity_monitor.Mem_MinActiveFreqType,
1189                         activity_monitor.Mem_MinActiveFreq,
1190                         activity_monitor.Mem_BoosterFreqType,
1191                         activity_monitor.Mem_BoosterFreq,
1192                         activity_monitor.Mem_PD_Data_limit_c,
1193                         activity_monitor.Mem_PD_Data_error_coeff,
1194                         activity_monitor.Mem_PD_Data_error_rate_coeff);
1195         }
1196
1197         return size;
1198 }
1199
1200 static int sienna_cichlid_set_power_profile_mode(struct smu_context *smu, long *input, uint32_t size)
1201 {
1202         DpmActivityMonitorCoeffInt_t activity_monitor;
1203         int workload_type, ret = 0;
1204
1205         smu->power_profile_mode = input[size];
1206
1207         if (smu->power_profile_mode > PP_SMC_POWER_PROFILE_CUSTOM) {
1208                 pr_err("Invalid power profile mode %d\n", smu->power_profile_mode);
1209                 return -EINVAL;
1210         }
1211
1212         if (smu->power_profile_mode == PP_SMC_POWER_PROFILE_CUSTOM) {
1213                 if (size < 0)
1214                         return -EINVAL;
1215
1216                 ret = smu_update_table(smu,
1217                                        SMU_TABLE_ACTIVITY_MONITOR_COEFF, WORKLOAD_PPLIB_CUSTOM_BIT,
1218                                        (void *)(&activity_monitor), false);
1219                 if (ret) {
1220                         pr_err("[%s] Failed to get activity monitor!", __func__);
1221                         return ret;
1222                 }
1223
1224                 switch (input[0]) {
1225                 case 0: /* Gfxclk */
1226                         activity_monitor.Gfx_FPS = input[1];
1227                         activity_monitor.Gfx_MinFreqStep = input[2];
1228                         activity_monitor.Gfx_MinActiveFreqType = input[3];
1229                         activity_monitor.Gfx_MinActiveFreq = input[4];
1230                         activity_monitor.Gfx_BoosterFreqType = input[5];
1231                         activity_monitor.Gfx_BoosterFreq = input[6];
1232                         activity_monitor.Gfx_PD_Data_limit_c = input[7];
1233                         activity_monitor.Gfx_PD_Data_error_coeff = input[8];
1234                         activity_monitor.Gfx_PD_Data_error_rate_coeff = input[9];
1235                         break;
1236                 case 1: /* Socclk */
1237                         activity_monitor.Fclk_FPS = input[1];
1238                         activity_monitor.Fclk_MinFreqStep = input[2];
1239                         activity_monitor.Fclk_MinActiveFreqType = input[3];
1240                         activity_monitor.Fclk_MinActiveFreq = input[4];
1241                         activity_monitor.Fclk_BoosterFreqType = input[5];
1242                         activity_monitor.Fclk_BoosterFreq = input[6];
1243                         activity_monitor.Fclk_PD_Data_limit_c = input[7];
1244                         activity_monitor.Fclk_PD_Data_error_coeff = input[8];
1245                         activity_monitor.Fclk_PD_Data_error_rate_coeff = input[9];
1246                         break;
1247                 case 2: /* Memlk */
1248                         activity_monitor.Mem_FPS = input[1];
1249                         activity_monitor.Mem_MinFreqStep = input[2];
1250                         activity_monitor.Mem_MinActiveFreqType = input[3];
1251                         activity_monitor.Mem_MinActiveFreq = input[4];
1252                         activity_monitor.Mem_BoosterFreqType = input[5];
1253                         activity_monitor.Mem_BoosterFreq = input[6];
1254                         activity_monitor.Mem_PD_Data_limit_c = input[7];
1255                         activity_monitor.Mem_PD_Data_error_coeff = input[8];
1256                         activity_monitor.Mem_PD_Data_error_rate_coeff = input[9];
1257                         break;
1258                 }
1259
1260                 ret = smu_update_table(smu,
1261                                        SMU_TABLE_ACTIVITY_MONITOR_COEFF, WORKLOAD_PPLIB_CUSTOM_BIT,
1262                                        (void *)(&activity_monitor), true);
1263                 if (ret) {
1264                         pr_err("[%s] Failed to set activity monitor!", __func__);
1265                         return ret;
1266                 }
1267         }
1268
1269         /* conv PP_SMC_POWER_PROFILE* to WORKLOAD_PPLIB_*_BIT */
1270         workload_type = smu_workload_get_type(smu, smu->power_profile_mode);
1271         if (workload_type < 0)
1272                 return -EINVAL;
1273         smu_send_smc_msg_with_param(smu, SMU_MSG_SetWorkloadMask,
1274                                     1 << workload_type, NULL);
1275
1276         return ret;
1277 }
1278
1279 static int sienna_cichlid_get_profiling_clk_mask(struct smu_context *smu,
1280                                          enum amd_dpm_forced_level level,
1281                                          uint32_t *sclk_mask,
1282                                          uint32_t *mclk_mask,
1283                                          uint32_t *soc_mask)
1284 {
1285         struct amdgpu_device *adev = smu->adev;
1286         int ret = 0;
1287         uint32_t level_count = 0;
1288
1289         if (level == AMD_DPM_FORCED_LEVEL_PROFILE_MIN_SCLK) {
1290                 if (sclk_mask)
1291                         *sclk_mask = 0;
1292         } else if (level == AMD_DPM_FORCED_LEVEL_PROFILE_MIN_MCLK) {
1293                 if (mclk_mask)
1294                         *mclk_mask = 0;
1295         } else if (level == AMD_DPM_FORCED_LEVEL_PROFILE_PEAK) {
1296                 if(sclk_mask) {
1297                         amdgpu_gfx_off_ctrl(adev, false);
1298                         ret = smu_get_dpm_level_count(smu, SMU_SCLK, &level_count);
1299                         amdgpu_gfx_off_ctrl(adev, true);
1300                         if (ret)
1301                                 return ret;
1302                         *sclk_mask = level_count - 1;
1303                 }
1304
1305                 if(mclk_mask) {
1306                         ret = smu_get_dpm_level_count(smu, SMU_MCLK, &level_count);
1307                         if (ret)
1308                                 return ret;
1309                         *mclk_mask = level_count - 1;
1310                 }
1311
1312                 if(soc_mask) {
1313                         ret = smu_get_dpm_level_count(smu, SMU_SOCCLK, &level_count);
1314                         if (ret)
1315                                 return ret;
1316                         *soc_mask = level_count - 1;
1317                 }
1318         }
1319
1320         return ret;
1321 }
1322
1323 static int sienna_cichlid_notify_smc_display_config(struct smu_context *smu)
1324 {
1325         struct smu_clocks min_clocks = {0};
1326         struct pp_display_clock_request clock_req;
1327         int ret = 0;
1328
1329         min_clocks.dcef_clock = smu->display_config->min_dcef_set_clk;
1330         min_clocks.dcef_clock_in_sr = smu->display_config->min_dcef_deep_sleep_set_clk;
1331         min_clocks.memory_clock = smu->display_config->min_mem_set_clock;
1332
1333         if (smu_feature_is_supported(smu, SMU_FEATURE_DPM_DCEFCLK_BIT)) {
1334                 clock_req.clock_type = amd_pp_dcef_clock;
1335                 clock_req.clock_freq_in_khz = min_clocks.dcef_clock * 10;
1336
1337                 ret = smu_v11_0_display_clock_voltage_request(smu, &clock_req);
1338                 if (!ret) {
1339                         if (smu_feature_is_supported(smu, SMU_FEATURE_DS_DCEFCLK_BIT)) {
1340                                 pr_err("Attempt to set divider for DCEFCLK Failed as it not support currently!");
1341                                 return ret;
1342                         }
1343                 } else {
1344                         pr_info("Attempt to set Hard Min for DCEFCLK Failed!");
1345                 }
1346         }
1347
1348         if (smu_feature_is_enabled(smu, SMU_FEATURE_DPM_UCLK_BIT)) {
1349                 ret = smu_set_hard_freq_range(smu, SMU_UCLK, min_clocks.memory_clock/100, 0);
1350                 if (ret) {
1351                         pr_err("[%s] Set hard min uclk failed!", __func__);
1352                         return ret;
1353                 }
1354         }
1355
1356         return 0;
1357 }
1358
1359 static int sienna_cichlid_set_watermarks_table(struct smu_context *smu,
1360                                        void *watermarks, struct
1361                                        dm_pp_wm_sets_with_clock_ranges_soc15
1362                                        *clock_ranges)
1363 {
1364         int i;
1365         Watermarks_t *table = watermarks;
1366
1367         if (!table || !clock_ranges)
1368                 return -EINVAL;
1369
1370         if (clock_ranges->num_wm_dmif_sets > 4 ||
1371             clock_ranges->num_wm_mcif_sets > 4)
1372                 return -EINVAL;
1373
1374         for (i = 0; i < clock_ranges->num_wm_dmif_sets; i++) {
1375                 table->WatermarkRow[1][i].MinClock =
1376                         cpu_to_le16((uint16_t)
1377                         (clock_ranges->wm_dmif_clocks_ranges[i].wm_min_dcfclk_clk_in_khz /
1378                         1000));
1379                 table->WatermarkRow[1][i].MaxClock =
1380                         cpu_to_le16((uint16_t)
1381                         (clock_ranges->wm_dmif_clocks_ranges[i].wm_max_dcfclk_clk_in_khz /
1382                         1000));
1383                 table->WatermarkRow[1][i].MinUclk =
1384                         cpu_to_le16((uint16_t)
1385                         (clock_ranges->wm_dmif_clocks_ranges[i].wm_min_mem_clk_in_khz /
1386                         1000));
1387                 table->WatermarkRow[1][i].MaxUclk =
1388                         cpu_to_le16((uint16_t)
1389                         (clock_ranges->wm_dmif_clocks_ranges[i].wm_max_mem_clk_in_khz /
1390                         1000));
1391                 table->WatermarkRow[1][i].WmSetting = (uint8_t)
1392                                 clock_ranges->wm_dmif_clocks_ranges[i].wm_set_id;
1393         }
1394
1395         for (i = 0; i < clock_ranges->num_wm_mcif_sets; i++) {
1396                 table->WatermarkRow[0][i].MinClock =
1397                         cpu_to_le16((uint16_t)
1398                         (clock_ranges->wm_mcif_clocks_ranges[i].wm_min_socclk_clk_in_khz /
1399                         1000));
1400                 table->WatermarkRow[0][i].MaxClock =
1401                         cpu_to_le16((uint16_t)
1402                         (clock_ranges->wm_mcif_clocks_ranges[i].wm_max_socclk_clk_in_khz /
1403                         1000));
1404                 table->WatermarkRow[0][i].MinUclk =
1405                         cpu_to_le16((uint16_t)
1406                         (clock_ranges->wm_mcif_clocks_ranges[i].wm_min_mem_clk_in_khz /
1407                         1000));
1408                 table->WatermarkRow[0][i].MaxUclk =
1409                         cpu_to_le16((uint16_t)
1410                         (clock_ranges->wm_mcif_clocks_ranges[i].wm_max_mem_clk_in_khz /
1411                         1000));
1412                 table->WatermarkRow[0][i].WmSetting = (uint8_t)
1413                                 clock_ranges->wm_mcif_clocks_ranges[i].wm_set_id;
1414         }
1415
1416         return 0;
1417 }
1418
1419 static int sienna_cichlid_thermal_get_temperature(struct smu_context *smu,
1420                                              enum amd_pp_sensors sensor,
1421                                              uint32_t *value)
1422 {
1423         SmuMetrics_t metrics;
1424         int ret = 0;
1425
1426         if (!value)
1427                 return -EINVAL;
1428
1429         ret = sienna_cichlid_get_metrics_table(smu, &metrics);
1430         if (ret)
1431                 return ret;
1432
1433         switch (sensor) {
1434         case AMDGPU_PP_SENSOR_HOTSPOT_TEMP:
1435                 *value = metrics.TemperatureHotspot *
1436                         SMU_TEMPERATURE_UNITS_PER_CENTIGRADES;
1437                 break;
1438         case AMDGPU_PP_SENSOR_EDGE_TEMP:
1439                 *value = metrics.TemperatureEdge *
1440                         SMU_TEMPERATURE_UNITS_PER_CENTIGRADES;
1441                 break;
1442         case AMDGPU_PP_SENSOR_MEM_TEMP:
1443                 *value = metrics.TemperatureMem *
1444                         SMU_TEMPERATURE_UNITS_PER_CENTIGRADES;
1445                 break;
1446         default:
1447                 pr_err("Invalid sensor for retrieving temp\n");
1448                 return -EINVAL;
1449         }
1450
1451         return 0;
1452 }
1453
1454 static int sienna_cichlid_read_sensor(struct smu_context *smu,
1455                                  enum amd_pp_sensors sensor,
1456                                  void *data, uint32_t *size)
1457 {
1458         int ret = 0;
1459         struct smu_table_context *table_context = &smu->smu_table;
1460         PPTable_t *pptable = table_context->driver_pptable;
1461
1462         if(!data || !size)
1463                 return -EINVAL;
1464
1465         mutex_lock(&smu->sensor_lock);
1466         switch (sensor) {
1467         case AMDGPU_PP_SENSOR_MAX_FAN_RPM:
1468                 *(uint32_t *)data = pptable->FanMaximumRpm;
1469                 *size = 4;
1470                 break;
1471         case AMDGPU_PP_SENSOR_MEM_LOAD:
1472         case AMDGPU_PP_SENSOR_GPU_LOAD:
1473                 ret = sienna_cichlid_get_current_activity_percent(smu, sensor, (uint32_t *)data);
1474                 *size = 4;
1475                 break;
1476         case AMDGPU_PP_SENSOR_GPU_POWER:
1477                 ret = sienna_cichlid_get_gpu_power(smu, (uint32_t *)data);
1478                 *size = 4;
1479                 break;
1480         case AMDGPU_PP_SENSOR_HOTSPOT_TEMP:
1481         case AMDGPU_PP_SENSOR_EDGE_TEMP:
1482         case AMDGPU_PP_SENSOR_MEM_TEMP:
1483                 ret = sienna_cichlid_thermal_get_temperature(smu, sensor, (uint32_t *)data);
1484                 *size = 4;
1485                 break;
1486         default:
1487                 ret = smu_v11_0_read_sensor(smu, sensor, data, size);
1488         }
1489         mutex_unlock(&smu->sensor_lock);
1490
1491         return ret;
1492 }
1493
1494 static int sienna_cichlid_get_uclk_dpm_states(struct smu_context *smu, uint32_t *clocks_in_khz, uint32_t *num_states)
1495 {
1496         uint32_t num_discrete_levels = 0;
1497         uint16_t *dpm_levels = NULL;
1498         uint16_t i = 0;
1499         struct smu_table_context *table_context = &smu->smu_table;
1500         PPTable_t *driver_ppt = NULL;
1501
1502         if (!clocks_in_khz || !num_states || !table_context->driver_pptable)
1503                 return -EINVAL;
1504
1505         driver_ppt = table_context->driver_pptable;
1506         num_discrete_levels = driver_ppt->DpmDescriptor[PPCLK_UCLK].NumDiscreteLevels;
1507         dpm_levels = driver_ppt->FreqTableUclk;
1508
1509         if (num_discrete_levels == 0 || dpm_levels == NULL)
1510                 return -EINVAL;
1511
1512         *num_states = num_discrete_levels;
1513         for (i = 0; i < num_discrete_levels; i++) {
1514                 /* convert to khz */
1515                 *clocks_in_khz = (*dpm_levels) * 1000;
1516                 clocks_in_khz++;
1517                 dpm_levels++;
1518         }
1519
1520         return 0;
1521 }
1522
1523 static int sienna_cichlid_set_performance_level(struct smu_context *smu,
1524                                         enum amd_dpm_forced_level level);
1525
1526 static int sienna_cichlid_set_standard_performance_level(struct smu_context *smu)
1527 {
1528         struct amdgpu_device *adev = smu->adev;
1529         int ret = 0;
1530         uint32_t sclk_freq = 0, uclk_freq = 0;
1531
1532         switch (adev->asic_type) {
1533         /* TODO: need to set specify clk value by asic type, not support yet*/
1534         default:
1535                 /* by default, this is same as auto performance level */
1536                 return sienna_cichlid_set_performance_level(smu, AMD_DPM_FORCED_LEVEL_AUTO);
1537         }
1538
1539         ret = smu_set_soft_freq_range(smu, SMU_SCLK, sclk_freq, sclk_freq, false);
1540         if (ret)
1541                 return ret;
1542         ret = smu_set_soft_freq_range(smu, SMU_UCLK, uclk_freq, uclk_freq, false);
1543         if (ret)
1544                 return ret;
1545
1546         return ret;
1547 }
1548
1549 static int sienna_cichlid_set_peak_performance_level(struct smu_context *smu)
1550 {
1551         int ret = 0;
1552
1553         /* TODO: not support yet*/
1554         return ret;
1555 }
1556
1557 static int sienna_cichlid_set_performance_level(struct smu_context *smu,
1558                                         enum amd_dpm_forced_level level)
1559 {
1560         int ret = 0;
1561         uint32_t sclk_mask, mclk_mask, soc_mask;
1562
1563         switch (level) {
1564         case AMD_DPM_FORCED_LEVEL_HIGH:
1565                 ret = smu_force_dpm_limit_value(smu, true);
1566                 break;
1567         case AMD_DPM_FORCED_LEVEL_LOW:
1568                 ret = smu_force_dpm_limit_value(smu, false);
1569                 break;
1570         case AMD_DPM_FORCED_LEVEL_AUTO:
1571                 ret = smu_unforce_dpm_levels(smu);
1572                 break;
1573         case AMD_DPM_FORCED_LEVEL_PROFILE_STANDARD:
1574                 ret = sienna_cichlid_set_standard_performance_level(smu);
1575                 break;
1576         case AMD_DPM_FORCED_LEVEL_PROFILE_MIN_SCLK:
1577         case AMD_DPM_FORCED_LEVEL_PROFILE_MIN_MCLK:
1578                 ret = smu_get_profiling_clk_mask(smu, level,
1579                                                  &sclk_mask,
1580                                                  &mclk_mask,
1581                                                  &soc_mask);
1582                 if (ret)
1583                         return ret;
1584                 smu_force_clk_levels(smu, SMU_SCLK, 1 << sclk_mask, false);
1585                 smu_force_clk_levels(smu, SMU_MCLK, 1 << mclk_mask, false);
1586                 smu_force_clk_levels(smu, SMU_SOCCLK, 1 << soc_mask, false);
1587                 break;
1588         case AMD_DPM_FORCED_LEVEL_PROFILE_PEAK:
1589                 ret = sienna_cichlid_set_peak_performance_level(smu);
1590                 break;
1591         case AMD_DPM_FORCED_LEVEL_MANUAL:
1592         case AMD_DPM_FORCED_LEVEL_PROFILE_EXIT:
1593         default:
1594                 break;
1595         }
1596         return ret;
1597 }
1598
1599 static int sienna_cichlid_get_thermal_temperature_range(struct smu_context *smu,
1600                                                 struct smu_temperature_range *range)
1601 {
1602         struct smu_table_context *table_context = &smu->smu_table;
1603         struct smu_11_0_powerplay_table *powerplay_table = table_context->power_play_table;
1604
1605         if (!range || !powerplay_table)
1606                 return -EINVAL;
1607
1608         range->max = powerplay_table->software_shutdown_temp *
1609                 SMU_TEMPERATURE_UNITS_PER_CENTIGRADES;
1610
1611         return 0;
1612 }
1613
1614 static int sienna_cichlid_display_disable_memory_clock_switch(struct smu_context *smu,
1615                                                 bool disable_memory_clock_switch)
1616 {
1617         int ret = 0;
1618         struct smu_11_0_max_sustainable_clocks *max_sustainable_clocks =
1619                 (struct smu_11_0_max_sustainable_clocks *)
1620                         smu->smu_table.max_sustainable_clocks;
1621         uint32_t min_memory_clock = smu->hard_min_uclk_req_from_dal;
1622         uint32_t max_memory_clock = max_sustainable_clocks->uclock;
1623
1624         if(smu->disable_uclk_switch == disable_memory_clock_switch)
1625                 return 0;
1626
1627         if(disable_memory_clock_switch)
1628                 ret = smu_set_hard_freq_range(smu, SMU_UCLK, max_memory_clock, 0);
1629         else
1630                 ret = smu_set_hard_freq_range(smu, SMU_UCLK, min_memory_clock, 0);
1631
1632         if(!ret)
1633                 smu->disable_uclk_switch = disable_memory_clock_switch;
1634
1635         return ret;
1636 }
1637
1638 static uint32_t sienna_cichlid_get_pptable_power_limit(struct smu_context *smu)
1639 {
1640         PPTable_t *pptable = smu->smu_table.driver_pptable;
1641         return pptable->SocketPowerLimitAc[PPT_THROTTLER_PPT0];
1642 }
1643
1644 static int sienna_cichlid_get_power_limit(struct smu_context *smu,
1645                                      uint32_t *limit,
1646                                      bool cap)
1647 {
1648         PPTable_t *pptable = smu->smu_table.driver_pptable;
1649         uint32_t asic_default_power_limit = 0;
1650         int ret = 0;
1651         int power_src;
1652
1653         if (!smu->power_limit) {
1654                 if (smu_feature_is_enabled(smu, SMU_FEATURE_PPT_BIT)) {
1655                         power_src = smu_power_get_index(smu, SMU_POWER_SOURCE_AC);
1656                         if (power_src < 0)
1657                                 return -EINVAL;
1658
1659                         ret = smu_send_smc_msg_with_param(smu, SMU_MSG_GetPptLimit,
1660                                                           power_src << 16, &asic_default_power_limit);
1661                         if (ret) {
1662                                 pr_err("[%s] get PPT limit failed!", __func__);
1663                                 return ret;
1664                         }
1665                 } else {
1666                         /* the last hope to figure out the ppt limit */
1667                         if (!pptable) {
1668                                 pr_err("Cannot get PPT limit due to pptable missing!");
1669                                 return -EINVAL;
1670                         }
1671                         asic_default_power_limit =
1672                                 pptable->SocketPowerLimitAc[PPT_THROTTLER_PPT0];
1673                 }
1674
1675                 smu->power_limit = asic_default_power_limit;
1676         }
1677
1678         if (cap)
1679                 *limit = smu_v11_0_get_max_power_limit(smu);
1680         else
1681                 *limit = smu->power_limit;
1682
1683         return 0;
1684 }
1685
1686 static int sienna_cichlid_update_pcie_parameters(struct smu_context *smu,
1687                                          uint32_t pcie_gen_cap,
1688                                          uint32_t pcie_width_cap)
1689 {
1690         PPTable_t *pptable = smu->smu_table.driver_pptable;
1691         int ret, i;
1692         uint32_t smu_pcie_arg;
1693
1694         struct smu_dpm_context *smu_dpm = &smu->smu_dpm;
1695         struct smu_11_0_dpm_context *dpm_context = smu_dpm->dpm_context;
1696
1697         for (i = 0; i < NUM_LINK_LEVELS; i++) {
1698                 smu_pcie_arg = (i << 16) |
1699                         ((pptable->PcieGenSpeed[i] <= pcie_gen_cap) ?
1700                                         (pptable->PcieGenSpeed[i] << 8) :
1701                                         (pcie_gen_cap << 8)) |
1702                         ((pptable->PcieLaneCount[i] <= pcie_width_cap) ?
1703                                         pptable->PcieLaneCount[i] :
1704                                         pcie_width_cap);
1705
1706                 ret = smu_send_smc_msg_with_param(smu,
1707                                                   SMU_MSG_OverridePcieParameters,
1708                                                   smu_pcie_arg, NULL);
1709                 if (ret)
1710                         return ret;
1711
1712                 if (pptable->PcieGenSpeed[i] > pcie_gen_cap)
1713                         dpm_context->dpm_tables.pcie_table.pcie_gen[i] = pcie_gen_cap;
1714                 if (pptable->PcieLaneCount[i] > pcie_width_cap)
1715                         dpm_context->dpm_tables.pcie_table.pcie_lane[i] = pcie_width_cap;
1716         }
1717
1718         return 0;
1719 }
1720
1721 int sienna_cichlid_get_dpm_ultimate_freq(struct smu_context *smu,
1722                                 enum smu_clk_type clk_type,
1723                                 uint32_t *min, uint32_t *max)
1724 {
1725         struct amdgpu_device *adev = smu->adev;
1726         int ret;
1727
1728         if (clk_type == SMU_GFXCLK)
1729                 amdgpu_gfx_off_ctrl(adev, false);
1730         ret = smu_v11_0_get_dpm_ultimate_freq(smu, clk_type, min, max);
1731         if (clk_type == SMU_GFXCLK)
1732                 amdgpu_gfx_off_ctrl(adev, true);
1733
1734         return ret;
1735 }
1736
1737 int sienna_cichlid_set_soft_freq_limited_range(struct smu_context *smu,
1738                                       enum smu_clk_type clk_type,
1739                                       uint32_t min, uint32_t max)
1740 {
1741         struct amdgpu_device *adev = smu->adev;
1742         int ret;
1743
1744         if (clk_type == SMU_GFXCLK)
1745                 amdgpu_gfx_off_ctrl(adev, false);
1746         ret = smu_v11_0_set_soft_freq_limited_range(smu, clk_type, min, max);
1747         if (clk_type == SMU_GFXCLK)
1748                 amdgpu_gfx_off_ctrl(adev, true);
1749
1750         return ret;
1751 }
1752
1753 static void sienna_cichlid_dump_pptable(struct smu_context *smu)
1754 {
1755         struct smu_table_context *table_context = &smu->smu_table;
1756         PPTable_t *pptable = table_context->driver_pptable;
1757         int i;
1758
1759         pr_info("Dumped PPTable:\n");
1760
1761         pr_info("Version = 0x%08x\n", pptable->Version);
1762         pr_info("FeaturesToRun[0] = 0x%08x\n", pptable->FeaturesToRun[0]);
1763         pr_info("FeaturesToRun[1] = 0x%08x\n", pptable->FeaturesToRun[1]);
1764
1765         for (i = 0; i < PPT_THROTTLER_COUNT; i++) {
1766                 pr_info("SocketPowerLimitAc[%d] = 0x%x\n", i, pptable->SocketPowerLimitAc[i]);
1767                 pr_info("SocketPowerLimitAcTau[%d] = 0x%x\n", i, pptable->SocketPowerLimitAcTau[i]);
1768                 pr_info("SocketPowerLimitDc[%d] = 0x%x\n", i, pptable->SocketPowerLimitDc[i]);
1769                 pr_info("SocketPowerLimitDcTau[%d] = 0x%x\n", i, pptable->SocketPowerLimitDcTau[i]);
1770         }
1771
1772         for (i = 0; i < TDC_THROTTLER_COUNT; i++) {
1773                 pr_info("TdcLimit[%d] = 0x%x\n", i, pptable->TdcLimit[i]);
1774                 pr_info("TdcLimitTau[%d] = 0x%x\n", i, pptable->TdcLimitTau[i]);
1775         }
1776
1777         for (i = 0; i < TEMP_COUNT; i++) {
1778                 pr_info("TemperatureLimit[%d] = 0x%x\n", i, pptable->TemperatureLimit[i]);
1779         }
1780
1781         pr_info("FitLimit = 0x%x\n", pptable->FitLimit);
1782         pr_info("TotalPowerConfig = 0x%x\n", pptable->TotalPowerConfig);
1783         pr_info("TotalPowerPadding[0] = 0x%x\n", pptable->TotalPowerPadding[0]);
1784         pr_info("TotalPowerPadding[1] = 0x%x\n", pptable->TotalPowerPadding[1]);
1785         pr_info("TotalPowerPadding[2] = 0x%x\n", pptable->TotalPowerPadding[2]);
1786
1787         pr_info("ApccPlusResidencyLimit = 0x%x\n", pptable->ApccPlusResidencyLimit);
1788         for (i = 0; i < NUM_SMNCLK_DPM_LEVELS; i++) {
1789                 pr_info("SmnclkDpmFreq[%d] = 0x%x\n", i, pptable->SmnclkDpmFreq[i]);
1790                 pr_info("SmnclkDpmVoltage[%d] = 0x%x\n", i, pptable->SmnclkDpmVoltage[i]);
1791         }
1792         pr_info("PaddingAPCC[0] = 0x%x\n", pptable->PaddingAPCC[0]);
1793         pr_info("PaddingAPCC[1] = 0x%x\n", pptable->PaddingAPCC[1]);
1794         pr_info("PaddingAPCC[2] = 0x%x\n", pptable->PaddingAPCC[2]);
1795         pr_info("PaddingAPCC[3] = 0x%x\n", pptable->PaddingAPCC[3]);
1796
1797         pr_info("ThrottlerControlMask = 0x%x\n", pptable->ThrottlerControlMask);
1798
1799         pr_info("FwDStateMask = 0x%x\n", pptable->FwDStateMask);
1800
1801         pr_info("UlvVoltageOffsetSoc = 0x%x\n", pptable->UlvVoltageOffsetSoc);
1802         pr_info("UlvVoltageOffsetGfx = 0x%x\n", pptable->UlvVoltageOffsetGfx);
1803         pr_info("MinVoltageUlvGfx = 0x%x\n", pptable->MinVoltageUlvGfx);
1804         pr_info("MinVoltageUlvSoc = 0x%x\n", pptable->MinVoltageUlvSoc);
1805
1806         pr_info("SocLIVmin = 0x%x\n", pptable->SocLIVmin);
1807         pr_info("PaddingLIVmin = 0x%x\n", pptable->PaddingLIVmin);
1808
1809         pr_info("GceaLinkMgrIdleThreshold = 0x%x\n", pptable->GceaLinkMgrIdleThreshold);
1810         pr_info("paddingRlcUlvParams[0] = 0x%x\n", pptable->paddingRlcUlvParams[0]);
1811         pr_info("paddingRlcUlvParams[1] = 0x%x\n", pptable->paddingRlcUlvParams[1]);
1812         pr_info("paddingRlcUlvParams[2] = 0x%x\n", pptable->paddingRlcUlvParams[2]);
1813
1814         pr_info("MinVoltageGfx = 0x%x\n", pptable->MinVoltageGfx);
1815         pr_info("MinVoltageSoc = 0x%x\n", pptable->MinVoltageSoc);
1816         pr_info("MaxVoltageGfx = 0x%x\n", pptable->MaxVoltageGfx);
1817         pr_info("MaxVoltageSoc = 0x%x\n", pptable->MaxVoltageSoc);
1818
1819         pr_info("LoadLineResistanceGfx = 0x%x\n", pptable->LoadLineResistanceGfx);
1820         pr_info("LoadLineResistanceSoc = 0x%x\n", pptable->LoadLineResistanceSoc);
1821
1822         pr_info("VDDGFX_TVmin = 0x%x\n", pptable->VDDGFX_TVmin);
1823         pr_info("VDDSOC_TVmin = 0x%x\n", pptable->VDDSOC_TVmin);
1824         pr_info("VDDGFX_Vmin_HiTemp = 0x%x\n", pptable->VDDGFX_Vmin_HiTemp);
1825         pr_info("VDDGFX_Vmin_LoTemp = 0x%x\n", pptable->VDDGFX_Vmin_LoTemp);
1826         pr_info("VDDSOC_Vmin_HiTemp = 0x%x\n", pptable->VDDSOC_Vmin_HiTemp);
1827         pr_info("VDDSOC_Vmin_LoTemp = 0x%x\n", pptable->VDDSOC_Vmin_LoTemp);
1828         pr_info("VDDGFX_TVminHystersis = 0x%x\n", pptable->VDDGFX_TVminHystersis);
1829         pr_info("VDDSOC_TVminHystersis = 0x%x\n", pptable->VDDSOC_TVminHystersis);
1830
1831         pr_info("[PPCLK_GFXCLK]\n"
1832                         "  .VoltageMode          = 0x%02x\n"
1833                         "  .SnapToDiscrete       = 0x%02x\n"
1834                         "  .NumDiscreteLevels    = 0x%02x\n"
1835                         "  .padding              = 0x%02x\n"
1836                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1837                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1838                         "  .SsFmin               = 0x%04x\n"
1839                         "  .Padding_16           = 0x%04x\n",
1840                         pptable->DpmDescriptor[PPCLK_GFXCLK].VoltageMode,
1841                         pptable->DpmDescriptor[PPCLK_GFXCLK].SnapToDiscrete,
1842                         pptable->DpmDescriptor[PPCLK_GFXCLK].NumDiscreteLevels,
1843                         pptable->DpmDescriptor[PPCLK_GFXCLK].Padding,
1844                         pptable->DpmDescriptor[PPCLK_GFXCLK].ConversionToAvfsClk.m,
1845                         pptable->DpmDescriptor[PPCLK_GFXCLK].ConversionToAvfsClk.b,
1846                         pptable->DpmDescriptor[PPCLK_GFXCLK].SsCurve.a,
1847                         pptable->DpmDescriptor[PPCLK_GFXCLK].SsCurve.b,
1848                         pptable->DpmDescriptor[PPCLK_GFXCLK].SsCurve.c,
1849                         pptable->DpmDescriptor[PPCLK_GFXCLK].SsFmin,
1850                         pptable->DpmDescriptor[PPCLK_GFXCLK].Padding16);
1851
1852         pr_info("[PPCLK_SOCCLK]\n"
1853                         "  .VoltageMode          = 0x%02x\n"
1854                         "  .SnapToDiscrete       = 0x%02x\n"
1855                         "  .NumDiscreteLevels    = 0x%02x\n"
1856                         "  .padding              = 0x%02x\n"
1857                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1858                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1859                         "  .SsFmin               = 0x%04x\n"
1860                         "  .Padding_16           = 0x%04x\n",
1861                         pptable->DpmDescriptor[PPCLK_SOCCLK].VoltageMode,
1862                         pptable->DpmDescriptor[PPCLK_SOCCLK].SnapToDiscrete,
1863                         pptable->DpmDescriptor[PPCLK_SOCCLK].NumDiscreteLevels,
1864                         pptable->DpmDescriptor[PPCLK_SOCCLK].Padding,
1865                         pptable->DpmDescriptor[PPCLK_SOCCLK].ConversionToAvfsClk.m,
1866                         pptable->DpmDescriptor[PPCLK_SOCCLK].ConversionToAvfsClk.b,
1867                         pptable->DpmDescriptor[PPCLK_SOCCLK].SsCurve.a,
1868                         pptable->DpmDescriptor[PPCLK_SOCCLK].SsCurve.b,
1869                         pptable->DpmDescriptor[PPCLK_SOCCLK].SsCurve.c,
1870                         pptable->DpmDescriptor[PPCLK_SOCCLK].SsFmin,
1871                         pptable->DpmDescriptor[PPCLK_SOCCLK].Padding16);
1872
1873         pr_info("[PPCLK_UCLK]\n"
1874                         "  .VoltageMode          = 0x%02x\n"
1875                         "  .SnapToDiscrete       = 0x%02x\n"
1876                         "  .NumDiscreteLevels    = 0x%02x\n"
1877                         "  .padding              = 0x%02x\n"
1878                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1879                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1880                         "  .SsFmin               = 0x%04x\n"
1881                         "  .Padding_16           = 0x%04x\n",
1882                         pptable->DpmDescriptor[PPCLK_UCLK].VoltageMode,
1883                         pptable->DpmDescriptor[PPCLK_UCLK].SnapToDiscrete,
1884                         pptable->DpmDescriptor[PPCLK_UCLK].NumDiscreteLevels,
1885                         pptable->DpmDescriptor[PPCLK_UCLK].Padding,
1886                         pptable->DpmDescriptor[PPCLK_UCLK].ConversionToAvfsClk.m,
1887                         pptable->DpmDescriptor[PPCLK_UCLK].ConversionToAvfsClk.b,
1888                         pptable->DpmDescriptor[PPCLK_UCLK].SsCurve.a,
1889                         pptable->DpmDescriptor[PPCLK_UCLK].SsCurve.b,
1890                         pptable->DpmDescriptor[PPCLK_UCLK].SsCurve.c,
1891                         pptable->DpmDescriptor[PPCLK_UCLK].SsFmin,
1892                         pptable->DpmDescriptor[PPCLK_UCLK].Padding16);
1893
1894         pr_info("[PPCLK_FCLK]\n"
1895                         "  .VoltageMode          = 0x%02x\n"
1896                         "  .SnapToDiscrete       = 0x%02x\n"
1897                         "  .NumDiscreteLevels    = 0x%02x\n"
1898                         "  .padding              = 0x%02x\n"
1899                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1900                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1901                         "  .SsFmin               = 0x%04x\n"
1902                         "  .Padding_16           = 0x%04x\n",
1903                         pptable->DpmDescriptor[PPCLK_FCLK].VoltageMode,
1904                         pptable->DpmDescriptor[PPCLK_FCLK].SnapToDiscrete,
1905                         pptable->DpmDescriptor[PPCLK_FCLK].NumDiscreteLevels,
1906                         pptable->DpmDescriptor[PPCLK_FCLK].Padding,
1907                         pptable->DpmDescriptor[PPCLK_FCLK].ConversionToAvfsClk.m,
1908                         pptable->DpmDescriptor[PPCLK_FCLK].ConversionToAvfsClk.b,
1909                         pptable->DpmDescriptor[PPCLK_FCLK].SsCurve.a,
1910                         pptable->DpmDescriptor[PPCLK_FCLK].SsCurve.b,
1911                         pptable->DpmDescriptor[PPCLK_FCLK].SsCurve.c,
1912                         pptable->DpmDescriptor[PPCLK_FCLK].SsFmin,
1913                         pptable->DpmDescriptor[PPCLK_FCLK].Padding16);
1914
1915         pr_info("[PPCLK_DCLK_0]\n"
1916                         "  .VoltageMode          = 0x%02x\n"
1917                         "  .SnapToDiscrete       = 0x%02x\n"
1918                         "  .NumDiscreteLevels    = 0x%02x\n"
1919                         "  .padding              = 0x%02x\n"
1920                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1921                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1922                         "  .SsFmin               = 0x%04x\n"
1923                         "  .Padding_16           = 0x%04x\n",
1924                         pptable->DpmDescriptor[PPCLK_DCLK_0].VoltageMode,
1925                         pptable->DpmDescriptor[PPCLK_DCLK_0].SnapToDiscrete,
1926                         pptable->DpmDescriptor[PPCLK_DCLK_0].NumDiscreteLevels,
1927                         pptable->DpmDescriptor[PPCLK_DCLK_0].Padding,
1928                         pptable->DpmDescriptor[PPCLK_DCLK_0].ConversionToAvfsClk.m,
1929                         pptable->DpmDescriptor[PPCLK_DCLK_0].ConversionToAvfsClk.b,
1930                         pptable->DpmDescriptor[PPCLK_DCLK_0].SsCurve.a,
1931                         pptable->DpmDescriptor[PPCLK_DCLK_0].SsCurve.b,
1932                         pptable->DpmDescriptor[PPCLK_DCLK_0].SsCurve.c,
1933                         pptable->DpmDescriptor[PPCLK_DCLK_0].SsFmin,
1934                         pptable->DpmDescriptor[PPCLK_DCLK_0].Padding16);
1935
1936         pr_info("[PPCLK_VCLK_0]\n"
1937                         "  .VoltageMode          = 0x%02x\n"
1938                         "  .SnapToDiscrete       = 0x%02x\n"
1939                         "  .NumDiscreteLevels    = 0x%02x\n"
1940                         "  .padding              = 0x%02x\n"
1941                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1942                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1943                         "  .SsFmin               = 0x%04x\n"
1944                         "  .Padding_16           = 0x%04x\n",
1945                         pptable->DpmDescriptor[PPCLK_VCLK_0].VoltageMode,
1946                         pptable->DpmDescriptor[PPCLK_VCLK_0].SnapToDiscrete,
1947                         pptable->DpmDescriptor[PPCLK_VCLK_0].NumDiscreteLevels,
1948                         pptable->DpmDescriptor[PPCLK_VCLK_0].Padding,
1949                         pptable->DpmDescriptor[PPCLK_VCLK_0].ConversionToAvfsClk.m,
1950                         pptable->DpmDescriptor[PPCLK_VCLK_0].ConversionToAvfsClk.b,
1951                         pptable->DpmDescriptor[PPCLK_VCLK_0].SsCurve.a,
1952                         pptable->DpmDescriptor[PPCLK_VCLK_0].SsCurve.b,
1953                         pptable->DpmDescriptor[PPCLK_VCLK_0].SsCurve.c,
1954                         pptable->DpmDescriptor[PPCLK_VCLK_0].SsFmin,
1955                         pptable->DpmDescriptor[PPCLK_VCLK_0].Padding16);
1956
1957         pr_info("[PPCLK_DCLK_1]\n"
1958                         "  .VoltageMode          = 0x%02x\n"
1959                         "  .SnapToDiscrete       = 0x%02x\n"
1960                         "  .NumDiscreteLevels    = 0x%02x\n"
1961                         "  .padding              = 0x%02x\n"
1962                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1963                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1964                         "  .SsFmin               = 0x%04x\n"
1965                         "  .Padding_16           = 0x%04x\n",
1966                         pptable->DpmDescriptor[PPCLK_DCLK_1].VoltageMode,
1967                         pptable->DpmDescriptor[PPCLK_DCLK_1].SnapToDiscrete,
1968                         pptable->DpmDescriptor[PPCLK_DCLK_1].NumDiscreteLevels,
1969                         pptable->DpmDescriptor[PPCLK_DCLK_1].Padding,
1970                         pptable->DpmDescriptor[PPCLK_DCLK_1].ConversionToAvfsClk.m,
1971                         pptable->DpmDescriptor[PPCLK_DCLK_1].ConversionToAvfsClk.b,
1972                         pptable->DpmDescriptor[PPCLK_DCLK_1].SsCurve.a,
1973                         pptable->DpmDescriptor[PPCLK_DCLK_1].SsCurve.b,
1974                         pptable->DpmDescriptor[PPCLK_DCLK_1].SsCurve.c,
1975                         pptable->DpmDescriptor[PPCLK_DCLK_1].SsFmin,
1976                         pptable->DpmDescriptor[PPCLK_DCLK_1].Padding16);
1977
1978         pr_info("[PPCLK_VCLK_1]\n"
1979                         "  .VoltageMode          = 0x%02x\n"
1980                         "  .SnapToDiscrete       = 0x%02x\n"
1981                         "  .NumDiscreteLevels    = 0x%02x\n"
1982                         "  .padding              = 0x%02x\n"
1983                         "  .ConversionToAvfsClk{m = 0x%08x b = 0x%08x}\n"
1984                         "  .SsCurve            {a = 0x%08x b = 0x%08x c = 0x%08x}\n"
1985                         "  .SsFmin               = 0x%04x\n"
1986                         "  .Padding_16           = 0x%04x\n",
1987                         pptable->DpmDescriptor[PPCLK_VCLK_1].VoltageMode,
1988                         pptable->DpmDescriptor[PPCLK_VCLK_1].SnapToDiscrete,
1989                         pptable->DpmDescriptor[PPCLK_VCLK_1].NumDiscreteLevels,
1990                         pptable->DpmDescriptor[PPCLK_VCLK_1].Padding,
1991                         pptable->DpmDescriptor[PPCLK_VCLK_1].ConversionToAvfsClk.m,
1992                         pptable->DpmDescriptor[PPCLK_VCLK_1].ConversionToAvfsClk.b,
1993                         pptable->DpmDescriptor[PPCLK_VCLK_1].SsCurve.a,
1994                         pptable->DpmDescriptor[PPCLK_VCLK_1].SsCurve.b,
1995                         pptable->DpmDescriptor[PPCLK_VCLK_1].SsCurve.c,
1996                         pptable->DpmDescriptor[PPCLK_VCLK_1].SsFmin,
1997                         pptable->DpmDescriptor[PPCLK_VCLK_1].Padding16);
1998
1999         pr_info("FreqTableGfx\n");
2000         for (i = 0; i < NUM_GFXCLK_DPM_LEVELS; i++)
2001                 pr_info("  .[%02d] = 0x%x\n", i, pptable->FreqTableGfx[i]);
2002
2003         pr_info("FreqTableVclk\n");
2004         for (i = 0; i < NUM_VCLK_DPM_LEVELS; i++)
2005                 pr_info("  .[%02d] = 0x%x\n", i, pptable->FreqTableVclk[i]);
2006
2007         pr_info("FreqTableDclk\n");
2008         for (i = 0; i < NUM_DCLK_DPM_LEVELS; i++)
2009                 pr_info("  .[%02d] = 0x%x\n", i, pptable->FreqTableDclk[i]);
2010
2011         pr_info("FreqTableSocclk\n");
2012         for (i = 0; i < NUM_SOCCLK_DPM_LEVELS; i++)
2013                 pr_info("  .[%02d] = 0x%x\n", i, pptable->FreqTableSocclk[i]);
2014
2015         pr_info("FreqTableUclk\n");
2016         for (i = 0; i < NUM_UCLK_DPM_LEVELS; i++)
2017                 pr_info("  .[%02d] = 0x%x\n", i, pptable->FreqTableUclk[i]);
2018
2019         pr_info("FreqTableFclk\n");
2020         for (i = 0; i < NUM_FCLK_DPM_LEVELS; i++)
2021                 pr_info("  .[%02d] = 0x%x\n", i, pptable->FreqTableFclk[i]);
2022
2023         pr_info("Paddingclks[0] = 0x%x\n",  pptable->Paddingclks[0]);
2024         pr_info("Paddingclks[1] = 0x%x\n",  pptable->Paddingclks[1]);
2025         pr_info("Paddingclks[2] = 0x%x\n",  pptable->Paddingclks[2]);
2026         pr_info("Paddingclks[3] = 0x%x\n",  pptable->Paddingclks[3]);
2027         pr_info("Paddingclks[4] = 0x%x\n",  pptable->Paddingclks[4]);
2028         pr_info("Paddingclks[5] = 0x%x\n",  pptable->Paddingclks[5]);
2029         pr_info("Paddingclks[6] = 0x%x\n",  pptable->Paddingclks[6]);
2030         pr_info("Paddingclks[7] = 0x%x\n",  pptable->Paddingclks[7]);
2031         pr_info("Paddingclks[8] = 0x%x\n",  pptable->Paddingclks[8]);
2032         pr_info("Paddingclks[9] = 0x%x\n",  pptable->Paddingclks[9]);
2033         pr_info("Paddingclks[10] = 0x%x\n", pptable->Paddingclks[10]);
2034         pr_info("Paddingclks[11] = 0x%x\n", pptable->Paddingclks[11]);
2035         pr_info("Paddingclks[12] = 0x%x\n", pptable->Paddingclks[12]);
2036         pr_info("Paddingclks[13] = 0x%x\n", pptable->Paddingclks[13]);
2037         pr_info("Paddingclks[14] = 0x%x\n", pptable->Paddingclks[14]);
2038         pr_info("Paddingclks[15] = 0x%x\n", pptable->Paddingclks[15]);
2039
2040         pr_info("DcModeMaxFreq\n");
2041         pr_info("  .PPCLK_GFXCLK = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_GFXCLK]);
2042         pr_info("  .PPCLK_SOCCLK = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_SOCCLK]);
2043         pr_info("  .PPCLK_UCLK   = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_UCLK]);
2044         pr_info("  .PPCLK_FCLK   = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_FCLK]);
2045         pr_info("  .PPCLK_DCLK_0 = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_DCLK_0]);
2046         pr_info("  .PPCLK_VCLK_0 = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_VCLK_0]);
2047         pr_info("  .PPCLK_DCLK_1 = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_DCLK_1]);
2048         pr_info("  .PPCLK_VCLK_1 = 0x%x\n", pptable->DcModeMaxFreq[PPCLK_VCLK_1]);
2049
2050         pr_info("FreqTableUclkDiv\n");
2051         for (i = 0; i < NUM_UCLK_DPM_LEVELS; i++)
2052                 pr_info("  .[%d] = 0x%x\n", i, pptable->FreqTableUclkDiv[i]);
2053
2054         pr_info("FclkBoostFreq = 0x%x\n", pptable->FclkBoostFreq);
2055         pr_info("FclkParamPadding = 0x%x\n", pptable->FclkParamPadding);
2056
2057         pr_info("Mp0clkFreq\n");
2058         for (i = 0; i < NUM_MP0CLK_DPM_LEVELS; i++)
2059                 pr_info("  .[%d] = 0x%x\n", i, pptable->Mp0clkFreq[i]);
2060
2061         pr_info("Mp0DpmVoltage\n");
2062         for (i = 0; i < NUM_MP0CLK_DPM_LEVELS; i++)
2063                 pr_info("  .[%d] = 0x%x\n", i, pptable->Mp0DpmVoltage[i]);
2064
2065         pr_info("MemVddciVoltage\n");
2066         for (i = 0; i < NUM_UCLK_DPM_LEVELS; i++)
2067                 pr_info("  .[%d] = 0x%x\n", i, pptable->MemVddciVoltage[i]);
2068
2069         pr_info("MemMvddVoltage\n");
2070         for (i = 0; i < NUM_UCLK_DPM_LEVELS; i++)
2071                 pr_info("  .[%d] = 0x%x\n", i, pptable->MemMvddVoltage[i]);
2072
2073         pr_info("GfxclkFgfxoffEntry = 0x%x\n", pptable->GfxclkFgfxoffEntry);
2074         pr_info("GfxclkFinit = 0x%x\n", pptable->GfxclkFinit);
2075         pr_info("GfxclkFidle = 0x%x\n", pptable->GfxclkFidle);
2076         pr_info("GfxclkSource = 0x%x\n", pptable->GfxclkSource);
2077         pr_info("GfxclkPadding = 0x%x\n", pptable->GfxclkPadding);
2078
2079         pr_info("GfxGpoSubFeatureMask = 0x%x\n", pptable->GfxGpoSubFeatureMask);
2080
2081         pr_info("GfxGpoEnabledWorkPolicyMask = 0x%x\n", pptable->GfxGpoEnabledWorkPolicyMask);
2082         pr_info("GfxGpoDisabledWorkPolicyMask = 0x%x\n", pptable->GfxGpoDisabledWorkPolicyMask);
2083         pr_info("GfxGpoPadding[0] = 0x%x\n", pptable->GfxGpoPadding[0]);
2084         pr_info("GfxGpoVotingAllow = 0x%x\n", pptable->GfxGpoVotingAllow);
2085         pr_info("GfxGpoPadding32[0] = 0x%x\n", pptable->GfxGpoPadding32[0]);
2086         pr_info("GfxGpoPadding32[1] = 0x%x\n", pptable->GfxGpoPadding32[1]);
2087         pr_info("GfxGpoPadding32[2] = 0x%x\n", pptable->GfxGpoPadding32[2]);
2088         pr_info("GfxGpoPadding32[3] = 0x%x\n", pptable->GfxGpoPadding32[3]);
2089         pr_info("GfxDcsFopt = 0x%x\n", pptable->GfxDcsFopt);
2090         pr_info("GfxDcsFclkFopt = 0x%x\n", pptable->GfxDcsFclkFopt);
2091         pr_info("GfxDcsUclkFopt = 0x%x\n", pptable->GfxDcsUclkFopt);
2092
2093         pr_info("DcsGfxOffVoltage = 0x%x\n", pptable->DcsGfxOffVoltage);
2094         pr_info("DcsMinGfxOffTime = 0x%x\n", pptable->DcsMinGfxOffTime);
2095         pr_info("DcsMaxGfxOffTime = 0x%x\n", pptable->DcsMaxGfxOffTime);
2096         pr_info("DcsMinCreditAccum = 0x%x\n", pptable->DcsMinCreditAccum);
2097         pr_info("DcsExitHysteresis = 0x%x\n", pptable->DcsExitHysteresis);
2098         pr_info("DcsTimeout = 0x%x\n", pptable->DcsTimeout);
2099
2100         pr_info("DcsParamPadding[0] = 0x%x\n", pptable->DcsParamPadding[0]);
2101         pr_info("DcsParamPadding[1] = 0x%x\n", pptable->DcsParamPadding[1]);
2102         pr_info("DcsParamPadding[2] = 0x%x\n", pptable->DcsParamPadding[2]);
2103         pr_info("DcsParamPadding[3] = 0x%x\n", pptable->DcsParamPadding[3]);
2104         pr_info("DcsParamPadding[4] = 0x%x\n", pptable->DcsParamPadding[4]);
2105
2106         pr_info("FlopsPerByteTable\n");
2107         for (i = 0; i < RLC_PACE_TABLE_NUM_LEVELS; i++)
2108                 pr_info("  .[%d] = 0x%x\n", i, pptable->FlopsPerByteTable[i]);
2109
2110         pr_info("LowestUclkReservedForUlv = 0x%x\n", pptable->LowestUclkReservedForUlv);
2111         pr_info("vddingMem[0] = 0x%x\n", pptable->PaddingMem[0]);
2112         pr_info("vddingMem[1] = 0x%x\n", pptable->PaddingMem[1]);
2113         pr_info("vddingMem[2] = 0x%x\n", pptable->PaddingMem[2]);
2114
2115         pr_info("UclkDpmPstates\n");
2116         for (i = 0; i < NUM_UCLK_DPM_LEVELS; i++)
2117                 pr_info("  .[%d] = 0x%x\n", i, pptable->UclkDpmPstates[i]);
2118
2119         pr_info("UclkDpmSrcFreqRange\n");
2120         pr_info("  .Fmin = 0x%x\n",
2121                 pptable->UclkDpmSrcFreqRange.Fmin);
2122         pr_info("  .Fmax = 0x%x\n",
2123                 pptable->UclkDpmSrcFreqRange.Fmax);
2124         pr_info("UclkDpmTargFreqRange\n");
2125         pr_info("  .Fmin = 0x%x\n",
2126                 pptable->UclkDpmTargFreqRange.Fmin);
2127         pr_info("  .Fmax = 0x%x\n",
2128                 pptable->UclkDpmTargFreqRange.Fmax);
2129         pr_info("UclkDpmMidstepFreq = 0x%x\n", pptable->UclkDpmMidstepFreq);
2130         pr_info("UclkMidstepPadding = 0x%x\n", pptable->UclkMidstepPadding);
2131
2132         pr_info("PcieGenSpeed\n");
2133         for (i = 0; i < NUM_LINK_LEVELS; i++)
2134                 pr_info("  .[%d] = 0x%x\n", i, pptable->PcieGenSpeed[i]);
2135
2136         pr_info("PcieLaneCount\n");
2137         for (i = 0; i < NUM_LINK_LEVELS; i++)
2138                 pr_info("  .[%d] = 0x%x\n", i, pptable->PcieLaneCount[i]);
2139
2140         pr_info("LclkFreq\n");
2141         for (i = 0; i < NUM_LINK_LEVELS; i++)
2142                 pr_info("  .[%d] = 0x%x\n", i, pptable->LclkFreq[i]);
2143
2144         pr_info("FanStopTemp = 0x%x\n", pptable->FanStopTemp);
2145         pr_info("FanStartTemp = 0x%x\n", pptable->FanStartTemp);
2146
2147         pr_info("FanGain\n");
2148         for (i = 0; i < TEMP_COUNT; i++)
2149                 pr_info("  .[%d] = 0x%x\n", i, pptable->FanGain[i]);
2150
2151         pr_info("FanPwmMin = 0x%x\n", pptable->FanPwmMin);
2152         pr_info("FanAcousticLimitRpm = 0x%x\n", pptable->FanAcousticLimitRpm);
2153         pr_info("FanThrottlingRpm = 0x%x\n", pptable->FanThrottlingRpm);
2154         pr_info("FanMaximumRpm = 0x%x\n", pptable->FanMaximumRpm);
2155         pr_info("MGpuFanBoostLimitRpm = 0x%x\n", pptable->MGpuFanBoostLimitRpm);
2156         pr_info("FanTargetTemperature = 0x%x\n", pptable->FanTargetTemperature);
2157         pr_info("FanTargetGfxclk = 0x%x\n", pptable->FanTargetGfxclk);
2158         pr_info("FanPadding16 = 0x%x\n", pptable->FanPadding16);
2159         pr_info("FanTempInputSelect = 0x%x\n", pptable->FanTempInputSelect);
2160         pr_info("FanPadding = 0x%x\n", pptable->FanPadding);
2161         pr_info("FanZeroRpmEnable = 0x%x\n", pptable->FanZeroRpmEnable);
2162         pr_info("FanTachEdgePerRev = 0x%x\n", pptable->FanTachEdgePerRev);
2163
2164         pr_info("FuzzyFan_ErrorSetDelta = 0x%x\n", pptable->FuzzyFan_ErrorSetDelta);
2165         pr_info("FuzzyFan_ErrorRateSetDelta = 0x%x\n", pptable->FuzzyFan_ErrorRateSetDelta);
2166         pr_info("FuzzyFan_PwmSetDelta = 0x%x\n", pptable->FuzzyFan_PwmSetDelta);
2167         pr_info("FuzzyFan_Reserved = 0x%x\n", pptable->FuzzyFan_Reserved);
2168
2169         pr_info("OverrideAvfsGb[AVFS_VOLTAGE_GFX] = 0x%x\n", pptable->OverrideAvfsGb[AVFS_VOLTAGE_GFX]);
2170         pr_info("OverrideAvfsGb[AVFS_VOLTAGE_SOC] = 0x%x\n", pptable->OverrideAvfsGb[AVFS_VOLTAGE_SOC]);
2171         pr_info("dBtcGbGfxDfllModelSelect = 0x%x\n", pptable->dBtcGbGfxDfllModelSelect);
2172         pr_info("Padding8_Avfs = 0x%x\n", pptable->Padding8_Avfs);
2173
2174         pr_info("qAvfsGb[AVFS_VOLTAGE_GFX]{a = 0x%x b = 0x%x c = 0x%x}\n",
2175                         pptable->qAvfsGb[AVFS_VOLTAGE_GFX].a,
2176                         pptable->qAvfsGb[AVFS_VOLTAGE_GFX].b,
2177                         pptable->qAvfsGb[AVFS_VOLTAGE_GFX].c);
2178         pr_info("qAvfsGb[AVFS_VOLTAGE_SOC]{a = 0x%x b = 0x%x c = 0x%x}\n",
2179                         pptable->qAvfsGb[AVFS_VOLTAGE_SOC].a,
2180                         pptable->qAvfsGb[AVFS_VOLTAGE_SOC].b,
2181                         pptable->qAvfsGb[AVFS_VOLTAGE_SOC].c);
2182         pr_info("dBtcGbGfxPll{a = 0x%x b = 0x%x c = 0x%x}\n",
2183                         pptable->dBtcGbGfxPll.a,
2184                         pptable->dBtcGbGfxPll.b,
2185                         pptable->dBtcGbGfxPll.c);
2186         pr_info("dBtcGbGfxAfll{a = 0x%x b = 0x%x c = 0x%x}\n",
2187                         pptable->dBtcGbGfxDfll.a,
2188                         pptable->dBtcGbGfxDfll.b,
2189                         pptable->dBtcGbGfxDfll.c);
2190         pr_info("dBtcGbSoc{a = 0x%x b = 0x%x c = 0x%x}\n",
2191                         pptable->dBtcGbSoc.a,
2192                         pptable->dBtcGbSoc.b,
2193                         pptable->dBtcGbSoc.c);
2194         pr_info("qAgingGb[AVFS_VOLTAGE_GFX]{m = 0x%x b = 0x%x}\n",
2195                         pptable->qAgingGb[AVFS_VOLTAGE_GFX].m,
2196                         pptable->qAgingGb[AVFS_VOLTAGE_GFX].b);
2197         pr_info("qAgingGb[AVFS_VOLTAGE_SOC]{m = 0x%x b = 0x%x}\n",
2198                         pptable->qAgingGb[AVFS_VOLTAGE_SOC].m,
2199                         pptable->qAgingGb[AVFS_VOLTAGE_SOC].b);
2200
2201         pr_info("PiecewiseLinearDroopIntGfxDfll\n");
2202         for (i = 0; i < NUM_PIECE_WISE_LINEAR_DROOP_MODEL_VF_POINTS; i++) {
2203                 pr_info("               Fset[%d] = 0x%x\n",
2204                         i, pptable->PiecewiseLinearDroopIntGfxDfll.Fset[i]);
2205                 pr_info("               Vdroop[%d] = 0x%x\n",
2206                         i, pptable->PiecewiseLinearDroopIntGfxDfll.Vdroop[i]);
2207         }
2208
2209         pr_info("qStaticVoltageOffset[AVFS_VOLTAGE_GFX]{a = 0x%x b = 0x%x c = 0x%x}\n",
2210                         pptable->qStaticVoltageOffset[AVFS_VOLTAGE_GFX].a,
2211                         pptable->qStaticVoltageOffset[AVFS_VOLTAGE_GFX].b,
2212                         pptable->qStaticVoltageOffset[AVFS_VOLTAGE_GFX].c);
2213         pr_info("qStaticVoltageOffset[AVFS_VOLTAGE_SOC]{a = 0x%x b = 0x%x c = 0x%x}\n",
2214                         pptable->qStaticVoltageOffset[AVFS_VOLTAGE_SOC].a,
2215                         pptable->qStaticVoltageOffset[AVFS_VOLTAGE_SOC].b,
2216                         pptable->qStaticVoltageOffset[AVFS_VOLTAGE_SOC].c);
2217
2218         pr_info("DcTol[AVFS_VOLTAGE_GFX] = 0x%x\n", pptable->DcTol[AVFS_VOLTAGE_GFX]);
2219         pr_info("DcTol[AVFS_VOLTAGE_SOC] = 0x%x\n", pptable->DcTol[AVFS_VOLTAGE_SOC]);
2220
2221         pr_info("DcBtcEnabled[AVFS_VOLTAGE_GFX] = 0x%x\n", pptable->DcBtcEnabled[AVFS_VOLTAGE_GFX]);
2222         pr_info("DcBtcEnabled[AVFS_VOLTAGE_SOC] = 0x%x\n", pptable->DcBtcEnabled[AVFS_VOLTAGE_SOC]);
2223         pr_info("Padding8_GfxBtc[0] = 0x%x\n", pptable->Padding8_GfxBtc[0]);
2224         pr_info("Padding8_GfxBtc[1] = 0x%x\n", pptable->Padding8_GfxBtc[1]);
2225
2226         pr_info("DcBtcMin[AVFS_VOLTAGE_GFX] = 0x%x\n", pptable->DcBtcMin[AVFS_VOLTAGE_GFX]);
2227         pr_info("DcBtcMin[AVFS_VOLTAGE_SOC] = 0x%x\n", pptable->DcBtcMin[AVFS_VOLTAGE_SOC]);
2228         pr_info("DcBtcMax[AVFS_VOLTAGE_GFX] = 0x%x\n", pptable->DcBtcMax[AVFS_VOLTAGE_GFX]);
2229         pr_info("DcBtcMax[AVFS_VOLTAGE_SOC] = 0x%x\n", pptable->DcBtcMax[AVFS_VOLTAGE_SOC]);
2230
2231         pr_info("DcBtcGb[AVFS_VOLTAGE_GFX] = 0x%x\n", pptable->DcBtcGb[AVFS_VOLTAGE_GFX]);
2232         pr_info("DcBtcGb[AVFS_VOLTAGE_SOC] = 0x%x\n", pptable->DcBtcGb[AVFS_VOLTAGE_SOC]);
2233
2234         pr_info("XgmiDpmPstates\n");
2235         for (i = 0; i < NUM_XGMI_LEVELS; i++)
2236                 pr_info("  .[%d] = 0x%x\n", i, pptable->XgmiDpmPstates[i]);
2237         pr_info("XgmiDpmSpare[0] = 0x%02x\n", pptable->XgmiDpmSpare[0]);
2238         pr_info("XgmiDpmSpare[1] = 0x%02x\n", pptable->XgmiDpmSpare[1]);
2239
2240         pr_info("DebugOverrides = 0x%x\n", pptable->DebugOverrides);
2241         pr_info("ReservedEquation0{a = 0x%x b = 0x%x c = 0x%x}\n",
2242                         pptable->ReservedEquation0.a,
2243                         pptable->ReservedEquation0.b,
2244                         pptable->ReservedEquation0.c);
2245         pr_info("ReservedEquation1{a = 0x%x b = 0x%x c = 0x%x}\n",
2246                         pptable->ReservedEquation1.a,
2247                         pptable->ReservedEquation1.b,
2248                         pptable->ReservedEquation1.c);
2249         pr_info("ReservedEquation2{a = 0x%x b = 0x%x c = 0x%x}\n",
2250                         pptable->ReservedEquation2.a,
2251                         pptable->ReservedEquation2.b,
2252                         pptable->ReservedEquation2.c);
2253         pr_info("ReservedEquation3{a = 0x%x b = 0x%x c = 0x%x}\n",
2254                         pptable->ReservedEquation3.a,
2255                         pptable->ReservedEquation3.b,
2256                         pptable->ReservedEquation3.c);
2257
2258         pr_info("SkuReserved[0] = 0x%x\n", pptable->SkuReserved[0]);
2259         pr_info("SkuReserved[1] = 0x%x\n", pptable->SkuReserved[1]);
2260         pr_info("SkuReserved[2] = 0x%x\n", pptable->SkuReserved[2]);
2261         pr_info("SkuReserved[3] = 0x%x\n", pptable->SkuReserved[3]);
2262         pr_info("SkuReserved[4] = 0x%x\n", pptable->SkuReserved[4]);
2263         pr_info("SkuReserved[5] = 0x%x\n", pptable->SkuReserved[5]);
2264         pr_info("SkuReserved[6] = 0x%x\n", pptable->SkuReserved[6]);
2265         pr_info("SkuReserved[7] = 0x%x\n", pptable->SkuReserved[7]);
2266         pr_info("SkuReserved[8] = 0x%x\n", pptable->SkuReserved[8]);
2267         pr_info("SkuReserved[9] = 0x%x\n", pptable->SkuReserved[9]);
2268         pr_info("SkuReserved[10] = 0x%x\n", pptable->SkuReserved[10]);
2269         pr_info("SkuReserved[11] = 0x%x\n", pptable->SkuReserved[11]);
2270         pr_info("SkuReserved[12] = 0x%x\n", pptable->SkuReserved[12]);
2271         pr_info("SkuReserved[13] = 0x%x\n", pptable->SkuReserved[13]);
2272         pr_info("SkuReserved[14] = 0x%x\n", pptable->SkuReserved[14]);
2273
2274         pr_info("GamingClk[0] = 0x%x\n", pptable->GamingClk[0]);
2275         pr_info("GamingClk[1] = 0x%x\n", pptable->GamingClk[1]);
2276         pr_info("GamingClk[2] = 0x%x\n", pptable->GamingClk[2]);
2277         pr_info("GamingClk[3] = 0x%x\n", pptable->GamingClk[3]);
2278         pr_info("GamingClk[4] = 0x%x\n", pptable->GamingClk[4]);
2279         pr_info("GamingClk[5] = 0x%x\n", pptable->GamingClk[5]);
2280
2281         for (i = 0; i < NUM_I2C_CONTROLLERS; i++) {
2282                 pr_info("I2cControllers[%d]:\n", i);
2283                 pr_info("                   .Enabled = 0x%x\n",
2284                                 pptable->I2cControllers[i].Enabled);
2285                 pr_info("                   .Speed = 0x%x\n",
2286                                 pptable->I2cControllers[i].Speed);
2287                 pr_info("                   .SlaveAddress = 0x%x\n",
2288                                 pptable->I2cControllers[i].SlaveAddress);
2289                 pr_info("                   .ControllerPort = 0x%x\n",
2290                                 pptable->I2cControllers[i].ControllerPort);
2291                 pr_info("                   .ControllerName = 0x%x\n",
2292                                 pptable->I2cControllers[i].ControllerName);
2293                 pr_info("                   .ThermalThrottler = 0x%x\n",
2294                                 pptable->I2cControllers[i].ThermalThrotter);
2295                 pr_info("                   .I2cProtocol = 0x%x\n",
2296                                 pptable->I2cControllers[i].I2cProtocol);
2297                 pr_info("                   .PaddingConfig = 0x%x\n",
2298                                 pptable->I2cControllers[i].PaddingConfig);
2299         }
2300
2301         pr_info("GpioScl = 0x%x\n", pptable->GpioScl);
2302         pr_info("GpioSda = 0x%x\n", pptable->GpioSda);
2303         pr_info("FchUsbPdSlaveAddr = 0x%x\n", pptable->FchUsbPdSlaveAddr);
2304         pr_info("I2cSpare[0] = 0x%x\n", pptable->I2cSpare[0]);
2305
2306         pr_info("Board Parameters:\n");
2307         pr_info("VddGfxVrMapping = 0x%x\n", pptable->VddGfxVrMapping);
2308         pr_info("VddSocVrMapping = 0x%x\n", pptable->VddSocVrMapping);
2309         pr_info("VddMem0VrMapping = 0x%x\n", pptable->VddMem0VrMapping);
2310         pr_info("VddMem1VrMapping = 0x%x\n", pptable->VddMem1VrMapping);
2311         pr_info("GfxUlvPhaseSheddingMask = 0x%x\n", pptable->GfxUlvPhaseSheddingMask);
2312         pr_info("SocUlvPhaseSheddingMask = 0x%x\n", pptable->SocUlvPhaseSheddingMask);
2313         pr_info("VddciUlvPhaseSheddingMask = 0x%x\n", pptable->VddciUlvPhaseSheddingMask);
2314         pr_info("MvddUlvPhaseSheddingMask = 0x%x\n", pptable->MvddUlvPhaseSheddingMask);
2315
2316         pr_info("GfxMaxCurrent = 0x%x\n", pptable->GfxMaxCurrent);
2317         pr_info("GfxOffset = 0x%x\n", pptable->GfxOffset);
2318         pr_info("Padding_TelemetryGfx = 0x%x\n", pptable->Padding_TelemetryGfx);
2319
2320         pr_info("SocMaxCurrent = 0x%x\n", pptable->SocMaxCurrent);
2321         pr_info("SocOffset = 0x%x\n", pptable->SocOffset);
2322         pr_info("Padding_TelemetrySoc = 0x%x\n", pptable->Padding_TelemetrySoc);
2323
2324         pr_info("Mem0MaxCurrent = 0x%x\n", pptable->Mem0MaxCurrent);
2325         pr_info("Mem0Offset = 0x%x\n", pptable->Mem0Offset);
2326         pr_info("Padding_TelemetryMem0 = 0x%x\n", pptable->Padding_TelemetryMem0);
2327
2328         pr_info("Mem1MaxCurrent = 0x%x\n", pptable->Mem1MaxCurrent);
2329         pr_info("Mem1Offset = 0x%x\n", pptable->Mem1Offset);
2330         pr_info("Padding_TelemetryMem1 = 0x%x\n", pptable->Padding_TelemetryMem1);
2331
2332         pr_info("MvddRatio = 0x%x\n", pptable->MvddRatio);
2333
2334         pr_info("AcDcGpio = 0x%x\n", pptable->AcDcGpio);
2335         pr_info("AcDcPolarity = 0x%x\n", pptable->AcDcPolarity);
2336         pr_info("VR0HotGpio = 0x%x\n", pptable->VR0HotGpio);
2337         pr_info("VR0HotPolarity = 0x%x\n", pptable->VR0HotPolarity);
2338         pr_info("VR1HotGpio = 0x%x\n", pptable->VR1HotGpio);
2339         pr_info("VR1HotPolarity = 0x%x\n", pptable->VR1HotPolarity);
2340         pr_info("GthrGpio = 0x%x\n", pptable->GthrGpio);
2341         pr_info("GthrPolarity = 0x%x\n", pptable->GthrPolarity);
2342         pr_info("LedPin0 = 0x%x\n", pptable->LedPin0);
2343         pr_info("LedPin1 = 0x%x\n", pptable->LedPin1);
2344         pr_info("LedPin2 = 0x%x\n", pptable->LedPin2);
2345         pr_info("LedEnableMask = 0x%x\n", pptable->LedEnableMask);
2346         pr_info("LedPcie = 0x%x\n", pptable->LedPcie);
2347         pr_info("LedError = 0x%x\n", pptable->LedError);
2348         pr_info("LedSpare1[0] = 0x%x\n", pptable->LedSpare1[0]);
2349         pr_info("LedSpare1[1] = 0x%x\n", pptable->LedSpare1[1]);
2350
2351         pr_info("PllGfxclkSpreadEnabled = 0x%x\n", pptable->PllGfxclkSpreadEnabled);
2352         pr_info("PllGfxclkSpreadPercent = 0x%x\n", pptable->PllGfxclkSpreadPercent);
2353         pr_info("PllGfxclkSpreadFreq = 0x%x\n",    pptable->PllGfxclkSpreadFreq);
2354
2355         pr_info("DfllGfxclkSpreadEnabled = 0x%x\n", pptable->DfllGfxclkSpreadEnabled);
2356         pr_info("DfllGfxclkSpreadPercent = 0x%x\n", pptable->DfllGfxclkSpreadPercent);
2357         pr_info("DfllGfxclkSpreadFreq = 0x%x\n",    pptable->DfllGfxclkSpreadFreq);
2358
2359         pr_info("UclkSpreadEnabled = 0x%x\n", pptable->UclkSpreadEnabled);
2360         pr_info("UclkSpreadPercent = 0x%x\n", pptable->UclkSpreadPercent);
2361         pr_info("UclkSpreadFreq = 0x%x\n", pptable->UclkSpreadFreq);
2362
2363         pr_info("FclkSpreadEnabled = 0x%x\n", pptable->FclkSpreadEnabled);
2364         pr_info("FclkSpreadPercent = 0x%x\n", pptable->FclkSpreadPercent);
2365         pr_info("FclkSpreadFreq = 0x%x\n", pptable->FclkSpreadFreq);
2366
2367         pr_info("MemoryChannelEnabled = 0x%x\n", pptable->MemoryChannelEnabled);
2368         pr_info("DramBitWidth = 0x%x\n", pptable->DramBitWidth);
2369         pr_info("PaddingMem1[0] = 0x%x\n", pptable->PaddingMem1[0]);
2370         pr_info("PaddingMem1[1] = 0x%x\n", pptable->PaddingMem1[1]);
2371         pr_info("PaddingMem1[2] = 0x%x\n", pptable->PaddingMem1[2]);
2372
2373         pr_info("TotalBoardPower = 0x%x\n", pptable->TotalBoardPower);
2374         pr_info("BoardPowerPadding = 0x%x\n", pptable->BoardPowerPadding);
2375
2376         pr_info("XgmiLinkSpeed\n");
2377         for (i = 0; i < NUM_XGMI_PSTATE_LEVELS; i++)
2378                 pr_info("  .[%d] = 0x%x\n", i, pptable->XgmiLinkSpeed[i]);
2379         pr_info("XgmiLinkWidth\n");
2380         for (i = 0; i < NUM_XGMI_PSTATE_LEVELS; i++)
2381                 pr_info("  .[%d] = 0x%x\n", i, pptable->XgmiLinkWidth[i]);
2382         pr_info("XgmiFclkFreq\n");
2383         for (i = 0; i < NUM_XGMI_PSTATE_LEVELS; i++)
2384                 pr_info("  .[%d] = 0x%x\n", i, pptable->XgmiFclkFreq[i]);
2385         pr_info("XgmiSocVoltage\n");
2386         for (i = 0; i < NUM_XGMI_PSTATE_LEVELS; i++)
2387                 pr_info("  .[%d] = 0x%x\n", i, pptable->XgmiSocVoltage[i]);
2388
2389         pr_info("HsrEnabled = 0x%x\n", pptable->HsrEnabled);
2390         pr_info("VddqOffEnabled = 0x%x\n", pptable->VddqOffEnabled);
2391         pr_info("PaddingUmcFlags[0] = 0x%x\n", pptable->PaddingUmcFlags[0]);
2392         pr_info("PaddingUmcFlags[1] = 0x%x\n", pptable->PaddingUmcFlags[1]);
2393
2394         pr_info("BoardReserved[0] = 0x%x\n", pptable->BoardReserved[0]);
2395         pr_info("BoardReserved[1] = 0x%x\n", pptable->BoardReserved[1]);
2396         pr_info("BoardReserved[2] = 0x%x\n", pptable->BoardReserved[2]);
2397         pr_info("BoardReserved[3] = 0x%x\n", pptable->BoardReserved[3]);
2398         pr_info("BoardReserved[4] = 0x%x\n", pptable->BoardReserved[4]);
2399         pr_info("BoardReserved[5] = 0x%x\n", pptable->BoardReserved[5]);
2400         pr_info("BoardReserved[6] = 0x%x\n", pptable->BoardReserved[6]);
2401         pr_info("BoardReserved[7] = 0x%x\n", pptable->BoardReserved[7]);
2402         pr_info("BoardReserved[8] = 0x%x\n", pptable->BoardReserved[8]);
2403         pr_info("BoardReserved[9] = 0x%x\n", pptable->BoardReserved[9]);
2404         pr_info("BoardReserved[10] = 0x%x\n", pptable->BoardReserved[10]);
2405         pr_info("BoardReserved[11] = 0x%x\n", pptable->BoardReserved[11]);
2406         pr_info("BoardReserved[12] = 0x%x\n", pptable->BoardReserved[12]);
2407         pr_info("BoardReserved[13] = 0x%x\n", pptable->BoardReserved[13]);
2408         pr_info("BoardReserved[14] = 0x%x\n", pptable->BoardReserved[14]);
2409
2410         pr_info("MmHubPadding[0] = 0x%x\n", pptable->MmHubPadding[0]);
2411         pr_info("MmHubPadding[1] = 0x%x\n", pptable->MmHubPadding[1]);
2412         pr_info("MmHubPadding[2] = 0x%x\n", pptable->MmHubPadding[2]);
2413         pr_info("MmHubPadding[3] = 0x%x\n", pptable->MmHubPadding[3]);
2414         pr_info("MmHubPadding[4] = 0x%x\n", pptable->MmHubPadding[4]);
2415         pr_info("MmHubPadding[5] = 0x%x\n", pptable->MmHubPadding[5]);
2416         pr_info("MmHubPadding[6] = 0x%x\n", pptable->MmHubPadding[6]);
2417         pr_info("MmHubPadding[7] = 0x%x\n", pptable->MmHubPadding[7]);
2418 }
2419
2420 static const struct pptable_funcs sienna_cichlid_ppt_funcs = {
2421         .tables_init = sienna_cichlid_tables_init,
2422         .alloc_dpm_context = sienna_cichlid_allocate_dpm_context,
2423         .store_powerplay_table = sienna_cichlid_store_powerplay_table,
2424         .check_powerplay_table = sienna_cichlid_check_powerplay_table,
2425         .append_powerplay_table = sienna_cichlid_append_powerplay_table,
2426         .get_smu_msg_index = sienna_cichlid_get_smu_msg_index,
2427         .get_smu_clk_index = sienna_cichlid_get_smu_clk_index,
2428         .get_smu_feature_index = sienna_cichlid_get_smu_feature_index,
2429         .get_smu_table_index = sienna_cichlid_get_smu_table_index,
2430         .get_smu_power_index = sienna_cichlid_get_pwr_src_index,
2431         .get_workload_type = sienna_cichlid_get_workload_type,
2432         .get_allowed_feature_mask = sienna_cichlid_get_allowed_feature_mask,
2433         .set_default_dpm_table = sienna_cichlid_set_default_dpm_table,
2434         .dpm_set_uvd_enable = sienna_cichlid_dpm_set_uvd_enable,
2435         .dpm_set_jpeg_enable = sienna_cichlid_dpm_set_jpeg_enable,
2436         .get_current_clk_freq_by_table = sienna_cichlid_get_current_clk_freq_by_table,
2437         .print_clk_levels = sienna_cichlid_print_clk_levels,
2438         .force_clk_levels = sienna_cichlid_force_clk_levels,
2439         .populate_umd_state_clk = sienna_cichlid_populate_umd_state_clk,
2440         .get_clock_by_type_with_latency = sienna_cichlid_get_clock_by_type_with_latency,
2441         .pre_display_config_changed = sienna_cichlid_pre_display_config_changed,
2442         .display_config_changed = sienna_cichlid_display_config_changed,
2443         .notify_smc_display_config = sienna_cichlid_notify_smc_display_config,
2444         .force_dpm_limit_value = sienna_cichlid_force_dpm_limit_value,
2445         .unforce_dpm_levels = sienna_cichlid_unforce_dpm_levels,
2446         .is_dpm_running = sienna_cichlid_is_dpm_running,
2447         .get_fan_speed_percent = sienna_cichlid_get_fan_speed_percent,
2448         .get_fan_speed_rpm = sienna_cichlid_get_fan_speed_rpm,
2449         .get_power_profile_mode = sienna_cichlid_get_power_profile_mode,
2450         .set_power_profile_mode = sienna_cichlid_set_power_profile_mode,
2451         .get_profiling_clk_mask = sienna_cichlid_get_profiling_clk_mask,
2452         .set_watermarks_table = sienna_cichlid_set_watermarks_table,
2453         .read_sensor = sienna_cichlid_read_sensor,
2454         .get_uclk_dpm_states = sienna_cichlid_get_uclk_dpm_states,
2455         .set_performance_level = sienna_cichlid_set_performance_level,
2456         .get_thermal_temperature_range = sienna_cichlid_get_thermal_temperature_range,
2457         .display_disable_memory_clock_switch = sienna_cichlid_display_disable_memory_clock_switch,
2458         .get_power_limit = sienna_cichlid_get_power_limit,
2459         .update_pcie_parameters = sienna_cichlid_update_pcie_parameters,
2460         .dump_pptable = sienna_cichlid_dump_pptable,
2461         .init_microcode = smu_v11_0_init_microcode,
2462         .load_microcode = smu_v11_0_load_microcode,
2463         .init_smc_tables = smu_v11_0_init_smc_tables,
2464         .fini_smc_tables = smu_v11_0_fini_smc_tables,
2465         .init_power = smu_v11_0_init_power,
2466         .fini_power = smu_v11_0_fini_power,
2467         .check_fw_status = smu_v11_0_check_fw_status,
2468         .setup_pptable = smu_v11_0_setup_pptable,
2469         .get_vbios_bootup_values = smu_v11_0_get_vbios_bootup_values,
2470         .get_clk_info_from_vbios = smu_v11_0_get_clk_info_from_vbios,
2471         .check_pptable = smu_v11_0_check_pptable,
2472         .parse_pptable = smu_v11_0_parse_pptable,
2473         .populate_smc_tables = smu_v11_0_populate_smc_pptable,
2474         .check_fw_version = smu_v11_0_check_fw_version,
2475         .write_pptable = smu_v11_0_write_pptable,
2476         .set_min_dcef_deep_sleep = smu_v11_0_set_min_dcef_deep_sleep,
2477         .set_driver_table_location = smu_v11_0_set_driver_table_location,
2478         .set_tool_table_location = smu_v11_0_set_tool_table_location,
2479         .notify_memory_pool_location = smu_v11_0_notify_memory_pool_location,
2480         .system_features_control = smu_v11_0_system_features_control,
2481         .send_smc_msg_with_param = smu_v11_0_send_msg_with_param,
2482         .init_display_count = smu_v11_0_init_display_count,
2483         .set_allowed_mask = smu_v11_0_set_allowed_mask,
2484         .get_enabled_mask = smu_v11_0_get_enabled_mask,
2485         .notify_display_change = smu_v11_0_notify_display_change,
2486         .set_power_limit = smu_v11_0_set_power_limit,
2487         .get_current_clk_freq = smu_v11_0_get_current_clk_freq,
2488         .init_max_sustainable_clocks = smu_v11_0_init_max_sustainable_clocks,
2489         .enable_thermal_alert = smu_v11_0_enable_thermal_alert,
2490         .disable_thermal_alert = smu_v11_0_disable_thermal_alert,
2491         .set_deep_sleep_dcefclk = smu_v11_0_set_deep_sleep_dcefclk,
2492         .display_clock_voltage_request = smu_v11_0_display_clock_voltage_request,
2493         .get_fan_control_mode = smu_v11_0_get_fan_control_mode,
2494         .set_fan_control_mode = smu_v11_0_set_fan_control_mode,
2495         .set_fan_speed_percent = smu_v11_0_set_fan_speed_percent,
2496         .set_fan_speed_rpm = smu_v11_0_set_fan_speed_rpm,
2497         .set_xgmi_pstate = smu_v11_0_set_xgmi_pstate,
2498         .gfx_off_control = smu_v11_0_gfx_off_control,
2499         .register_irq_handler = smu_v11_0_register_irq_handler,
2500         .set_azalia_d3_pme = smu_v11_0_set_azalia_d3_pme,
2501         .get_max_sustainable_clocks_by_dc = smu_v11_0_get_max_sustainable_clocks_by_dc,
2502         .baco_is_support= smu_v11_0_baco_is_support,
2503         .baco_get_state = smu_v11_0_baco_get_state,
2504         .baco_set_state = smu_v11_0_baco_set_state,
2505         .baco_enter = smu_v11_0_baco_enter,
2506         .baco_exit = smu_v11_0_baco_exit,
2507         .get_dpm_ultimate_freq = sienna_cichlid_get_dpm_ultimate_freq,
2508         .set_soft_freq_limited_range = sienna_cichlid_set_soft_freq_limited_range,
2509         .override_pcie_parameters = smu_v11_0_override_pcie_parameters,
2510         .get_pptable_power_limit = sienna_cichlid_get_pptable_power_limit,
2511 };
2512
2513 void sienna_cichlid_set_ppt_funcs(struct smu_context *smu)
2514 {
2515         smu->ppt_funcs = &sienna_cichlid_ppt_funcs;
2516 }