From d94eb061338a573c1303a95fcc51d45162f20c90 Mon Sep 17 00:00:00 2001 From: David Rokhvarg Date: Mon, 30 Nov 2015 14:42:51 -0500 Subject: [PATCH 0538/1110] drm/amd/dal: Add PPLib interfaces to get Static Clocks and Clocks-by-level. Signed-off-by: David Rokhvarg Signed-off-by: Harry Wentland Acked-by: Harry Wentland --- .../drm/amd/dal/amdgpu_dm/amdgpu_dal_services.c | 54 ++++++++++++++----- drivers/gpu/drm/amd/dal/dc/dc_services.h | 60 ++++++++++++++++++++-- 2 files changed, 98 insertions(+), 16 deletions(-) diff --git a/drivers/gpu/drm/amd/dal/amdgpu_dm/amdgpu_dal_services.c b/drivers/gpu/drm/amd/dal/amdgpu_dm/amdgpu_dal_services.c index a497093..ba54282 100644 --- a/drivers/gpu/drm/amd/dal/amdgpu_dm/amdgpu_dal_services.c +++ b/drivers/gpu/drm/amd/dal/amdgpu_dm/amdgpu_dal_services.c @@ -147,17 +147,20 @@ bool dal_get_platform_info(struct dc_context *ctx, return false; } -/* Next calls are to power component */ -bool dc_service_pp_pre_dce_clock_change(struct dc_context *ctx, - struct dal_to_power_info *input, - struct power_to_dal_info *output) +/**** power component interfaces ****/ + +bool dc_service_pp_pre_dce_clock_change( + struct dc_context *ctx, + struct dal_to_power_info *input, + struct power_to_dal_info *output) { /*TODO*/ return false; } -bool dc_service_pp_post_dce_clock_change(struct dc_context *ctx, - const struct dc_pp_display_configuration *pp_display_cfg) +bool dc_service_pp_post_dce_clock_change( + struct dc_context *ctx, + const struct dc_pp_display_configuration *pp_display_cfg) { #ifdef CONFIG_DRM_AMD_POWERPLAY struct amdgpu_device *adev = ctx->driver_context; @@ -179,6 +182,11 @@ bool dc_service_pp_post_dce_clock_change(struct dc_context *ctx, adev->pm.pm_display_cfg.nb_pstate_switch_disable = pp_display_cfg->nb_pstate_switch_disable; + /* TODO: complete implementation of + * amd_powerplay_display_configuration_change(). + * Follow example of: + * PHM_StoreDALConfigurationData - powerplay\hwmgr\hardwaremanager.c + * PP_IRI_DisplayConfigurationChange - powerplay\eventmgr\iri.c */ amd_powerplay_display_configuration_change( adev->powerplay.pp_handle, &adev->pm.pm_display_cfg); @@ -192,8 +200,9 @@ bool dc_service_pp_post_dce_clock_change(struct dc_context *ctx, #endif } -bool dc_service_get_system_clocks_range(struct dc_context *ctx, - struct dal_system_clock_range *sys_clks) +bool dc_service_get_system_clocks_range( + struct dc_context *ctx, + struct dal_system_clock_range *sys_clks) { struct amdgpu_device *adev = ctx->driver_context; @@ -218,14 +227,35 @@ bool dc_service_get_system_clocks_range(struct dc_context *ctx, } -bool dc_service_pp_set_display_clock(struct dc_context *ctx, - struct dal_to_power_dclk *dclk) +bool dc_service_get_clock_levels_by_type( + struct dc_context *ctx, + enum dc_pp_clock_type clk_type, + struct dc_pp_clock_levels *clk_level_info) { - /* TODO: need power component to provide appropriate interface */ + /* TODO: follow implementation of: + * PhwCz_GetClocksByType - powerplay\hwmgr\cz_hwmgr.c + * PHM_GetClockByType - powerplay\hwmgr\hardwaremanager.c + * PP_IRI_GetClockByType - powerplay\eventmgr\iri.c */ + + DRM_INFO("%s - not implemented\n", __func__); return false; } -/* end of calls to power component */ +bool dc_service_get_static_clocks( + struct dc_context *ctx, + struct dc_pp_static_clock_info *static_clk_info) +{ + /* TODO: follow implementation of: + * PhwCz_GetDALPowerLevel - powerplay\hwmgr\cz_hwmgr.c + * PHM_GetDALPowerLevel - powerplay\hwmgr\hardwaremanager.c + * PP_IRI_GetStaticClocksInfo - powerplay\eventmgr\iri.c */ + + DRM_INFO("%s - not implemented\n", __func__); + return false; +} + +/**** end of power component interfaces ****/ + /* Calls to notification */ diff --git a/drivers/gpu/drm/amd/dal/dc/dc_services.h b/drivers/gpu/drm/amd/dal/dc/dc_services.h index f430864..6290885 100644 --- a/drivers/gpu/drm/amd/dal/dc/dc_services.h +++ b/drivers/gpu/drm/amd/dal/dc/dc_services.h @@ -64,7 +64,7 @@ void dc_service_unregister_interrupt( irq_handler_idx handler_idx); /************************************** - * Calls to Power Play (PP) component + * Power Play (PP) interfaces **************************************/ /* DAL calls this function to notify PP about clocks it needs for the Mode Set. @@ -95,6 +95,47 @@ struct dc_pp_display_configuration { uint32_t cpu_pstate_separation_time; }; +enum dc_pp_clock_type { + DC_PP_CLOCK_TYPE_DISPLAY_CLK = 1, + DC_PP_CLOCK_TYPE_ENGINE_CLK, + DC_PP_CLOCK_TYPE_MEMORY_CLK +}; + +#define DC_PP_MAX_CLOCK_LEVELS 8 + +struct dc_pp_clock_levels { + enum dc_pp_clock_type clock_type; + uint32_t num_levels; + uint32_t clocks_in_hz[DC_PP_MAX_CLOCK_LEVELS]; +}; + +enum dc_pp_clocks_state { + DC_PP_CLOCKS_STATE_INVALID = 0, + DC_PP_CLOCKS_STATE_ULTRA_LOW, + DC_PP_CLOCKS_STATE_LOW, + DC_PP_CLOCKS_STATE_NOMINAL, + DC_PP_CLOCKS_STATE_PERFORMANCE, + + /* Starting from DCE11, Max 8 levels of DPM state supported. */ + DC_PP_CLOCKS_DPM_STATE_LEVEL_INVALID = DC_PP_CLOCKS_STATE_INVALID, + DC_PP_CLOCKS_DPM_STATE_LEVEL_0 = DC_PP_CLOCKS_STATE_ULTRA_LOW, + DC_PP_CLOCKS_DPM_STATE_LEVEL_1 = DC_PP_CLOCKS_STATE_LOW, + DC_PP_CLOCKS_DPM_STATE_LEVEL_2 = DC_PP_CLOCKS_STATE_NOMINAL, + /* to be backward compatible */ + DC_PP_CLOCKS_DPM_STATE_LEVEL_3 = DC_PP_CLOCKS_STATE_PERFORMANCE, + DC_PP_CLOCKS_DPM_STATE_LEVEL_4 = DC_PP_CLOCKS_DPM_STATE_LEVEL_3 + 1, + DC_PP_CLOCKS_DPM_STATE_LEVEL_5 = DC_PP_CLOCKS_DPM_STATE_LEVEL_4 + 1, + DC_PP_CLOCKS_DPM_STATE_LEVEL_6 = DC_PP_CLOCKS_DPM_STATE_LEVEL_5 + 1, + DC_PP_CLOCKS_DPM_STATE_LEVEL_7 = DC_PP_CLOCKS_DPM_STATE_LEVEL_6 + 1, +}; + +struct dc_pp_static_clock_info { + uint32_t max_engine_clock_hz; + uint32_t max_memory_clock_hz; + /* max possible display block clocks state */ + enum dc_pp_clocks_state max_clocks_state; +}; + /* DAL calls this function to notify PP about completion of Mode Set. * For PP it means that current DCE clocks are those which were returned * by dc_service_pp_pre_dce_clock_change(), in the 'output' parameter. @@ -120,10 +161,21 @@ bool dc_service_get_system_clocks_range( struct dc_context *ctx, struct dal_system_clock_range *sys_clks); -/* for future use */ -bool dc_service_pp_set_display_clock( + +bool dc_service_get_clock_levels_by_type( struct dc_context *ctx, - struct dal_to_power_dclk *dclk); + enum dc_pp_clock_type clk_type, + struct dc_pp_clock_levels *clk_level_info); + +/* Use this for mode validation. + * TODO: when this interface is implemented on Linux, should we remove + * dc_service_get_system_clocks_range() ?? */ +bool dc_service_get_static_clocks( + struct dc_context *ctx, + struct dc_pp_static_clock_info *static_clk_info); + + +/****** end of PP interfaces ******/ void dc_service_sleep_in_milliseconds(struct dc_context *ctx, uint32_t milliseconds); -- 2.7.4