Merge branch 'stable-4.13' of git://git.infradead.org/users/pcmoore/audit
[sfrench/cifs-2.6.git] / drivers / gpu / drm / amd / powerplay / hwmgr / vega10_powertune.c
1 /*
2  * Copyright 2016 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 "hwmgr.h"
25 #include "vega10_hwmgr.h"
26 #include "vega10_powertune.h"
27 #include "vega10_smumgr.h"
28 #include "vega10_ppsmc.h"
29 #include "pp_debug.h"
30
31 void vega10_initialize_power_tune_defaults(struct pp_hwmgr *hwmgr)
32 {
33         struct vega10_hwmgr *data = (struct vega10_hwmgr *)(hwmgr->backend);
34         struct phm_ppt_v2_information *table_info =
35                         (struct phm_ppt_v2_information *)(hwmgr->pptable);
36         struct phm_tdp_table *tdp_table = table_info->tdp_table;
37         PPTable_t *table = &(data->smc_state_table.pp_table);
38
39         table->SocketPowerLimit = cpu_to_le16(
40                         tdp_table->usMaximumPowerDeliveryLimit);
41         table->TdcLimit = cpu_to_le16(tdp_table->usTDC);
42         table->EdcLimit = cpu_to_le16(tdp_table->usEDCLimit);
43         table->TedgeLimit = cpu_to_le16(tdp_table->usTemperatureLimitTedge);
44         table->ThotspotLimit = cpu_to_le16(tdp_table->usTemperatureLimitHotspot);
45         table->ThbmLimit = cpu_to_le16(tdp_table->usTemperatureLimitHBM);
46         table->Tvr_socLimit = cpu_to_le16(tdp_table->usTemperatureLimitVrVddc);
47         table->Tvr_memLimit = cpu_to_le16(tdp_table->usTemperatureLimitVrMvdd);
48         table->Tliquid1Limit = cpu_to_le16(tdp_table->usTemperatureLimitLiquid1);
49         table->Tliquid2Limit = cpu_to_le16(tdp_table->usTemperatureLimitLiquid2);
50         table->TplxLimit = cpu_to_le16(tdp_table->usTemperatureLimitPlx);
51         table->LoadLineResistance =
52                         hwmgr->platform_descriptor.LoadLineSlope * 256;
53         table->FitLimit = 0; /* Not used for Vega10 */
54
55         table->Liquid1_I2C_address = tdp_table->ucLiquid1_I2C_address;
56         table->Liquid2_I2C_address = tdp_table->ucLiquid2_I2C_address;
57         table->Vr_I2C_address = tdp_table->ucVr_I2C_address;
58         table->Plx_I2C_address = tdp_table->ucPlx_I2C_address;
59
60         table->Liquid_I2C_LineSCL = tdp_table->ucLiquid_I2C_Line;
61         table->Liquid_I2C_LineSDA = tdp_table->ucLiquid_I2C_LineSDA;
62
63         table->Vr_I2C_LineSCL = tdp_table->ucVr_I2C_Line;
64         table->Vr_I2C_LineSDA = tdp_table->ucVr_I2C_LineSDA;
65
66         table->Plx_I2C_LineSCL = tdp_table->ucPlx_I2C_Line;
67         table->Plx_I2C_LineSDA = tdp_table->ucPlx_I2C_LineSDA;
68 }
69
70 int vega10_set_power_limit(struct pp_hwmgr *hwmgr, uint32_t n)
71 {
72         struct vega10_hwmgr *data =
73                         (struct vega10_hwmgr *)(hwmgr->backend);
74
75         if (data->registry_data.enable_pkg_pwr_tracking_feature)
76                 return smum_send_msg_to_smc_with_parameter(hwmgr->smumgr,
77                                 PPSMC_MSG_SetPptLimit, n);
78
79         return 0;
80 }
81
82 int vega10_enable_power_containment(struct pp_hwmgr *hwmgr)
83 {
84         struct vega10_hwmgr *data =
85                         (struct vega10_hwmgr *)(hwmgr->backend);
86         struct phm_ppt_v2_information *table_info =
87                         (struct phm_ppt_v2_information *)(hwmgr->pptable);
88         struct phm_tdp_table *tdp_table = table_info->tdp_table;
89         uint32_t default_pwr_limit =
90                         (uint32_t)(tdp_table->usMaximumPowerDeliveryLimit);
91         int result = 0;
92
93         if (phm_cap_enabled(hwmgr->platform_descriptor.platformCaps,
94                         PHM_PlatformCaps_PowerContainment)) {
95                 if (data->smu_features[GNLD_PPT].supported)
96                         PP_ASSERT_WITH_CODE(!vega10_enable_smc_features(hwmgr->smumgr,
97                                         true, data->smu_features[GNLD_PPT].smu_feature_bitmap),
98                                         "Attempt to enable PPT feature Failed!",
99                                         data->smu_features[GNLD_PPT].supported = false);
100
101                 if (data->smu_features[GNLD_TDC].supported)
102                         PP_ASSERT_WITH_CODE(!vega10_enable_smc_features(hwmgr->smumgr,
103                                         true, data->smu_features[GNLD_TDC].smu_feature_bitmap),
104                                         "Attempt to enable PPT feature Failed!",
105                                         data->smu_features[GNLD_TDC].supported = false);
106
107                 result = vega10_set_power_limit(hwmgr, default_pwr_limit);
108                 PP_ASSERT_WITH_CODE(!result,
109                                 "Failed to set Default Power Limit in SMC!",
110                                 return result);
111         }
112
113         return result;
114 }
115
116 int vega10_disable_power_containment(struct pp_hwmgr *hwmgr)
117 {
118         struct vega10_hwmgr *data =
119                         (struct vega10_hwmgr *)(hwmgr->backend);
120
121         if (phm_cap_enabled(hwmgr->platform_descriptor.platformCaps,
122                         PHM_PlatformCaps_PowerContainment)) {
123                 if (data->smu_features[GNLD_PPT].supported)
124                         PP_ASSERT_WITH_CODE(!vega10_enable_smc_features(hwmgr->smumgr,
125                                         false, data->smu_features[GNLD_PPT].smu_feature_bitmap),
126                                         "Attempt to disable PPT feature Failed!",
127                                         data->smu_features[GNLD_PPT].supported = false);
128
129                 if (data->smu_features[GNLD_TDC].supported)
130                         PP_ASSERT_WITH_CODE(!vega10_enable_smc_features(hwmgr->smumgr,
131                                         false, data->smu_features[GNLD_TDC].smu_feature_bitmap),
132                                         "Attempt to disable PPT feature Failed!",
133                                         data->smu_features[GNLD_TDC].supported = false);
134         }
135
136         return 0;
137 }
138
139 static int vega10_set_overdrive_target_percentage(struct pp_hwmgr *hwmgr,
140                 uint32_t adjust_percent)
141 {
142         return smum_send_msg_to_smc_with_parameter(hwmgr->smumgr,
143                         PPSMC_MSG_OverDriveSetPercentage, adjust_percent);
144 }
145
146 int vega10_power_control_set_level(struct pp_hwmgr *hwmgr)
147 {
148         int adjust_percent, result = 0;
149
150         if (phm_cap_enabled(hwmgr->platform_descriptor.platformCaps,
151                         PHM_PlatformCaps_PowerContainment)) {
152                 adjust_percent =
153                                 hwmgr->platform_descriptor.TDPAdjustmentPolarity ?
154                                 hwmgr->platform_descriptor.TDPAdjustment :
155                                 (-1 * hwmgr->platform_descriptor.TDPAdjustment);
156                 result = vega10_set_overdrive_target_percentage(hwmgr,
157                                 (uint32_t)adjust_percent);
158         }
159         return result;
160 }