Skip to content

Commit 1958946

Browse files
Ma Junalexdeucher
authored andcommitted
drm/amd/pm: Support for getting power1_cap_min value
Support for getting power1_cap_min value on smu13 and smu11. For other Asics, we still use 0 as the default value. Signed-off-by: Ma Jun <Jun.Ma2@amd.com> Reviewed-by: Kenneth Feng <kenneth.feng@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
1 parent afcf949 commit 1958946

12 files changed

Lines changed: 148 additions & 88 deletions

File tree

drivers/gpu/drm/amd/pm/amdgpu_pm.c

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2921,14 +2921,6 @@ static ssize_t amdgpu_hwmon_show_power_input(struct device *dev,
29212921
return sysfs_emit(buf, "%zd\n", val);
29222922
}
29232923

2924-
static ssize_t amdgpu_hwmon_show_power_cap_min(struct device *dev,
2925-
struct device_attribute *attr,
2926-
char *buf)
2927-
{
2928-
return sysfs_emit(buf, "%i\n", 0);
2929-
}
2930-
2931-
29322924
static ssize_t amdgpu_hwmon_show_power_cap_generic(struct device *dev,
29332925
struct device_attribute *attr,
29342926
char *buf,
@@ -2965,6 +2957,12 @@ static ssize_t amdgpu_hwmon_show_power_cap_generic(struct device *dev,
29652957
return size;
29662958
}
29672959

2960+
static ssize_t amdgpu_hwmon_show_power_cap_min(struct device *dev,
2961+
struct device_attribute *attr,
2962+
char *buf)
2963+
{
2964+
return amdgpu_hwmon_show_power_cap_generic(dev, attr, buf, PP_PWR_LIMIT_MIN);
2965+
}
29682966

29692967
static ssize_t amdgpu_hwmon_show_power_cap_max(struct device *dev,
29702968
struct device_attribute *attr,

drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -849,7 +849,8 @@ static int smu_late_init(void *handle)
849849
ret = smu_get_asic_power_limits(smu,
850850
&smu->current_power_limit,
851851
&smu->default_power_limit,
852-
&smu->max_power_limit);
852+
&smu->max_power_limit,
853+
&smu->min_power_limit);
853854
if (ret) {
854855
dev_err(adev->dev, "Failed to get asic power limits!\n");
855856
return ret;
@@ -2447,6 +2448,8 @@ int smu_get_power_limit(void *handle,
24472448
limit_level = SMU_PPT_LIMIT_MAX;
24482449
break;
24492450
case PP_PWR_LIMIT_MIN:
2451+
limit_level = SMU_PPT_LIMIT_MIN;
2452+
break;
24502453
default:
24512454
return -EOPNOTSUPP;
24522455
break;
@@ -2466,8 +2469,7 @@ int smu_get_power_limit(void *handle,
24662469
case IP_VERSION(11, 0, 13):
24672470
ret = smu_get_asic_power_limits(smu,
24682471
&smu->current_power_limit,
2469-
NULL,
2470-
NULL);
2472+
NULL, NULL, NULL);
24712473
break;
24722474
default:
24732475
break;
@@ -2480,6 +2482,9 @@ int smu_get_power_limit(void *handle,
24802482
case SMU_PPT_LIMIT_MAX:
24812483
*limit = smu->max_power_limit;
24822484
break;
2485+
case SMU_PPT_LIMIT_MIN:
2486+
*limit = smu->min_power_limit;
2487+
break;
24832488
default:
24842489
break;
24852490
}
@@ -2502,10 +2507,10 @@ static int smu_set_power_limit(void *handle, uint32_t limit)
25022507
if (smu->ppt_funcs->set_power_limit)
25032508
return smu->ppt_funcs->set_power_limit(smu, limit_type, limit);
25042509

2505-
if (limit > smu->max_power_limit) {
2510+
if ((limit > smu->max_power_limit) || (limit < smu->min_power_limit)) {
25062511
dev_err(smu->adev->dev,
2507-
"New power limit (%d) is over the max allowed %d\n",
2508-
limit, smu->max_power_limit);
2512+
"New power limit (%d) is out of range [%d,%d]\n",
2513+
limit, smu->min_power_limit, smu->max_power_limit);
25092514
return -EINVAL;
25102515
}
25112516

drivers/gpu/drm/amd/pm/swsmu/inc/amdgpu_smu.h

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -500,6 +500,7 @@ struct smu_context {
500500
uint32_t current_power_limit;
501501
uint32_t default_power_limit;
502502
uint32_t max_power_limit;
503+
uint32_t min_power_limit;
503504

504505
/* soft pptable */
505506
uint32_t ppt_offset_bytes;
@@ -821,9 +822,10 @@ struct pptable_funcs {
821822
* @get_power_limit: Get the device's power limits.
822823
*/
823824
int (*get_power_limit)(struct smu_context *smu,
824-
uint32_t *current_power_limit,
825-
uint32_t *default_power_limit,
826-
uint32_t *max_power_limit);
825+
uint32_t *current_power_limit,
826+
uint32_t *default_power_limit,
827+
uint32_t *max_power_limit,
828+
uint32_t *min_power_limit);
827829

828830
/**
829831
* @get_ppt_limit: Get the device's ppt limits.

drivers/gpu/drm/amd/pm/swsmu/smu11/arcturus_ppt.c

Lines changed: 21 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1278,14 +1278,15 @@ static int arcturus_get_fan_parameters(struct smu_context *smu)
12781278
}
12791279

12801280
static int arcturus_get_power_limit(struct smu_context *smu,
1281-
uint32_t *current_power_limit,
1282-
uint32_t *default_power_limit,
1283-
uint32_t *max_power_limit)
1281+
uint32_t *current_power_limit,
1282+
uint32_t *default_power_limit,
1283+
uint32_t *max_power_limit,
1284+
uint32_t *min_power_limit)
12841285
{
12851286
struct smu_11_0_powerplay_table *powerplay_table =
12861287
(struct smu_11_0_powerplay_table *)smu->smu_table.power_play_table;
12871288
PPTable_t *pptable = smu->smu_table.driver_pptable;
1288-
uint32_t power_limit, od_percent;
1289+
uint32_t power_limit, od_percent_upper, od_percent_lower;
12891290

12901291
if (smu_v11_0_get_current_power_limit(smu, &power_limit)) {
12911292
/* the last hope to figure out the ppt limit */
@@ -1302,17 +1303,25 @@ static int arcturus_get_power_limit(struct smu_context *smu,
13021303
if (default_power_limit)
13031304
*default_power_limit = power_limit;
13041305

1305-
if (max_power_limit) {
1306-
if (smu->od_enabled) {
1307-
od_percent = le32_to_cpu(powerplay_table->overdrive_table.max[SMU_11_0_ODSETTING_POWERPERCENTAGE]);
1306+
if (smu->od_enabled) {
1307+
od_percent_upper = le32_to_cpu(powerplay_table->overdrive_table.max[SMU_11_0_ODSETTING_POWERPERCENTAGE]);
1308+
od_percent_lower = le32_to_cpu(powerplay_table->overdrive_table.min[SMU_11_0_ODSETTING_POWERPERCENTAGE]);
1309+
} else {
1310+
od_percent_upper = 0;
1311+
od_percent_lower = 100;
1312+
}
13081313

1309-
dev_dbg(smu->adev->dev, "ODSETTING_POWERPERCENTAGE: %d (default: %d)\n", od_percent, power_limit);
1314+
dev_dbg(smu->adev->dev, "od percent upper:%d, od percent lower:%d (default power: %d)\n",
1315+
od_percent_upper, od_percent_lower, power_limit);
13101316

1311-
power_limit *= (100 + od_percent);
1312-
power_limit /= 100;
1313-
}
1317+
if (max_power_limit) {
1318+
*max_power_limit = power_limit * (100 + od_percent_upper);
1319+
*max_power_limit /= 100;
1320+
}
13141321

1315-
*max_power_limit = power_limit;
1322+
if (min_power_limit) {
1323+
*min_power_limit = power_limit * (100 - od_percent_lower);
1324+
*min_power_limit /= 100;
13161325
}
13171326

13181327
return 0;

drivers/gpu/drm/amd/pm/swsmu/smu11/navi10_ppt.c

Lines changed: 21 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2330,15 +2330,16 @@ static int navi10_display_disable_memory_clock_switch(struct smu_context *smu,
23302330
}
23312331

23322332
static int navi10_get_power_limit(struct smu_context *smu,
2333-
uint32_t *current_power_limit,
2334-
uint32_t *default_power_limit,
2335-
uint32_t *max_power_limit)
2333+
uint32_t *current_power_limit,
2334+
uint32_t *default_power_limit,
2335+
uint32_t *max_power_limit,
2336+
uint32_t *min_power_limit)
23362337
{
23372338
struct smu_11_0_powerplay_table *powerplay_table =
23382339
(struct smu_11_0_powerplay_table *)smu->smu_table.power_play_table;
23392340
struct smu_11_0_overdrive_table *od_settings = smu->od_settings;
23402341
PPTable_t *pptable = smu->smu_table.driver_pptable;
2341-
uint32_t power_limit, od_percent;
2342+
uint32_t power_limit, od_percent_upper, od_percent_lower;
23422343

23432344
if (smu_v11_0_get_current_power_limit(smu, &power_limit)) {
23442345
/* the last hope to figure out the ppt limit */
@@ -2355,18 +2356,26 @@ static int navi10_get_power_limit(struct smu_context *smu,
23552356
if (default_power_limit)
23562357
*default_power_limit = power_limit;
23572358

2358-
if (max_power_limit) {
2359-
if (smu->od_enabled &&
2359+
if (smu->od_enabled &&
23602360
navi10_od_feature_is_supported(od_settings, SMU_11_0_ODCAP_POWER_LIMIT)) {
2361-
od_percent = le32_to_cpu(powerplay_table->overdrive_table.max[SMU_11_0_ODSETTING_POWERPERCENTAGE]);
2361+
od_percent_upper = le32_to_cpu(powerplay_table->overdrive_table.max[SMU_11_0_ODSETTING_POWERPERCENTAGE]);
2362+
od_percent_lower = le32_to_cpu(powerplay_table->overdrive_table.min[SMU_11_0_ODSETTING_POWERPERCENTAGE]);
2363+
} else {
2364+
od_percent_upper = 0;
2365+
od_percent_lower = 100;
2366+
}
23622367

2363-
dev_dbg(smu->adev->dev, "ODSETTING_POWERPERCENTAGE: %d (default: %d)\n", od_percent, power_limit);
2368+
dev_dbg(smu->adev->dev, "od percent upper:%d, od percent lower:%d (default power: %d)\n",
2369+
od_percent_upper, od_percent_lower, power_limit);
23642370

2365-
power_limit *= (100 + od_percent);
2366-
power_limit /= 100;
2367-
}
2371+
if (max_power_limit) {
2372+
*max_power_limit = power_limit * (100 + od_percent_upper);
2373+
*max_power_limit /= 100;
2374+
}
23682375

2369-
*max_power_limit = power_limit;
2376+
if (min_power_limit) {
2377+
*min_power_limit = power_limit * (100 - od_percent_lower);
2378+
*min_power_limit /= 100;
23702379
}
23712380

23722381
return 0;

drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.c

Lines changed: 20 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -620,11 +620,12 @@ static uint32_t sienna_cichlid_get_throttler_status_locked(struct smu_context *s
620620
static int sienna_cichlid_get_power_limit(struct smu_context *smu,
621621
uint32_t *current_power_limit,
622622
uint32_t *default_power_limit,
623-
uint32_t *max_power_limit)
623+
uint32_t *max_power_limit,
624+
uint32_t *min_power_limit)
624625
{
625626
struct smu_11_0_7_powerplay_table *powerplay_table =
626627
(struct smu_11_0_7_powerplay_table *)smu->smu_table.power_play_table;
627-
uint32_t power_limit, od_percent;
628+
uint32_t power_limit, od_percent_upper, od_percent_lower;
628629
uint16_t *table_member;
629630

630631
GET_PPTABLE_MEMBER(SocketPowerLimitAc, &table_member);
@@ -639,21 +640,26 @@ static int sienna_cichlid_get_power_limit(struct smu_context *smu,
639640
if (default_power_limit)
640641
*default_power_limit = power_limit;
641642

642-
if (max_power_limit) {
643-
if (smu->od_enabled) {
644-
od_percent =
645-
le32_to_cpu(powerplay_table->overdrive_table.max[
646-
SMU_11_0_7_ODSETTING_POWERPERCENTAGE]);
643+
if (smu->od_enabled) {
644+
od_percent_upper = le32_to_cpu(powerplay_table->overdrive_table.max[SMU_11_0_7_ODSETTING_POWERPERCENTAGE]);
645+
od_percent_lower = le32_to_cpu(powerplay_table->overdrive_table.min[SMU_11_0_7_ODSETTING_POWERPERCENTAGE]);
646+
} else {
647+
od_percent_upper = 0;
648+
od_percent_lower = 100;
649+
}
647650

648-
dev_dbg(smu->adev->dev, "ODSETTING_POWERPERCENTAGE: %d (default: %d)\n",
649-
od_percent, power_limit);
651+
dev_dbg(smu->adev->dev, "od percent upper:%d, od percent lower:%d (default power: %d)\n",
652+
od_percent_upper, od_percent_lower, power_limit);
650653

651-
power_limit *= (100 + od_percent);
652-
power_limit /= 100;
653-
}
654-
*max_power_limit = power_limit;
654+
if (max_power_limit) {
655+
*max_power_limit = power_limit * (100 + od_percent_upper);
656+
*max_power_limit /= 100;
655657
}
656658

659+
if (min_power_limit) {
660+
*min_power_limit = power_limit * (100 - od_percent_lower);
661+
*min_power_limit /= 100;
662+
}
657663
return 0;
658664
}
659665

@@ -672,7 +678,7 @@ static void sienna_cichlid_get_smartshift_power_percentage(struct smu_context *s
672678
uint32_t cur_power_limit;
673679

674680
if (metrics_v4->ApuSTAPMSmartShiftLimit != 0) {
675-
sienna_cichlid_get_power_limit(smu, &cur_power_limit, NULL, NULL);
681+
sienna_cichlid_get_power_limit(smu, &cur_power_limit, NULL, NULL, NULL);
676682
apu_power_limit = metrics_v4->ApuSTAPMLimit;
677683
dgpu_power_limit = cur_power_limit;
678684
powerRatio = (((apu_power_limit +

drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.c

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2314,7 +2314,8 @@ static u32 vangogh_get_gfxoff_status(struct smu_context *smu)
23142314
static int vangogh_get_power_limit(struct smu_context *smu,
23152315
uint32_t *current_power_limit,
23162316
uint32_t *default_power_limit,
2317-
uint32_t *max_power_limit)
2317+
uint32_t *max_power_limit,
2318+
uint32_t *min_power_limit)
23182319
{
23192320
struct smu_11_5_power_context *power_context =
23202321
smu->smu_power.power_context;
@@ -2336,6 +2337,8 @@ static int vangogh_get_power_limit(struct smu_context *smu,
23362337
*default_power_limit = ppt_limit / 1000;
23372338
if (max_power_limit)
23382339
*max_power_limit = 29;
2340+
if (min_power_limit)
2341+
*min_power_limit = 0;
23392342

23402343
ret = smu_cmn_send_smc_msg(smu, SMU_MSG_GetFastPPTLimit, &ppt_limit);
23412344
if (ret) {

drivers/gpu/drm/amd/pm/swsmu/smu13/aldebaran_ppt.c

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1139,9 +1139,10 @@ static int aldebaran_read_sensor(struct smu_context *smu,
11391139
}
11401140

11411141
static int aldebaran_get_power_limit(struct smu_context *smu,
1142-
uint32_t *current_power_limit,
1143-
uint32_t *default_power_limit,
1144-
uint32_t *max_power_limit)
1142+
uint32_t *current_power_limit,
1143+
uint32_t *default_power_limit,
1144+
uint32_t *max_power_limit,
1145+
uint32_t *min_power_limit)
11451146
{
11461147
PPTable_t *pptable = smu->smu_table.driver_pptable;
11471148
uint32_t power_limit = 0;
@@ -1154,7 +1155,8 @@ static int aldebaran_get_power_limit(struct smu_context *smu,
11541155
*default_power_limit = 0;
11551156
if (max_power_limit)
11561157
*max_power_limit = 0;
1157-
1158+
if (min_power_limit)
1159+
*min_power_limit = 0;
11581160
dev_warn(smu->adev->dev,
11591161
"PPT feature is not enabled, power values can't be fetched.");
11601162

@@ -1189,6 +1191,9 @@ static int aldebaran_get_power_limit(struct smu_context *smu,
11891191
*max_power_limit = pptable->PptLimit;
11901192
}
11911193

1194+
if (min_power_limit)
1195+
*min_power_limit = 0;
1196+
11921197
return 0;
11931198
}
11941199

drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c

Lines changed: 22 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2341,16 +2341,17 @@ static int smu_v13_0_0_enable_mgpu_fan_boost(struct smu_context *smu)
23412341
}
23422342

23432343
static int smu_v13_0_0_get_power_limit(struct smu_context *smu,
2344-
uint32_t *current_power_limit,
2345-
uint32_t *default_power_limit,
2346-
uint32_t *max_power_limit)
2344+
uint32_t *current_power_limit,
2345+
uint32_t *default_power_limit,
2346+
uint32_t *max_power_limit,
2347+
uint32_t *min_power_limit)
23472348
{
23482349
struct smu_table_context *table_context = &smu->smu_table;
23492350
struct smu_13_0_0_powerplay_table *powerplay_table =
23502351
(struct smu_13_0_0_powerplay_table *)table_context->power_play_table;
23512352
PPTable_t *pptable = table_context->driver_pptable;
23522353
SkuTable_t *skutable = &pptable->SkuTable;
2353-
uint32_t power_limit, od_percent;
2354+
uint32_t power_limit, od_percent_upper, od_percent_lower;
23542355

23552356
if (smu_v13_0_get_current_power_limit(smu, &power_limit))
23562357
power_limit = smu->adev->pm.ac_power ?
@@ -2362,16 +2363,25 @@ static int smu_v13_0_0_get_power_limit(struct smu_context *smu,
23622363
if (default_power_limit)
23632364
*default_power_limit = power_limit;
23642365

2365-
if (max_power_limit) {
2366-
if (smu->od_enabled) {
2367-
od_percent = le32_to_cpu(powerplay_table->overdrive_table.max[SMU_13_0_0_ODSETTING_POWERPERCENTAGE]);
2366+
if (smu->od_enabled) {
2367+
od_percent_upper = le32_to_cpu(powerplay_table->overdrive_table.max[SMU_13_0_0_ODSETTING_POWERPERCENTAGE]);
2368+
od_percent_lower = le32_to_cpu(powerplay_table->overdrive_table.min[SMU_13_0_0_ODSETTING_POWERPERCENTAGE]);
2369+
} else {
2370+
od_percent_upper = 0;
2371+
od_percent_lower = 100;
2372+
}
23682373

2369-
dev_dbg(smu->adev->dev, "ODSETTING_POWERPERCENTAGE: %d (default: %d)\n", od_percent, power_limit);
2374+
dev_dbg(smu->adev->dev, "od percent upper:%d, od percent lower:%d (default power: %d)\n",
2375+
od_percent_upper, od_percent_lower, power_limit);
23702376

2371-
power_limit *= (100 + od_percent);
2372-
power_limit /= 100;
2373-
}
2374-
*max_power_limit = power_limit;
2377+
if (max_power_limit) {
2378+
*max_power_limit = power_limit * (100 + od_percent_upper);
2379+
*max_power_limit /= 100;
2380+
}
2381+
2382+
if (min_power_limit) {
2383+
*min_power_limit = power_limit * (100 - od_percent_lower);
2384+
*min_power_limit /= 100;
23752385
}
23762386

23772387
return 0;

0 commit comments

Comments
 (0)