diff options
Diffstat (limited to 'meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.19.8/4653-drm-amd-display-cleanup-of-function-pointer-tables.patch')
-rw-r--r-- | meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.19.8/4653-drm-amd-display-cleanup-of-function-pointer-tables.patch | 3251 |
1 files changed, 3251 insertions, 0 deletions
diff --git a/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.19.8/4653-drm-amd-display-cleanup-of-function-pointer-tables.patch b/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.19.8/4653-drm-amd-display-cleanup-of-function-pointer-tables.patch new file mode 100644 index 00000000..a45f630b --- /dev/null +++ b/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.19.8/4653-drm-amd-display-cleanup-of-function-pointer-tables.patch @@ -0,0 +1,3251 @@ +From 30f07444549b52d8d00c4b540cfce280e0943d26 Mon Sep 17 00:00:00 2001 +From: Anthony Koo <Anthony.Koo@amd.com> +Date: Tue, 29 Oct 2019 15:05:56 -0400 +Subject: [PATCH 4653/4736] drm/amd/display: cleanup of function pointer tables + +[Why] +It is becoming increasingly hard to figure out which +function is called on the different DCN versions + +[How] +1. Make function pointer table init in its own init.c file +2. Remove other scenarios in hwseq.c file that need to +include headers of other DCN versions. (If needed, +it should have been done via the function pointers) + +Change-Id: I09ca21dfd5848cc7e678dbefef8df201947df7d3 +Signed-off-by: Anthony Koo <Anthony.Koo@amd.com> +Reviewed-by: Aric Cyr <Aric.Cyr@amd.com> +Acked-by: Rodrigo Siqueira <Rodrigo.Siqueira@amd.com> +Signed-off-by: Rahul Kumar <rahul.kumar1@amd.com> +--- + .../gpu/drm/amd/display/dc/basics/Makefile | 2 +- + .../gpu/drm/amd/display/dc/basics/dc_common.c | 101 ++++ + .../gpu/drm/amd/display/dc/basics/dc_common.h | 42 ++ + drivers/gpu/drm/amd/display/dc/core/dc.c | 4 +- + .../gpu/drm/amd/display/dc/core/dc_stream.c | 3 +- + .../display/dc/dce110/dce110_hw_sequencer.c | 12 +- + .../display/dc/dce110/dce110_hw_sequencer.h | 1 - + drivers/gpu/drm/amd/display/dc/dcn10/Makefile | 3 +- + .../amd/display/dc/dcn10/dcn10_hw_sequencer.c | 436 +++++------------- + .../amd/display/dc/dcn10/dcn10_hw_sequencer.h | 181 ++++++-- + .../dc/dcn10/dcn10_hw_sequencer_debug.h | 43 ++ + .../gpu/drm/amd/display/dc/dcn10/dcn10_init.c | 105 +++++ + .../gpu/drm/amd/display/dc/dcn10/dcn10_init.h | 33 ++ + .../drm/amd/display/dc/dcn10/dcn10_resource.c | 2 + + drivers/gpu/drm/amd/display/dc/dcn20/Makefile | 2 +- + .../drm/amd/display/dc/dcn20/dcn20_hwseq.c | 428 +++++++---------- + .../drm/amd/display/dc/dcn20/dcn20_hwseq.h | 152 +++--- + .../gpu/drm/amd/display/dc/dcn20/dcn20_init.c | 131 ++++++ + .../gpu/drm/amd/display/dc/dcn20/dcn20_init.h | 33 ++ + .../gpu/drm/amd/display/dc/dcn20/dcn20_optc.c | 12 +- + .../gpu/drm/amd/display/dc/dcn20/dcn20_optc.h | 2 +- + .../drm/amd/display/dc/dcn20/dcn20_resource.c | 4 +- + drivers/gpu/drm/amd/display/dc/dcn21/Makefile | 3 +- + .../drm/amd/display/dc/dcn21/dcn21_hwseq.c | 13 +- + .../drm/amd/display/dc/dcn21/dcn21_hwseq.h | 14 +- + .../gpu/drm/amd/display/dc/dcn21/dcn21_init.c | 135 ++++++ + .../gpu/drm/amd/display/dc/dcn21/dcn21_init.h | 33 ++ + .../drm/amd/display/dc/dcn21/dcn21_resource.c | 2 + + .../gpu/drm/amd/display/dc/inc/hw_sequencer.h | 40 +- + 29 files changed, 1256 insertions(+), 716 deletions(-) + create mode 100644 drivers/gpu/drm/amd/display/dc/basics/dc_common.c + create mode 100644 drivers/gpu/drm/amd/display/dc/basics/dc_common.h + create mode 100644 drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer_debug.h + create mode 100644 drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.c + create mode 100644 drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.h + create mode 100644 drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.c + create mode 100644 drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.h + create mode 100644 drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.c + create mode 100644 drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.h + +diff --git a/drivers/gpu/drm/amd/display/dc/basics/Makefile b/drivers/gpu/drm/amd/display/dc/basics/Makefile +index a50a76471107..7ad0cad0f4ef 100644 +--- a/drivers/gpu/drm/amd/display/dc/basics/Makefile ++++ b/drivers/gpu/drm/amd/display/dc/basics/Makefile +@@ -25,7 +25,7 @@ + # subcomponents. + + BASICS = conversion.o fixpt31_32.o \ +- log_helpers.o vector.o ++ log_helpers.o vector.o dc_common.o + + AMD_DAL_BASICS = $(addprefix $(AMDDALPATH)/dc/basics/,$(BASICS)) + +diff --git a/drivers/gpu/drm/amd/display/dc/basics/dc_common.c b/drivers/gpu/drm/amd/display/dc/basics/dc_common.c +new file mode 100644 +index 000000000000..b2fc4f8e6482 +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/basics/dc_common.c +@@ -0,0 +1,101 @@ ++/* ++ * Copyright 2012-15 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#include "core_types.h" ++#include "dc_common.h" ++#include "basics/conversion.h" ++ ++bool is_rgb_cspace(enum dc_color_space output_color_space) ++{ ++ switch (output_color_space) { ++ case COLOR_SPACE_SRGB: ++ case COLOR_SPACE_SRGB_LIMITED: ++ case COLOR_SPACE_2020_RGB_FULLRANGE: ++ case COLOR_SPACE_2020_RGB_LIMITEDRANGE: ++ case COLOR_SPACE_ADOBERGB: ++ return true; ++ case COLOR_SPACE_YCBCR601: ++ case COLOR_SPACE_YCBCR709: ++ case COLOR_SPACE_YCBCR601_LIMITED: ++ case COLOR_SPACE_YCBCR709_LIMITED: ++ case COLOR_SPACE_2020_YCBCR: ++ return false; ++ default: ++ /* Add a case to switch */ ++ BREAK_TO_DEBUGGER(); ++ return false; ++ } ++} ++ ++bool is_lower_pipe_tree_visible(struct pipe_ctx *pipe_ctx) ++{ ++ if (pipe_ctx->plane_state && pipe_ctx->plane_state->visible) ++ return true; ++ if (pipe_ctx->bottom_pipe && is_lower_pipe_tree_visible(pipe_ctx->bottom_pipe)) ++ return true; ++ return false; ++} ++ ++bool is_upper_pipe_tree_visible(struct pipe_ctx *pipe_ctx) ++{ ++ if (pipe_ctx->plane_state && pipe_ctx->plane_state->visible) ++ return true; ++ if (pipe_ctx->top_pipe && is_upper_pipe_tree_visible(pipe_ctx->top_pipe)) ++ return true; ++ return false; ++} ++ ++bool is_pipe_tree_visible(struct pipe_ctx *pipe_ctx) ++{ ++ if (pipe_ctx->plane_state && pipe_ctx->plane_state->visible) ++ return true; ++ if (pipe_ctx->top_pipe && is_upper_pipe_tree_visible(pipe_ctx->top_pipe)) ++ return true; ++ if (pipe_ctx->bottom_pipe && is_lower_pipe_tree_visible(pipe_ctx->bottom_pipe)) ++ return true; ++ return false; ++} ++ ++void build_prescale_params(struct dc_bias_and_scale *bias_and_scale, ++ const struct dc_plane_state *plane_state) ++{ ++ if (plane_state->format >= SURFACE_PIXEL_FORMAT_VIDEO_BEGIN ++ && plane_state->format != SURFACE_PIXEL_FORMAT_INVALID ++ && plane_state->input_csc_color_matrix.enable_adjustment ++ && plane_state->coeff_reduction_factor.value != 0) { ++ bias_and_scale->scale_blue = fixed_point_to_int_frac( ++ dc_fixpt_mul(plane_state->coeff_reduction_factor, ++ dc_fixpt_from_fraction(256, 255)), ++ 2, ++ 13); ++ bias_and_scale->scale_red = bias_and_scale->scale_blue; ++ bias_and_scale->scale_green = bias_and_scale->scale_blue; ++ } else { ++ bias_and_scale->scale_blue = 0x2000; ++ bias_and_scale->scale_red = 0x2000; ++ bias_and_scale->scale_green = 0x2000; ++ } ++} ++ +diff --git a/drivers/gpu/drm/amd/display/dc/basics/dc_common.h b/drivers/gpu/drm/amd/display/dc/basics/dc_common.h +new file mode 100644 +index 000000000000..7c0cbf47e8ce +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/basics/dc_common.h +@@ -0,0 +1,42 @@ ++/* ++ * Copyright 2012-15 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#ifndef __DAL_DC_COMMON_H__ ++#define __DAL_DC_COMMON_H__ ++ ++#include "core_types.h" ++ ++bool is_rgb_cspace(enum dc_color_space output_color_space); ++ ++bool is_lower_pipe_tree_visible(struct pipe_ctx *pipe_ctx); ++ ++bool is_upper_pipe_tree_visible(struct pipe_ctx *pipe_ctx); ++ ++bool is_pipe_tree_visible(struct pipe_ctx *pipe_ctx); ++ ++void build_prescale_params(struct dc_bias_and_scale *bias_and_scale, ++ const struct dc_plane_state *plane_state); ++ ++#endif +diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c +index 121465bf223f..562a24f4553f 100644 +--- a/drivers/gpu/drm/amd/display/dc/core/dc.c ++++ b/drivers/gpu/drm/amd/display/dc/core/dc.c +@@ -1968,11 +1968,11 @@ static void commit_planes_do_stream_update(struct dc *dc, + + if (stream_update->periodic_interrupt0 && + dc->hwss.setup_periodic_interrupt) +- dc->hwss.setup_periodic_interrupt(pipe_ctx, VLINE0); ++ dc->hwss.setup_periodic_interrupt(dc, pipe_ctx, VLINE0); + + if (stream_update->periodic_interrupt1 && + dc->hwss.setup_periodic_interrupt) +- dc->hwss.setup_periodic_interrupt(pipe_ctx, VLINE1); ++ dc->hwss.setup_periodic_interrupt(dc, pipe_ctx, VLINE1); + + if ((stream_update->hdr_static_metadata && !stream->use_dynamic_meta) || + stream_update->vrr_infopacket || +diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_stream.c b/drivers/gpu/drm/amd/display/dc/core/dc_stream.c +index 59eaa5c172a9..9029786c7b08 100644 +--- a/drivers/gpu/drm/amd/display/dc/core/dc_stream.c ++++ b/drivers/gpu/drm/amd/display/dc/core/dc_stream.c +@@ -24,6 +24,7 @@ + */ + + #include "dm_services.h" ++#include "basics/dc_common.h" + #include "dc.h" + #include "core_types.h" + #include "resource.h" +@@ -241,7 +242,7 @@ static void delay_cursor_until_vupdate(struct pipe_ctx *pipe_ctx, struct dc *dc) + if (stream->ctx->asic_id.chip_family == FAMILY_RV && + ASICREV_IS_RAVEN(stream->ctx->asic_id.hw_internal_rev)) { + +- vupdate_line = get_vupdate_offset_from_vsync(pipe_ctx); ++ vupdate_line = dc->hwss.get_vupdate_offset_from_vsync(pipe_ctx); + if (!dc_stream_get_crtc_position(dc, &stream, 1, &vpos, &nvpos)) + return; + +diff --git a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c +index 01fefe19ee92..6291f803cd16 100644 +--- a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c ++++ b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c +@@ -58,6 +58,8 @@ + + #include "atomfirmware.h" + ++#define GAMMA_HW_POINTS_NUM 256 ++ + /* + * All values are in milliseconds; + * For eDP, after power-up/power/down, +@@ -265,7 +267,7 @@ static void build_prescale_params(struct ipp_prescale_params *prescale_params, + } + + static bool +-dce110_set_input_transfer_func(struct pipe_ctx *pipe_ctx, ++dce110_set_input_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, + const struct dc_plane_state *plane_state) + { + struct input_pixel_processor *ipp = pipe_ctx->plane_res.ipp; +@@ -593,7 +595,7 @@ dce110_translate_regamma_to_hw_format(const struct dc_transfer_func *output_tf, + } + + static bool +-dce110_set_output_transfer_func(struct pipe_ctx *pipe_ctx, ++dce110_set_output_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, + const struct dc_stream_state *stream) + { + struct transform *xfm = pipe_ctx->plane_res.xfm; +@@ -1355,7 +1357,7 @@ static enum dc_status apply_single_controller_ctx_to_hw( + dc->hwss.enable_stream_timing(pipe_ctx, context, dc); + + if (dc->hwss.setup_vupdate_interrupt) +- dc->hwss.setup_vupdate_interrupt(pipe_ctx); ++ dc->hwss.setup_vupdate_interrupt(dc, pipe_ctx); + + params.vertical_total_min = stream->adjust.v_total_min; + params.vertical_total_max = stream->adjust.v_total_max; +@@ -2498,10 +2500,10 @@ static void dce110_program_front_end_for_pipe( + if (pipe_ctx->plane_state->update_flags.bits.full_update || + pipe_ctx->plane_state->update_flags.bits.in_transfer_func_change || + pipe_ctx->plane_state->update_flags.bits.gamma_change) +- dc->hwss.set_input_transfer_func(pipe_ctx, pipe_ctx->plane_state); ++ dc->hwss.set_input_transfer_func(dc, pipe_ctx, pipe_ctx->plane_state); + + if (pipe_ctx->plane_state->update_flags.bits.full_update) +- dc->hwss.set_output_transfer_func(pipe_ctx, pipe_ctx->stream); ++ dc->hwss.set_output_transfer_func(dc, pipe_ctx, pipe_ctx->stream); + + DC_LOG_SURFACE( + "Pipe:%d %p: addr hi:0x%x, " +diff --git a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.h b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.h +index 2f9b7dbdf415..c639e1680b7b 100644 +--- a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.h ++++ b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.h +@@ -28,7 +28,6 @@ + + #include "core_types.h" + +-#define GAMMA_HW_POINTS_NUM 256 + struct dc; + struct dc_state; + struct dm_pp_display_configuration; +diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/Makefile b/drivers/gpu/drm/amd/display/dc/dcn10/Makefile +index 032f872be89c..62ad1a11bff9 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn10/Makefile ++++ b/drivers/gpu/drm/amd/display/dc/dcn10/Makefile +@@ -22,7 +22,8 @@ + # + # Makefile for DCN. + +-DCN10 = dcn10_resource.o dcn10_ipp.o dcn10_hw_sequencer.o dcn10_hw_sequencer_debug.o \ ++DCN10 = dcn10_init.o dcn10_resource.o dcn10_ipp.o dcn10_hw_sequencer.o \ ++ dcn10_hw_sequencer_debug.o \ + dcn10_dpp.o dcn10_opp.o dcn10_optc.o \ + dcn10_hubp.o dcn10_mpc.o \ + dcn10_dpp_dscl.o dcn10_dpp_cm.o dcn10_cm_common.o \ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c +index df59bd9185b5..08d15982f526 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c +@@ -24,17 +24,18 @@ + */ + + #include "dm_services.h" ++#include "basics/dc_common.h" + #include "core_types.h" + #include "resource.h" + #include "custom_float.h" + #include "dcn10_hw_sequencer.h" +-#include "dce110/dce110_hw_sequencer.h" ++#include "dcn10_hw_sequencer_debug.h" + #include "dce/dce_hwseq.h" + #include "abm.h" + #include "dmcu.h" + #include "dcn10_optc.h" +-#include "dcn10/dcn10_dpp.h" +-#include "dcn10/dcn10_mpc.h" ++#include "dcn10_dpp.h" ++#include "dcn10_mpc.h" + #include "timing_generator.h" + #include "opp.h" + #include "ipp.h" +@@ -65,6 +66,8 @@ + #define DTN_INFO_MICRO_SEC(ref_cycle) \ + print_microsec(dc_ctx, log_ctx, ref_cycle) + ++#define GAMMA_HW_POINTS_NUM 256 ++ + void print_microsec(struct dc_context *dc_ctx, + struct dc_log_buffer_ctx *log_ctx, + uint32_t ref_cycle) +@@ -78,6 +81,33 @@ void print_microsec(struct dc_context *dc_ctx, + us_x10 % frac); + } + ++static void dcn10_lock_all_pipes(struct dc *dc, ++ struct dc_state *context, ++ bool lock) ++{ ++ struct pipe_ctx *pipe_ctx; ++ struct timing_generator *tg; ++ int i; ++ ++ for (i = 0; i < dc->res_pool->pipe_count; i++) { ++ pipe_ctx = &context->res_ctx.pipe_ctx[i]; ++ tg = pipe_ctx->stream_res.tg; ++ /* ++ * Only lock the top pipe's tg to prevent redundant ++ * (un)locking. Also skip if pipe is disabled. ++ */ ++ if (pipe_ctx->top_pipe || ++ !pipe_ctx->stream || !pipe_ctx->plane_state || ++ !tg->funcs->is_tg_enabled(tg)) ++ continue; ++ ++ if (lock) ++ tg->funcs->lock(tg); ++ else ++ tg->funcs->unlock(tg); ++ } ++} ++ + static void log_mpc_crc(struct dc *dc, + struct dc_log_buffer_ctx *log_ctx) + { +@@ -444,7 +474,7 @@ bool dcn10_did_underflow_occur(struct dc *dc, struct pipe_ctx *pipe_ctx) + return false; + } + +-static void dcn10_enable_power_gating_plane( ++void dcn10_enable_power_gating_plane( + struct dce_hwseq *hws, + bool enable) + { +@@ -466,7 +496,7 @@ static void dcn10_enable_power_gating_plane( + REG_UPDATE(DOMAIN7_PG_CONFIG, DOMAIN7_POWER_FORCEON, force_on); + } + +-static void dcn10_disable_vga( ++void dcn10_disable_vga( + struct dce_hwseq *hws) + { + unsigned int in_vga1_mode = 0; +@@ -499,7 +529,7 @@ static void dcn10_disable_vga( + REG_UPDATE(VGA_TEST_CONTROL, VGA_TEST_RENDER_START, 1); + } + +-static void dcn10_dpp_pg_control( ++void dcn10_dpp_pg_control( + struct dce_hwseq *hws, + unsigned int dpp_inst, + bool power_on) +@@ -551,7 +581,7 @@ static void dcn10_dpp_pg_control( + } + } + +-static void dcn10_hubp_pg_control( ++void dcn10_hubp_pg_control( + struct dce_hwseq *hws, + unsigned int hubp_inst, + bool power_on) +@@ -670,7 +700,7 @@ static void apply_DEGVIDCN10_253_wa(struct dc *dc) + hws->wa_state.DEGVIDCN10_253_applied = true; + } + +-static void dcn10_bios_golden_init(struct dc *dc) ++void dcn10_bios_golden_init(struct dc *dc) + { + struct dc_bios *bp = dc->ctx->dc_bios; + int i; +@@ -738,7 +768,7 @@ static void false_optc_underflow_wa( + tg->funcs->clear_optc_underflow(tg); + } + +-static enum dc_status dcn10_enable_stream_timing( ++enum dc_status dcn10_enable_stream_timing( + struct pipe_ctx *pipe_ctx, + struct dc_state *context, + struct dc *dc) +@@ -984,7 +1014,7 @@ void dcn10_verify_allow_pstate_change_high(struct dc *dc) + } + + /* trigger HW to start disconnect plane from stream on the next vsync */ +-void hwss1_plane_atomic_disconnect(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn10_plane_atomic_disconnect(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct hubp *hubp = pipe_ctx->plane_res.hubp; + int dpp_id = pipe_ctx->plane_res.dpp->inst; +@@ -1010,10 +1040,10 @@ void hwss1_plane_atomic_disconnect(struct dc *dc, struct pipe_ctx *pipe_ctx) + hubp->funcs->hubp_disconnect(hubp); + + if (dc->debug.sanity_checks) +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + +-static void dcn10_plane_atomic_power_down(struct dc *dc, ++void dcn10_plane_atomic_power_down(struct dc *dc, + struct dpp *dpp, + struct hubp *hubp) + { +@@ -1036,7 +1066,7 @@ static void dcn10_plane_atomic_power_down(struct dc *dc, + /* disable HW used by plane. + * note: cannot disable until disconnect is complete + */ +-static void dcn10_plane_atomic_disable(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn10_plane_atomic_disable(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct hubp *hubp = pipe_ctx->plane_res.hubp; + struct dpp *dpp = pipe_ctx->plane_res.dpp; +@@ -1068,7 +1098,7 @@ static void dcn10_plane_atomic_disable(struct dc *dc, struct pipe_ctx *pipe_ctx) + pipe_ctx->plane_state = NULL; + } + +-static void dcn10_disable_plane(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn10_disable_plane(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + DC_LOGGER_INIT(dc->ctx->logger); + +@@ -1083,7 +1113,7 @@ static void dcn10_disable_plane(struct dc *dc, struct pipe_ctx *pipe_ctx) + pipe_ctx->pipe_idx); + } + +-static void dcn10_init_pipes(struct dc *dc, struct dc_state *context) ++void dcn10_init_pipes(struct dc *dc, struct dc_state *context) + { + int i; + bool can_apply_seamless_boot = false; +@@ -1182,7 +1212,7 @@ static void dcn10_init_pipes(struct dc *dc, struct dc_state *context) + } + } + +-static void dcn10_init_hw(struct dc *dc) ++void dcn10_init_hw(struct dc *dc) + { + int i; + struct abm *abm = dc->res_pool->abm; +@@ -1314,7 +1344,7 @@ static void dcn10_init_hw(struct dc *dc) + + } + +-static void dcn10_reset_hw_ctx_wrap( ++void dcn10_reset_hw_ctx_wrap( + struct dc *dc, + struct dc_state *context) + { +@@ -1371,9 +1401,7 @@ static bool patch_address_for_sbs_tb_stereo( + return false; + } + +- +- +-static void dcn10_update_plane_addr(const struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn10_update_plane_addr(const struct dc *dc, struct pipe_ctx *pipe_ctx) + { + bool addr_patched = false; + PHYSICAL_ADDRESS_LOC addr; +@@ -1398,8 +1426,8 @@ static void dcn10_update_plane_addr(const struct dc *dc, struct pipe_ctx *pipe_c + pipe_ctx->plane_state->address.grph_stereo.left_addr = addr; + } + +-static bool dcn10_set_input_transfer_func(struct pipe_ctx *pipe_ctx, +- const struct dc_plane_state *plane_state) ++bool dcn10_set_input_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, ++ const struct dc_plane_state *plane_state) + { + struct dpp *dpp_base = pipe_ctx->plane_res.dpp; + const struct dc_transfer_func *tf = NULL; +@@ -1475,9 +1503,8 @@ static void log_tf(struct dc_context *ctx, + } + } + +-static bool +-dcn10_set_output_transfer_func(struct pipe_ctx *pipe_ctx, +- const struct dc_stream_state *stream) ++bool dcn10_set_output_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, ++ const struct dc_stream_state *stream) + { + struct dpp *dpp = pipe_ctx->plane_res.dpp; + +@@ -1513,7 +1540,7 @@ dcn10_set_output_transfer_func(struct pipe_ctx *pipe_ctx, + return true; + } + +-static void dcn10_pipe_control_lock( ++void dcn10_pipe_control_lock( + struct dc *dc, + struct pipe_ctx *pipe, + bool lock) +@@ -1525,7 +1552,7 @@ static void dcn10_pipe_control_lock( + return; + + if (dc->debug.sanity_checks) +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + + if (lock) + pipe->stream_res.tg->funcs->lock(pipe->stream_res.tg); +@@ -1533,7 +1560,7 @@ static void dcn10_pipe_control_lock( + pipe->stream_res.tg->funcs->unlock(pipe->stream_res.tg); + + if (dc->debug.sanity_checks) +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + + static bool wait_for_reset_trigger_to_occur( +@@ -1573,7 +1600,7 @@ static bool wait_for_reset_trigger_to_occur( + return rc; + } + +-static void dcn10_enable_timing_synchronization( ++void dcn10_enable_timing_synchronization( + struct dc *dc, + int group_index, + int group_size, +@@ -1603,7 +1630,7 @@ static void dcn10_enable_timing_synchronization( + DC_SYNC_INFO("Sync complete\n"); + } + +-static void dcn10_enable_per_frame_crtc_position_reset( ++void dcn10_enable_per_frame_crtc_position_reset( + struct dc *dc, + int group_size, + struct pipe_ctx *grouped_pipes[]) +@@ -1841,7 +1868,7 @@ static void dcn10_enable_plane( + struct dce_hwseq *hws = dc->hwseq; + + if (dc->debug.sanity_checks) { +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + + undo_DEGVIDCN10_253_wa(dc); +@@ -1898,11 +1925,11 @@ static void dcn10_enable_plane( + dcn10_program_pte_vm(hws, pipe_ctx->plane_res.hubp); + + if (dc->debug.sanity_checks) { +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + } + +-static void dcn10_program_gamut_remap(struct pipe_ctx *pipe_ctx) ++void dcn10_program_gamut_remap(struct pipe_ctx *pipe_ctx) + { + int i = 0; + struct dpp_grph_csc_adjustment adjust; +@@ -1950,7 +1977,7 @@ static void dcn10_set_csc_adjustment_rgb_mpo_fix(struct pipe_ctx *pipe_ctx, uint + matrix[11] = rgb_bias; + } + +-static void dcn10_program_output_csc(struct dc *dc, ++void dcn10_program_output_csc(struct dc *dc, + struct pipe_ctx *pipe_ctx, + enum dc_color_space colorspace, + uint16_t *matrix, +@@ -1982,57 +2009,6 @@ static void dcn10_program_output_csc(struct dc *dc, + } + } + +-bool is_lower_pipe_tree_visible(struct pipe_ctx *pipe_ctx) +-{ +- if (pipe_ctx->plane_state && pipe_ctx->plane_state->visible) +- return true; +- if (pipe_ctx->bottom_pipe && is_lower_pipe_tree_visible(pipe_ctx->bottom_pipe)) +- return true; +- return false; +-} +- +-bool is_upper_pipe_tree_visible(struct pipe_ctx *pipe_ctx) +-{ +- if (pipe_ctx->plane_state && pipe_ctx->plane_state->visible) +- return true; +- if (pipe_ctx->top_pipe && is_upper_pipe_tree_visible(pipe_ctx->top_pipe)) +- return true; +- return false; +-} +- +-bool is_pipe_tree_visible(struct pipe_ctx *pipe_ctx) +-{ +- if (pipe_ctx->plane_state && pipe_ctx->plane_state->visible) +- return true; +- if (pipe_ctx->top_pipe && is_upper_pipe_tree_visible(pipe_ctx->top_pipe)) +- return true; +- if (pipe_ctx->bottom_pipe && is_lower_pipe_tree_visible(pipe_ctx->bottom_pipe)) +- return true; +- return false; +-} +- +-bool is_rgb_cspace(enum dc_color_space output_color_space) +-{ +- switch (output_color_space) { +- case COLOR_SPACE_SRGB: +- case COLOR_SPACE_SRGB_LIMITED: +- case COLOR_SPACE_2020_RGB_FULLRANGE: +- case COLOR_SPACE_2020_RGB_LIMITEDRANGE: +- case COLOR_SPACE_ADOBERGB: +- return true; +- case COLOR_SPACE_YCBCR601: +- case COLOR_SPACE_YCBCR709: +- case COLOR_SPACE_YCBCR601_LIMITED: +- case COLOR_SPACE_YCBCR709_LIMITED: +- case COLOR_SPACE_2020_YCBCR: +- return false; +- default: +- /* Add a case to switch */ +- BREAK_TO_DEBUGGER(); +- return false; +- } +-} +- + void dcn10_get_surface_visual_confirm_color( + const struct pipe_ctx *pipe_ctx, + struct tg_color *color) +@@ -2106,70 +2082,7 @@ void dcn10_get_hdr_visual_confirm_color( + } + } + +-static uint16_t fixed_point_to_int_frac( +- struct fixed31_32 arg, +- uint8_t integer_bits, +- uint8_t fractional_bits) +-{ +- int32_t numerator; +- int32_t divisor = 1 << fractional_bits; +- +- uint16_t result; +- +- uint16_t d = (uint16_t)dc_fixpt_floor( +- dc_fixpt_abs( +- arg)); +- +- if (d <= (uint16_t)(1 << integer_bits) - (1 / (uint16_t)divisor)) +- numerator = (uint16_t)dc_fixpt_floor( +- dc_fixpt_mul_int( +- arg, +- divisor)); +- else { +- numerator = dc_fixpt_floor( +- dc_fixpt_sub( +- dc_fixpt_from_int( +- 1LL << integer_bits), +- dc_fixpt_recip( +- dc_fixpt_from_int( +- divisor)))); +- } +- +- if (numerator >= 0) +- result = (uint16_t)numerator; +- else +- result = (uint16_t)( +- (1 << (integer_bits + fractional_bits + 1)) + numerator); +- +- if ((result != 0) && dc_fixpt_lt( +- arg, dc_fixpt_zero)) +- result |= 1 << (integer_bits + fractional_bits); +- +- return result; +-} +- +-void dcn10_build_prescale_params(struct dc_bias_and_scale *bias_and_scale, +- const struct dc_plane_state *plane_state) +-{ +- if (plane_state->format >= SURFACE_PIXEL_FORMAT_VIDEO_BEGIN +- && plane_state->format != SURFACE_PIXEL_FORMAT_INVALID +- && plane_state->input_csc_color_matrix.enable_adjustment +- && plane_state->coeff_reduction_factor.value != 0) { +- bias_and_scale->scale_blue = fixed_point_to_int_frac( +- dc_fixpt_mul(plane_state->coeff_reduction_factor, +- dc_fixpt_from_fraction(256, 255)), +- 2, +- 13); +- bias_and_scale->scale_red = bias_and_scale->scale_blue; +- bias_and_scale->scale_green = bias_and_scale->scale_blue; +- } else { +- bias_and_scale->scale_blue = 0x2000; +- bias_and_scale->scale_red = 0x2000; +- bias_and_scale->scale_green = 0x2000; +- } +-} +- +-static void update_dpp(struct dpp *dpp, struct dc_plane_state *plane_state) ++static void dcn10_update_dpp(struct dpp *dpp, struct dc_plane_state *plane_state) + { + struct dc_bias_and_scale bns_params = {0}; + +@@ -2182,12 +2095,12 @@ static void update_dpp(struct dpp *dpp, struct dc_plane_state *plane_state) + NULL); + + //set scale and bias registers +- dcn10_build_prescale_params(&bns_params, plane_state); ++ build_prescale_params(&bns_params, plane_state); + if (dpp->funcs->dpp_program_bias_and_scale) + dpp->funcs->dpp_program_bias_and_scale(dpp, &bns_params); + } + +-static void dcn10_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn10_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct hubp *hubp = pipe_ctx->plane_res.hubp; + struct mpcc_blnd_cfg blnd_cfg = {{0}}; +@@ -2198,10 +2111,10 @@ static void dcn10_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx) + struct mpc_tree *mpc_tree_params = &(pipe_ctx->stream_res.opp->mpc_tree_params); + + if (dc->debug.visual_confirm == VISUAL_CONFIRM_HDR) { +- dcn10_get_hdr_visual_confirm_color( ++ dc->hwss.get_hdr_visual_confirm_color( + pipe_ctx, &blnd_cfg.black_color); + } else if (dc->debug.visual_confirm == VISUAL_CONFIRM_SURFACE) { +- dcn10_get_surface_visual_confirm_color( ++ dc->hwss.get_surface_visual_confirm_color( + pipe_ctx, &blnd_cfg.black_color); + } else { + color_space_to_black_color( +@@ -2283,7 +2196,7 @@ static void update_scaler(struct pipe_ctx *pipe_ctx) + pipe_ctx->plane_res.dpp, &pipe_ctx->plane_res.scl_data); + } + +-void update_dchubp_dpp( ++static void dcn10_update_dchubp_dpp( + struct dc *dc, + struct pipe_ctx *pipe_ctx, + struct dc_state *context) +@@ -2341,7 +2254,7 @@ void update_dchubp_dpp( + + if (plane_state->update_flags.bits.full_update || + plane_state->update_flags.bits.bpp_change) +- update_dpp(dpp, plane_state); ++ dcn10_update_dpp(dpp, plane_state); + + if (plane_state->update_flags.bits.full_update || + plane_state->update_flags.bits.per_pixel_alpha_change || +@@ -2412,7 +2325,7 @@ void update_dchubp_dpp( + hubp->funcs->set_blank(hubp, false); + } + +-static void dcn10_blank_pixel_data( ++void dcn10_blank_pixel_data( + struct dc *dc, + struct pipe_ctx *pipe_ctx, + bool blank) +@@ -2455,7 +2368,7 @@ static void dcn10_blank_pixel_data( + } + } + +-void set_hdr_multiplier(struct pipe_ctx *pipe_ctx) ++void dcn10_set_hdr_multiplier(struct pipe_ctx *pipe_ctx) + { + struct fixed31_32 multiplier = pipe_ctx->plane_state->hdr_mult; + uint32_t hw_mult = 0x1f000; // 1.0 default multiplier +@@ -2485,14 +2398,14 @@ void dcn10_program_pipe( + if (pipe_ctx->plane_state->update_flags.bits.full_update) + dcn10_enable_plane(dc, pipe_ctx, context); + +- update_dchubp_dpp(dc, pipe_ctx, context); ++ dcn10_update_dchubp_dpp(dc, pipe_ctx, context); + +- set_hdr_multiplier(pipe_ctx); ++ dc->hwss.set_hdr_multiplier(pipe_ctx); + + if (pipe_ctx->plane_state->update_flags.bits.full_update || + pipe_ctx->plane_state->update_flags.bits.in_transfer_func_change || + pipe_ctx->plane_state->update_flags.bits.gamma_change) +- dc->hwss.set_input_transfer_func(pipe_ctx, pipe_ctx->plane_state); ++ dc->hwss.set_input_transfer_func(dc, pipe_ctx, pipe_ctx->plane_state); + + /* dcn10_translate_regamma_to_hw_format takes 750us to finish + * only do gamma programming for full update. +@@ -2501,10 +2414,10 @@ void dcn10_program_pipe( + * doing heavy calculation and programming + */ + if (pipe_ctx->plane_state->update_flags.bits.full_update) +- dc->hwss.set_output_transfer_func(pipe_ctx, pipe_ctx->stream); ++ dc->hwss.set_output_transfer_func(dc, pipe_ctx, pipe_ctx->stream); + } + +-static void program_all_pipe_in_tree( ++static void dcn10_program_all_pipe_in_tree( + struct dc *dc, + struct pipe_ctx *pipe_ctx, + struct dc_state *context) +@@ -2523,19 +2436,19 @@ static void program_all_pipe_in_tree( + pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing); + + if (dc->hwss.setup_vupdate_interrupt) +- dc->hwss.setup_vupdate_interrupt(pipe_ctx); ++ dc->hwss.setup_vupdate_interrupt(dc, pipe_ctx); + + dc->hwss.blank_pixel_data(dc, pipe_ctx, blank); + } + + if (pipe_ctx->plane_state != NULL) +- dcn10_program_pipe(dc, pipe_ctx, context); ++ dc->hwss.program_pipe(dc, pipe_ctx, context); + + if (pipe_ctx->bottom_pipe != NULL && pipe_ctx->bottom_pipe != pipe_ctx) +- program_all_pipe_in_tree(dc, pipe_ctx->bottom_pipe, context); ++ dcn10_program_all_pipe_in_tree(dc, pipe_ctx->bottom_pipe, context); + } + +-struct pipe_ctx *find_top_pipe_for_stream( ++static struct pipe_ctx *dcn10_find_top_pipe_for_stream( + struct dc *dc, + struct dc_state *context, + const struct dc_stream_state *stream) +@@ -2559,7 +2472,7 @@ struct pipe_ctx *find_top_pipe_for_stream( + return NULL; + } + +-static void dcn10_apply_ctx_for_surface( ++void dcn10_apply_ctx_for_surface( + struct dc *dc, + const struct dc_stream_state *stream, + int num_planes, +@@ -2571,7 +2484,7 @@ static void dcn10_apply_ctx_for_surface( + bool removed_pipe[4] = { false }; + bool interdependent_update = false; + struct pipe_ctx *top_pipe_to_program = +- find_top_pipe_for_stream(dc, context, stream); ++ dcn10_find_top_pipe_for_stream(dc, context, stream); + DC_LOGGER_INIT(dc->ctx->logger); + + if (!top_pipe_to_program) +@@ -2588,7 +2501,7 @@ static void dcn10_apply_ctx_for_surface( + ASSERT(dc->hwss.did_underflow_occur(dc, top_pipe_to_program)); + + if (interdependent_update) +- lock_all_pipes(dc, context, true); ++ dcn10_lock_all_pipes(dc, context, true); + else + dcn10_pipe_control_lock(dc, top_pipe_to_program, true); + +@@ -2635,7 +2548,7 @@ static void dcn10_apply_ctx_for_surface( + } + + if (num_planes > 0) +- program_all_pipe_in_tree(dc, top_pipe_to_program, context); ++ dcn10_program_all_pipe_in_tree(dc, top_pipe_to_program, context); + + /* Program secondary blending tree and writeback pipes */ + if ((stream->num_wb_info > 0) && (dc->hwss.program_all_writeback_pipes_in_tree)) +@@ -2655,7 +2568,7 @@ static void dcn10_apply_ctx_for_surface( + } + + if (interdependent_update) +- lock_all_pipes(dc, context, false); ++ dcn10_lock_all_pipes(dc, context, false); + else + dcn10_pipe_control_lock(dc, top_pipe_to_program, false); + +@@ -2692,14 +2605,14 @@ static void dcn10_stereo_hw_frame_pack_wa(struct dc *dc, struct dc_state *contex + } + } + +-static void dcn10_prepare_bandwidth( ++void dcn10_prepare_bandwidth( + struct dc *dc, + struct dc_state *context) + { + struct hubbub *hubbub = dc->res_pool->hubbub; + + if (dc->debug.sanity_checks) +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + + if (!IS_FPGA_MAXIMUS_DC(dc->ctx->dce_environment)) { + if (context->stream_count == 0) +@@ -2721,17 +2634,17 @@ static void dcn10_prepare_bandwidth( + dcn_bw_notify_pplib_of_wm_ranges(dc); + + if (dc->debug.sanity_checks) +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + +-static void dcn10_optimize_bandwidth( ++void dcn10_optimize_bandwidth( + struct dc *dc, + struct dc_state *context) + { + struct hubbub *hubbub = dc->res_pool->hubbub; + + if (dc->debug.sanity_checks) +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + + if (!IS_FPGA_MAXIMUS_DC(dc->ctx->dce_environment)) { + if (context->stream_count == 0) +@@ -2753,10 +2666,10 @@ static void dcn10_optimize_bandwidth( + dcn_bw_notify_pplib_of_wm_ranges(dc); + + if (dc->debug.sanity_checks) +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + +-static void dcn10_set_drr(struct pipe_ctx **pipe_ctx, ++void dcn10_set_drr(struct pipe_ctx **pipe_ctx, + int num_pipes, unsigned int vmin, unsigned int vmax, + unsigned int vmid, unsigned int vmid_frame_number) + { +@@ -2784,7 +2697,7 @@ static void dcn10_set_drr(struct pipe_ctx **pipe_ctx, + } + } + +-static void dcn10_get_position(struct pipe_ctx **pipe_ctx, ++void dcn10_get_position(struct pipe_ctx **pipe_ctx, + int num_pipes, + struct crtc_position *position) + { +@@ -2796,7 +2709,7 @@ static void dcn10_get_position(struct pipe_ctx **pipe_ctx, + pipe_ctx[i]->stream_res.tg->funcs->get_position(pipe_ctx[i]->stream_res.tg, position); + } + +-static void dcn10_set_static_screen_control(struct pipe_ctx **pipe_ctx, ++void dcn10_set_static_screen_control(struct pipe_ctx **pipe_ctx, + int num_pipes, const struct dc_static_screen_events *events) + { + unsigned int i; +@@ -2851,7 +2764,7 @@ static void dcn10_config_stereo_parameters( + return; + } + +-static void dcn10_setup_stereo(struct pipe_ctx *pipe_ctx, struct dc *dc) ++void dcn10_setup_stereo(struct pipe_ctx *pipe_ctx, struct dc *dc) + { + struct crtc_stereo_flags flags = { 0 }; + struct dc_stream_state *stream = pipe_ctx->stream; +@@ -2890,7 +2803,7 @@ static struct hubp *get_hubp_by_inst(struct resource_pool *res_pool, int mpcc_in + return NULL; + } + +-static void dcn10_wait_for_mpcc_disconnect( ++void dcn10_wait_for_mpcc_disconnect( + struct dc *dc, + struct resource_pool *res_pool, + struct pipe_ctx *pipe_ctx) +@@ -2898,7 +2811,7 @@ static void dcn10_wait_for_mpcc_disconnect( + int mpcc_inst; + + if (dc->debug.sanity_checks) { +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + + if (!pipe_ctx->stream_res.opp) +@@ -2915,12 +2828,12 @@ static void dcn10_wait_for_mpcc_disconnect( + } + + if (dc->debug.sanity_checks) { +- dcn10_verify_allow_pstate_change_high(dc); ++ dc->hwss.verify_allow_pstate_change_high(dc); + } + + } + +-static bool dcn10_dummy_display_power_gating( ++bool dcn10_dummy_display_power_gating( + struct dc *dc, + uint8_t controller_id, + struct dc_bios *dcb, +@@ -2929,7 +2842,7 @@ static bool dcn10_dummy_display_power_gating( + return true; + } + +-static void dcn10_update_pending_status(struct pipe_ctx *pipe_ctx) ++void dcn10_update_pending_status(struct pipe_ctx *pipe_ctx) + { + struct dc_plane_state *plane_state = pipe_ctx->plane_state; + struct timing_generator *tg = pipe_ctx->stream_res.tg; +@@ -2953,7 +2866,7 @@ static void dcn10_update_pending_status(struct pipe_ctx *pipe_ctx) + } + } + +-static void dcn10_update_dchub(struct dce_hwseq *hws, struct dchub_init_data *dh_data) ++void dcn10_update_dchub(struct dce_hwseq *hws, struct dchub_init_data *dh_data) + { + struct hubbub *hubbub = hws->ctx->dc->res_pool->hubbub; + +@@ -2961,7 +2874,7 @@ static void dcn10_update_dchub(struct dce_hwseq *hws, struct dchub_init_data *dh + hubbub->funcs->update_dchub(hubbub, dh_data); + } + +-static void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx) ++void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx) + { + struct dc_cursor_position pos_cpy = pipe_ctx->stream->cursor_position; + struct hubp *hubp = pipe_ctx->plane_res.hubp; +@@ -3027,7 +2940,7 @@ static void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx) + dpp->funcs->set_cursor_position(dpp, &pos_cpy, ¶m, hubp->curs_attr.width, hubp->curs_attr.height); + } + +-static void dcn10_set_cursor_attribute(struct pipe_ctx *pipe_ctx) ++void dcn10_set_cursor_attribute(struct pipe_ctx *pipe_ctx) + { + struct dc_cursor_attributes *attributes = &pipe_ctx->stream->cursor_attributes; + +@@ -3037,7 +2950,7 @@ static void dcn10_set_cursor_attribute(struct pipe_ctx *pipe_ctx) + pipe_ctx->plane_res.dpp, attributes); + } + +-static void dcn10_set_cursor_sdr_white_level(struct pipe_ctx *pipe_ctx) ++void dcn10_set_cursor_sdr_white_level(struct pipe_ctx *pipe_ctx) + { + uint32_t sdr_white_level = pipe_ctx->stream->cursor_attributes.sdr_white_level; + struct fixed31_32 multiplier; +@@ -3064,12 +2977,12 @@ static void dcn10_set_cursor_sdr_white_level(struct pipe_ctx *pipe_ctx) + pipe_ctx->plane_res.dpp, &opt_attr); + } + +-/** +-* apply_front_porch_workaround TODO FPGA still need? +-* +-* This is a workaround for a bug that has existed since R5xx and has not been +-* fixed keep Front porch at minimum 2 for Interlaced mode or 1 for progressive. +-*/ ++/* ++ * apply_front_porch_workaround TODO FPGA still need? ++ * ++ * This is a workaround for a bug that has existed since R5xx and has not been ++ * fixed keep Front porch at minimum 2 for Interlaced mode or 1 for progressive. ++ */ + static void apply_front_porch_workaround( + struct dc_crtc_timing *timing) + { +@@ -3082,7 +2995,7 @@ static void apply_front_porch_workaround( + } + } + +-int get_vupdate_offset_from_vsync(struct pipe_ctx *pipe_ctx) ++int dcn10_get_vupdate_offset_from_vsync(struct pipe_ctx *pipe_ctx) + { + const struct dc_crtc_timing *dc_crtc_timing = &pipe_ctx->stream->timing; + struct dc_crtc_timing patched_crtc_timing; +@@ -3111,34 +3024,8 @@ int get_vupdate_offset_from_vsync(struct pipe_ctx *pipe_ctx) + return vertical_line_start; + } + +-void lock_all_pipes(struct dc *dc, +- struct dc_state *context, +- bool lock) +-{ +- struct pipe_ctx *pipe_ctx; +- struct timing_generator *tg; +- int i; +- +- for (i = 0; i < dc->res_pool->pipe_count; i++) { +- pipe_ctx = &context->res_ctx.pipe_ctx[i]; +- tg = pipe_ctx->stream_res.tg; +- /* +- * Only lock the top pipe's tg to prevent redundant +- * (un)locking. Also skip if pipe is disabled. +- */ +- if (pipe_ctx->top_pipe || +- !pipe_ctx->stream || !pipe_ctx->plane_state || +- !tg->funcs->is_tg_enabled(tg)) +- continue; +- +- if (lock) +- tg->funcs->lock(tg); +- else +- tg->funcs->unlock(tg); +- } +-} +- +-static void calc_vupdate_position( ++static void dcn10_calc_vupdate_position( ++ struct dc *dc, + struct pipe_ctx *pipe_ctx, + uint32_t *start_line, + uint32_t *end_line) +@@ -3146,7 +3033,7 @@ static void calc_vupdate_position( + const struct dc_crtc_timing *dc_crtc_timing = &pipe_ctx->stream->timing; + int vline_int_offset_from_vupdate = + pipe_ctx->stream->periodic_interrupt0.lines_offset; +- int vupdate_offset_from_vsync = get_vupdate_offset_from_vsync(pipe_ctx); ++ int vupdate_offset_from_vsync = dc->hwss.get_vupdate_offset_from_vsync(pipe_ctx); + int start_position; + + if (vline_int_offset_from_vupdate > 0) +@@ -3167,7 +3054,8 @@ static void calc_vupdate_position( + *end_line = 2; + } + +-static void cal_vline_position( ++static void dcn10_cal_vline_position( ++ struct dc *dc, + struct pipe_ctx *pipe_ctx, + enum vline_select vline, + uint32_t *start_line, +@@ -3182,7 +3070,8 @@ static void cal_vline_position( + + switch (ref_point) { + case START_V_UPDATE: +- calc_vupdate_position( ++ dcn10_calc_vupdate_position( ++ dc, + pipe_ctx, + start_line, + end_line); +@@ -3196,7 +3085,8 @@ static void cal_vline_position( + } + } + +-static void dcn10_setup_periodic_interrupt( ++void dcn10_setup_periodic_interrupt( ++ struct dc *dc, + struct pipe_ctx *pipe_ctx, + enum vline_select vline) + { +@@ -3206,7 +3096,7 @@ static void dcn10_setup_periodic_interrupt( + uint32_t start_line = 0; + uint32_t end_line = 0; + +- cal_vline_position(pipe_ctx, vline, &start_line, &end_line); ++ dcn10_cal_vline_position(dc, pipe_ctx, vline, &start_line, &end_line); + + tg->funcs->setup_vertical_interrupt0(tg, start_line, end_line); + +@@ -3217,10 +3107,10 @@ static void dcn10_setup_periodic_interrupt( + } + } + +-static void dcn10_setup_vupdate_interrupt(struct pipe_ctx *pipe_ctx) ++void dcn10_setup_vupdate_interrupt(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct timing_generator *tg = pipe_ctx->stream_res.tg; +- int start_line = get_vupdate_offset_from_vsync(pipe_ctx); ++ int start_line = dc->hwss.get_vupdate_offset_from_vsync(pipe_ctx); + + if (start_line < 0) { + ASSERT(0); +@@ -3231,7 +3121,7 @@ static void dcn10_setup_vupdate_interrupt(struct pipe_ctx *pipe_ctx) + tg->funcs->setup_vertical_interrupt2(tg, start_line); + } + +-static void dcn10_unblank_stream(struct pipe_ctx *pipe_ctx, ++void dcn10_unblank_stream(struct pipe_ctx *pipe_ctx, + struct dc_link_settings *link_settings) + { + struct encoder_unblank_param params = { { 0 } }; +@@ -3254,7 +3144,7 @@ static void dcn10_unblank_stream(struct pipe_ctx *pipe_ctx, + } + } + +-static void dcn10_send_immediate_sdp_message(struct pipe_ctx *pipe_ctx, ++void dcn10_send_immediate_sdp_message(struct pipe_ctx *pipe_ctx, + const uint8_t *custom_sdp_message, + unsigned int sdp_message_size) + { +@@ -3265,7 +3155,7 @@ static void dcn10_send_immediate_sdp_message(struct pipe_ctx *pipe_ctx, + sdp_message_size); + } + } +-static enum dc_status dcn10_set_clock(struct dc *dc, ++enum dc_status dcn10_set_clock(struct dc *dc, + enum dc_clock_type clock_type, + uint32_t clk_khz, + uint32_t stepping) +@@ -3305,7 +3195,7 @@ static enum dc_status dcn10_set_clock(struct dc *dc, + + } + +-static void dcn10_get_clock(struct dc *dc, ++void dcn10_get_clock(struct dc *dc, + enum dc_clock_type clock_type, + struct dc_clock_config *clock_cfg) + { +@@ -3315,77 +3205,3 @@ static void dcn10_get_clock(struct dc *dc, + dc->clk_mgr->funcs->get_clock(dc->clk_mgr, context, clock_type, clock_cfg); + + } +- +-static const struct hw_sequencer_funcs dcn10_funcs = { +- .program_gamut_remap = dcn10_program_gamut_remap, +- .init_hw = dcn10_init_hw, +- .init_pipes = dcn10_init_pipes, +- .apply_ctx_to_hw = dce110_apply_ctx_to_hw, +- .apply_ctx_for_surface = dcn10_apply_ctx_for_surface, +- .update_plane_addr = dcn10_update_plane_addr, +- .plane_atomic_disconnect = hwss1_plane_atomic_disconnect, +- .update_dchub = dcn10_update_dchub, +- .update_mpcc = dcn10_update_mpcc, +- .update_pending_status = dcn10_update_pending_status, +- .set_input_transfer_func = dcn10_set_input_transfer_func, +- .set_output_transfer_func = dcn10_set_output_transfer_func, +- .program_output_csc = dcn10_program_output_csc, +- .power_down = dce110_power_down, +- .enable_accelerated_mode = dce110_enable_accelerated_mode, +- .enable_timing_synchronization = dcn10_enable_timing_synchronization, +- .enable_per_frame_crtc_position_reset = dcn10_enable_per_frame_crtc_position_reset, +- .update_info_frame = dce110_update_info_frame, +- .send_immediate_sdp_message = dcn10_send_immediate_sdp_message, +- .enable_stream = dce110_enable_stream, +- .disable_stream = dce110_disable_stream, +- .unblank_stream = dcn10_unblank_stream, +- .blank_stream = dce110_blank_stream, +- .enable_audio_stream = dce110_enable_audio_stream, +- .disable_audio_stream = dce110_disable_audio_stream, +- .enable_display_power_gating = dcn10_dummy_display_power_gating, +- .disable_plane = dcn10_disable_plane, +- .blank_pixel_data = dcn10_blank_pixel_data, +- .pipe_control_lock = dcn10_pipe_control_lock, +- .prepare_bandwidth = dcn10_prepare_bandwidth, +- .optimize_bandwidth = dcn10_optimize_bandwidth, +- .reset_hw_ctx_wrap = dcn10_reset_hw_ctx_wrap, +- .enable_stream_timing = dcn10_enable_stream_timing, +- .set_drr = dcn10_set_drr, +- .get_position = dcn10_get_position, +- .set_static_screen_control = dcn10_set_static_screen_control, +- .setup_stereo = dcn10_setup_stereo, +- .set_avmute = dce110_set_avmute, +- .log_hw_state = dcn10_log_hw_state, +- .get_hw_state = dcn10_get_hw_state, +- .clear_status_bits = dcn10_clear_status_bits, +- .wait_for_mpcc_disconnect = dcn10_wait_for_mpcc_disconnect, +- .edp_backlight_control = dce110_edp_backlight_control, +- .edp_power_control = dce110_edp_power_control, +- .edp_wait_for_hpd_ready = dce110_edp_wait_for_hpd_ready, +- .set_cursor_position = dcn10_set_cursor_position, +- .set_cursor_attribute = dcn10_set_cursor_attribute, +- .set_cursor_sdr_white_level = dcn10_set_cursor_sdr_white_level, +- .disable_stream_gating = NULL, +- .enable_stream_gating = NULL, +- .setup_periodic_interrupt = dcn10_setup_periodic_interrupt, +- .setup_vupdate_interrupt = dcn10_setup_vupdate_interrupt, +- .set_clock = dcn10_set_clock, +- .get_clock = dcn10_get_clock, +- .did_underflow_occur = dcn10_did_underflow_occur, +- .init_blank = NULL, +- .disable_vga = dcn10_disable_vga, +- .bios_golden_init = dcn10_bios_golden_init, +- .plane_atomic_disable = dcn10_plane_atomic_disable, +- .plane_atomic_power_down = dcn10_plane_atomic_power_down, +- .enable_power_gating_plane = dcn10_enable_power_gating_plane, +- .dpp_pg_control = dcn10_dpp_pg_control, +- .hubp_pg_control = dcn10_hubp_pg_control, +- .dsc_pg_control = NULL, +-}; +- +- +-void dcn10_hw_sequencer_construct(struct dc *dc) +-{ +- dc->hwss = dcn10_funcs; +-} +- +diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.h b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.h +index d3616b1948cc..5aad3922be6c 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.h ++++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.h +@@ -31,64 +31,155 @@ + struct dc; + + void dcn10_hw_sequencer_construct(struct dc *dc); +-extern void fill_display_configs( +- const struct dc_state *context, +- struct dm_pp_display_configuration *pp_display_cfg); +- +-bool is_rgb_cspace(enum dc_color_space output_color_space); +- +-void hwss1_plane_atomic_disconnect(struct dc *dc, struct pipe_ctx *pipe_ctx); +- +-void dcn10_verify_allow_pstate_change_high(struct dc *dc); + ++int dcn10_get_vupdate_offset_from_vsync(struct pipe_ctx *pipe_ctx); ++void dcn10_setup_vupdate_interrupt(struct dc *dc, struct pipe_ctx *pipe_ctx); ++enum dc_status dcn10_enable_stream_timing( ++ struct pipe_ctx *pipe_ctx, ++ struct dc_state *context, ++ struct dc *dc); ++void dcn10_optimize_bandwidth( ++ struct dc *dc, ++ struct dc_state *context); ++void dcn10_prepare_bandwidth( ++ struct dc *dc, ++ struct dc_state *context); ++void dcn10_pipe_control_lock( ++ struct dc *dc, ++ struct pipe_ctx *pipe, ++ bool lock); ++void dcn10_blank_pixel_data( ++ struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ bool blank); ++void dcn10_unblank_stream(struct pipe_ctx *pipe_ctx, ++ struct dc_link_settings *link_settings); ++void dcn10_program_output_csc(struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ enum dc_color_space colorspace, ++ uint16_t *matrix, ++ int opp_id); ++bool dcn10_set_output_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, ++ const struct dc_stream_state *stream); ++bool dcn10_set_input_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, ++ const struct dc_plane_state *plane_state); ++void dcn10_update_plane_addr(const struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn10_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn10_reset_hw_ctx_wrap( ++ struct dc *dc, ++ struct dc_state *context); ++void dcn10_disable_plane(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn10_apply_ctx_for_surface( ++ struct dc *dc, ++ const struct dc_stream_state *stream, ++ int num_planes, ++ struct dc_state *context); ++void dcn10_hubp_pg_control( ++ struct dce_hwseq *hws, ++ unsigned int hubp_inst, ++ bool power_on); ++void dcn10_dpp_pg_control( ++ struct dce_hwseq *hws, ++ unsigned int dpp_inst, ++ bool power_on); ++void dcn10_enable_power_gating_plane( ++ struct dce_hwseq *hws, ++ bool enable); ++void dcn10_plane_atomic_disable(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn10_disable_vga( ++ struct dce_hwseq *hws); + void dcn10_program_pipe( + struct dc *dc, + struct pipe_ctx *pipe_ctx, + struct dc_state *context); +- +-void dcn10_get_hw_state( ++void dcn10_program_gamut_remap(struct pipe_ctx *pipe_ctx); ++void dcn10_init_hw(struct dc *dc); ++void dcn10_init_pipes(struct dc *dc, struct dc_state *context); ++enum dc_status dce110_apply_ctx_to_hw( ++ struct dc *dc, ++ struct dc_state *context); ++void dcn10_plane_atomic_disconnect(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn10_update_dchub(struct dce_hwseq *hws, struct dchub_init_data *dh_data); ++void dcn10_update_pending_status(struct pipe_ctx *pipe_ctx); ++void dce110_power_down(struct dc *dc); ++void dce110_enable_accelerated_mode(struct dc *dc, struct dc_state *context); ++void dcn10_enable_timing_synchronization( ++ struct dc *dc, ++ int group_index, ++ int group_size, ++ struct pipe_ctx *grouped_pipes[]); ++void dcn10_enable_per_frame_crtc_position_reset( ++ struct dc *dc, ++ int group_size, ++ struct pipe_ctx *grouped_pipes[]); ++void dce110_update_info_frame(struct pipe_ctx *pipe_ctx); ++void dcn10_send_immediate_sdp_message(struct pipe_ctx *pipe_ctx, ++ const uint8_t *custom_sdp_message, ++ unsigned int sdp_message_size); ++void dce110_blank_stream(struct pipe_ctx *pipe_ctx); ++void dce110_enable_audio_stream(struct pipe_ctx *pipe_ctx); ++void dce110_disable_audio_stream(struct pipe_ctx *pipe_ctx); ++bool dcn10_dummy_display_power_gating( + struct dc *dc, +- char *pBuf, unsigned int bufSize, ++ uint8_t controller_id, ++ struct dc_bios *dcb, ++ enum pipe_gating_control power_gating); ++void dcn10_set_drr(struct pipe_ctx **pipe_ctx, ++ int num_pipes, unsigned int vmin, unsigned int vmax, ++ unsigned int vmid, unsigned int vmid_frame_number); ++void dcn10_get_position(struct pipe_ctx **pipe_ctx, ++ int num_pipes, ++ struct crtc_position *position); ++void dcn10_set_static_screen_control(struct pipe_ctx **pipe_ctx, ++ int num_pipes, const struct dc_static_screen_events *events); ++void dcn10_setup_stereo(struct pipe_ctx *pipe_ctx, struct dc *dc); ++void dce110_set_avmute(struct pipe_ctx *pipe_ctx, bool enable); ++void dcn10_log_hw_state(struct dc *dc, ++ struct dc_log_buffer_ctx *log_ctx); ++void dcn10_get_hw_state(struct dc *dc, ++ char *pBuf, ++ unsigned int bufSize, + unsigned int mask); +- + void dcn10_clear_status_bits(struct dc *dc, unsigned int mask); +- +-bool is_lower_pipe_tree_visible(struct pipe_ctx *pipe_ctx); +- +-bool is_upper_pipe_tree_visible(struct pipe_ctx *pipe_ctx); +- +-bool is_pipe_tree_visible(struct pipe_ctx *pipe_ctx); +- +-void dcn10_program_pte_vm(struct dce_hwseq *hws, struct hubp *hubp); +- +-void set_hdr_multiplier(struct pipe_ctx *pipe_ctx); +- ++void dcn10_wait_for_mpcc_disconnect( ++ struct dc *dc, ++ struct resource_pool *res_pool, ++ struct pipe_ctx *pipe_ctx); ++void dce110_edp_backlight_control( ++ struct dc_link *link, ++ bool enable); ++void dce110_edp_power_control( ++ struct dc_link *link, ++ bool power_up); ++void dce110_edp_wait_for_hpd_ready( ++ struct dc_link *link, ++ bool power_up); ++void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx); ++void dcn10_set_cursor_attribute(struct pipe_ctx *pipe_ctx); ++void dcn10_set_cursor_sdr_white_level(struct pipe_ctx *pipe_ctx); ++void dcn10_setup_periodic_interrupt( ++ struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ enum vline_select vline); ++enum dc_status dcn10_set_clock(struct dc *dc, ++ enum dc_clock_type clock_type, ++ uint32_t clk_khz, ++ uint32_t stepping); ++void dcn10_get_clock(struct dc *dc, ++ enum dc_clock_type clock_type, ++ struct dc_clock_config *clock_cfg); ++bool dcn10_did_underflow_occur(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn10_bios_golden_init(struct dc *dc); ++void dcn10_plane_atomic_power_down(struct dc *dc, ++ struct dpp *dpp, ++ struct hubp *hubp); + void dcn10_get_surface_visual_confirm_color( + const struct pipe_ctx *pipe_ctx, + struct tg_color *color); +- + void dcn10_get_hdr_visual_confirm_color( + struct pipe_ctx *pipe_ctx, + struct tg_color *color); +- +-bool dcn10_did_underflow_occur(struct dc *dc, struct pipe_ctx *pipe_ctx); +- +-void update_dchubp_dpp( +- struct dc *dc, +- struct pipe_ctx *pipe_ctx, +- struct dc_state *context); +- +-struct pipe_ctx *find_top_pipe_for_stream( +- struct dc *dc, +- struct dc_state *context, +- const struct dc_stream_state *stream); +- +-int get_vupdate_offset_from_vsync(struct pipe_ctx *pipe_ctx); +- +-void dcn10_build_prescale_params(struct dc_bias_and_scale *bias_and_scale, +- const struct dc_plane_state *plane_state); +-void lock_all_pipes(struct dc *dc, +- struct dc_state *context, +- bool lock); ++void dcn10_set_hdr_multiplier(struct pipe_ctx *pipe_ctx); ++void dcn10_verify_allow_pstate_change_high(struct dc *dc); + + #endif /* __DC_HWSS_DCN10_H__ */ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer_debug.h b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer_debug.h +new file mode 100644 +index 000000000000..596f95c22e85 +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer_debug.h +@@ -0,0 +1,43 @@ ++/* ++ * Copyright 2016 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#ifndef __DC_HWSS_DCN10_DEBUG_H__ ++#define __DC_HWSS_DCN10_DEBUG_H__ ++ ++#include "core_types.h" ++ ++struct dc; ++ ++void dcn10_clear_status_bits(struct dc *dc, unsigned int mask); ++ ++void dcn10_log_hw_state(struct dc *dc, ++ struct dc_log_buffer_ctx *log_ctx); ++ ++void dcn10_get_hw_state(struct dc *dc, ++ char *pBuf, ++ unsigned int bufSize, ++ unsigned int mask); ++ ++#endif /* __DC_HWSS_DCN10_DEBUG_H__ */ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.c +new file mode 100644 +index 000000000000..38923f3120ee +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.c +@@ -0,0 +1,105 @@ ++/* ++ * Copyright 2016 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#include "dce110/dce110_hw_sequencer.h" ++#include "dcn10_hw_sequencer.h" ++ ++static const struct hw_sequencer_funcs dcn10_funcs = { ++ .program_gamut_remap = dcn10_program_gamut_remap, ++ .init_hw = dcn10_init_hw, ++ .init_pipes = dcn10_init_pipes, ++ .apply_ctx_to_hw = dce110_apply_ctx_to_hw, ++ .apply_ctx_for_surface = dcn10_apply_ctx_for_surface, ++ .update_plane_addr = dcn10_update_plane_addr, ++ .plane_atomic_disconnect = dcn10_plane_atomic_disconnect, ++ .program_pipe = dcn10_program_pipe, ++ .update_dchub = dcn10_update_dchub, ++ .update_mpcc = dcn10_update_mpcc, ++ .update_pending_status = dcn10_update_pending_status, ++ .set_input_transfer_func = dcn10_set_input_transfer_func, ++ .set_output_transfer_func = dcn10_set_output_transfer_func, ++ .program_output_csc = dcn10_program_output_csc, ++ .power_down = dce110_power_down, ++ .enable_accelerated_mode = dce110_enable_accelerated_mode, ++ .enable_timing_synchronization = dcn10_enable_timing_synchronization, ++ .enable_per_frame_crtc_position_reset = dcn10_enable_per_frame_crtc_position_reset, ++ .update_info_frame = dce110_update_info_frame, ++ .send_immediate_sdp_message = dcn10_send_immediate_sdp_message, ++ .enable_stream = dce110_enable_stream, ++ .disable_stream = dce110_disable_stream, ++ .unblank_stream = dcn10_unblank_stream, ++ .blank_stream = dce110_blank_stream, ++ .enable_audio_stream = dce110_enable_audio_stream, ++ .disable_audio_stream = dce110_disable_audio_stream, ++ .enable_display_power_gating = dcn10_dummy_display_power_gating, ++ .disable_plane = dcn10_disable_plane, ++ .blank_pixel_data = dcn10_blank_pixel_data, ++ .pipe_control_lock = dcn10_pipe_control_lock, ++ .prepare_bandwidth = dcn10_prepare_bandwidth, ++ .optimize_bandwidth = dcn10_optimize_bandwidth, ++ .reset_hw_ctx_wrap = dcn10_reset_hw_ctx_wrap, ++ .enable_stream_timing = dcn10_enable_stream_timing, ++ .set_drr = dcn10_set_drr, ++ .get_position = dcn10_get_position, ++ .set_static_screen_control = dcn10_set_static_screen_control, ++ .setup_stereo = dcn10_setup_stereo, ++ .set_avmute = dce110_set_avmute, ++ .log_hw_state = dcn10_log_hw_state, ++ .get_hw_state = dcn10_get_hw_state, ++ .clear_status_bits = dcn10_clear_status_bits, ++ .wait_for_mpcc_disconnect = dcn10_wait_for_mpcc_disconnect, ++ .edp_backlight_control = dce110_edp_backlight_control, ++ .edp_power_control = dce110_edp_power_control, ++ .edp_wait_for_hpd_ready = dce110_edp_wait_for_hpd_ready, ++ .set_cursor_position = dcn10_set_cursor_position, ++ .set_cursor_attribute = dcn10_set_cursor_attribute, ++ .set_cursor_sdr_white_level = dcn10_set_cursor_sdr_white_level, ++ .disable_stream_gating = NULL, ++ .enable_stream_gating = NULL, ++ .setup_periodic_interrupt = dcn10_setup_periodic_interrupt, ++ .setup_vupdate_interrupt = dcn10_setup_vupdate_interrupt, ++ .set_clock = dcn10_set_clock, ++ .get_clock = dcn10_get_clock, ++ .did_underflow_occur = dcn10_did_underflow_occur, ++ .init_blank = NULL, ++ .disable_vga = dcn10_disable_vga, ++ .bios_golden_init = dcn10_bios_golden_init, ++ .plane_atomic_disable = dcn10_plane_atomic_disable, ++ .plane_atomic_power_down = dcn10_plane_atomic_power_down, ++ .enable_power_gating_plane = dcn10_enable_power_gating_plane, ++ .dpp_pg_control = dcn10_dpp_pg_control, ++ .hubp_pg_control = dcn10_hubp_pg_control, ++ .dsc_pg_control = NULL, ++ .get_surface_visual_confirm_color = dcn10_get_surface_visual_confirm_color, ++ .get_hdr_visual_confirm_color = dcn10_get_hdr_visual_confirm_color, ++ .set_hdr_multiplier = dcn10_set_hdr_multiplier, ++ .verify_allow_pstate_change_high = dcn10_verify_allow_pstate_change_high, ++ .get_vupdate_offset_from_vsync = dcn10_get_vupdate_offset_from_vsync, ++}; ++ ++void dcn10_hw_sequencer_construct(struct dc *dc) ++{ ++ dc->hwss = dcn10_funcs; ++} +diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.h b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.h +new file mode 100644 +index 000000000000..8c6fd7b844a4 +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_init.h +@@ -0,0 +1,33 @@ ++/* ++ * Copyright 2016 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#ifndef __DC_DCN10_INIT_H__ ++#define __DC_DCN10_INIT_H__ ++ ++struct dc; ++ ++void dcn10_hw_sequencer_construct(struct dc *dc); ++ ++#endif /* __DC_DCN10_INIT_H__ */ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c +index c4129e21e643..db820a0c79d6 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c +@@ -26,6 +26,8 @@ + #include "dm_services.h" + #include "dc.h" + ++#include "dcn10_init.h" ++ + #include "resource.h" + #include "include/irq_service_interface.h" + #include "dcn10_resource.h" +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/Makefile b/drivers/gpu/drm/amd/display/dc/dcn20/Makefile +index 89c581196c4c..c49ebe7a6fd9 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn20/Makefile ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/Makefile +@@ -1,7 +1,7 @@ + # + # Makefile for DCN. + +-DCN20 = dcn20_resource.o dcn20_hwseq.o dcn20_dpp.o dcn20_dpp_cm.o dcn20_hubp.o \ ++DCN20 = dcn20_resource.o dcn20_init.o dcn20_hwseq.o dcn20_dpp.o dcn20_dpp_cm.o dcn20_hubp.o \ + dcn20_mpc.o dcn20_opp.o dcn20_hubbub.o dcn20_optc.o dcn20_mmhubbub.o \ + dcn20_stream_encoder.o dcn20_link_encoder.o dcn20_dccg.o \ + dcn20_vmid.o dcn20_dwb.o dcn20_dwb_scl.o +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +index fa1ecff747a1..937ecb28948d 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +@@ -25,15 +25,19 @@ + #include <linux/delay.h> + + #include "dm_services.h" ++#include "basics/dc_common.h" + #include "dm_helpers.h" + #include "core_types.h" + #include "resource.h" +-#include "dcn20/dcn20_resource.h" +-#include "dce110/dce110_hw_sequencer.h" +-#include "dcn10/dcn10_hw_sequencer.h" ++#include "dcn20_resource.h" + #include "dcn20_hwseq.h" + #include "dce/dce_hwseq.h" ++// TODO: This may be cause problem ++#ifdef CONFIG_DRM_AMD_DC_DSC_SUPPORT + #include "dcn20/dcn20_dsc.h" ++#endif ++#include "dcn20_dsc.h" ++#include "dcn20_optc.h" + #include "abm.h" + #include "clk_mgr.h" + #include "dmcu.h" +@@ -43,10 +47,9 @@ + #include "ipp.h" + #include "mpc.h" + #include "mcif_wb.h" ++#include "dchubbub.h" + #include "reg_helper.h" + #include "dcn10/dcn10_cm_common.h" +-#include "dcn10/dcn10_hubbub.h" +-#include "dcn10/dcn10_optc.h" + #include "dc_link_dp.h" + #include "vm_helper.h" + #include "dccg.h" +@@ -62,7 +65,125 @@ + #define FN(reg_name, field_name) \ + hws->shifts->field_name, hws->masks->field_name + +-static void dcn20_enable_power_gating_plane( ++static int find_free_gsl_group(const struct dc *dc) ++{ ++ if (dc->res_pool->gsl_groups.gsl_0 == 0) ++ return 1; ++ if (dc->res_pool->gsl_groups.gsl_1 == 0) ++ return 2; ++ if (dc->res_pool->gsl_groups.gsl_2 == 0) ++ return 3; ++ ++ return 0; ++} ++ ++/* NOTE: This is not a generic setup_gsl function (hence the suffix as_lock) ++ * This is only used to lock pipes in pipe splitting case with immediate flip ++ * Ordinary MPC/OTG locks suppress VUPDATE which doesn't help with immediate, ++ * so we get tearing with freesync since we cannot flip multiple pipes ++ * atomically. ++ * We use GSL for this: ++ * - immediate flip: find first available GSL group if not already assigned ++ * program gsl with that group, set current OTG as master ++ * and always us 0x4 = AND of flip_ready from all pipes ++ * - vsync flip: disable GSL if used ++ * ++ * Groups in stream_res are stored as +1 from HW registers, i.e. ++ * gsl_0 <=> pipe_ctx->stream_res.gsl_group == 1 ++ * Using a magic value like -1 would require tracking all inits/resets ++ */ ++static void dcn20_setup_gsl_group_as_lock( ++ const struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ bool enable) ++{ ++ struct gsl_params gsl; ++ int group_idx; ++ ++ memset(&gsl, 0, sizeof(struct gsl_params)); ++ ++ if (enable) { ++ /* return if group already assigned since GSL was set up ++ * for vsync flip, we would unassign so it can't be "left over" ++ */ ++ if (pipe_ctx->stream_res.gsl_group > 0) ++ return; ++ ++ group_idx = find_free_gsl_group(dc); ++ ASSERT(group_idx != 0); ++ pipe_ctx->stream_res.gsl_group = group_idx; ++ ++ /* set gsl group reg field and mark resource used */ ++ switch (group_idx) { ++ case 1: ++ gsl.gsl0_en = 1; ++ dc->res_pool->gsl_groups.gsl_0 = 1; ++ break; ++ case 2: ++ gsl.gsl1_en = 1; ++ dc->res_pool->gsl_groups.gsl_1 = 1; ++ break; ++ case 3: ++ gsl.gsl2_en = 1; ++ dc->res_pool->gsl_groups.gsl_2 = 1; ++ break; ++ default: ++ BREAK_TO_DEBUGGER(); ++ return; // invalid case ++ } ++ gsl.gsl_master_en = 1; ++ } else { ++ group_idx = pipe_ctx->stream_res.gsl_group; ++ if (group_idx == 0) ++ return; // if not in use, just return ++ ++ pipe_ctx->stream_res.gsl_group = 0; ++ ++ /* unset gsl group reg field and mark resource free */ ++ switch (group_idx) { ++ case 1: ++ gsl.gsl0_en = 0; ++ dc->res_pool->gsl_groups.gsl_0 = 0; ++ break; ++ case 2: ++ gsl.gsl1_en = 0; ++ dc->res_pool->gsl_groups.gsl_1 = 0; ++ break; ++ case 3: ++ gsl.gsl2_en = 0; ++ dc->res_pool->gsl_groups.gsl_2 = 0; ++ break; ++ default: ++ BREAK_TO_DEBUGGER(); ++ return; ++ } ++ gsl.gsl_master_en = 0; ++ } ++ ++ /* at this point we want to program whether it's to enable or disable */ ++ if (pipe_ctx->stream_res.tg->funcs->set_gsl != NULL && ++ pipe_ctx->stream_res.tg->funcs->set_gsl_source_select != NULL) { ++ pipe_ctx->stream_res.tg->funcs->set_gsl( ++ pipe_ctx->stream_res.tg, ++ &gsl); ++ ++ pipe_ctx->stream_res.tg->funcs->set_gsl_source_select( ++ pipe_ctx->stream_res.tg, group_idx, enable ? 4 : 0); ++ } else ++ BREAK_TO_DEBUGGER(); ++} ++ ++void dcn20_set_flip_control_gsl( ++ struct pipe_ctx *pipe_ctx, ++ bool flip_immediate) ++{ ++ if (pipe_ctx && pipe_ctx->plane_res.hubp->funcs->hubp_set_flip_control_surface_gsl) ++ pipe_ctx->plane_res.hubp->funcs->hubp_set_flip_control_surface_gsl( ++ pipe_ctx->plane_res.hubp, flip_immediate); ++ ++} ++ ++void dcn20_enable_power_gating_plane( + struct dce_hwseq *hws, + bool enable) + { +@@ -126,44 +247,6 @@ void dcn20_dccg_init(struct dce_hwseq *hws) + /* This value is dependent on the hardware pipeline delay so set once per SOC */ + REG_WRITE(DISPCLK_FREQ_CHANGE_CNTL, 0x801003c); + } +-void dcn20_display_init(struct dc *dc) +-{ +- struct dce_hwseq *hws = dc->hwseq; +- +- /* RBBMIF +- * disable RBBMIF timeout detection for all clients +- * Ensure RBBMIF does not drop register accesses due to the per-client timeout +- */ +- REG_WRITE(RBBMIF_TIMEOUT_DIS, 0xFFFFFFFF); +- REG_WRITE(RBBMIF_TIMEOUT_DIS_2, 0xFFFFFFFF); +- +- /* DCCG */ +- dcn20_dccg_init(hws); +- +- REG_UPDATE(DC_MEM_GLOBAL_PWR_REQ_CNTL, DC_MEM_GLOBAL_PWR_REQ_DIS, 0); +- +- /* DCHUB/MMHUBBUB +- * set global timer refclk divider +- * 100Mhz refclk -> 2 +- * 27Mhz refclk -> 1 +- * 48Mhz refclk -> 1 +- */ +- REG_UPDATE(DCHUBBUB_GLOBAL_TIMER_CNTL, DCHUBBUB_GLOBAL_TIMER_REFDIV, 2); +- REG_UPDATE(DCHUBBUB_GLOBAL_TIMER_CNTL, DCHUBBUB_GLOBAL_TIMER_ENABLE, 1); +- REG_WRITE(REFCLK_CNTL, 0); +- +- /* OPTC +- * OTG_CONTROL.OTG_DISABLE_POINT_CNTL = 0x3; will be set during optc2_enable_crtc +- */ +- +- /* AZ +- * default value is 0x64 for 100Mhz ref clock, if the ref clock is 100Mhz, no need to program this regiser, +- * if not, it should be programmed according to the ref clock +- */ +- REG_UPDATE(AZALIA_AUDIO_DTO, AZALIA_AUDIO_DTO_MODULE, 0x64); +- /* Enable controller clock gating */ +- REG_WRITE(AZALIA_CONTROLLER_CLOCK_GATING, 0x1); +-} + + void dcn20_disable_vga( + struct dce_hwseq *hws) +@@ -176,15 +259,15 @@ void dcn20_disable_vga( + REG_WRITE(D6VGA_CONTROL, 0); + } + +-void dcn20_program_tripleBuffer( ++void dcn20_program_triple_buffer( + const struct dc *dc, + struct pipe_ctx *pipe_ctx, +- bool enableTripleBuffer) ++ bool enable_triple_buffer) + { + if (pipe_ctx->plane_res.hubp && pipe_ctx->plane_res.hubp->funcs) { + pipe_ctx->plane_res.hubp->funcs->hubp_enable_tripleBuffer( + pipe_ctx->plane_res.hubp, +- enableTripleBuffer); ++ enable_triple_buffer); + } + } + +@@ -240,10 +323,10 @@ void dcn20_init_blank( + otg_active_height); + } + +- dcn20_hwss_wait_for_blank_complete(opp); ++ dc->hwss.wait_for_blank_complete(opp); + } + +-static void dcn20_dsc_pg_control( ++void dcn20_dsc_pg_control( + struct dce_hwseq *hws, + unsigned int dsc_inst, + bool power_on) +@@ -320,7 +403,7 @@ static void dcn20_dsc_pg_control( + REG_SET(DC_IP_REQUEST_CNTL, 0, IP_REQUEST_EN, 0); + } + +-static void dcn20_dpp_pg_control( ++void dcn20_dpp_pg_control( + struct dce_hwseq *hws, + unsigned int dpp_inst, + bool power_on) +@@ -394,7 +477,7 @@ static void dcn20_dpp_pg_control( + } + + +-static void dcn20_hubp_pg_control( ++void dcn20_hubp_pg_control( + struct dce_hwseq *hws, + unsigned int hubp_inst, + bool power_on) +@@ -471,7 +554,7 @@ static void dcn20_hubp_pg_control( + /* disable HW used by plane. + * note: cannot disable until disconnect is complete + */ +-static void dcn20_plane_atomic_disable(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn20_plane_atomic_disable(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct hubp *hubp = pipe_ctx->plane_res.hubp; + struct dpp *dpp = pipe_ctx->plane_res.dpp; +@@ -591,7 +674,7 @@ enum dc_status dcn20_enable_stream_timing( + return DC_ERROR_UNEXPECTED; + } + +- dcn20_hwss_wait_for_blank_complete(pipe_ctx->stream_res.opp); ++ dc->hwss.wait_for_blank_complete(pipe_ctx->stream_res.opp); + + params.vertical_total_min = stream->adjust.v_total_min; + params.vertical_total_max = stream->adjust.v_total_max; +@@ -647,7 +730,7 @@ void dcn20_program_output_csc(struct dc *dc, + } + } + +-bool dcn20_set_output_transfer_func(struct pipe_ctx *pipe_ctx, ++bool dcn20_set_output_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, + const struct dc_stream_state *stream) + { + int mpcc_id = pipe_ctx->plane_res.hubp->inst; +@@ -737,8 +820,9 @@ bool dcn20_set_shaper_3dlut( + return result; + } + +-bool dcn20_set_input_transfer_func(struct pipe_ctx *pipe_ctx, +- const struct dc_plane_state *plane_state) ++bool dcn20_set_input_transfer_func(struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ const struct dc_plane_state *plane_state) + { + struct dpp *dpp_base = pipe_ctx->plane_res.dpp; + const struct dc_transfer_func *tf = NULL; +@@ -748,8 +832,8 @@ bool dcn20_set_input_transfer_func(struct pipe_ctx *pipe_ctx, + if (dpp_base == NULL || plane_state == NULL) + return false; + +- dcn20_set_shaper_3dlut(pipe_ctx, plane_state); +- dcn20_set_blend_lut(pipe_ctx, plane_state); ++ dc->hwss.set_shaper_3dlut(pipe_ctx, plane_state); ++ dc->hwss.set_blend_lut(pipe_ctx, plane_state); + + if (plane_state->in_transfer_func) + tf = plane_state->in_transfer_func; +@@ -814,7 +898,7 @@ bool dcn20_set_input_transfer_func(struct pipe_ctx *pipe_ctx, + return result; + } + +-static void dcn20_update_odm(struct dc *dc, struct dc_state *context, struct pipe_ctx *pipe_ctx) ++void dcn20_update_odm(struct dc *dc, struct dc_state *context, struct pipe_ctx *pipe_ctx) + { + struct pipe_ctx *odm_pipe; + int opp_cnt = 1; +@@ -1256,7 +1340,7 @@ static void dcn20_update_dchubp_dpp( + + if (dpp->funcs->dpp_program_bias_and_scale) { + //TODO :for CNVC set scale and bias registers if necessary +- dcn10_build_prescale_params(&bns_params, plane_state); ++ build_prescale_params(&bns_params, plane_state); + dpp->funcs->dpp_program_bias_and_scale(dpp, &bns_params); + } + } +@@ -1380,7 +1464,7 @@ static void dcn20_program_pipe( + pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing); + + if (dc->hwss.setup_vupdate_interrupt) +- dc->hwss.setup_vupdate_interrupt(pipe_ctx); ++ dc->hwss.setup_vupdate_interrupt(dc, pipe_ctx); + } + + if (pipe_ctx->update_flags.bits.odm) +@@ -1394,19 +1478,19 @@ static void dcn20_program_pipe( + + if (pipe_ctx->update_flags.bits.enable + || pipe_ctx->plane_state->update_flags.bits.hdr_mult) +- set_hdr_multiplier(pipe_ctx); ++ dc->hwss.set_hdr_multiplier(pipe_ctx); + + if (pipe_ctx->update_flags.bits.enable || + pipe_ctx->plane_state->update_flags.bits.in_transfer_func_change || + pipe_ctx->plane_state->update_flags.bits.gamma_change) +- dc->hwss.set_input_transfer_func(pipe_ctx, pipe_ctx->plane_state); ++ dc->hwss.set_input_transfer_func(dc, pipe_ctx, pipe_ctx->plane_state); + + /* dcn10_translate_regamma_to_hw_format takes 750us to finish + * only do gamma programming for powering on, internal memcmp to avoid + * updating on slave planes + */ + if (pipe_ctx->update_flags.bits.enable || pipe_ctx->stream->update_flags.bits.out_tf) +- dc->hwss.set_output_transfer_func(pipe_ctx, pipe_ctx->stream); ++ dc->hwss.set_output_transfer_func(dc, pipe_ctx, pipe_ctx->stream); + + /* If the pipe has been enabled or has a different opp, we + * should reprogram the fmt. This deals with cases where +@@ -1440,7 +1524,7 @@ static bool does_pipe_need_lock(struct pipe_ctx *pipe) + return false; + } + +-static void dcn20_program_front_end_for_ctx( ++void dcn20_program_front_end_for_ctx( + struct dc *dc, + struct dc_state *context) + { +@@ -1621,7 +1705,7 @@ bool dcn20_update_bandwidth( + dc->hwss.blank_pixel_data(dc, pipe_ctx, blank); + + if (dc->hwss.setup_vupdate_interrupt) +- dc->hwss.setup_vupdate_interrupt(pipe_ctx); ++ dc->hwss.setup_vupdate_interrupt(dc, pipe_ctx); + } + + pipe_ctx->plane_res.hubp->funcs->hubp_setup( +@@ -1635,7 +1719,7 @@ bool dcn20_update_bandwidth( + return true; + } + +-static void dcn20_enable_writeback( ++void dcn20_enable_writeback( + struct dc *dc, + const struct dc_stream_status *stream_status, + struct dc_writeback_info *wb_info, +@@ -1679,7 +1763,7 @@ void dcn20_disable_writeback( + mcif_wb->funcs->disable_mcif(mcif_wb); + } + +-bool dcn20_hwss_wait_for_blank_complete( ++bool dcn20_wait_for_blank_complete( + struct output_pixel_processor *opp) + { + int counter; +@@ -1708,7 +1792,7 @@ bool dcn20_dmdata_status_done(struct pipe_ctx *pipe_ctx) + return hubp->funcs->dmdata_status_done(hubp); + } + +-static void dcn20_disable_stream_gating(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn20_disable_stream_gating(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct dce_hwseq *hws = dc->hwseq; + +@@ -1723,7 +1807,7 @@ static void dcn20_disable_stream_gating(struct dc *dc, struct pipe_ctx *pipe_ctx + } + } + +-static void dcn20_enable_stream_gating(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn20_enable_stream_gating(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct dce_hwseq *hws = dc->hwseq; + +@@ -1758,12 +1842,7 @@ void dcn20_set_dmdata_attributes(struct pipe_ctx *pipe_ctx) + hubp->funcs->dmdata_set_attributes(hubp, &attr); + } + +-void dcn20_disable_stream(struct pipe_ctx *pipe_ctx) +-{ +- dce110_disable_stream(pipe_ctx); +-} +- +-static void dcn20_init_vm_ctx( ++void dcn20_init_vm_ctx( + struct dce_hwseq *hws, + struct dc *dc, + struct dc_virtual_addr_space_config *va_config, +@@ -1785,7 +1864,7 @@ static void dcn20_init_vm_ctx( + dc->res_pool->hubbub->funcs->init_vm_ctx(dc->res_pool->hubbub, &config, vmid); + } + +-static int dcn20_init_sys_ctx(struct dce_hwseq *hws, struct dc *dc, struct dc_phy_addr_space_config *pa_config) ++int dcn20_init_sys_ctx(struct dce_hwseq *hws, struct dc *dc, struct dc_phy_addr_space_config *pa_config) + { + struct dcn_hubbub_phys_addr_config config; + +@@ -1829,8 +1908,7 @@ static bool patch_address_for_sbs_tb_stereo( + return false; + } + +- +-static void dcn20_update_plane_addr(const struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn20_update_plane_addr(const struct dc *dc, struct pipe_ctx *pipe_ctx) + { + bool addr_patched = false; + PHYSICAL_ADDRESS_LOC addr; +@@ -1876,7 +1954,7 @@ void dcn20_unblank_stream(struct pipe_ctx *pipe_ctx, + params.link_settings.link_rate = link_settings->link_rate; + + if (dc_is_dp_signal(pipe_ctx->stream->signal)) { +- if (optc1_is_two_pixels_per_containter(&stream->timing) || params.opp_cnt > 1) ++ if (optc2_is_two_pixels_per_containter(&stream->timing) || params.opp_cnt > 1) + params.timing.pix_clk_100hz /= 2; + pipe_ctx->stream_res.stream_enc->funcs->dp_set_odm_combine( + pipe_ctx->stream_res.stream_enc, params.opp_cnt > 1); +@@ -1888,10 +1966,10 @@ void dcn20_unblank_stream(struct pipe_ctx *pipe_ctx, + } + } + +-void dcn20_setup_vupdate_interrupt(struct pipe_ctx *pipe_ctx) ++void dcn20_setup_vupdate_interrupt(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct timing_generator *tg = pipe_ctx->stream_res.tg; +- int start_line = get_vupdate_offset_from_vsync(pipe_ctx); ++ int start_line = dc->hwss.get_vupdate_offset_from_vsync(pipe_ctx); + + if (start_line < 0) + start_line = 0; +@@ -1967,7 +2045,7 @@ static void dcn20_reset_back_end_for_pipe( + pipe_ctx->pipe_idx, pipe_ctx->stream_res.tg->inst); + } + +-static void dcn20_reset_hw_ctx_wrap( ++void dcn20_reset_hw_ctx_wrap( + struct dc *dc, + struct dc_state *context) + { +@@ -2020,7 +2098,7 @@ void dcn20_get_mpctree_visual_confirm_color( + *color = pipe_colors[top_pipe->pipe_idx]; + } + +-static void dcn20_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx) ++void dcn20_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx) + { + struct hubp *hubp = pipe_ctx->plane_res.hubp; + struct mpcc_blnd_cfg blnd_cfg = { {0} }; +@@ -2032,10 +2110,10 @@ static void dcn20_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx) + + // input to MPCC is always RGB, by default leave black_color at 0 + if (dc->debug.visual_confirm == VISUAL_CONFIRM_HDR) { +- dcn10_get_hdr_visual_confirm_color( ++ dc->hwss.get_hdr_visual_confirm_color( + pipe_ctx, &blnd_cfg.black_color); + } else if (dc->debug.visual_confirm == VISUAL_CONFIRM_SURFACE) { +- dcn10_get_surface_visual_confirm_color( ++ dc->hwss.get_surface_visual_confirm_color( + pipe_ctx, &blnd_cfg.black_color); + } else if (dc->debug.visual_confirm == VISUAL_CONFIRM_MPCTREE) { + dcn20_get_mpctree_visual_confirm_color( +@@ -2102,125 +2180,7 @@ static void dcn20_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx) + hubp->mpcc_id = mpcc_id; + } + +-static int find_free_gsl_group(const struct dc *dc) +-{ +- if (dc->res_pool->gsl_groups.gsl_0 == 0) +- return 1; +- if (dc->res_pool->gsl_groups.gsl_1 == 0) +- return 2; +- if (dc->res_pool->gsl_groups.gsl_2 == 0) +- return 3; +- +- return 0; +-} +- +-/* NOTE: This is not a generic setup_gsl function (hence the suffix as_lock) +- * This is only used to lock pipes in pipe splitting case with immediate flip +- * Ordinary MPC/OTG locks suppress VUPDATE which doesn't help with immediate, +- * so we get tearing with freesync since we cannot flip multiple pipes +- * atomically. +- * We use GSL for this: +- * - immediate flip: find first available GSL group if not already assigned +- * program gsl with that group, set current OTG as master +- * and always us 0x4 = AND of flip_ready from all pipes +- * - vsync flip: disable GSL if used +- * +- * Groups in stream_res are stored as +1 from HW registers, i.e. +- * gsl_0 <=> pipe_ctx->stream_res.gsl_group == 1 +- * Using a magic value like -1 would require tracking all inits/resets +- */ +-void dcn20_setup_gsl_group_as_lock( +- const struct dc *dc, +- struct pipe_ctx *pipe_ctx, +- bool enable) +-{ +- struct gsl_params gsl; +- int group_idx; +- +- memset(&gsl, 0, sizeof(struct gsl_params)); +- +- if (enable) { +- /* return if group already assigned since GSL was set up +- * for vsync flip, we would unassign so it can't be "left over" +- */ +- if (pipe_ctx->stream_res.gsl_group > 0) +- return; +- +- group_idx = find_free_gsl_group(dc); +- ASSERT(group_idx != 0); +- pipe_ctx->stream_res.gsl_group = group_idx; +- +- /* set gsl group reg field and mark resource used */ +- switch (group_idx) { +- case 1: +- gsl.gsl0_en = 1; +- dc->res_pool->gsl_groups.gsl_0 = 1; +- break; +- case 2: +- gsl.gsl1_en = 1; +- dc->res_pool->gsl_groups.gsl_1 = 1; +- break; +- case 3: +- gsl.gsl2_en = 1; +- dc->res_pool->gsl_groups.gsl_2 = 1; +- break; +- default: +- BREAK_TO_DEBUGGER(); +- return; // invalid case +- } +- gsl.gsl_master_en = 1; +- } else { +- group_idx = pipe_ctx->stream_res.gsl_group; +- if (group_idx == 0) +- return; // if not in use, just return +- +- pipe_ctx->stream_res.gsl_group = 0; +- +- /* unset gsl group reg field and mark resource free */ +- switch (group_idx) { +- case 1: +- gsl.gsl0_en = 0; +- dc->res_pool->gsl_groups.gsl_0 = 0; +- break; +- case 2: +- gsl.gsl1_en = 0; +- dc->res_pool->gsl_groups.gsl_1 = 0; +- break; +- case 3: +- gsl.gsl2_en = 0; +- dc->res_pool->gsl_groups.gsl_2 = 0; +- break; +- default: +- BREAK_TO_DEBUGGER(); +- return; +- } +- gsl.gsl_master_en = 0; +- } +- +- /* at this point we want to program whether it's to enable or disable */ +- if (pipe_ctx->stream_res.tg->funcs->set_gsl != NULL && +- pipe_ctx->stream_res.tg->funcs->set_gsl_source_select != NULL) { +- pipe_ctx->stream_res.tg->funcs->set_gsl( +- pipe_ctx->stream_res.tg, +- &gsl); +- +- pipe_ctx->stream_res.tg->funcs->set_gsl_source_select( +- pipe_ctx->stream_res.tg, group_idx, enable ? 4 : 0); +- } else +- BREAK_TO_DEBUGGER(); +-} +- +-static void dcn20_set_flip_control_gsl( +- struct pipe_ctx *pipe_ctx, +- bool flip_immediate) +-{ +- if (pipe_ctx && pipe_ctx->plane_res.hubp->funcs->hubp_set_flip_control_surface_gsl) +- pipe_ctx->plane_res.hubp->funcs->hubp_set_flip_control_surface_gsl( +- pipe_ctx->plane_res.hubp, flip_immediate); +- +-} +- +-static void dcn20_enable_stream(struct pipe_ctx *pipe_ctx) ++void dcn20_enable_stream(struct pipe_ctx *pipe_ctx) + { + enum dc_lane_count lane_count = + pipe_ctx->stream->link->cur_link_settings.lane_count; +@@ -2268,7 +2228,7 @@ static void dcn20_enable_stream(struct pipe_ctx *pipe_ctx) + } + } + +-static void dcn20_program_dmdata_engine(struct pipe_ctx *pipe_ctx) ++void dcn20_program_dmdata_engine(struct pipe_ctx *pipe_ctx) + { + struct dc_stream_state *stream = pipe_ctx->stream; + struct hubp *hubp = pipe_ctx->plane_res.hubp; +@@ -2294,7 +2254,7 @@ static void dcn20_program_dmdata_engine(struct pipe_ctx *pipe_ctx) + hubp->inst, mode); + } + +-static void dcn20_fpga_init_hw(struct dc *dc) ++void dcn20_fpga_init_hw(struct dc *dc) + { + int i, j; + struct dce_hwseq *hws = dc->hwseq; +@@ -2315,7 +2275,7 @@ static void dcn20_fpga_init_hw(struct dc *dc) + REG_WRITE(RBBMIF_TIMEOUT_DIS, 0xFFFFFFFF); + REG_WRITE(RBBMIF_TIMEOUT_DIS_2, 0xFFFFFFFF); + +- dcn20_dccg_init(hws); ++ dc->hwss.dccg_init(hws); + + REG_UPDATE(DCHUBBUB_GLOBAL_TIMER_CNTL, DCHUBBUB_GLOBAL_TIMER_REFDIV, 2); + REG_UPDATE(DCHUBBUB_GLOBAL_TIMER_CNTL, DCHUBBUB_GLOBAL_TIMER_ENABLE, 1); +@@ -2379,7 +2339,7 @@ static void dcn20_fpga_init_hw(struct dc *dc) + dc->res_pool->opps[i]->mpcc_disconnect_pending[pipe_ctx->plane_res.mpcc_inst] = true; + pipe_ctx->stream_res.opp = dc->res_pool->opps[i]; + /*to do*/ +- hwss1_plane_atomic_disconnect(dc, pipe_ctx); ++ dc->hwss.plane_atomic_disconnect(dc, pipe_ctx); + } + + /* initialize DWB pointer to MCIF_WB */ +@@ -2408,53 +2368,3 @@ static void dcn20_fpga_init_hw(struct dc *dc) + tg->funcs->tg_init(tg); + } + } +- +-void dcn20_hw_sequencer_construct(struct dc *dc) +-{ +- dcn10_hw_sequencer_construct(dc); +- dc->hwss.unblank_stream = dcn20_unblank_stream; +- dc->hwss.update_plane_addr = dcn20_update_plane_addr; +- dc->hwss.enable_stream_timing = dcn20_enable_stream_timing; +- dc->hwss.program_triplebuffer = dcn20_program_tripleBuffer; +- dc->hwss.set_input_transfer_func = dcn20_set_input_transfer_func; +- dc->hwss.set_output_transfer_func = dcn20_set_output_transfer_func; +- dc->hwss.apply_ctx_for_surface = NULL; +- dc->hwss.program_front_end_for_ctx = dcn20_program_front_end_for_ctx; +- dc->hwss.pipe_control_lock = dcn20_pipe_control_lock; +- dc->hwss.pipe_control_lock_global = dcn20_pipe_control_lock_global; +- dc->hwss.optimize_bandwidth = dcn20_optimize_bandwidth; +- dc->hwss.prepare_bandwidth = dcn20_prepare_bandwidth; +- dc->hwss.update_bandwidth = dcn20_update_bandwidth; +- dc->hwss.enable_writeback = dcn20_enable_writeback; +- dc->hwss.disable_writeback = dcn20_disable_writeback; +- dc->hwss.program_output_csc = dcn20_program_output_csc; +- dc->hwss.update_odm = dcn20_update_odm; +- dc->hwss.blank_pixel_data = dcn20_blank_pixel_data; +- dc->hwss.dmdata_status_done = dcn20_dmdata_status_done; +- dc->hwss.program_dmdata_engine = dcn20_program_dmdata_engine; +- dc->hwss.enable_stream = dcn20_enable_stream; +- dc->hwss.disable_stream = dcn20_disable_stream; +- dc->hwss.init_sys_ctx = dcn20_init_sys_ctx; +- dc->hwss.init_vm_ctx = dcn20_init_vm_ctx; +- dc->hwss.disable_stream_gating = dcn20_disable_stream_gating; +- dc->hwss.enable_stream_gating = dcn20_enable_stream_gating; +- dc->hwss.setup_vupdate_interrupt = dcn20_setup_vupdate_interrupt; +- dc->hwss.reset_hw_ctx_wrap = dcn20_reset_hw_ctx_wrap; +- dc->hwss.update_mpcc = dcn20_update_mpcc; +- dc->hwss.set_flip_control_gsl = dcn20_set_flip_control_gsl; +- dc->hwss.init_blank = dcn20_init_blank; +- dc->hwss.disable_plane = dcn20_disable_plane; +- dc->hwss.plane_atomic_disable = dcn20_plane_atomic_disable; +- dc->hwss.enable_power_gating_plane = dcn20_enable_power_gating_plane; +- dc->hwss.dpp_pg_control = dcn20_dpp_pg_control; +- dc->hwss.hubp_pg_control = dcn20_hubp_pg_control; +- dc->hwss.dsc_pg_control = dcn20_dsc_pg_control; +- dc->hwss.disable_vga = dcn20_disable_vga; +- +- if (IS_FPGA_MAXIMUS_DC(dc->ctx->dce_environment)) { +- dc->hwss.init_hw = dcn20_fpga_init_hw; +- dc->hwss.init_pipes = NULL; +- } +- +- +-} +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.h b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.h +index 3098f1049ed7..f58b69c1b321 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.h ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.h +@@ -26,90 +26,112 @@ + #ifndef __DC_HWSS_DCN20_H__ + #define __DC_HWSS_DCN20_H__ + +-struct dc; +- +-void dcn20_hw_sequencer_construct(struct dc *dc); +- +-enum dc_status dcn20_enable_stream_timing( +- struct pipe_ctx *pipe_ctx, +- struct dc_state *context, +- struct dc *dc); +- +-void dcn20_blank_pixel_data( ++bool dcn20_set_blend_lut( ++ struct pipe_ctx *pipe_ctx, const struct dc_plane_state *plane_state); ++bool dcn20_set_shaper_3dlut( ++ struct pipe_ctx *pipe_ctx, const struct dc_plane_state *plane_state); ++void dcn20_program_front_end_for_ctx( + struct dc *dc, +- struct pipe_ctx *pipe_ctx, +- bool blank); +- ++ struct dc_state *context); ++void dcn20_update_plane_addr(const struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn20_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx); ++bool dcn20_set_input_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, ++ const struct dc_plane_state *plane_state); ++bool dcn20_set_output_transfer_func(struct dc *dc, struct pipe_ctx *pipe_ctx, ++ const struct dc_stream_state *stream); + void dcn20_program_output_csc(struct dc *dc, + struct pipe_ctx *pipe_ctx, + enum dc_color_space colorspace, + uint16_t *matrix, + int opp_id); +- ++void dcn20_enable_stream(struct pipe_ctx *pipe_ctx); ++void dcn20_unblank_stream(struct pipe_ctx *pipe_ctx, ++ struct dc_link_settings *link_settings); ++void dcn20_disable_plane(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn20_blank_pixel_data( ++ struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ bool blank); ++void dcn20_pipe_control_lock( ++ struct dc *dc, ++ struct pipe_ctx *pipe, ++ bool lock); ++void dcn20_pipe_control_lock_global( ++ struct dc *dc, ++ struct pipe_ctx *pipe, ++ bool lock); + void dcn20_prepare_bandwidth( + struct dc *dc, + struct dc_state *context); +- + void dcn20_optimize_bandwidth( + struct dc *dc, + struct dc_state *context); +- + bool dcn20_update_bandwidth( + struct dc *dc, + struct dc_state *context); +- ++void dcn20_reset_hw_ctx_wrap( ++ struct dc *dc, ++ struct dc_state *context); ++enum dc_status dcn20_enable_stream_timing( ++ struct pipe_ctx *pipe_ctx, ++ struct dc_state *context, ++ struct dc *dc); ++void dcn20_disable_stream_gating(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn20_enable_stream_gating(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn20_setup_vupdate_interrupt(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn20_init_blank( ++ struct dc *dc, ++ struct timing_generator *tg); ++void dcn20_disable_vga( ++ struct dce_hwseq *hws); ++void dcn20_plane_atomic_disable(struct dc *dc, struct pipe_ctx *pipe_ctx); ++void dcn20_enable_power_gating_plane( ++ struct dce_hwseq *hws, ++ bool enable); ++void dcn20_dpp_pg_control( ++ struct dce_hwseq *hws, ++ unsigned int dpp_inst, ++ bool power_on); ++void dcn20_hubp_pg_control( ++ struct dce_hwseq *hws, ++ unsigned int hubp_inst, ++ bool power_on); ++void dcn20_program_triple_buffer( ++ const struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ bool enable_triple_buffer); ++void dcn20_enable_writeback( ++ struct dc *dc, ++ const struct dc_stream_status *stream_status, ++ struct dc_writeback_info *wb_info, ++ struct dc_state *context); + void dcn20_disable_writeback( + struct dc *dc, + unsigned int dwb_pipe_inst); +- +-bool dcn20_hwss_wait_for_blank_complete( +- struct output_pixel_processor *opp); +- +-bool dcn20_set_output_transfer_func(struct pipe_ctx *pipe_ctx, +- const struct dc_stream_state *stream); +- +-bool dcn20_set_input_transfer_func(struct pipe_ctx *pipe_ctx, +- const struct dc_plane_state *plane_state); +- ++void dcn20_update_odm(struct dc *dc, struct dc_state *context, struct pipe_ctx *pipe_ctx); + bool dcn20_dmdata_status_done(struct pipe_ctx *pipe_ctx); +- +-void dcn20_set_dmdata_attributes(struct pipe_ctx *pipe_ctx); +- +-void dcn20_disable_stream(struct pipe_ctx *pipe_ctx); +- +-void dcn20_program_tripleBuffer( +- const struct dc *dc, +- struct pipe_ctx *pipe_ctx, +- bool enableTripleBuffer); +- +-void dcn20_setup_vupdate_interrupt(struct pipe_ctx *pipe_ctx); +- +-void dcn20_pipe_control_lock_global( ++void dcn20_program_dmdata_engine(struct pipe_ctx *pipe_ctx); ++void dcn20_init_vm_ctx( ++ struct dce_hwseq *hws, + struct dc *dc, +- struct pipe_ctx *pipe, +- bool lock); +-void dcn20_setup_gsl_group_as_lock(const struct dc *dc, +- struct pipe_ctx *pipe_ctx, +- bool enable); +-void dcn20_dccg_init(struct dce_hwseq *hws); +-void dcn20_init_blank( +- struct dc *dc, +- struct timing_generator *tg); +-void dcn20_display_init(struct dc *dc); +-void dcn20_pipe_control_lock( +- struct dc *dc, +- struct pipe_ctx *pipe, +- bool lock); +-void dcn20_disable_plane(struct dc *dc, struct pipe_ctx *pipe_ctx); +-void dcn20_enable_plane( +- struct dc *dc, +- struct pipe_ctx *pipe_ctx, +- struct dc_state *context); +-bool dcn20_set_blend_lut( +- struct pipe_ctx *pipe_ctx, const struct dc_plane_state *plane_state); +-bool dcn20_set_shaper_3dlut( +- struct pipe_ctx *pipe_ctx, const struct dc_plane_state *plane_state); +-void dcn20_get_mpctree_visual_confirm_color( ++ struct dc_virtual_addr_space_config *va_config, ++ int vmid); ++void dcn20_set_flip_control_gsl( + struct pipe_ctx *pipe_ctx, +- struct tg_color *color); ++ bool flip_immediate); ++#ifdef CONFIG_DRM_AMD_DC_DSC_SUPPORT ++void dcn20_dsc_pg_control( ++ struct dce_hwseq *hws, ++ unsigned int dsc_inst, ++ bool power_on); ++#endif ++void dcn20_fpga_init_hw(struct dc *dc); ++bool dcn20_wait_for_blank_complete( ++ struct output_pixel_processor *opp); ++void dcn20_dccg_init(struct dce_hwseq *hws); ++int dcn20_init_sys_ctx(struct dce_hwseq *hws, ++ struct dc *dc, ++ struct dc_phy_addr_space_config *pa_config); ++ + #endif /* __DC_HWSS_DCN20_H__ */ ++ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.c +new file mode 100644 +index 000000000000..10493777d192 +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.c +@@ -0,0 +1,131 @@ ++/* ++ * Copyright 2016 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#include "dce110/dce110_hw_sequencer.h" ++#include "dcn10/dcn10_hw_sequencer.h" ++#include "dcn20_hwseq.h" ++ ++static const struct hw_sequencer_funcs dcn20_funcs = { ++ .program_gamut_remap = dcn10_program_gamut_remap, ++ .init_hw = dcn10_init_hw, ++ .init_pipes = dcn10_init_pipes, ++ .apply_ctx_to_hw = dce110_apply_ctx_to_hw, ++ .apply_ctx_for_surface = NULL, ++ .program_front_end_for_ctx = dcn20_program_front_end_for_ctx, ++ .update_plane_addr = dcn20_update_plane_addr, ++ .plane_atomic_disconnect = dcn10_plane_atomic_disconnect, ++ .update_dchub = dcn10_update_dchub, ++ .update_mpcc = dcn20_update_mpcc, ++ .update_pending_status = dcn10_update_pending_status, ++ .set_input_transfer_func = dcn20_set_input_transfer_func, ++ .set_output_transfer_func = dcn20_set_output_transfer_func, ++ .program_output_csc = dcn20_program_output_csc, ++ .power_down = dce110_power_down, ++ .enable_accelerated_mode = dce110_enable_accelerated_mode, ++ .enable_timing_synchronization = dcn10_enable_timing_synchronization, ++ .enable_per_frame_crtc_position_reset = dcn10_enable_per_frame_crtc_position_reset, ++ .update_info_frame = dce110_update_info_frame, ++ .send_immediate_sdp_message = dcn10_send_immediate_sdp_message, ++ .enable_stream = dcn20_enable_stream, ++ .disable_stream = dce110_disable_stream, ++ .unblank_stream = dcn20_unblank_stream, ++ .blank_stream = dce110_blank_stream, ++ .enable_audio_stream = dce110_enable_audio_stream, ++ .disable_audio_stream = dce110_disable_audio_stream, ++ .enable_display_power_gating = dcn10_dummy_display_power_gating, ++ .disable_plane = dcn20_disable_plane, ++ .blank_pixel_data = dcn20_blank_pixel_data, ++ .pipe_control_lock = dcn20_pipe_control_lock, ++ .pipe_control_lock_global = dcn20_pipe_control_lock_global, ++ .prepare_bandwidth = dcn20_prepare_bandwidth, ++ .optimize_bandwidth = dcn20_optimize_bandwidth, ++ .update_bandwidth = dcn20_update_bandwidth, ++ .reset_hw_ctx_wrap = dcn20_reset_hw_ctx_wrap, ++ .enable_stream_timing = dcn20_enable_stream_timing, ++ .set_drr = dcn10_set_drr, ++ .get_position = dcn10_get_position, ++ .set_static_screen_control = dcn10_set_static_screen_control, ++ .setup_stereo = dcn10_setup_stereo, ++ .set_avmute = dce110_set_avmute, ++ .log_hw_state = dcn10_log_hw_state, ++ .get_hw_state = dcn10_get_hw_state, ++ .clear_status_bits = dcn10_clear_status_bits, ++ .wait_for_mpcc_disconnect = dcn10_wait_for_mpcc_disconnect, ++ .edp_backlight_control = dce110_edp_backlight_control, ++ .edp_power_control = dce110_edp_power_control, ++ .edp_wait_for_hpd_ready = dce110_edp_wait_for_hpd_ready, ++ .set_cursor_position = dcn10_set_cursor_position, ++ .set_cursor_attribute = dcn10_set_cursor_attribute, ++ .set_cursor_sdr_white_level = dcn10_set_cursor_sdr_white_level, ++ .disable_stream_gating = dcn20_disable_stream_gating, ++ .enable_stream_gating = dcn20_enable_stream_gating, ++ .setup_periodic_interrupt = dcn10_setup_periodic_interrupt, ++ .setup_vupdate_interrupt = dcn20_setup_vupdate_interrupt, ++ .set_clock = dcn10_set_clock, ++ .get_clock = dcn10_get_clock, ++ .did_underflow_occur = dcn10_did_underflow_occur, ++ .init_blank = dcn20_init_blank, ++ .disable_vga = dcn20_disable_vga, ++ .bios_golden_init = dcn10_bios_golden_init, ++ .plane_atomic_disable = dcn20_plane_atomic_disable, ++ .plane_atomic_power_down = dcn10_plane_atomic_power_down, ++ .enable_power_gating_plane = dcn20_enable_power_gating_plane, ++ .dpp_pg_control = dcn20_dpp_pg_control, ++ .hubp_pg_control = dcn20_hubp_pg_control, ++ .dsc_pg_control = NULL, ++ .program_triplebuffer = dcn20_program_triple_buffer, ++ .enable_writeback = dcn20_enable_writeback, ++ .disable_writeback = dcn20_disable_writeback, ++ .update_odm = dcn20_update_odm, ++ .dmdata_status_done = dcn20_dmdata_status_done, ++ .program_dmdata_engine = dcn20_program_dmdata_engine, ++ .init_sys_ctx = dcn20_init_sys_ctx, ++ .init_vm_ctx = dcn20_init_vm_ctx, ++ .set_flip_control_gsl = dcn20_set_flip_control_gsl, ++#ifdef CONFIG_DRM_AMD_DC_DSC_SUPPORT ++ .dsc_pg_control = dcn20_dsc_pg_control, ++#else ++ .dsc_pg_control = NULL, ++#endif ++ .get_surface_visual_confirm_color = dcn10_get_surface_visual_confirm_color, ++ .get_hdr_visual_confirm_color = dcn10_get_hdr_visual_confirm_color, ++ .set_hdr_multiplier = dcn10_set_hdr_multiplier, ++ .verify_allow_pstate_change_high = dcn10_verify_allow_pstate_change_high, ++ .wait_for_blank_complete = dcn20_wait_for_blank_complete, ++ .dccg_init = dcn20_dccg_init, ++ .set_blend_lut = dcn20_set_blend_lut, ++ .set_shaper_3dlut = dcn20_set_shaper_3dlut, ++ .get_vupdate_offset_from_vsync = dcn10_get_vupdate_offset_from_vsync, ++}; ++ ++void dcn20_hw_sequencer_construct(struct dc *dc) ++{ ++ dc->hwss = dcn20_funcs; ++ ++ if (IS_FPGA_MAXIMUS_DC(dc->ctx->dce_environment)) { ++ dc->hwss.init_hw = dcn20_fpga_init_hw; ++ dc->hwss.init_pipes = NULL; ++ } ++} +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.h b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.h +new file mode 100644 +index 000000000000..12277797cd71 +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_init.h +@@ -0,0 +1,33 @@ ++/* ++ * Copyright 2016 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#ifndef __DC_DCN20_INIT_H__ ++#define __DC_DCN20_INIT_H__ ++ ++struct dc; ++ ++void dcn20_hw_sequencer_construct(struct dc *dc); ++ ++#endif /* __DC_DCN20_INIT_H__ */ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.c +index 0e50dc9b611a..f5854a5d2b76 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.c +@@ -201,11 +201,11 @@ void optc2_set_dsc_config(struct timing_generator *optc, + OPTC_DSC_SLICE_WIDTH, dsc_slice_width); + } + +-/** +- * PTI i think is already done somewhere else for 2ka +- * (opp?, please double check. +- * OPTC side only has 1 register to set for PTI_ENABLE) +- */ ++/*TEMP: Need to figure out inheritance model here.*/ ++bool optc2_is_two_pixels_per_containter(const struct dc_crtc_timing *timing) ++{ ++ return optc1_is_two_pixels_per_containter(timing); ++} + + void optc2_set_odm_bypass(struct timing_generator *optc, + const struct dc_crtc_timing *dc_crtc_timing) +@@ -219,7 +219,7 @@ void optc2_set_odm_bypass(struct timing_generator *optc, + OPTC_SEG1_SRC_SEL, 0xf); + REG_WRITE(OTG_H_TIMING_CNTL, 0); + +- h_div_2 = optc1_is_two_pixels_per_containter(dc_crtc_timing); ++ h_div_2 = optc2_is_two_pixels_per_containter(dc_crtc_timing); + REG_UPDATE(OTG_H_TIMING_CNTL, + OTG_H_TIMING_DIV_BY2, h_div_2); + REG_SET(OPTC_MEMORY_CONFIG, 0, +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.h b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.h +index 9ae22146d2d8..ac93fbfaee03 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.h ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_optc.h +@@ -107,5 +107,5 @@ void optc2_triplebuffer_unlock(struct timing_generator *optc); + void optc2_lock_doublebuffer_disable(struct timing_generator *optc); + void optc2_lock_doublebuffer_enable(struct timing_generator *optc); + void optc2_program_manual_trigger(struct timing_generator *optc); +- ++bool optc2_is_two_pixels_per_containter(const struct dc_crtc_timing *timing); + #endif /* __DC_OPTC_DCN20_H__ */ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c +index 2315da20fd41..b000d5289684 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c +@@ -26,6 +26,8 @@ + #include "dm_services.h" + #include "dc.h" + ++#include "dcn20_init.h" ++ + #include "resource.h" + #include "include/irq_service_interface.h" + #include "dcn20/dcn20_resource.h" +@@ -1453,7 +1455,7 @@ static void get_pixel_clock_parameters( + + if (opp_cnt == 4) + pixel_clk_params->requested_pix_clk_100hz /= 4; +- else if (optc1_is_two_pixels_per_containter(&stream->timing) || opp_cnt == 2) ++ else if (optc2_is_two_pixels_per_containter(&stream->timing) || opp_cnt == 2) + pixel_clk_params->requested_pix_clk_100hz /= 2; + + if (stream->timing.timing_3d_format == TIMING_3D_FORMAT_HW_FRAME_PACKING) +diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/Makefile b/drivers/gpu/drm/amd/display/dc/dcn21/Makefile +index feb7e705e792..5a061e10ef4d 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn21/Makefile ++++ b/drivers/gpu/drm/amd/display/dc/dcn21/Makefile +@@ -1,7 +1,8 @@ + # + # Makefile for DCN21. + +-DCN21 = dcn21_hubp.o dcn21_hubbub.o dcn21_resource.o dcn21_hwseq.o dcn21_link_encoder.o ++DCN21 = dcn21_init.o dcn21_hubp.o dcn21_hubbub.o dcn21_resource.o \ ++ dcn21_hwseq.o dcn21_link_encoder.o + + CFLAGS_dcn21_resource.o := -mhard-float -msse + +diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c +index b25215cadf85..005894dcabc9 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c +@@ -28,7 +28,6 @@ + #include "core_types.h" + #include "resource.h" + #include "dce/dce_hwseq.h" +-#include "dcn20/dcn20_hwseq.h" + #include "vmid.h" + #include "reg_helper.h" + #include "hw/clk_mgr.h" +@@ -61,7 +60,7 @@ static void mmhub_update_page_table_config(struct dcn_hubbub_phys_addr_config *c + + } + +-static int dcn21_init_sys_ctx(struct dce_hwseq *hws, struct dc *dc, struct dc_phy_addr_space_config *pa_config) ++int dcn21_init_sys_ctx(struct dce_hwseq *hws, struct dc *dc, struct dc_phy_addr_space_config *pa_config) + { + struct dcn_hubbub_phys_addr_config config; + +@@ -82,7 +81,7 @@ static int dcn21_init_sys_ctx(struct dce_hwseq *hws, struct dc *dc, struct dc_ph + + // work around for Renoir s0i3, if register is programmed, bypass golden init. + +-static bool dcn21_s0i3_golden_init_wa(struct dc *dc) ++bool dcn21_s0i3_golden_init_wa(struct dc *dc) + { + struct dce_hwseq *hws = dc->hwseq; + uint32_t value = 0; +@@ -112,11 +111,3 @@ void dcn21_optimize_pwr_state( + true); + } + +-void dcn21_hw_sequencer_construct(struct dc *dc) +-{ +- dcn20_hw_sequencer_construct(dc); +- dc->hwss.init_sys_ctx = dcn21_init_sys_ctx; +- dc->hwss.s0i3_golden_init_wa = dcn21_s0i3_golden_init_wa; +- dc->hwss.optimize_pwr_state = dcn21_optimize_pwr_state; +- dc->hwss.exit_optimized_pwr_state = dcn21_exit_optimized_pwr_state; +-} +diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.h b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.h +index be67b62e6fb1..2f7b8a220eb9 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.h ++++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.h +@@ -28,6 +28,18 @@ + + struct dc; + +-void dcn21_hw_sequencer_construct(struct dc *dc); ++int dcn21_init_sys_ctx(struct dce_hwseq *hws, ++ struct dc *dc, ++ struct dc_phy_addr_space_config *pa_config); ++ ++bool dcn21_s0i3_golden_init_wa(struct dc *dc); ++ ++void dcn21_exit_optimized_pwr_state( ++ const struct dc *dc, ++ struct dc_state *context); ++ ++void dcn21_optimize_pwr_state( ++ const struct dc *dc, ++ struct dc_state *context); + + #endif /* __DC_HWSS_DCN21_H__ */ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.c +new file mode 100644 +index 000000000000..cbd55037a04a +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.c +@@ -0,0 +1,135 @@ ++/* ++ * Copyright 2016 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#include "dce110/dce110_hw_sequencer.h" ++#include "dcn10/dcn10_hw_sequencer.h" ++#include "dcn20/dcn20_hwseq.h" ++#include "dcn21_hwseq.h" ++ ++static const struct hw_sequencer_funcs dcn21_funcs = { ++ .program_gamut_remap = dcn10_program_gamut_remap, ++ .init_hw = dcn10_init_hw, ++ .init_pipes = dcn10_init_pipes, ++ .apply_ctx_to_hw = dce110_apply_ctx_to_hw, ++ .apply_ctx_for_surface = NULL, ++ .program_front_end_for_ctx = dcn20_program_front_end_for_ctx, ++ .update_plane_addr = dcn20_update_plane_addr, ++ .plane_atomic_disconnect = dcn10_plane_atomic_disconnect, ++ .update_dchub = dcn10_update_dchub, ++ .update_mpcc = dcn20_update_mpcc, ++ .update_pending_status = dcn10_update_pending_status, ++ .set_input_transfer_func = dcn20_set_input_transfer_func, ++ .set_output_transfer_func = dcn20_set_output_transfer_func, ++ .program_output_csc = dcn20_program_output_csc, ++ .power_down = dce110_power_down, ++ .enable_accelerated_mode = dce110_enable_accelerated_mode, ++ .enable_timing_synchronization = dcn10_enable_timing_synchronization, ++ .enable_per_frame_crtc_position_reset = dcn10_enable_per_frame_crtc_position_reset, ++ .update_info_frame = dce110_update_info_frame, ++ .send_immediate_sdp_message = dcn10_send_immediate_sdp_message, ++ .enable_stream = dcn20_enable_stream, ++ .disable_stream = dce110_disable_stream, ++ .unblank_stream = dcn20_unblank_stream, ++ .blank_stream = dce110_blank_stream, ++ .enable_audio_stream = dce110_enable_audio_stream, ++ .disable_audio_stream = dce110_disable_audio_stream, ++ .enable_display_power_gating = dcn10_dummy_display_power_gating, ++ .disable_plane = dcn20_disable_plane, ++ .blank_pixel_data = dcn20_blank_pixel_data, ++ .pipe_control_lock = dcn20_pipe_control_lock, ++ .pipe_control_lock_global = dcn20_pipe_control_lock_global, ++ .prepare_bandwidth = dcn20_prepare_bandwidth, ++ .optimize_bandwidth = dcn20_optimize_bandwidth, ++ .update_bandwidth = dcn20_update_bandwidth, ++ .reset_hw_ctx_wrap = dcn20_reset_hw_ctx_wrap, ++ .enable_stream_timing = dcn20_enable_stream_timing, ++ .set_drr = dcn10_set_drr, ++ .get_position = dcn10_get_position, ++ .set_static_screen_control = dcn10_set_static_screen_control, ++ .setup_stereo = dcn10_setup_stereo, ++ .set_avmute = dce110_set_avmute, ++ .log_hw_state = dcn10_log_hw_state, ++ .get_hw_state = dcn10_get_hw_state, ++ .clear_status_bits = dcn10_clear_status_bits, ++ .wait_for_mpcc_disconnect = dcn10_wait_for_mpcc_disconnect, ++ .edp_backlight_control = dce110_edp_backlight_control, ++ .edp_power_control = dce110_edp_power_control, ++ .edp_wait_for_hpd_ready = dce110_edp_wait_for_hpd_ready, ++ .set_cursor_position = dcn10_set_cursor_position, ++ .set_cursor_attribute = dcn10_set_cursor_attribute, ++ .set_cursor_sdr_white_level = dcn10_set_cursor_sdr_white_level, ++ .disable_stream_gating = dcn20_disable_stream_gating, ++ .enable_stream_gating = dcn20_enable_stream_gating, ++ .setup_periodic_interrupt = dcn10_setup_periodic_interrupt, ++ .setup_vupdate_interrupt = dcn20_setup_vupdate_interrupt, ++ .set_clock = dcn10_set_clock, ++ .get_clock = dcn10_get_clock, ++ .did_underflow_occur = dcn10_did_underflow_occur, ++ .init_blank = dcn20_init_blank, ++ .disable_vga = dcn20_disable_vga, ++ .bios_golden_init = dcn10_bios_golden_init, ++ .plane_atomic_disable = dcn20_plane_atomic_disable, ++ .plane_atomic_power_down = dcn10_plane_atomic_power_down, ++ .enable_power_gating_plane = dcn20_enable_power_gating_plane, ++ .dpp_pg_control = dcn20_dpp_pg_control, ++ .hubp_pg_control = dcn20_hubp_pg_control, ++ .dsc_pg_control = NULL, ++ .program_triplebuffer = dcn20_program_triple_buffer, ++ .enable_writeback = dcn20_enable_writeback, ++ .disable_writeback = dcn20_disable_writeback, ++ .update_odm = dcn20_update_odm, ++ .dmdata_status_done = dcn20_dmdata_status_done, ++ .program_dmdata_engine = dcn20_program_dmdata_engine, ++ .init_sys_ctx = dcn21_init_sys_ctx, ++ .init_vm_ctx = dcn20_init_vm_ctx, ++ .set_flip_control_gsl = dcn20_set_flip_control_gsl, ++#ifdef CONFIG_DRM_AMD_DC_DSC_SUPPORT ++ .dsc_pg_control = dcn20_dsc_pg_control, ++#else ++ .dsc_pg_control = NULL, ++#endif ++ .get_surface_visual_confirm_color = dcn10_get_surface_visual_confirm_color, ++ .get_hdr_visual_confirm_color = dcn10_get_hdr_visual_confirm_color, ++ .set_hdr_multiplier = dcn10_set_hdr_multiplier, ++ .verify_allow_pstate_change_high = dcn10_verify_allow_pstate_change_high, ++ .s0i3_golden_init_wa = dcn21_s0i3_golden_init_wa, ++ .optimize_pwr_state = dcn21_optimize_pwr_state, ++ .exit_optimized_pwr_state = dcn21_exit_optimized_pwr_state, ++ .wait_for_blank_complete = dcn20_wait_for_blank_complete, ++ .dccg_init = dcn20_dccg_init, ++ .set_blend_lut = dcn20_set_blend_lut, ++ .set_shaper_3dlut = dcn20_set_shaper_3dlut, ++ .get_vupdate_offset_from_vsync = dcn10_get_vupdate_offset_from_vsync, ++}; ++ ++void dcn21_hw_sequencer_construct(struct dc *dc) ++{ ++ dc->hwss = dcn21_funcs; ++ ++ if (IS_FPGA_MAXIMUS_DC(dc->ctx->dce_environment)) { ++ dc->hwss.init_hw = dcn20_fpga_init_hw; ++ dc->hwss.init_pipes = NULL; ++ } ++} +diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.h b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.h +new file mode 100644 +index 000000000000..3ed24292648a +--- /dev/null ++++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.h +@@ -0,0 +1,33 @@ ++/* ++ * Copyright 2016 Advanced Micro Devices, Inc. ++ * ++ * Permission is hereby granted, free of charge, to any person obtaining a ++ * copy of this software and associated documentation files (the "Software"), ++ * to deal in the Software without restriction, including without limitation ++ * the rights to use, copy, modify, merge, publish, distribute, sublicense, ++ * and/or sell copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following conditions: ++ * ++ * The above copyright notice and this permission notice shall be included in ++ * all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ++ * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR ++ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ++ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ * Authors: AMD ++ * ++ */ ++ ++#ifndef __DC_DCN21_INIT_H__ ++#define __DC_DCN21_INIT_H__ ++ ++struct dc; ++ ++void dcn21_hw_sequencer_construct(struct dc *dc); ++ ++#endif /* __DC_DCN20_INIT_H__ */ +diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +index f68f643a82af..260471ac20c2 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +@@ -26,6 +26,8 @@ + #include "dm_services.h" + #include "dc.h" + ++#include "dcn21_init.h" ++ + #include "resource.h" + #include "include/irq_service_interface.h" + #include "dcn20/dcn20_resource.h" +diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw_sequencer.h b/drivers/gpu/drm/amd/display/dc/inc/hw_sequencer.h +index 23e3a541b7c9..937a02d02f18 100644 +--- a/drivers/gpu/drm/amd/display/dc/inc/hw_sequencer.h ++++ b/drivers/gpu/drm/amd/display/dc/inc/hw_sequencer.h +@@ -148,11 +148,11 @@ struct hw_sequencer_funcs { + void (*update_pending_status)( + struct pipe_ctx *pipe_ctx); + +- bool (*set_input_transfer_func)( ++ bool (*set_input_transfer_func)(struct dc *dc, + struct pipe_ctx *pipe_ctx, + const struct dc_plane_state *plane_state); + +- bool (*set_output_transfer_func)( ++ bool (*set_output_transfer_func)(struct dc *dc, + struct pipe_ctx *pipe_ctx, + const struct dc_stream_state *stream); + +@@ -279,8 +279,10 @@ struct hw_sequencer_funcs { + void (*set_cursor_attribute)(struct pipe_ctx *pipe); + void (*set_cursor_sdr_white_level)(struct pipe_ctx *pipe); + +- void (*setup_periodic_interrupt)(struct pipe_ctx *pipe_ctx, enum vline_select vline); +- void (*setup_vupdate_interrupt)(struct pipe_ctx *pipe_ctx); ++ void (*setup_periodic_interrupt)(struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ enum vline_select vline); ++ void (*setup_vupdate_interrupt)(struct dc *dc, struct pipe_ctx *pipe_ctx); + bool (*did_underflow_occur)(struct dc *dc, struct pipe_ctx *pipe_ctx); + + void (*init_blank)(struct dc *dc, struct timing_generator *tg); +@@ -340,6 +342,36 @@ struct hw_sequencer_funcs { + #if defined(CONFIG_DRM_AMD_DC_DCN2_1) + bool (*s0i3_golden_init_wa)(struct dc *dc); + #endif ++ ++ void (*get_surface_visual_confirm_color)( ++ const struct pipe_ctx *pipe_ctx, ++ struct tg_color *color); ++ ++ void (*get_hdr_visual_confirm_color)( ++ struct pipe_ctx *pipe_ctx, ++ struct tg_color *color); ++ ++ void (*set_hdr_multiplier)(struct pipe_ctx *pipe_ctx); ++ ++ void (*verify_allow_pstate_change_high)(struct dc *dc); ++ ++ void (*program_pipe)( ++ struct dc *dc, ++ struct pipe_ctx *pipe_ctx, ++ struct dc_state *context); ++ ++ bool (*wait_for_blank_complete)( ++ struct output_pixel_processor *opp); ++ ++ void (*dccg_init)(struct dce_hwseq *hws); ++ ++ bool (*set_blend_lut)( ++ struct pipe_ctx *pipe_ctx, const struct dc_plane_state *plane_state); ++ ++ bool (*set_shaper_3dlut)( ++ struct pipe_ctx *pipe_ctx, const struct dc_plane_state *plane_state); ++ ++ int (*get_vupdate_offset_from_vsync)(struct pipe_ctx *pipe_ctx); + }; + + void color_space_to_black_color( +-- +2.17.1 + |