aboutsummaryrefslogtreecommitdiffstats
path: root/common/recipes-kernel/linux/linux-yocto-4.19.8/1409-drm-amd-powerplay-implement-sysfs-of-pp_table-for-sm.patch
diff options
context:
space:
mode:
Diffstat (limited to 'common/recipes-kernel/linux/linux-yocto-4.19.8/1409-drm-amd-powerplay-implement-sysfs-of-pp_table-for-sm.patch')
-rw-r--r--common/recipes-kernel/linux/linux-yocto-4.19.8/1409-drm-amd-powerplay-implement-sysfs-of-pp_table-for-sm.patch201
1 files changed, 201 insertions, 0 deletions
diff --git a/common/recipes-kernel/linux/linux-yocto-4.19.8/1409-drm-amd-powerplay-implement-sysfs-of-pp_table-for-sm.patch b/common/recipes-kernel/linux/linux-yocto-4.19.8/1409-drm-amd-powerplay-implement-sysfs-of-pp_table-for-sm.patch
new file mode 100644
index 00000000..e7ddf9b6
--- /dev/null
+++ b/common/recipes-kernel/linux/linux-yocto-4.19.8/1409-drm-amd-powerplay-implement-sysfs-of-pp_table-for-sm.patch
@@ -0,0 +1,201 @@
+From a1220536a263badf6ebb67ddc1ab788f6b40e68b Mon Sep 17 00:00:00 2001
+From: Kevin Wang <Kevin1.Wang@amd.com>
+Date: Fri, 11 Jan 2019 15:07:52 +0800
+Subject: [PATCH 1409/2940] drm/amd/powerplay: implement sysfs of pp_table for
+ smu11 (v2)
+
+add pp_table sysfs interface for new sw-smu.
+get: return pptable raw data
+set: write pptable raw data to pptable, then reset smu (hw_fini -> hw_init)
+
+v2: fix mutex lock issue
+
+Signed-off-by: Kevin Wang <Kevin1.Wang@amd.com>
+Reviewed-by: Huang Rui <ray.huang@amd.com>
+Acked-by: Alex Deucher <alexander.deucher@amd.com>
+---
+ drivers/gpu/drm/amd/amdgpu/amdgpu_pm.c | 14 +++-
+ drivers/gpu/drm/amd/powerplay/amdgpu_smu.c | 73 ++++++++++++++++++-
+ .../gpu/drm/amd/powerplay/inc/amdgpu_smu.h | 4 +
+ drivers/gpu/drm/amd/powerplay/smu_v11_0.c | 6 +-
+ 4 files changed, 89 insertions(+), 8 deletions(-)
+
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_pm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_pm.c
+index e2d423528135..7a9e658c42ad 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_pm.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_pm.c
+@@ -464,7 +464,12 @@ static ssize_t amdgpu_get_pp_table(struct device *dev,
+ char *table = NULL;
+ int size;
+
+- if (adev->powerplay.pp_funcs->get_pp_table)
++ if (is_support_sw_smu(adev)) {
++ size = smu_sys_get_pp_table(&adev->smu, (void **)&table);
++ if (size < 0)
++ return size;
++ }
++ else if (adev->powerplay.pp_funcs->get_pp_table)
+ size = amdgpu_dpm_get_pp_table(adev, &table);
+ else
+ return 0;
+@@ -484,8 +489,13 @@ static ssize_t amdgpu_set_pp_table(struct device *dev,
+ {
+ struct drm_device *ddev = dev_get_drvdata(dev);
+ struct amdgpu_device *adev = ddev->dev_private;
++ int ret = 0;
+
+- if (adev->powerplay.pp_funcs->set_pp_table)
++ if (is_support_sw_smu(adev)) {
++ ret = smu_sys_set_pp_table(&adev->smu, (void *)buf, count);
++ if (ret)
++ return ret;
++ } else if (adev->powerplay.pp_funcs->set_pp_table)
+ amdgpu_dpm_set_pp_table(adev, buf, count);
+
+ return count;
+diff --git a/drivers/gpu/drm/amd/powerplay/amdgpu_smu.c b/drivers/gpu/drm/amd/powerplay/amdgpu_smu.c
+index f35c2177d13d..f17c85fc61e9 100644
+--- a/drivers/gpu/drm/amd/powerplay/amdgpu_smu.c
++++ b/drivers/gpu/drm/amd/powerplay/amdgpu_smu.c
+@@ -76,6 +76,54 @@ bool is_support_sw_smu(struct amdgpu_device *adev)
+ return false;
+ }
+
++int smu_sys_get_pp_table(struct smu_context *smu, void **table)
++{
++ struct smu_table_context *smu_table = &smu->smu_table;
++
++ if (!smu_table->power_play_table && !smu_table->hardcode_pptable)
++ return -EINVAL;
++
++ if (smu_table->hardcode_pptable)
++ *table = smu_table->hardcode_pptable;
++ else
++ *table = smu_table->power_play_table;
++
++ return smu_table->power_play_table_size;
++}
++
++int smu_sys_set_pp_table(struct smu_context *smu, void *buf, size_t size)
++{
++ struct smu_table_context *smu_table = &smu->smu_table;
++ ATOM_COMMON_TABLE_HEADER *header = (ATOM_COMMON_TABLE_HEADER *)buf;
++ int ret = 0;
++
++ if (header->usStructureSize != size) {
++ pr_err("pp table size not matched !\n");
++ return -EIO;
++ }
++
++ mutex_lock(&smu->mutex);
++ if (!smu_table->hardcode_pptable)
++ smu_table->hardcode_pptable = kzalloc(size, GFP_KERNEL);
++ if (!smu_table->hardcode_pptable) {
++ ret = -ENOMEM;
++ goto failed;
++ }
++
++ memcpy(smu_table->hardcode_pptable, buf, size);
++ smu_table->power_play_table = smu_table->hardcode_pptable;
++ smu_table->power_play_table_size = size;
++ mutex_unlock(&smu->mutex);
++
++ ret = smu_reset(smu);
++ if (ret)
++ pr_info("smu reset failed, ret = %d\n", ret);
++
++failed:
++ mutex_unlock(&smu->mutex);
++ return ret;
++}
++
+ int smu_feature_init_dpm(struct smu_context *smu)
+ {
+ struct smu_feature *feature = &smu->smu_feature;
+@@ -328,7 +376,7 @@ static int smu_fini_fb_allocations(struct smu_context *smu)
+ uint32_t i = 0;
+
+ if (table_count == 0 || tables == NULL)
+- return -EINVAL;
++ return 0;
+
+ for (i = 0 ; i < table_count; i++) {
+ if (tables[i].size == 0)
+@@ -590,9 +638,10 @@ static int smu_hw_fini(void *handle)
+ if (!is_support_sw_smu(adev))
+ return -EINVAL;
+
+- if (!table_context->driver_pptable)
+- return -EINVAL;
+- kfree(table_context->driver_pptable);
++ if (table_context->driver_pptable) {
++ kfree(table_context->driver_pptable);
++ table_context->driver_pptable = NULL;
++ }
+
+ if (table_context->max_sustainable_clocks) {
+ kfree(table_context->max_sustainable_clocks);
+@@ -610,6 +659,22 @@ static int smu_hw_fini(void *handle)
+ return 0;
+ }
+
++int smu_reset(struct smu_context *smu)
++{
++ struct amdgpu_device *adev = smu->adev;
++ int ret = 0;
++
++ ret = smu_hw_fini(adev);
++ if (ret)
++ return ret;
++
++ ret = smu_hw_init(adev);
++ if (ret)
++ return ret;
++
++ return ret;
++}
++
+ static int smu_suspend(void *handle)
+ {
+ struct amdgpu_device *adev = (struct amdgpu_device *)handle;
+diff --git a/drivers/gpu/drm/amd/powerplay/inc/amdgpu_smu.h b/drivers/gpu/drm/amd/powerplay/inc/amdgpu_smu.h
+index 43c2b9e981f5..11e7797e2fae 100644
+--- a/drivers/gpu/drm/amd/powerplay/inc/amdgpu_smu.h
++++ b/drivers/gpu/drm/amd/powerplay/inc/amdgpu_smu.h
+@@ -158,6 +158,7 @@ struct smu_table_context
+ {
+ void *power_play_table;
+ uint32_t power_play_table_size;
++ void *hardcode_pptable;
+
+ void *max_sustainable_clocks;
+ struct smu_bios_boot_up_values boot_values;
+@@ -372,5 +373,8 @@ extern int smu_feature_set_supported(struct smu_context *smu, int feature_id, bo
+ int smu_update_table(struct smu_context *smu, uint32_t table_id,
+ void *table_data, bool drv2smu);
+ bool is_support_sw_smu(struct amdgpu_device *adev);
++int smu_reset(struct smu_context *smu);
++int smu_sys_get_pp_table(struct smu_context *smu, void **table);
++int smu_sys_set_pp_table(struct smu_context *smu, void *buf, size_t size);
+
+ #endif
+diff --git a/drivers/gpu/drm/amd/powerplay/smu_v11_0.c b/drivers/gpu/drm/amd/powerplay/smu_v11_0.c
+index e6b16b64a778..7ea19eb5896d 100644
+--- a/drivers/gpu/drm/amd/powerplay/smu_v11_0.c
++++ b/drivers/gpu/drm/amd/powerplay/smu_v11_0.c
+@@ -241,8 +241,10 @@ static int smu_v11_0_read_pptable_from_vbios(struct smu_context *smu)
+ if (ret)
+ return ret;
+
+- smu->smu_table.power_play_table = table;
+- smu->smu_table.power_play_table_size = size;
++ if (!smu->smu_table.power_play_table)
++ smu->smu_table.power_play_table = table;
++ if (!smu->smu_table.power_play_table_size)
++ smu->smu_table.power_play_table_size = size;
+
+ return 0;
+ }
+--
+2.17.1
+