aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu
diff options
context:
space:
mode:
authorEvan Quan <evan.quan@amd.com>2018-09-17 02:59:54 -0400
committerAlex Deucher <alexander.deucher@amd.com>2018-09-19 13:38:02 -0400
commit32f2a0d117769bdca7f7ee6224659f2c688ebc85 (patch)
treee8eaeffdd76b415db03428350474a361270cf052 /drivers/gpu
parentb1f82cb21231ccfec3c15b628f8deed778cce22b (diff)
drm/amd/powerplay: retrieve the updated clock table after OD
With OD settings applied, the clock table will be updated accordingly. We need to retrieve the new clock tables then. Signed-off-by: Evan Quan <evan.quan@amd.com> Acked-by: Alex Deucher <alexander.deucher@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
Diffstat (limited to 'drivers/gpu')
-rw-r--r--drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.c114
-rw-r--r--drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.h2
2 files changed, 90 insertions, 26 deletions
diff --git a/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.c b/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.c
index 4f9bf6049d1c..d45cbfe8e184 100644
--- a/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.c
+++ b/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.c
@@ -514,6 +514,47 @@ static int vega20_setup_single_dpm_table(struct pp_hwmgr *hwmgr,
514 return ret; 514 return ret;
515} 515}
516 516
517static int vega20_setup_gfxclk_dpm_table(struct pp_hwmgr *hwmgr)
518{
519 struct vega20_hwmgr *data =
520 (struct vega20_hwmgr *)(hwmgr->backend);
521 struct vega20_single_dpm_table *dpm_table;
522 int ret = 0;
523
524 dpm_table = &(data->dpm_table.gfx_table);
525 if (data->smu_features[GNLD_DPM_GFXCLK].enabled) {
526 ret = vega20_setup_single_dpm_table(hwmgr, dpm_table, PPCLK_GFXCLK);
527 PP_ASSERT_WITH_CODE(!ret,
528 "[SetupDefaultDpmTable] failed to get gfxclk dpm levels!",
529 return ret);
530 } else {
531 dpm_table->count = 1;
532 dpm_table->dpm_levels[0].value = data->vbios_boot_state.gfx_clock / 100;
533 }
534
535 return ret;
536}
537
538static int vega20_setup_memclk_dpm_table(struct pp_hwmgr *hwmgr)
539{
540 struct vega20_hwmgr *data =
541 (struct vega20_hwmgr *)(hwmgr->backend);
542 struct vega20_single_dpm_table *dpm_table;
543 int ret = 0;
544
545 dpm_table = &(data->dpm_table.mem_table);
546 if (data->smu_features[GNLD_DPM_UCLK].enabled) {
547 ret = vega20_setup_single_dpm_table(hwmgr, dpm_table, PPCLK_UCLK);
548 PP_ASSERT_WITH_CODE(!ret,
549 "[SetupDefaultDpmTable] failed to get memclk dpm levels!",
550 return ret);
551 } else {
552 dpm_table->count = 1;
553 dpm_table->dpm_levels[0].value = data->vbios_boot_state.mem_clock / 100;
554 }
555
556 return ret;
557}
517 558
518/* 559/*
519 * This function is to initialize all DPM state tables 560 * This function is to initialize all DPM state tables
@@ -547,28 +588,16 @@ static int vega20_setup_default_dpm_tables(struct pp_hwmgr *hwmgr)
547 588
548 /* gfxclk */ 589 /* gfxclk */
549 dpm_table = &(data->dpm_table.gfx_table); 590 dpm_table = &(data->dpm_table.gfx_table);
550 if (data->smu_features[GNLD_DPM_GFXCLK].enabled) { 591 ret = vega20_setup_gfxclk_dpm_table(hwmgr);
551 ret = vega20_setup_single_dpm_table(hwmgr, dpm_table, PPCLK_GFXCLK); 592 if (ret)
552 PP_ASSERT_WITH_CODE(!ret, 593 return ret;
553 "[SetupDefaultDpmTable] failed to get gfxclk dpm levels!",
554 return ret);
555 } else {
556 dpm_table->count = 1;
557 dpm_table->dpm_levels[0].value = data->vbios_boot_state.gfx_clock / 100;
558 }
559 vega20_init_dpm_state(&(dpm_table->dpm_state)); 594 vega20_init_dpm_state(&(dpm_table->dpm_state));
560 595
561 /* memclk */ 596 /* memclk */
562 dpm_table = &(data->dpm_table.mem_table); 597 dpm_table = &(data->dpm_table.mem_table);
563 if (data->smu_features[GNLD_DPM_UCLK].enabled) { 598 ret = vega20_setup_memclk_dpm_table(hwmgr);
564 ret = vega20_setup_single_dpm_table(hwmgr, dpm_table, PPCLK_UCLK); 599 if (ret)
565 PP_ASSERT_WITH_CODE(!ret, 600 return ret;
566 "[SetupDefaultDpmTable] failed to get memclk dpm levels!",
567 return ret);
568 } else {
569 dpm_table->count = 1;
570 dpm_table->dpm_levels[0].value = data->vbios_boot_state.mem_clock / 100;
571 }
572 vega20_init_dpm_state(&(dpm_table->dpm_state)); 601 vega20_init_dpm_state(&(dpm_table->dpm_state));
573 602
574 /* eclk */ 603 /* eclk */
@@ -1181,6 +1210,9 @@ static int vega20_od8_set_settings(
1181{ 1210{
1182 OverDriveTable_t od_table; 1211 OverDriveTable_t od_table;
1183 int ret = 0; 1212 int ret = 0;
1213 struct vega20_hwmgr *data = (struct vega20_hwmgr *)(hwmgr->backend);
1214 struct vega20_od8_single_setting *od8_settings =
1215 data->od8_settings.od8_settings_array;
1184 1216
1185 ret = vega20_copy_table_from_smc(hwmgr, (uint8_t *)(&od_table), TABLE_OVERDRIVE); 1217 ret = vega20_copy_table_from_smc(hwmgr, (uint8_t *)(&od_table), TABLE_OVERDRIVE);
1186 PP_ASSERT_WITH_CODE(!ret, 1218 PP_ASSERT_WITH_CODE(!ret,
@@ -1192,6 +1224,10 @@ static int vega20_od8_set_settings(
1192 od_table.GfxclkFmin = (uint16_t)value; 1224 od_table.GfxclkFmin = (uint16_t)value;
1193 break; 1225 break;
1194 case OD8_SETTING_GFXCLK_FMAX: 1226 case OD8_SETTING_GFXCLK_FMAX:
1227 if (value < od8_settings[OD8_SETTING_GFXCLK_FMAX].min_value ||
1228 value > od8_settings[OD8_SETTING_GFXCLK_FMAX].max_value)
1229 return -EINVAL;
1230
1195 od_table.GfxclkFmax = (uint16_t)value; 1231 od_table.GfxclkFmax = (uint16_t)value;
1196 break; 1232 break;
1197 case OD8_SETTING_GFXCLK_FREQ1: 1233 case OD8_SETTING_GFXCLK_FREQ1:
@@ -1213,6 +1249,9 @@ static int vega20_od8_set_settings(
1213 od_table.GfxclkVolt3 = (uint16_t)value; 1249 od_table.GfxclkVolt3 = (uint16_t)value;
1214 break; 1250 break;
1215 case OD8_SETTING_UCLK_FMAX: 1251 case OD8_SETTING_UCLK_FMAX:
1252 if (value < od8_settings[OD8_SETTING_UCLK_FMAX].min_value ||
1253 value > od8_settings[OD8_SETTING_UCLK_FMAX].max_value)
1254 return -EINVAL;
1216 od_table.UclkFmax = (uint16_t)value; 1255 od_table.UclkFmax = (uint16_t)value;
1217 break; 1256 break;
1218 case OD8_SETTING_POWER_PERCENTAGE: 1257 case OD8_SETTING_POWER_PERCENTAGE:
@@ -1262,8 +1301,6 @@ static int vega20_set_sclk_od(
1262 struct pp_hwmgr *hwmgr, uint32_t value) 1301 struct pp_hwmgr *hwmgr, uint32_t value)
1263{ 1302{
1264 struct vega20_hwmgr *data = hwmgr->backend; 1303 struct vega20_hwmgr *data = hwmgr->backend;
1265 struct vega20_single_dpm_table *sclk_table =
1266 &(data->dpm_table.gfx_table);
1267 struct vega20_single_dpm_table *golden_sclk_table = 1304 struct vega20_single_dpm_table *golden_sclk_table =
1268 &(data->golden_dpm_table.gfx_table); 1305 &(data->golden_dpm_table.gfx_table);
1269 uint32_t od_sclk; 1306 uint32_t od_sclk;
@@ -1278,8 +1315,8 @@ static int vega20_set_sclk_od(
1278 "[SetSclkOD] failed to set od gfxclk!", 1315 "[SetSclkOD] failed to set od gfxclk!",
1279 return ret); 1316 return ret);
1280 1317
1281 /* refresh gfxclk table */ 1318 /* retrieve updated gfxclk table */
1282 ret = vega20_setup_single_dpm_table(hwmgr, sclk_table, PPCLK_GFXCLK); 1319 ret = vega20_setup_gfxclk_dpm_table(hwmgr);
1283 PP_ASSERT_WITH_CODE(!ret, 1320 PP_ASSERT_WITH_CODE(!ret,
1284 "[SetSclkOD] failed to refresh gfxclk table!", 1321 "[SetSclkOD] failed to refresh gfxclk table!",
1285 return ret); 1322 return ret);
@@ -1309,8 +1346,6 @@ static int vega20_set_mclk_od(
1309 struct pp_hwmgr *hwmgr, uint32_t value) 1346 struct pp_hwmgr *hwmgr, uint32_t value)
1310{ 1347{
1311 struct vega20_hwmgr *data = hwmgr->backend; 1348 struct vega20_hwmgr *data = hwmgr->backend;
1312 struct vega20_single_dpm_table *mclk_table =
1313 &(data->dpm_table.mem_table);
1314 struct vega20_single_dpm_table *golden_mclk_table = 1349 struct vega20_single_dpm_table *golden_mclk_table =
1315 &(data->golden_dpm_table.mem_table); 1350 &(data->golden_dpm_table.mem_table);
1316 uint32_t od_mclk; 1351 uint32_t od_mclk;
@@ -1325,8 +1360,8 @@ static int vega20_set_mclk_od(
1325 "[SetMclkOD] failed to set od memclk!", 1360 "[SetMclkOD] failed to set od memclk!",
1326 return ret); 1361 return ret);
1327 1362
1328 /* refresh memclk table */ 1363 /* retrieve updated memclk table */
1329 ret = vega20_setup_single_dpm_table(hwmgr, mclk_table, PPCLK_UCLK); 1364 ret = vega20_setup_memclk_dpm_table(hwmgr);
1330 PP_ASSERT_WITH_CODE(!ret, 1365 PP_ASSERT_WITH_CODE(!ret,
1331 "[SetMclkOD] failed to refresh memclk table!", 1366 "[SetMclkOD] failed to refresh memclk table!",
1332 return ret); 1367 return ret);
@@ -2451,6 +2486,10 @@ static int vega20_odn_edit_dpm_table(struct pp_hwmgr *hwmgr,
2451 return -EINVAL; 2486 return -EINVAL;
2452 } 2487 }
2453 2488
2489 if ((input_index == 0 && od_table->GfxclkFmin != input_clk) ||
2490 (input_index == 1 && od_table->GfxclkFmax != input_clk))
2491 data->gfxclk_overdrive = true;
2492
2454 if (input_index == 0) 2493 if (input_index == 0)
2455 od_table->GfxclkFmin = input_clk; 2494 od_table->GfxclkFmin = input_clk;
2456 else 2495 else
@@ -2495,6 +2534,9 @@ static int vega20_odn_edit_dpm_table(struct pp_hwmgr *hwmgr,
2495 return -EINVAL; 2534 return -EINVAL;
2496 } 2535 }
2497 2536
2537 if (input_index == 1 && od_table->UclkFmax != input_clk)
2538 data->memclk_overdrive = true;
2539
2498 od_table->UclkFmax = input_clk; 2540 od_table->UclkFmax = input_clk;
2499 } 2541 }
2500 2542
@@ -2567,6 +2609,9 @@ static int vega20_odn_edit_dpm_table(struct pp_hwmgr *hwmgr,
2567 break; 2609 break;
2568 2610
2569 case PP_OD_RESTORE_DEFAULT_TABLE: 2611 case PP_OD_RESTORE_DEFAULT_TABLE:
2612 data->gfxclk_overdrive = false;
2613 data->memclk_overdrive = false;
2614
2570 ret = vega20_copy_table_from_smc(hwmgr, 2615 ret = vega20_copy_table_from_smc(hwmgr,
2571 (uint8_t *)od_table, 2616 (uint8_t *)od_table,
2572 TABLE_OVERDRIVE); 2617 TABLE_OVERDRIVE);
@@ -2583,6 +2628,23 @@ static int vega20_odn_edit_dpm_table(struct pp_hwmgr *hwmgr,
2583 "Failed to import overdrive table!", 2628 "Failed to import overdrive table!",
2584 return ret); 2629 return ret);
2585 2630
2631 /* retrieve updated gfxclk table */
2632 if (data->gfxclk_overdrive) {
2633 data->gfxclk_overdrive = false;
2634
2635 ret = vega20_setup_gfxclk_dpm_table(hwmgr);
2636 if (ret)
2637 return ret;
2638 }
2639
2640 /* retrieve updated memclk table */
2641 if (data->memclk_overdrive) {
2642 data->memclk_overdrive = false;
2643
2644 ret = vega20_setup_memclk_dpm_table(hwmgr);
2645 if (ret)
2646 return ret;
2647 }
2586 break; 2648 break;
2587 2649
2588 default: 2650 default:
diff --git a/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.h b/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.h
index b71a5f25c734..56fe6a0d42e8 100644
--- a/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.h
+++ b/drivers/gpu/drm/amd/powerplay/hwmgr/vega20_hwmgr.h
@@ -502,6 +502,8 @@ struct vega20_hwmgr {
502 502
503 /* ---- Overdrive next setting ---- */ 503 /* ---- Overdrive next setting ---- */
504 struct vega20_odn_data odn_data; 504 struct vega20_odn_data odn_data;
505 bool gfxclk_overdrive;
506 bool memclk_overdrive;
505 507
506 /* ---- Overdrive8 Setting ---- */ 508 /* ---- Overdrive8 Setting ---- */
507 struct vega20_od8_settings od8_settings; 509 struct vega20_od8_settings od8_settings;