From: Evan Quan <evan.quan@xxxxxxx> Support more GFX clockgating features(3D_CGCG, 3D_CGLS, MGCG, FGCG and PERF_CLK). Signed-off-by: Evan Quan <evan.quan@xxxxxxx> Reviewed-by: Likun Gao <Likun.Gao@xxxxxxx> Signed-off-by: Alex Deucher <alexander.deucher@xxxxxxx> --- drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c | 100 +++++++++++++++++++---- drivers/gpu/drm/amd/amdgpu/soc21.c | 5 ++ drivers/gpu/drm/amd/include/amd_shared.h | 1 + drivers/gpu/drm/amd/pm/amdgpu_pm.c | 2 +- 4 files changed, 93 insertions(+), 15 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c b/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c index 184bf554acca..8a1c0f783a2a 100644 --- a/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c +++ b/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c @@ -4888,6 +4888,44 @@ static void gfx_v11_0_unset_safe_mode(struct amdgpu_device *adev) WREG32_SOC15(GC, 0, regRLC_SAFE_MODE, RLC_SAFE_MODE__CMD_MASK); } +static void gfx_v11_0_update_perf_clk(struct amdgpu_device *adev, + bool enable) +{ + uint32_t def, data; + + if (!(adev->cg_flags & AMD_CG_SUPPORT_GFX_PERF_CLK)) + return; + + def = data = RREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE); + + if (enable) + data &= ~RLC_CGTT_MGCG_OVERRIDE__PERFMON_CLOCK_STATE_MASK; + else + data |= RLC_CGTT_MGCG_OVERRIDE__PERFMON_CLOCK_STATE_MASK; + + if (def != data) + WREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE, data); +} + +static void gfx_v11_0_update_sram_fgcg(struct amdgpu_device *adev, + bool enable) +{ + uint32_t def, data; + + if (!(adev->cg_flags & AMD_CG_SUPPORT_GFX_FGCG)) + return; + + def = data = RREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE); + + if (enable) + data &= ~RLC_CGTT_MGCG_OVERRIDE__GFXIP_FGCG_OVERRIDE_MASK; + else + data |= RLC_CGTT_MGCG_OVERRIDE__GFXIP_FGCG_OVERRIDE_MASK; + + if (def != data) + WREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE, data); +} + static void gfx_v11_0_update_repeater_fgcg(struct amdgpu_device *adev, bool enable) { @@ -4907,19 +4945,40 @@ static void gfx_v11_0_update_repeater_fgcg(struct amdgpu_device *adev, WREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE, data); } -#if 0 static void gfx_v11_0_update_medium_grain_clock_gating(struct amdgpu_device *adev, - bool enable) + bool enable) { - /* TODO: add power related feature later. */ -} + uint32_t data, def; -static void gfx_v11_0_update_3d_clock_gating(struct amdgpu_device *adev, - bool enable) -{ - /* TODO: add power related feature later. */ + if (!(adev->cg_flags & (AMD_CG_SUPPORT_GFX_MGCG | AMD_CG_SUPPORT_GFX_MGLS))) + return; + + /* It is disabled by HW by default */ + if (enable) { + if (adev->cg_flags & AMD_CG_SUPPORT_GFX_MGCG) { + /* 1 - RLC_CGTT_MGCG_OVERRIDE */ + def = data = RREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE); + + data &= ~(RLC_CGTT_MGCG_OVERRIDE__GRBM_CGTT_SCLK_OVERRIDE_MASK | + RLC_CGTT_MGCG_OVERRIDE__RLC_CGTT_SCLK_OVERRIDE_MASK | + RLC_CGTT_MGCG_OVERRIDE__GFXIP_MGCG_OVERRIDE_MASK); + + if (def != data) + WREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE, data); + } + } else { + if (adev->cg_flags & AMD_CG_SUPPORT_GFX_MGCG) { + def = data = RREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE); + + data |= (RLC_CGTT_MGCG_OVERRIDE__RLC_CGTT_SCLK_OVERRIDE_MASK | + RLC_CGTT_MGCG_OVERRIDE__GRBM_CGTT_SCLK_OVERRIDE_MASK | + RLC_CGTT_MGCG_OVERRIDE__GFXIP_MGCG_OVERRIDE_MASK); + + if (def != data) + WREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE, data); + } + } } -#endif static void gfx_v11_0_update_coarse_grain_clock_gating(struct amdgpu_device *adev, bool enable) @@ -5050,8 +5109,14 @@ static int gfx_v11_0_update_gfx_clock_gating(struct amdgpu_device *adev, gfx_v11_0_update_coarse_grain_clock_gating(adev, enable); + gfx_v11_0_update_medium_grain_clock_gating(adev, enable); + gfx_v11_0_update_repeater_fgcg(adev, enable); + gfx_v11_0_update_sram_fgcg(adev, enable); + + gfx_v11_0_update_perf_clk(adev, enable); + if (adev->cg_flags & (AMD_CG_SUPPORT_GFX_MGCG | AMD_CG_SUPPORT_GFX_CGLS | @@ -5144,16 +5209,23 @@ static void gfx_v11_0_get_clockgating_state(void *handle, u64 *flags) struct amdgpu_device *adev = (struct amdgpu_device *)handle; int data; - /* AMD_CG_SUPPORT_GFX_FGCG */ - data = RREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE); - if (!(data & RLC_CGTT_MGCG_OVERRIDE__GFXIP_FGCG_OVERRIDE_MASK)) - *flags |= AMD_CG_SUPPORT_GFX_FGCG; - /* AMD_CG_SUPPORT_GFX_MGCG */ data = RREG32_SOC15(GC, 0, regRLC_CGTT_MGCG_OVERRIDE); if (!(data & RLC_CGTT_MGCG_OVERRIDE__GFXIP_MGCG_OVERRIDE_MASK)) *flags |= AMD_CG_SUPPORT_GFX_MGCG; + /* AMD_CG_SUPPORT_REPEATER_FGCG */ + if (!(data & RLC_CGTT_MGCG_OVERRIDE__GFXIP_REPEATER_FGCG_OVERRIDE_MASK)) + *flags |= AMD_CG_SUPPORT_REPEATER_FGCG; + + /* AMD_CG_SUPPORT_GFX_FGCG */ + if (!(data & RLC_CGTT_MGCG_OVERRIDE__GFXIP_FGCG_OVERRIDE_MASK)) + *flags |= AMD_CG_SUPPORT_GFX_FGCG; + + /* AMD_CG_SUPPORT_GFX_PERF_CLK */ + if (!(data & RLC_CGTT_MGCG_OVERRIDE__PERFMON_CLOCK_STATE_MASK)) + *flags |= AMD_CG_SUPPORT_GFX_PERF_CLK; + /* AMD_CG_SUPPORT_GFX_CGCG */ data = RREG32_SOC15(GC, 0, regRLC_CGCG_CGLS_CTRL); if (data & RLC_CGCG_CGLS_CTRL__CGCG_EN_MASK) diff --git a/drivers/gpu/drm/amd/amdgpu/soc21.c b/drivers/gpu/drm/amd/amdgpu/soc21.c index 9e689a1f2ea4..c618f2b8ece8 100644 --- a/drivers/gpu/drm/amd/amdgpu/soc21.c +++ b/drivers/gpu/drm/amd/amdgpu/soc21.c @@ -526,7 +526,12 @@ static int soc21_common_early_init(void *handle) case IP_VERSION(11, 0, 0): adev->cg_flags = AMD_CG_SUPPORT_GFX_CGCG | AMD_CG_SUPPORT_GFX_CGLS | + AMD_CG_SUPPORT_GFX_3D_CGCG | + AMD_CG_SUPPORT_GFX_3D_CGLS | + AMD_CG_SUPPORT_GFX_MGCG | AMD_CG_SUPPORT_REPEATER_FGCG | + AMD_CG_SUPPORT_GFX_FGCG | + AMD_CG_SUPPORT_GFX_PERF_CLK | AMD_CG_SUPPORT_VCN_MGCG | AMD_CG_SUPPORT_JPEG_MGCG; adev->pg_flags = AMD_PG_SUPPORT_VCN | diff --git a/drivers/gpu/drm/amd/include/amd_shared.h b/drivers/gpu/drm/amd/include/amd_shared.h index 9ae4060a9d0f..bcdf7453a403 100644 --- a/drivers/gpu/drm/amd/include/amd_shared.h +++ b/drivers/gpu/drm/amd/include/amd_shared.h @@ -149,6 +149,7 @@ enum amd_powergating_state { #define AMD_CG_SUPPORT_JPEG_MGCG (1ULL << 30) #define AMD_CG_SUPPORT_GFX_FGCG (1ULL << 31) #define AMD_CG_SUPPORT_REPEATER_FGCG (1ULL << 32) +#define AMD_CG_SUPPORT_GFX_PERF_CLK (1ULL << 33) /* PG flags */ #define AMD_PG_SUPPORT_GFX_PG (1 << 0) #define AMD_PG_SUPPORT_GFX_SMG (1 << 1) diff --git a/drivers/gpu/drm/amd/pm/amdgpu_pm.c b/drivers/gpu/drm/amd/pm/amdgpu_pm.c index e92d07f88048..6e40e9ba9ff0 100644 --- a/drivers/gpu/drm/amd/pm/amdgpu_pm.c +++ b/drivers/gpu/drm/amd/pm/amdgpu_pm.c @@ -67,7 +67,7 @@ static const struct cg_flag_name clocks[] = { {AMD_CG_SUPPORT_IH_CG, "Interrupt Handler Clock Gating"}, {AMD_CG_SUPPORT_JPEG_MGCG, "JPEG Medium Grain Clock Gating"}, {AMD_CG_SUPPORT_REPEATER_FGCG, "Repeater Fine Grain Clock Gating"}, - + {AMD_CG_SUPPORT_GFX_PERF_CLK, "Perfmon Clock Gating"}, {AMD_CG_SUPPORT_ATHUB_MGCG, "Address Translation Hub Medium Grain Clock Gating"}, {AMD_CG_SUPPORT_ATHUB_LS, "Address Translation Hub Light Sleep"}, {0, NULL}, -- 2.35.1