aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/radeon/si_dpm.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/drm/radeon/si_dpm.c')
-rw-r--r--drivers/gpu/drm/radeon/si_dpm.c80
1 files changed, 67 insertions, 13 deletions
diff --git a/drivers/gpu/drm/radeon/si_dpm.c b/drivers/gpu/drm/radeon/si_dpm.c
index 88699e3cd868..5be9b4e72350 100644
--- a/drivers/gpu/drm/radeon/si_dpm.c
+++ b/drivers/gpu/drm/radeon/si_dpm.c
@@ -1753,6 +1753,9 @@ static int si_calculate_sclk_params(struct radeon_device *rdev,
1753 u32 engine_clock, 1753 u32 engine_clock,
1754 SISLANDS_SMC_SCLK_VALUE *sclk); 1754 SISLANDS_SMC_SCLK_VALUE *sclk);
1755 1755
1756extern void si_update_cg(struct radeon_device *rdev,
1757 u32 block, bool enable);
1758
1756static struct si_power_info *si_get_pi(struct radeon_device *rdev) 1759static struct si_power_info *si_get_pi(struct radeon_device *rdev)
1757{ 1760{
1758 struct si_power_info *pi = rdev->pm.dpm.priv; 1761 struct si_power_info *pi = rdev->pm.dpm.priv;
@@ -3663,7 +3666,7 @@ static void si_clear_vc(struct radeon_device *rdev)
3663 WREG32(CG_FTV, 0); 3666 WREG32(CG_FTV, 0);
3664} 3667}
3665 3668
3666static u8 si_get_ddr3_mclk_frequency_ratio(u32 memory_clock) 3669u8 si_get_ddr3_mclk_frequency_ratio(u32 memory_clock)
3667{ 3670{
3668 u8 mc_para_index; 3671 u8 mc_para_index;
3669 3672
@@ -3676,7 +3679,7 @@ static u8 si_get_ddr3_mclk_frequency_ratio(u32 memory_clock)
3676 return mc_para_index; 3679 return mc_para_index;
3677} 3680}
3678 3681
3679static u8 si_get_mclk_frequency_ratio(u32 memory_clock, bool strobe_mode) 3682u8 si_get_mclk_frequency_ratio(u32 memory_clock, bool strobe_mode)
3680{ 3683{
3681 u8 mc_para_index; 3684 u8 mc_para_index;
3682 3685
@@ -3758,20 +3761,21 @@ static bool si_validate_phase_shedding_tables(struct radeon_device *rdev,
3758 return true; 3761 return true;
3759} 3762}
3760 3763
3761static void si_trim_voltage_table_to_fit_state_table(struct radeon_device *rdev, 3764void si_trim_voltage_table_to_fit_state_table(struct radeon_device *rdev,
3762 struct atom_voltage_table *voltage_table) 3765 u32 max_voltage_steps,
3766 struct atom_voltage_table *voltage_table)
3763{ 3767{
3764 unsigned int i, diff; 3768 unsigned int i, diff;
3765 3769
3766 if (voltage_table->count <= SISLANDS_MAX_NO_VREG_STEPS) 3770 if (voltage_table->count <= max_voltage_steps)
3767 return; 3771 return;
3768 3772
3769 diff = voltage_table->count - SISLANDS_MAX_NO_VREG_STEPS; 3773 diff = voltage_table->count - max_voltage_steps;
3770 3774
3771 for (i= 0; i < SISLANDS_MAX_NO_VREG_STEPS; i++) 3775 for (i= 0; i < max_voltage_steps; i++)
3772 voltage_table->entries[i] = voltage_table->entries[i + diff]; 3776 voltage_table->entries[i] = voltage_table->entries[i + diff];
3773 3777
3774 voltage_table->count = SISLANDS_MAX_NO_VREG_STEPS; 3778 voltage_table->count = max_voltage_steps;
3775} 3779}
3776 3780
3777static int si_construct_voltage_tables(struct radeon_device *rdev) 3781static int si_construct_voltage_tables(struct radeon_device *rdev)
@@ -3787,7 +3791,9 @@ static int si_construct_voltage_tables(struct radeon_device *rdev)
3787 return ret; 3791 return ret;
3788 3792
3789 if (eg_pi->vddc_voltage_table.count > SISLANDS_MAX_NO_VREG_STEPS) 3793 if (eg_pi->vddc_voltage_table.count > SISLANDS_MAX_NO_VREG_STEPS)
3790 si_trim_voltage_table_to_fit_state_table(rdev, &eg_pi->vddc_voltage_table); 3794 si_trim_voltage_table_to_fit_state_table(rdev,
3795 SISLANDS_MAX_NO_VREG_STEPS,
3796 &eg_pi->vddc_voltage_table);
3791 3797
3792 if (eg_pi->vddci_control) { 3798 if (eg_pi->vddci_control) {
3793 ret = radeon_atom_get_voltage_table(rdev, VOLTAGE_TYPE_VDDCI, 3799 ret = radeon_atom_get_voltage_table(rdev, VOLTAGE_TYPE_VDDCI,
@@ -3796,7 +3802,9 @@ static int si_construct_voltage_tables(struct radeon_device *rdev)
3796 return ret; 3802 return ret;
3797 3803
3798 if (eg_pi->vddci_voltage_table.count > SISLANDS_MAX_NO_VREG_STEPS) 3804 if (eg_pi->vddci_voltage_table.count > SISLANDS_MAX_NO_VREG_STEPS)
3799 si_trim_voltage_table_to_fit_state_table(rdev, &eg_pi->vddci_voltage_table); 3805 si_trim_voltage_table_to_fit_state_table(rdev,
3806 SISLANDS_MAX_NO_VREG_STEPS,
3807 &eg_pi->vddci_voltage_table);
3800 } 3808 }
3801 3809
3802 if (pi->mvdd_control) { 3810 if (pi->mvdd_control) {
@@ -3814,7 +3822,9 @@ static int si_construct_voltage_tables(struct radeon_device *rdev)
3814 } 3822 }
3815 3823
3816 if (si_pi->mvdd_voltage_table.count > SISLANDS_MAX_NO_VREG_STEPS) 3824 if (si_pi->mvdd_voltage_table.count > SISLANDS_MAX_NO_VREG_STEPS)
3817 si_trim_voltage_table_to_fit_state_table(rdev, &si_pi->mvdd_voltage_table); 3825 si_trim_voltage_table_to_fit_state_table(rdev,
3826 SISLANDS_MAX_NO_VREG_STEPS,
3827 &si_pi->mvdd_voltage_table);
3818 } 3828 }
3819 3829
3820 if (si_pi->vddc_phase_shed_control) { 3830 if (si_pi->vddc_phase_shed_control) {
@@ -5752,6 +5762,13 @@ int si_dpm_enable(struct radeon_device *rdev)
5752 struct radeon_ps *boot_ps = rdev->pm.dpm.boot_ps; 5762 struct radeon_ps *boot_ps = rdev->pm.dpm.boot_ps;
5753 int ret; 5763 int ret;
5754 5764
5765 si_update_cg(rdev, (RADEON_CG_BLOCK_GFX |
5766 RADEON_CG_BLOCK_MC |
5767 RADEON_CG_BLOCK_SDMA |
5768 RADEON_CG_BLOCK_BIF |
5769 RADEON_CG_BLOCK_UVD |
5770 RADEON_CG_BLOCK_HDP), false);
5771
5755 if (si_is_smc_running(rdev)) 5772 if (si_is_smc_running(rdev))
5756 return -EINVAL; 5773 return -EINVAL;
5757 if (pi->voltage_control) 5774 if (pi->voltage_control)
@@ -5871,6 +5888,13 @@ int si_dpm_enable(struct radeon_device *rdev)
5871 5888
5872 si_enable_auto_throttle_source(rdev, RADEON_DPM_AUTO_THROTTLE_SRC_THERMAL, true); 5889 si_enable_auto_throttle_source(rdev, RADEON_DPM_AUTO_THROTTLE_SRC_THERMAL, true);
5873 5890
5891 si_update_cg(rdev, (RADEON_CG_BLOCK_GFX |
5892 RADEON_CG_BLOCK_MC |
5893 RADEON_CG_BLOCK_SDMA |
5894 RADEON_CG_BLOCK_BIF |
5895 RADEON_CG_BLOCK_UVD |
5896 RADEON_CG_BLOCK_HDP), true);
5897
5874 ni_update_current_ps(rdev, boot_ps); 5898 ni_update_current_ps(rdev, boot_ps);
5875 5899
5876 return 0; 5900 return 0;
@@ -5881,6 +5905,13 @@ void si_dpm_disable(struct radeon_device *rdev)
5881 struct rv7xx_power_info *pi = rv770_get_pi(rdev); 5905 struct rv7xx_power_info *pi = rv770_get_pi(rdev);
5882 struct radeon_ps *boot_ps = rdev->pm.dpm.boot_ps; 5906 struct radeon_ps *boot_ps = rdev->pm.dpm.boot_ps;
5883 5907
5908 si_update_cg(rdev, (RADEON_CG_BLOCK_GFX |
5909 RADEON_CG_BLOCK_MC |
5910 RADEON_CG_BLOCK_SDMA |
5911 RADEON_CG_BLOCK_BIF |
5912 RADEON_CG_BLOCK_UVD |
5913 RADEON_CG_BLOCK_HDP), false);
5914
5884 if (!si_is_smc_running(rdev)) 5915 if (!si_is_smc_running(rdev))
5885 return; 5916 return;
5886 si_disable_ulv(rdev); 5917 si_disable_ulv(rdev);
@@ -5945,6 +5976,13 @@ int si_dpm_set_power_state(struct radeon_device *rdev)
5945 struct radeon_ps *old_ps = &eg_pi->current_rps; 5976 struct radeon_ps *old_ps = &eg_pi->current_rps;
5946 int ret; 5977 int ret;
5947 5978
5979 si_update_cg(rdev, (RADEON_CG_BLOCK_GFX |
5980 RADEON_CG_BLOCK_MC |
5981 RADEON_CG_BLOCK_SDMA |
5982 RADEON_CG_BLOCK_BIF |
5983 RADEON_CG_BLOCK_UVD |
5984 RADEON_CG_BLOCK_HDP), false);
5985
5948 ret = si_disable_ulv(rdev); 5986 ret = si_disable_ulv(rdev);
5949 if (ret) { 5987 if (ret) {
5950 DRM_ERROR("si_disable_ulv failed\n"); 5988 DRM_ERROR("si_disable_ulv failed\n");
@@ -6043,6 +6081,13 @@ int si_dpm_set_power_state(struct radeon_device *rdev)
6043 return ret; 6081 return ret;
6044 } 6082 }
6045 6083
6084 si_update_cg(rdev, (RADEON_CG_BLOCK_GFX |
6085 RADEON_CG_BLOCK_MC |
6086 RADEON_CG_BLOCK_SDMA |
6087 RADEON_CG_BLOCK_BIF |
6088 RADEON_CG_BLOCK_UVD |
6089 RADEON_CG_BLOCK_HDP), true);
6090
6046 return 0; 6091 return 0;
6047} 6092}
6048 6093
@@ -6232,6 +6277,7 @@ static int si_parse_power_table(struct radeon_device *rdev)
6232 rdev->pm.dpm.backbias_response_time = le16_to_cpu(power_info->pplib.usBackbiasTime); 6277 rdev->pm.dpm.backbias_response_time = le16_to_cpu(power_info->pplib.usBackbiasTime);
6233 rdev->pm.dpm.voltage_response_time = le16_to_cpu(power_info->pplib.usVoltageTime); 6278 rdev->pm.dpm.voltage_response_time = le16_to_cpu(power_info->pplib.usVoltageTime);
6234 for (i = 0; i < state_array->ucNumEntries; i++) { 6279 for (i = 0; i < state_array->ucNumEntries; i++) {
6280 u8 *idx;
6235 power_state = (union pplib_power_state *)power_state_offset; 6281 power_state = (union pplib_power_state *)power_state_offset;
6236 non_clock_array_index = power_state->v2.nonClockInfoIndex; 6282 non_clock_array_index = power_state->v2.nonClockInfoIndex;
6237 non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) 6283 non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *)
@@ -6248,14 +6294,16 @@ static int si_parse_power_table(struct radeon_device *rdev)
6248 non_clock_info, 6294 non_clock_info,
6249 non_clock_info_array->ucEntrySize); 6295 non_clock_info_array->ucEntrySize);
6250 k = 0; 6296 k = 0;
6297 idx = (u8 *)&power_state->v2.clockInfoIndex[0];
6251 for (j = 0; j < power_state->v2.ucNumDPMLevels; j++) { 6298 for (j = 0; j < power_state->v2.ucNumDPMLevels; j++) {
6252 clock_array_index = power_state->v2.clockInfoIndex[j]; 6299 clock_array_index = idx[j];
6253 if (clock_array_index >= clock_info_array->ucNumEntries) 6300 if (clock_array_index >= clock_info_array->ucNumEntries)
6254 continue; 6301 continue;
6255 if (k >= SISLANDS_MAX_HARDWARE_POWERLEVELS) 6302 if (k >= SISLANDS_MAX_HARDWARE_POWERLEVELS)
6256 break; 6303 break;
6257 clock_info = (union pplib_clock_info *) 6304 clock_info = (union pplib_clock_info *)
6258 &clock_info_array->clockInfo[clock_array_index * clock_info_array->ucEntrySize]; 6305 ((u8 *)&clock_info_array->clockInfo[0] +
6306 (clock_array_index * clock_info_array->ucEntrySize));
6259 si_parse_pplib_clock_info(rdev, 6307 si_parse_pplib_clock_info(rdev,
6260 &rdev->pm.dpm.ps[i], k, 6308 &rdev->pm.dpm.ps[i], k,
6261 clock_info); 6309 clock_info);
@@ -6401,6 +6449,12 @@ int si_dpm_init(struct radeon_device *rdev)
6401 6449
6402 si_initialize_powertune_defaults(rdev); 6450 si_initialize_powertune_defaults(rdev);
6403 6451
6452 /* make sure dc limits are valid */
6453 if ((rdev->pm.dpm.dyn_state.max_clock_voltage_on_dc.sclk == 0) ||
6454 (rdev->pm.dpm.dyn_state.max_clock_voltage_on_dc.mclk == 0))
6455 rdev->pm.dpm.dyn_state.max_clock_voltage_on_dc =
6456 rdev->pm.dpm.dyn_state.max_clock_voltage_on_ac;
6457
6404 return 0; 6458 return 0;
6405} 6459}
6406 6460