diff options
Diffstat (limited to 'drivers/gpu/drm/i915/display/intel_dp.c')
-rw-r--r-- | drivers/gpu/drm/i915/display/intel_dp.c | 1275 |
1 files changed, 670 insertions, 605 deletions
diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c index ff5ba7b3035f..aa77ddcee42c 100644 --- a/drivers/gpu/drm/i915/display/intel_dp.c +++ b/drivers/gpu/drm/i915/display/intel_dp.c @@ -28,6 +28,7 @@ #include <linux/export.h> #include <linux/i2c.h> #include <linux/notifier.h> +#include <linux/seq_buf.h> #include <linux/slab.h> #include <linux/sort.h> #include <linux/string_helpers.h> @@ -93,8 +94,6 @@ #include "intel_vrr.h" #include "intel_crtc_state_dump.h" -#define dp_to_i915(__intel_dp) to_i915(dp_to_dig_port(__intel_dp)->base.base.dev) - /* DP DSC throughput values used for slice count calculations KPixels/s */ #define DP_DSC_PEAK_PIXEL_RATE 2720000 #define DP_DSC_MAX_ENC_THROUGHPUT_0 340000 @@ -109,10 +108,19 @@ /* Constants for DP DSC configurations */ static const u8 valid_dsc_bpp[] = {6, 8, 10, 12, 15}; -/* With Single pipe configuration, HW is capable of supporting maximum - * of 4 slices per line. +/* + * With Single pipe configuration, HW is capable of supporting maximum of: + * 2 slices per line for ICL, BMG + * 4 slices per line for other platforms. + * For now consider a max of 2 slices per line, which works for all platforms. + * With this we can have max of 4 DSC Slices per pipe. + * + * For higher resolutions where 12 slice support is required with + * ultrajoiner, only then each pipe can support 3 slices. + * + * #TODO Split this better to use 4 slices/dsc engine where supported. */ -static const u8 valid_dsc_slicecount[] = {1, 2, 4}; +static const u8 valid_dsc_slicecount[] = {1, 2, 3, 4}; /** * intel_dp_is_edp - is the given port attached to an eDP panel (either CPU or PCH) @@ -257,6 +265,7 @@ static void intel_dp_set_dpcd_sink_rates(struct intel_dp *intel_dp) static void intel_dp_set_sink_rates(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp); struct intel_encoder *encoder = &intel_dig_port->base; @@ -266,7 +275,7 @@ static void intel_dp_set_sink_rates(struct intel_dp *intel_dp) if (intel_dp->num_sink_rates) return; - drm_err(&dp_to_i915(intel_dp)->drm, + drm_err(display->drm, "[CONNECTOR:%d:%s][ENCODER:%d:%s] Invalid DPCD with no link rates, using defaults\n", connector->base.base.id, connector->base.name, encoder->base.base.id, encoder->base.name); @@ -281,6 +290,7 @@ static void intel_dp_set_default_max_sink_lane_count(struct intel_dp *intel_dp) static void intel_dp_set_max_sink_lane_count(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp); struct intel_encoder *encoder = &intel_dig_port->base; @@ -294,7 +304,7 @@ static void intel_dp_set_max_sink_lane_count(struct intel_dp *intel_dp) return; } - drm_err(&dp_to_i915(intel_dp)->drm, + drm_err(display->drm, "[CONNECTOR:%d:%s][ENCODER:%d:%s] Invalid DPCD max lane count (%d), using default\n", connector->base.base.id, connector->base.name, encoder->base.base.id, encoder->base.name, @@ -327,7 +337,9 @@ static int intel_dp_common_len_rate_limit(const struct intel_dp *intel_dp, int intel_dp_common_rate(struct intel_dp *intel_dp, int index) { - if (drm_WARN_ON(&dp_to_i915(intel_dp)->drm, + struct intel_display *display = to_intel_display(intel_dp); + + if (drm_WARN_ON(display->drm, index < 0 || index >= intel_dp->num_common_rates)) return 162000; @@ -454,16 +466,16 @@ int intel_dp_max_link_data_rate(struct intel_dp *intel_dp, bool intel_dp_has_joiner(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp); struct intel_encoder *encoder = &intel_dig_port->base; - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); /* eDP MSO is not compatible with joiner */ if (intel_dp->mso_link_count) return false; - return DISPLAY_VER(dev_priv) >= 12 || - (DISPLAY_VER(dev_priv) == 11 && + return DISPLAY_VER(display) >= 12 || + (DISPLAY_VER(display) == 11 && encoder->port != PORT_A); } @@ -492,12 +504,13 @@ static int ehl_max_source_rate(struct intel_dp *intel_dp) static int mtl_max_source_rate(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_encoder *encoder = &dp_to_dig_port(intel_dp)->base; if (intel_encoder_is_c10phy(encoder)) return 810000; - if (DISPLAY_VERx100(to_i915(encoder->base.dev)) == 1401) + if (DISPLAY_VERx100(display) == 1401) return 1350000; return 2000000; @@ -551,17 +564,16 @@ intel_dp_set_source_rates(struct intel_dp *intel_dp) static const int g4x_rates[] = { 162000, 270000 }; - struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); - struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev); + struct intel_display *display = to_intel_display(intel_dp); const int *source_rates; int size, max_rate = 0, vbt_max_rate; /* This should only be done once */ - drm_WARN_ON(&dev_priv->drm, + drm_WARN_ON(display->drm, intel_dp->source_rates || intel_dp->num_source_rates); - if (DISPLAY_VER(dev_priv) >= 14) { - if (IS_BATTLEMAGE(dev_priv)) { + if (DISPLAY_VER(display) >= 14) { + if (display->platform.battlemage) { source_rates = bmg_rates; size = ARRAY_SIZE(bmg_rates); } else { @@ -569,26 +581,26 @@ intel_dp_set_source_rates(struct intel_dp *intel_dp) size = ARRAY_SIZE(mtl_rates); } max_rate = mtl_max_source_rate(intel_dp); - } else if (DISPLAY_VER(dev_priv) >= 11) { + } else if (DISPLAY_VER(display) >= 11) { source_rates = icl_rates; size = ARRAY_SIZE(icl_rates); - if (IS_DG2(dev_priv)) + if (display->platform.dg2) max_rate = dg2_max_source_rate(intel_dp); - else if (IS_ALDERLAKE_P(dev_priv) || IS_ALDERLAKE_S(dev_priv) || - IS_DG1(dev_priv) || IS_ROCKETLAKE(dev_priv)) + else if (display->platform.alderlake_p || display->platform.alderlake_s || + display->platform.dg1 || display->platform.rocketlake) max_rate = 810000; - else if (IS_JASPERLAKE(dev_priv) || IS_ELKHARTLAKE(dev_priv)) + else if (display->platform.jasperlake || display->platform.elkhartlake) max_rate = ehl_max_source_rate(intel_dp); else max_rate = icl_max_source_rate(intel_dp); - } else if (IS_GEMINILAKE(dev_priv) || IS_BROXTON(dev_priv)) { + } else if (display->platform.geminilake || display->platform.broxton) { source_rates = bxt_rates; size = ARRAY_SIZE(bxt_rates); - } else if (DISPLAY_VER(dev_priv) == 9) { + } else if (DISPLAY_VER(display) == 9) { source_rates = skl_rates; size = ARRAY_SIZE(skl_rates); - } else if ((IS_HASWELL(dev_priv) && !IS_HASWELL_ULX(dev_priv)) || - IS_BROADWELL(dev_priv)) { + } else if ((display->platform.haswell && !display->platform.haswell_ulx) || + display->platform.broadwell) { source_rates = hsw_rates; size = ARRAY_SIZE(hsw_rates); } else { @@ -679,18 +691,18 @@ static int link_config_cmp_by_bw(const void *a, const void *b, const void *p) static void intel_dp_link_config_init(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_dp_link_config *lc; int num_common_lane_configs; int i; int j; - if (drm_WARN_ON(&i915->drm, !is_power_of_2(intel_dp_max_common_lane_count(intel_dp)))) + if (drm_WARN_ON(display->drm, !is_power_of_2(intel_dp_max_common_lane_count(intel_dp)))) return; num_common_lane_configs = ilog2(intel_dp_max_common_lane_count(intel_dp)) + 1; - if (drm_WARN_ON(&i915->drm, intel_dp->num_common_rates * num_common_lane_configs > + if (drm_WARN_ON(display->drm, intel_dp->num_common_rates * num_common_lane_configs > ARRAY_SIZE(intel_dp->link.configs))) return; @@ -714,10 +726,10 @@ static void intel_dp_link_config_init(struct intel_dp *intel_dp) void intel_dp_link_config_get(struct intel_dp *intel_dp, int idx, int *link_rate, int *lane_count) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); const struct intel_dp_link_config *lc; - if (drm_WARN_ON(&i915->drm, idx < 0 || idx >= intel_dp->link.num_configs)) + if (drm_WARN_ON(display->drm, idx < 0 || idx >= intel_dp->link.num_configs)) idx = 0; lc = &intel_dp->link.configs[idx]; @@ -746,9 +758,9 @@ int intel_dp_link_config_index(struct intel_dp *intel_dp, int link_rate, int lan static void intel_dp_set_common_rates(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); - drm_WARN_ON(&i915->drm, + drm_WARN_ON(display->drm, !intel_dp->num_source_rates || !intel_dp->num_sink_rates); intel_dp->num_common_rates = intersect_rates(intel_dp->source_rates, @@ -758,7 +770,7 @@ static void intel_dp_set_common_rates(struct intel_dp *intel_dp) intel_dp->common_rates); /* Paranoia, there should always be something in common. */ - if (drm_WARN_ON(&i915->drm, intel_dp->num_common_rates == 0)) { + if (drm_WARN_ON(display->drm, intel_dp->num_common_rates == 0)) { intel_dp->common_rates[0] = 162000; intel_dp->num_common_rates = 1; } @@ -806,30 +818,30 @@ int intel_dp_bw_fec_overhead(bool fec_enabled) } static int -small_joiner_ram_size_bits(struct drm_i915_private *i915) +small_joiner_ram_size_bits(struct intel_display *display) { - if (DISPLAY_VER(i915) >= 13) + if (DISPLAY_VER(display) >= 13) return 17280 * 8; - else if (DISPLAY_VER(i915) >= 11) + else if (DISPLAY_VER(display) >= 11) return 7680 * 8; else return 6144 * 8; } -u32 intel_dp_dsc_nearest_valid_bpp(struct drm_i915_private *i915, u32 bpp, u32 pipe_bpp) +u32 intel_dp_dsc_nearest_valid_bpp(struct intel_display *display, u32 bpp, u32 pipe_bpp) { u32 bits_per_pixel = bpp; int i; /* Error out if the max bpp is less than smallest allowed valid bpp */ if (bits_per_pixel < valid_dsc_bpp[0]) { - drm_dbg_kms(&i915->drm, "Unsupported BPP %u, min %u\n", + drm_dbg_kms(display->drm, "Unsupported BPP %u, min %u\n", bits_per_pixel, valid_dsc_bpp[0]); return 0; } /* From XE_LPD onwards we support from bpc upto uncompressed bpp-1 BPPs */ - if (DISPLAY_VER(i915) >= 13) { + if (DISPLAY_VER(display) >= 13) { bits_per_pixel = min(bits_per_pixel, pipe_bpp - 1); /* @@ -841,7 +853,8 @@ u32 intel_dp_dsc_nearest_valid_bpp(struct drm_i915_private *i915, u32 bpp, u32 p * DSC enabled. */ if (bits_per_pixel < 8) { - drm_dbg_kms(&i915->drm, "Unsupported BPP %u, min 8\n", + drm_dbg_kms(display->drm, + "Unsupported BPP %u, min 8\n", bits_per_pixel); return 0; } @@ -852,7 +865,7 @@ u32 intel_dp_dsc_nearest_valid_bpp(struct drm_i915_private *i915, u32 bpp, u32 p if (bits_per_pixel < valid_dsc_bpp[i + 1]) break; } - drm_dbg_kms(&i915->drm, "Set dsc bpp from %d to VESA %d\n", + drm_dbg_kms(display->drm, "Set dsc bpp from %d to VESA %d\n", bits_per_pixel, valid_dsc_bpp[i]); bits_per_pixel = valid_dsc_bpp[i]; @@ -887,11 +900,10 @@ static u32 small_joiner_ram_max_bpp(struct intel_display *display, u32 mode_hdisplay, int num_joined_pipes) { - struct drm_i915_private *i915 = to_i915(display->drm); u32 max_bpp; /* Small Joiner Check: output bpp <= joiner RAM (bits) / Horiz. width */ - max_bpp = small_joiner_ram_size_bits(i915) / mode_hdisplay; + max_bpp = small_joiner_ram_size_bits(display) / mode_hdisplay; max_bpp *= num_joined_pipes; @@ -909,11 +921,10 @@ static u32 ultrajoiner_ram_max_bpp(u32 mode_hdisplay) } static -u32 get_max_compressed_bpp_with_joiner(struct drm_i915_private *i915, +u32 get_max_compressed_bpp_with_joiner(struct intel_display *display, u32 mode_clock, u32 mode_hdisplay, int num_joined_pipes) { - struct intel_display *display = to_intel_display(&i915->drm); u32 max_bpp = small_joiner_ram_max_bpp(display, mode_hdisplay, num_joined_pipes); if (num_joined_pipes > 1) @@ -925,7 +936,7 @@ u32 get_max_compressed_bpp_with_joiner(struct drm_i915_private *i915, return max_bpp; } -u16 intel_dp_dsc_get_max_compressed_bpp(struct drm_i915_private *i915, +u16 intel_dp_dsc_get_max_compressed_bpp(struct intel_display *display, u32 link_clock, u32 lane_count, u32 mode_clock, u32 mode_hdisplay, int num_joined_pipes, @@ -967,17 +978,17 @@ u16 intel_dp_dsc_get_max_compressed_bpp(struct drm_i915_private *i915, if (output_format == INTEL_OUTPUT_FORMAT_YCBCR420) bits_per_pixel = min_t(u32, bits_per_pixel, 31); - drm_dbg_kms(&i915->drm, "Max link bpp is %u for %u timeslots " + drm_dbg_kms(display->drm, "Max link bpp is %u for %u timeslots " "total bw %u pixel clock %u\n", bits_per_pixel, timeslots, (link_clock * lane_count * 8), intel_dp_mode_to_fec_clock(mode_clock)); - joiner_max_bpp = get_max_compressed_bpp_with_joiner(i915, mode_clock, + joiner_max_bpp = get_max_compressed_bpp_with_joiner(display, mode_clock, mode_hdisplay, num_joined_pipes); bits_per_pixel = min(bits_per_pixel, joiner_max_bpp); - bits_per_pixel = intel_dp_dsc_nearest_valid_bpp(i915, bits_per_pixel, pipe_bpp); + bits_per_pixel = intel_dp_dsc_nearest_valid_bpp(display, bits_per_pixel, pipe_bpp); return bits_per_pixel; } @@ -986,7 +997,7 @@ u8 intel_dp_dsc_get_slice_count(const struct intel_connector *connector, int mode_clock, int mode_hdisplay, int num_joined_pipes) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); u8 min_slice_count, i; int max_slice_width; @@ -1001,12 +1012,12 @@ u8 intel_dp_dsc_get_slice_count(const struct intel_connector *connector, * Due to some DSC engine BW limitations, we need to enable second * slice and VDSC engine, whenever we approach close enough to max CDCLK */ - if (mode_clock >= ((i915->display.cdclk.max_cdclk_freq * 85) / 100)) + if (mode_clock >= ((display->cdclk.max_cdclk_freq * 85) / 100)) min_slice_count = max_t(u8, min_slice_count, 2); max_slice_width = drm_dp_dsc_sink_max_slice_width(connector->dp.dsc_dpcd); if (max_slice_width < DP_DSC_MIN_SLICE_WIDTH_VALUE) { - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "Unsupported slice width %d by DP DSC Sink device\n", max_slice_width); return 0; @@ -1020,6 +1031,13 @@ u8 intel_dp_dsc_get_slice_count(const struct intel_connector *connector, for (i = 0; i < ARRAY_SIZE(valid_dsc_slicecount); i++) { u8 test_slice_count = valid_dsc_slicecount[i] * num_joined_pipes; + /* + * 3 DSC Slices per pipe need 3 DSC engines, + * which is supported only with Ultrajoiner. + */ + if (valid_dsc_slicecount[i] == 3 && num_joined_pipes != 4) + continue; + if (test_slice_count > drm_dp_dsc_sink_max_slice_count(connector->dp.dsc_dpcd, false)) break; @@ -1032,11 +1050,14 @@ u8 intel_dp_dsc_get_slice_count(const struct intel_connector *connector, if (num_joined_pipes > 1 && valid_dsc_slicecount[i] < 2) continue; + if (mode_hdisplay % test_slice_count) + continue; + if (min_slice_count <= test_slice_count) return test_slice_count; } - drm_dbg_kms(&i915->drm, "Unsupported Slice Count %d\n", + drm_dbg_kms(display->drm, "Unsupported Slice Count %d\n", min_slice_count); return 0; } @@ -1044,7 +1065,7 @@ u8 intel_dp_dsc_get_slice_count(const struct intel_connector *connector, static bool source_can_output(struct intel_dp *intel_dp, enum intel_output_format format) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); switch (format) { case INTEL_OUTPUT_FORMAT_RGB: @@ -1056,11 +1077,11 @@ static bool source_can_output(struct intel_dp *intel_dp, * Also, ILK doesn't seem capable of DP YCbCr output. * The displayed image is severly corrupted. SNB+ is fine. */ - return !HAS_GMCH(i915) && !IS_IRONLAKE(i915); + return !HAS_GMCH(display) && !display->platform.ironlake; case INTEL_OUTPUT_FORMAT_YCBCR420: /* Platform < Gen 11 cannot output YCbCr420 format */ - return DISPLAY_VER(i915) >= 11; + return DISPLAY_VER(display) >= 11; default: MISSING_CASE(format); @@ -1120,8 +1141,8 @@ static enum intel_output_format intel_dp_output_format(struct intel_connector *connector, enum intel_output_format sink_format) { + struct intel_display *display = to_intel_display(connector); struct intel_dp *intel_dp = intel_attached_dp(connector); - struct drm_i915_private *i915 = dp_to_i915(intel_dp); enum intel_output_format force_dsc_output_format = intel_dp->force_dsc_output_format; enum intel_output_format output_format; @@ -1132,7 +1153,7 @@ intel_dp_output_format(struct intel_connector *connector, dfp_can_convert(intel_dp, force_dsc_output_format, sink_format))) return force_dsc_output_format; - drm_dbg_kms(&i915->drm, "Cannot force DSC output format\n"); + drm_dbg_kms(display->drm, "Cannot force DSC output format\n"); } if (sink_format == INTEL_OUTPUT_FORMAT_RGB || @@ -1146,7 +1167,7 @@ intel_dp_output_format(struct intel_connector *connector, else output_format = INTEL_OUTPUT_FORMAT_YCBCR420; - drm_WARN_ON(&i915->drm, !source_can_output(intel_dp, output_format)); + drm_WARN_ON(display->drm, !source_can_output(intel_dp, output_format)); return output_format; } @@ -1197,7 +1218,7 @@ intel_dp_mode_min_output_bpp(struct intel_connector *connector, return intel_dp_output_bpp(output_format, intel_dp_min_bpp(output_format)); } -static bool intel_dp_hdisplay_bad(struct drm_i915_private *dev_priv, +static bool intel_dp_hdisplay_bad(struct intel_display *display, int hdisplay) { /* @@ -1213,7 +1234,7 @@ static bool intel_dp_hdisplay_bad(struct drm_i915_private *dev_priv, * * TODO: confirm the behaviour on HSW+ */ - return hdisplay == 4096 && !HAS_DDI(dev_priv); + return hdisplay == 4096 && !HAS_DDI(display); } static int intel_dp_max_tmds_clock(struct intel_dp *intel_dp) @@ -1314,7 +1335,7 @@ bool intel_dp_needs_joiner(struct intel_dp *intel_dp, int hdisplay, int clock, int num_joined_pipes) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); int hdisplay_limit; if (!intel_dp_has_joiner(intel_dp)) @@ -1322,9 +1343,9 @@ bool intel_dp_needs_joiner(struct intel_dp *intel_dp, num_joined_pipes /= 2; - hdisplay_limit = DISPLAY_VER(i915) >= 30 ? 6144 : 5120; + hdisplay_limit = DISPLAY_VER(display) >= 30 ? 6144 : 5120; - return clock > num_joined_pipes * i915->display.cdclk.max_dotclk_freq || + return clock > num_joined_pipes * display->cdclk.max_dotclk_freq || hdisplay > num_joined_pipes * hdisplay_limit; } @@ -1333,16 +1354,15 @@ int intel_dp_num_joined_pipes(struct intel_dp *intel_dp, int hdisplay, int clock) { struct intel_display *display = to_intel_display(intel_dp); - struct drm_i915_private *i915 = to_i915(display->drm); if (connector->force_joined_pipes) return connector->force_joined_pipes; - if (HAS_ULTRAJOINER(i915) && + if (HAS_ULTRAJOINER(display) && intel_dp_needs_joiner(intel_dp, connector, hdisplay, clock, 4)) return 4; - if ((HAS_BIGJOINER(i915) || HAS_UNCOMPRESSED_JOINER(i915)) && + if ((HAS_BIGJOINER(display) || HAS_UNCOMPRESSED_JOINER(display)) && intel_dp_needs_joiner(intel_dp, connector, hdisplay, clock, 2)) return 2; @@ -1351,12 +1371,12 @@ int intel_dp_num_joined_pipes(struct intel_dp *intel_dp, bool intel_dp_has_dsc(const struct intel_connector *connector) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); - if (!HAS_DSC(i915)) + if (!HAS_DSC(display)) return false; - if (connector->mst_port && !HAS_DSC_MST(i915)) + if (connector->mst_port && !HAS_DSC_MST(display)) return false; if (connector->base.connector_type == DRM_MODE_CONNECTOR_eDP && @@ -1373,13 +1393,14 @@ static enum drm_mode_status intel_dp_mode_valid(struct drm_connector *_connector, struct drm_display_mode *mode) { + struct intel_display *display = to_intel_display(_connector->dev); struct intel_connector *connector = to_intel_connector(_connector); struct intel_dp *intel_dp = intel_attached_dp(connector); struct drm_i915_private *dev_priv = to_i915(connector->base.dev); const struct drm_display_mode *fixed_mode; int target_clock = mode->clock; int max_rate, mode_rate, max_lanes, max_link_clock; - int max_dotclk = dev_priv->display.cdclk.max_dotclk_freq; + int max_dotclk = display->cdclk.max_dotclk_freq; u16 dsc_max_compressed_bpp = 0; u8 dsc_slice_count = 0; enum drm_mode_status status; @@ -1412,7 +1433,7 @@ intel_dp_mode_valid(struct drm_connector *_connector, if (target_clock > max_dotclk) return MODE_CLOCK_HIGH; - if (intel_dp_hdisplay_bad(dev_priv, mode->hdisplay)) + if (intel_dp_hdisplay_bad(display, mode->hdisplay)) return MODE_H_ILLEGAL; max_link_clock = intel_dp_max_link_rate(intel_dp); @@ -1447,7 +1468,7 @@ intel_dp_mode_valid(struct drm_connector *_connector, true); } else if (drm_dp_sink_supports_fec(connector->dp.fec_capability)) { dsc_max_compressed_bpp = - intel_dp_dsc_get_max_compressed_bpp(dev_priv, + intel_dp_dsc_get_max_compressed_bpp(display, max_link_clock, max_lanes, target_clock, @@ -1465,7 +1486,7 @@ intel_dp_mode_valid(struct drm_connector *_connector, dsc = dsc_max_compressed_bpp && dsc_slice_count; } - if (intel_dp_joiner_needs_dsc(dev_priv, num_joined_pipes) && !dsc) + if (intel_dp_joiner_needs_dsc(display, num_joined_pipes) && !dsc) return MODE_CLOCK_HIGH; if (mode_rate > max_rate && !dsc) @@ -1478,51 +1499,43 @@ intel_dp_mode_valid(struct drm_connector *_connector, return intel_mode_valid_max_plane_size(dev_priv, mode, num_joined_pipes); } -bool intel_dp_source_supports_tps3(struct drm_i915_private *i915) +bool intel_dp_source_supports_tps3(struct intel_display *display) { - return DISPLAY_VER(i915) >= 9 || IS_BROADWELL(i915) || IS_HASWELL(i915); + return DISPLAY_VER(display) >= 9 || + display->platform.broadwell || display->platform.haswell; } -bool intel_dp_source_supports_tps4(struct drm_i915_private *i915) +bool intel_dp_source_supports_tps4(struct intel_display *display) { - return DISPLAY_VER(i915) >= 10; + return DISPLAY_VER(display) >= 10; } -static void snprintf_int_array(char *str, size_t len, - const int *array, int nelem) +static void seq_buf_print_array(struct seq_buf *s, const int *array, int nelem) { int i; - str[0] = '\0'; - - for (i = 0; i < nelem; i++) { - int r = snprintf(str, len, "%s%d", i ? ", " : "", array[i]); - if (r >= len) - return; - str += r; - len -= r; - } + for (i = 0; i < nelem; i++) + seq_buf_printf(s, "%s%d", i ? ", " : "", array[i]); } static void intel_dp_print_rates(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); - char str[128]; /* FIXME: too big for stack? */ + struct intel_display *display = to_intel_display(intel_dp); + DECLARE_SEQ_BUF(s, 128); /* FIXME: too big for stack? */ if (!drm_debug_enabled(DRM_UT_KMS)) return; - snprintf_int_array(str, sizeof(str), - intel_dp->source_rates, intel_dp->num_source_rates); - drm_dbg_kms(&i915->drm, "source rates: %s\n", str); + seq_buf_print_array(&s, intel_dp->source_rates, intel_dp->num_source_rates); + drm_dbg_kms(display->drm, "source rates: %s\n", seq_buf_str(&s)); - snprintf_int_array(str, sizeof(str), - intel_dp->sink_rates, intel_dp->num_sink_rates); - drm_dbg_kms(&i915->drm, "sink rates: %s\n", str); + seq_buf_clear(&s); + seq_buf_print_array(&s, intel_dp->sink_rates, intel_dp->num_sink_rates); + drm_dbg_kms(display->drm, "sink rates: %s\n", seq_buf_str(&s)); - snprintf_int_array(str, sizeof(str), - intel_dp->common_rates, intel_dp->num_common_rates); - drm_dbg_kms(&i915->drm, "common rates: %s\n", str); + seq_buf_clear(&s); + seq_buf_print_array(&s, intel_dp->common_rates, intel_dp->num_common_rates); + drm_dbg_kms(display->drm, "common rates: %s\n", seq_buf_str(&s)); } static int forced_link_rate(struct intel_dp *intel_dp) @@ -1559,11 +1572,11 @@ intel_dp_min_link_rate(struct intel_dp *intel_dp) int intel_dp_rate_select(struct intel_dp *intel_dp, int rate) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); int i = intel_dp_rate_index(intel_dp->sink_rates, intel_dp->num_sink_rates, rate); - if (drm_WARN_ON(&i915->drm, i < 0)) + if (drm_WARN_ON(display->drm, i < 0)) i = 0; return i; @@ -1593,13 +1606,13 @@ bool intel_dp_has_hdmi_sink(struct intel_dp *intel_dp) static bool intel_dp_source_supports_fec(struct intel_dp *intel_dp, const struct intel_crtc_state *pipe_config) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_encoder *encoder = &dp_to_dig_port(intel_dp)->base; - struct drm_i915_private *dev_priv = dp_to_i915(intel_dp); - if (DISPLAY_VER(dev_priv) >= 12) + if (DISPLAY_VER(display) >= 12) return true; - if (DISPLAY_VER(dev_priv) == 11 && encoder->port != PORT_A && + if (DISPLAY_VER(display) == 11 && encoder->port != PORT_A && !intel_crtc_has_type(pipe_config, INTEL_OUTPUT_DP_MST)) return true; @@ -1614,13 +1627,15 @@ bool intel_dp_supports_fec(struct intel_dp *intel_dp, drm_dp_sink_supports_fec(connector->dp.fec_capability); } -bool intel_dp_supports_dsc(const struct intel_connector *connector, +bool intel_dp_supports_dsc(struct intel_dp *intel_dp, + const struct intel_connector *connector, const struct intel_crtc_state *crtc_state) { if (!intel_dp_has_dsc(connector)) return false; - if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_DP) && !crtc_state->fec_enable) + if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_DP) && + !intel_dp_supports_fec(intel_dp, connector, crtc_state)) return false; return intel_dsc_source_support(crtc_state); @@ -1662,8 +1677,8 @@ static int intel_dp_max_bpp(struct intel_dp *intel_dp, const struct intel_crtc_state *crtc_state, bool respect_downstream_limits) { - struct drm_i915_private *dev_priv = dp_to_i915(intel_dp); - struct intel_connector *intel_connector = intel_dp->attached_connector; + struct intel_display *display = to_intel_display(intel_dp); + struct intel_connector *connector = intel_dp->attached_connector; int bpp, bpc; bpc = crtc_state->pipe_bpp / 3; @@ -1685,13 +1700,13 @@ static int intel_dp_max_bpp(struct intel_dp *intel_dp, bpp = bpc * 3; if (intel_dp_is_edp(intel_dp)) { /* Get bpp from vbt only for panels that dont have bpp in edid */ - if (intel_connector->base.display_info.bpc == 0 && - intel_connector->panel.vbt.edp.bpp && - intel_connector->panel.vbt.edp.bpp < bpp) { - drm_dbg_kms(&dev_priv->drm, + if (connector->base.display_info.bpc == 0 && + connector->panel.vbt.edp.bpp && + connector->panel.vbt.edp.bpp < bpp) { + drm_dbg_kms(display->drm, "clamping bpp for eDP panel to BIOS-provided %i\n", - intel_connector->panel.vbt.edp.bpp); - bpp = intel_connector->panel.vbt.edp.bpp; + connector->panel.vbt.edp.bpp); + bpp = connector->panel.vbt.edp.bpp; } } @@ -1700,13 +1715,13 @@ static int intel_dp_max_bpp(struct intel_dp *intel_dp, static bool has_seamless_m_n(struct intel_connector *connector) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); /* * Seamless M/N reprogramming only implemented * for BDW+ double buffered M/N registers so far. */ - return HAS_DOUBLE_BUFFERED_M_N(i915) && + return HAS_DOUBLE_BUFFERED_M_N(display) && intel_panel_drrs_type(connector) == DRRS_TYPE_SEAMLESS; } @@ -1768,32 +1783,31 @@ intel_dp_compute_link_config_wide(struct intel_dp *intel_dp, return -EINVAL; } -static -u8 intel_dp_dsc_max_src_input_bpc(struct drm_i915_private *i915) +int intel_dp_dsc_max_src_input_bpc(struct intel_display *display) { /* Max DSC Input BPC for ICL is 10 and for TGL+ is 12 */ - if (DISPLAY_VER(i915) >= 12) + if (DISPLAY_VER(display) >= 12) return 12; - if (DISPLAY_VER(i915) == 11) + if (DISPLAY_VER(display) == 11) return 10; - return 0; + return intel_dp_dsc_min_src_input_bpc(); } int intel_dp_dsc_compute_max_bpp(const struct intel_connector *connector, u8 max_req_bpc) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); int i, num_bpc; u8 dsc_bpc[3] = {}; - u8 dsc_max_bpc; + int dsc_max_bpc; - dsc_max_bpc = intel_dp_dsc_max_src_input_bpc(i915); + dsc_max_bpc = intel_dp_dsc_max_src_input_bpc(display); if (!dsc_max_bpc) return dsc_max_bpc; - dsc_max_bpc = min_t(u8, dsc_max_bpc, max_req_bpc); + dsc_max_bpc = min(dsc_max_bpc, max_req_bpc); num_bpc = drm_dp_dsc_sink_supported_input_bpcs(connector->dp.dsc_dpcd, dsc_bpc); @@ -1805,9 +1819,9 @@ int intel_dp_dsc_compute_max_bpp(const struct intel_connector *connector, return 0; } -static int intel_dp_source_dsc_version_minor(struct drm_i915_private *i915) +static int intel_dp_source_dsc_version_minor(struct intel_display *display) { - return DISPLAY_VER(i915) >= 14 ? 2 : 1; + return DISPLAY_VER(display) >= 14 ? 2 : 1; } static int intel_dp_sink_dsc_version_minor(const u8 dsc_dpcd[DP_DSC_RECEIVER_CAP_SIZE]) @@ -1841,7 +1855,7 @@ static int intel_dp_get_slice_height(int vactive) static int intel_dp_dsc_compute_params(const struct intel_connector *connector, struct intel_crtc_state *crtc_state) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); struct drm_dsc_config *vdsc_cfg = &crtc_state->dsc.config; int ret; @@ -1864,7 +1878,7 @@ static int intel_dp_dsc_compute_params(const struct intel_connector *connector, (connector->dp.dsc_dpcd[DP_DSC_REV - DP_DSC_SUPPORT] & DP_DSC_MAJOR_MASK) >> DP_DSC_MAJOR_SHIFT; vdsc_cfg->dsc_version_minor = - min(intel_dp_source_dsc_version_minor(i915), + min(intel_dp_source_dsc_version_minor(display), intel_dp_sink_dsc_version_minor(connector->dp.dsc_dpcd)); if (vdsc_cfg->convert_rgb) vdsc_cfg->convert_rgb = @@ -1874,7 +1888,7 @@ static int intel_dp_dsc_compute_params(const struct intel_connector *connector, vdsc_cfg->line_buf_depth = min(INTEL_DP_DSC_MAX_LINE_BUF_DEPTH, drm_dp_dsc_sink_line_buf_depth(connector->dp.dsc_dpcd)); if (!vdsc_cfg->line_buf_depth) { - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "DSC Sink Line Buffer Depth invalid\n"); return -EINVAL; } @@ -1889,7 +1903,7 @@ static int intel_dp_dsc_compute_params(const struct intel_connector *connector, static bool intel_dp_dsc_supports_format(const struct intel_connector *connector, enum intel_output_format output_format) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); u8 sink_dsc_format; switch (output_format) { @@ -1900,7 +1914,7 @@ static bool intel_dp_dsc_supports_format(const struct intel_connector *connector sink_dsc_format = DP_DSC_YCbCr444; break; case INTEL_OUTPUT_FORMAT_YCBCR420: - if (min(intel_dp_source_dsc_version_minor(i915), + if (min(intel_dp_source_dsc_version_minor(display), intel_dp_sink_dsc_version_minor(connector->dp.dsc_dpcd)) < 2) return false; sink_dsc_format = DP_DSC_YCbCr420_Native; @@ -1961,7 +1975,7 @@ static int dsc_compute_link_config(struct intel_dp *intel_dp, static u16 intel_dp_dsc_max_sink_compressed_bppx16(const struct intel_connector *connector, - struct intel_crtc_state *pipe_config, + const struct intel_crtc_state *pipe_config, int bpc) { u16 max_bppx16 = drm_edp_dsc_sink_output_bpp(connector->dp.dsc_dpcd); @@ -1986,7 +2000,7 @@ u16 intel_dp_dsc_max_sink_compressed_bppx16(const struct intel_connector *connec return 0; } -int intel_dp_dsc_sink_min_compressed_bpp(struct intel_crtc_state *pipe_config) +int intel_dp_dsc_sink_min_compressed_bpp(const struct intel_crtc_state *pipe_config) { /* From Mandatory bit rate range Support Table 2-157 (DP v2.0) */ switch (pipe_config->output_format) { @@ -2004,7 +2018,7 @@ int intel_dp_dsc_sink_min_compressed_bpp(struct intel_crtc_state *pipe_config) } int intel_dp_dsc_sink_max_compressed_bpp(const struct intel_connector *connector, - struct intel_crtc_state *pipe_config, + const struct intel_crtc_state *pipe_config, int bpc) { return intel_dp_dsc_max_sink_compressed_bppx16(connector, @@ -2019,13 +2033,22 @@ static int dsc_src_min_compressed_bpp(void) static int dsc_src_max_compressed_bpp(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); + + /* + * Forcing DSC and using the platform's max compressed bpp is seen to cause + * underruns. Since DSC isn't needed in these cases, limit the + * max compressed bpp to 18, which is a safe value across platforms with different + * pipe bpps. + */ + if (intel_dp->force_dsc_en) + return 18; /* * Max Compressed bpp for Gen 13+ is 27bpp. * For earlier platform is 23bpp. (Bspec:49259). */ - if (DISPLAY_VER(i915) < 13) + if (DISPLAY_VER(display) < 13) return 23; else return 27; @@ -2049,11 +2072,10 @@ icl_dsc_compute_link_config(struct intel_dp *intel_dp, /* Compressed BPP should be less than the Input DSC bpp */ dsc_max_bpp = min(dsc_max_bpp, pipe_bpp - 1); - for (i = 0; i < ARRAY_SIZE(valid_dsc_bpp); i++) { - if (valid_dsc_bpp[i] < dsc_min_bpp) + for (i = ARRAY_SIZE(valid_dsc_bpp) - 1; i >= 0; i--) { + if (valid_dsc_bpp[i] < dsc_min_bpp || + valid_dsc_bpp[i] > dsc_max_bpp) continue; - if (valid_dsc_bpp[i] > dsc_max_bpp) - break; ret = dsc_compute_link_config(intel_dp, pipe_config, @@ -2086,13 +2108,13 @@ xelpd_dsc_compute_link_config(struct intel_dp *intel_dp, int pipe_bpp, int timeslots) { + struct intel_display *display = to_intel_display(intel_dp); u8 bppx16_incr = drm_dp_dsc_sink_bpp_incr(connector->dp.dsc_dpcd); - struct drm_i915_private *i915 = dp_to_i915(intel_dp); u16 compressed_bppx16; u8 bppx16_step; int ret; - if (DISPLAY_VER(i915) < 14 || bppx16_incr <= 1) + if (DISPLAY_VER(display) < 14 || bppx16_incr <= 1) bppx16_step = 16; else bppx16_step = 16 / bppx16_incr; @@ -2116,7 +2138,8 @@ xelpd_dsc_compute_link_config(struct intel_dp *intel_dp, pipe_config->dsc.compressed_bpp_x16 = compressed_bppx16; if (intel_dp->force_dsc_fractional_bpp_en && fxp_q4_to_frac(compressed_bppx16)) - drm_dbg_kms(&i915->drm, "Forcing DSC fractional bpp\n"); + drm_dbg_kms(display->drm, + "Forcing DSC fractional bpp\n"); return 0; } @@ -2131,68 +2154,46 @@ static int dsc_compute_compressed_bpp(struct intel_dp *intel_dp, int pipe_bpp, int timeslots) { + struct intel_display *display = to_intel_display(intel_dp); const struct drm_display_mode *adjusted_mode = &pipe_config->hw.adjusted_mode; - struct drm_i915_private *i915 = dp_to_i915(intel_dp); - int dsc_src_min_bpp, dsc_sink_min_bpp, dsc_min_bpp; - int dsc_src_max_bpp, dsc_sink_max_bpp, dsc_max_bpp; + int dsc_min_bpp; + int dsc_max_bpp; int dsc_joiner_max_bpp; int num_joined_pipes = intel_crtc_num_joined_pipes(pipe_config); - dsc_src_min_bpp = dsc_src_min_compressed_bpp(); - dsc_sink_min_bpp = intel_dp_dsc_sink_min_compressed_bpp(pipe_config); - dsc_min_bpp = max(dsc_src_min_bpp, dsc_sink_min_bpp); - dsc_min_bpp = max(dsc_min_bpp, fxp_q4_to_int_roundup(limits->link.min_bpp_x16)); + dsc_min_bpp = fxp_q4_to_int_roundup(limits->link.min_bpp_x16); - dsc_src_max_bpp = dsc_src_max_compressed_bpp(intel_dp); - dsc_sink_max_bpp = intel_dp_dsc_sink_max_compressed_bpp(connector, - pipe_config, - pipe_bpp / 3); - dsc_max_bpp = dsc_sink_max_bpp ? min(dsc_sink_max_bpp, dsc_src_max_bpp) : dsc_src_max_bpp; - - dsc_joiner_max_bpp = get_max_compressed_bpp_with_joiner(i915, adjusted_mode->clock, + dsc_joiner_max_bpp = get_max_compressed_bpp_with_joiner(display, adjusted_mode->clock, adjusted_mode->hdisplay, num_joined_pipes); - dsc_max_bpp = min(dsc_max_bpp, dsc_joiner_max_bpp); - dsc_max_bpp = min(dsc_max_bpp, fxp_q4_to_int(limits->link.max_bpp_x16)); + dsc_max_bpp = min(dsc_joiner_max_bpp, fxp_q4_to_int(limits->link.max_bpp_x16)); - if (DISPLAY_VER(i915) >= 13) + if (DISPLAY_VER(display) >= 13) return xelpd_dsc_compute_link_config(intel_dp, connector, pipe_config, limits, dsc_max_bpp, dsc_min_bpp, pipe_bpp, timeslots); return icl_dsc_compute_link_config(intel_dp, pipe_config, limits, dsc_max_bpp, dsc_min_bpp, pipe_bpp, timeslots); } -static -u8 intel_dp_dsc_min_src_input_bpc(struct drm_i915_private *i915) +int intel_dp_dsc_min_src_input_bpc(void) { /* Min DSC Input BPC for ICL+ is 8 */ - return HAS_DSC(i915) ? 8 : 0; + return 8; } static -bool is_dsc_pipe_bpp_sufficient(struct drm_i915_private *i915, - struct drm_connector_state *conn_state, - struct link_config_limits *limits, +bool is_dsc_pipe_bpp_sufficient(struct link_config_limits *limits, int pipe_bpp) { - u8 dsc_max_bpc, dsc_min_bpc, dsc_max_pipe_bpp, dsc_min_pipe_bpp; - - dsc_max_bpc = min(intel_dp_dsc_max_src_input_bpc(i915), conn_state->max_requested_bpc); - dsc_min_bpc = intel_dp_dsc_min_src_input_bpc(i915); - - dsc_max_pipe_bpp = min(dsc_max_bpc * 3, limits->pipe.max_bpp); - dsc_min_pipe_bpp = max(dsc_min_bpc * 3, limits->pipe.min_bpp); - - return pipe_bpp >= dsc_min_pipe_bpp && - pipe_bpp <= dsc_max_pipe_bpp; + return pipe_bpp >= limits->pipe.min_bpp && + pipe_bpp <= limits->pipe.max_bpp; } static int intel_dp_force_dsc_pipe_bpp(struct intel_dp *intel_dp, - struct drm_connector_state *conn_state, struct link_config_limits *limits) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); int forced_bpp; if (!intel_dp->force_dsc_bpc) @@ -2200,12 +2201,14 @@ int intel_dp_force_dsc_pipe_bpp(struct intel_dp *intel_dp, forced_bpp = intel_dp->force_dsc_bpc * 3; - if (is_dsc_pipe_bpp_sufficient(i915, conn_state, limits, forced_bpp)) { - drm_dbg_kms(&i915->drm, "Input DSC BPC forced to %d\n", intel_dp->force_dsc_bpc); + if (is_dsc_pipe_bpp_sufficient(limits, forced_bpp)) { + drm_dbg_kms(display->drm, "Input DSC BPC forced to %d\n", + intel_dp->force_dsc_bpc); return forced_bpp; } - drm_dbg_kms(&i915->drm, "Cannot force DSC BPC:%d, due to DSC BPC limits\n", + drm_dbg_kms(display->drm, + "Cannot force DSC BPC:%d, due to DSC BPC limits\n", intel_dp->force_dsc_bpc); return 0; @@ -2217,17 +2220,15 @@ static int intel_dp_dsc_compute_pipe_bpp(struct intel_dp *intel_dp, struct link_config_limits *limits, int timeslots) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); const struct intel_connector *connector = to_intel_connector(conn_state->connector); - u8 max_req_bpc = conn_state->max_requested_bpc; - u8 dsc_max_bpc, dsc_max_bpp; - u8 dsc_min_bpc, dsc_min_bpp; + int dsc_max_bpp; + int dsc_min_bpp; u8 dsc_bpc[3] = {}; int forced_bpp, pipe_bpp; int num_bpc, i, ret; - forced_bpp = intel_dp_force_dsc_pipe_bpp(intel_dp, conn_state, limits); + forced_bpp = intel_dp_force_dsc_pipe_bpp(intel_dp, limits); if (forced_bpp) { ret = dsc_compute_compressed_bpp(intel_dp, connector, pipe_config, @@ -2238,15 +2239,8 @@ static int intel_dp_dsc_compute_pipe_bpp(struct intel_dp *intel_dp, } } - dsc_max_bpc = intel_dp_dsc_max_src_input_bpc(i915); - if (!dsc_max_bpc) - return -EINVAL; - - dsc_max_bpc = min_t(u8, dsc_max_bpc, max_req_bpc); - dsc_max_bpp = min(dsc_max_bpc * 3, limits->pipe.max_bpp); - - dsc_min_bpc = intel_dp_dsc_min_src_input_bpc(i915); - dsc_min_bpp = max(dsc_min_bpc * 3, limits->pipe.min_bpp); + dsc_max_bpp = limits->pipe.max_bpp; + dsc_min_bpp = limits->pipe.min_bpp; /* * Get the maximum DSC bpc that will be supported by any valid @@ -2275,24 +2269,24 @@ static int intel_edp_dsc_compute_pipe_bpp(struct intel_dp *intel_dp, struct drm_connector_state *conn_state, struct link_config_limits *limits) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = to_intel_connector(conn_state->connector); int pipe_bpp, forced_bpp; - int dsc_src_min_bpp, dsc_sink_min_bpp, dsc_min_bpp; - int dsc_src_max_bpp, dsc_sink_max_bpp, dsc_max_bpp; + int dsc_min_bpp; + int dsc_max_bpp; - forced_bpp = intel_dp_force_dsc_pipe_bpp(intel_dp, conn_state, limits); + forced_bpp = intel_dp_force_dsc_pipe_bpp(intel_dp, limits); if (forced_bpp) { pipe_bpp = forced_bpp; } else { - int max_bpc = min(limits->pipe.max_bpp / 3, (int)conn_state->max_requested_bpc); + int max_bpc = limits->pipe.max_bpp / 3; /* For eDP use max bpp that can be supported with DSC. */ pipe_bpp = intel_dp_dsc_compute_max_bpp(connector, max_bpc); - if (!is_dsc_pipe_bpp_sufficient(i915, conn_state, limits, pipe_bpp)) { - drm_dbg_kms(&i915->drm, + if (!is_dsc_pipe_bpp_sufficient(limits, pipe_bpp)) { + drm_dbg_kms(display->drm, "Computed BPC is not in DSC BPC limits\n"); return -EINVAL; } @@ -2300,17 +2294,9 @@ static int intel_edp_dsc_compute_pipe_bpp(struct intel_dp *intel_dp, pipe_config->port_clock = limits->max_rate; pipe_config->lane_count = limits->max_lane_count; - dsc_src_min_bpp = dsc_src_min_compressed_bpp(); - dsc_sink_min_bpp = intel_dp_dsc_sink_min_compressed_bpp(pipe_config); - dsc_min_bpp = max(dsc_src_min_bpp, dsc_sink_min_bpp); - dsc_min_bpp = max(dsc_min_bpp, fxp_q4_to_int_roundup(limits->link.min_bpp_x16)); + dsc_min_bpp = fxp_q4_to_int_roundup(limits->link.min_bpp_x16); - dsc_src_max_bpp = dsc_src_max_compressed_bpp(intel_dp); - dsc_sink_max_bpp = intel_dp_dsc_sink_max_compressed_bpp(connector, - pipe_config, - pipe_bpp / 3); - dsc_max_bpp = dsc_sink_max_bpp ? min(dsc_sink_max_bpp, dsc_src_max_bpp) : dsc_src_max_bpp; - dsc_max_bpp = min(dsc_max_bpp, fxp_q4_to_int(limits->link.max_bpp_x16)); + dsc_max_bpp = fxp_q4_to_int(limits->link.max_bpp_x16); /* Compressed BPP should be less than the Input DSC bpp */ dsc_max_bpp = min(dsc_max_bpp, pipe_bpp - 1); @@ -2323,6 +2309,26 @@ static int intel_edp_dsc_compute_pipe_bpp(struct intel_dp *intel_dp, return 0; } +static void intel_dp_fec_compute_config(struct intel_dp *intel_dp, + struct intel_crtc_state *crtc_state) +{ + if (crtc_state->fec_enable) + return; + + /* + * Though eDP v1.5 supports FEC with DSC, unlike DP, it is optional. + * Since, FEC is a bandwidth overhead, continue to not enable it for + * eDP. Until, there is a good reason to do so. + */ + if (intel_dp_is_edp(intel_dp)) + return; + + if (intel_dp_is_uhbr(crtc_state)) + return; + + crtc_state->fec_enable = true; +} + int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, struct intel_crtc_state *pipe_config, struct drm_connector_state *conn_state, @@ -2330,8 +2336,7 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, int timeslots, bool compute_pipe_bpp) { - struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); - struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev); + struct intel_display *display = to_intel_display(intel_dp); const struct intel_connector *connector = to_intel_connector(conn_state->connector); const struct drm_display_mode *adjusted_mode = @@ -2339,18 +2344,7 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, int num_joined_pipes = intel_crtc_num_joined_pipes(pipe_config); int ret; - /* - * Though eDP v1.5 supports FEC with DSC, unlike DP, it is optional. - * Since, FEC is a bandwidth overhead, continue to not enable it for - * eDP. Until, there is a good reason to do so. - */ - pipe_config->fec_enable = pipe_config->fec_enable || - (!intel_dp_is_edp(intel_dp) && - intel_dp_supports_fec(intel_dp, connector, pipe_config) && - !intel_dp_is_uhbr(pipe_config)); - - if (!intel_dp_supports_dsc(connector, pipe_config)) - return -EINVAL; + intel_dp_fec_compute_config(intel_dp, pipe_config); if (!intel_dp_dsc_supports_format(connector, pipe_config->output_format)) return -EINVAL; @@ -2369,7 +2363,7 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, ret = intel_dp_dsc_compute_pipe_bpp(intel_dp, pipe_config, conn_state, limits, timeslots); if (ret) { - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "No Valid pipe bpp for given mode ret = %d\n", ret); return ret; } @@ -2381,7 +2375,8 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, drm_dp_dsc_sink_max_slice_count(connector->dp.dsc_dpcd, true); if (!pipe_config->dsc.slice_count) { - drm_dbg_kms(&dev_priv->drm, "Unsupported Slice Count %d\n", + drm_dbg_kms(display->drm, + "Unsupported Slice Count %d\n", pipe_config->dsc.slice_count); return -EINVAL; } @@ -2394,7 +2389,7 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, adjusted_mode->crtc_hdisplay, num_joined_pipes); if (!dsc_dp_slice_count) { - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "Compressed Slice Count not supported\n"); return -EINVAL; } @@ -2405,13 +2400,20 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, * VDSC engine operates at 1 Pixel per clock, so if peak pixel rate * is greater than the maximum Cdclock and if slice count is even * then we need to use 2 VDSC instances. + * In case of Ultrajoiner along with 12 slices we need to use 3 + * VDSC instances. */ - if (pipe_config->joiner_pipes || pipe_config->dsc.slice_count > 1) - pipe_config->dsc.dsc_split = true; + if (pipe_config->joiner_pipes && num_joined_pipes == 4 && + pipe_config->dsc.slice_count == 12) + pipe_config->dsc.num_streams = 3; + else if (pipe_config->joiner_pipes || pipe_config->dsc.slice_count > 1) + pipe_config->dsc.num_streams = 2; + else + pipe_config->dsc.num_streams = 1; ret = intel_dp_dsc_compute_params(connector, pipe_config); if (ret < 0) { - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "Cannot compute valid DSC parameters for Input Bpp = %d" "Compressed BPP = " FXP_Q4_FMT "\n", pipe_config->pipe_bpp, @@ -2420,7 +2422,7 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, } pipe_config->dsc.compression_enable = true; - drm_dbg_kms(&dev_priv->drm, "DP DSC computed with Input Bpp = %d " + drm_dbg_kms(display->drm, "DP DSC computed with Input Bpp = %d " "Compressed Bpp = " FXP_Q4_FMT " Slice Count = %d\n", pipe_config->pipe_bpp, FXP_Q4_ARGS(pipe_config->dsc.compressed_bpp_x16), @@ -2429,25 +2431,18 @@ int intel_dp_dsc_compute_config(struct intel_dp *intel_dp, return 0; } -/** - * intel_dp_compute_config_link_bpp_limits - compute output link bpp limits - * @intel_dp: intel DP - * @crtc_state: crtc state - * @dsc: DSC compression mode - * @limits: link configuration limits - * - * Calculates the output link min, max bpp values in @limits based on the - * pipe bpp range, @crtc_state and @dsc mode. - * - * Returns %true in case of success. +/* + * Calculate the output link min, max bpp values in limits based on the pipe bpp + * range, crtc_state and dsc mode. Return true on success. */ -bool +static bool intel_dp_compute_config_link_bpp_limits(struct intel_dp *intel_dp, + const struct intel_connector *connector, const struct intel_crtc_state *crtc_state, bool dsc, struct link_config_limits *limits) { - struct drm_i915_private *i915 = to_i915(crtc_state->uapi.crtc->dev); + struct intel_display *display = to_intel_display(intel_dp); const struct drm_display_mode *adjusted_mode = &crtc_state->hw.adjusted_mode; const struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc); @@ -2465,17 +2460,27 @@ intel_dp_compute_config_link_bpp_limits(struct intel_dp *intel_dp, limits->link.min_bpp_x16 = fxp_q4_from_int(limits->pipe.min_bpp); } else { - /* - * TODO: set the DSC link limits already here, atm these are - * initialized only later in intel_edp_dsc_compute_pipe_bpp() / - * intel_dp_dsc_compute_pipe_bpp() - */ - limits->link.min_bpp_x16 = 0; + int dsc_src_min_bpp, dsc_sink_min_bpp, dsc_min_bpp; + int dsc_src_max_bpp, dsc_sink_max_bpp, dsc_max_bpp; + + dsc_src_min_bpp = dsc_src_min_compressed_bpp(); + dsc_sink_min_bpp = intel_dp_dsc_sink_min_compressed_bpp(crtc_state); + dsc_min_bpp = max(dsc_src_min_bpp, dsc_sink_min_bpp); + limits->link.min_bpp_x16 = fxp_q4_from_int(dsc_min_bpp); + + dsc_src_max_bpp = dsc_src_max_compressed_bpp(intel_dp); + dsc_sink_max_bpp = intel_dp_dsc_sink_max_compressed_bpp(connector, + crtc_state, + limits->pipe.max_bpp / 3); + dsc_max_bpp = dsc_sink_max_bpp ? + min(dsc_sink_max_bpp, dsc_src_max_bpp) : dsc_src_max_bpp; + + max_link_bpp_x16 = min(max_link_bpp_x16, fxp_q4_from_int(dsc_max_bpp)); } limits->link.max_bpp_x16 = max_link_bpp_x16; - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "[ENCODER:%d:%s][CRTC:%d:%s] DP link limits: pixel clock %d kHz DSC %s max lanes %d max rate %d max pipe_bpp %d max link_bpp " FXP_Q4_FMT "\n", encoder->base.base.id, encoder->base.name, crtc->base.base.id, crtc->base.name, @@ -2489,29 +2494,62 @@ intel_dp_compute_config_link_bpp_limits(struct intel_dp *intel_dp, return true; } -static bool +static void +intel_dp_dsc_compute_pipe_bpp_limits(struct intel_dp *intel_dp, + struct link_config_limits *limits) +{ + struct intel_display *display = to_intel_display(intel_dp); + int dsc_min_bpc = intel_dp_dsc_min_src_input_bpc(); + int dsc_max_bpc = intel_dp_dsc_max_src_input_bpc(display); + + limits->pipe.max_bpp = clamp(limits->pipe.max_bpp, dsc_min_bpc * 3, dsc_max_bpc * 3); + limits->pipe.min_bpp = clamp(limits->pipe.min_bpp, dsc_min_bpc * 3, dsc_max_bpc * 3); +} + +bool intel_dp_compute_config_limits(struct intel_dp *intel_dp, struct intel_crtc_state *crtc_state, bool respect_downstream_limits, bool dsc, struct link_config_limits *limits) { + bool is_mst = intel_crtc_has_type(crtc_state, INTEL_OUTPUT_DP_MST); + limits->min_rate = intel_dp_min_link_rate(intel_dp); limits->max_rate = intel_dp_max_link_rate(intel_dp); - /* FIXME 128b/132b SST support missing */ - limits->max_rate = min(limits->max_rate, 810000); + /* FIXME 128b/132b SST+DSC support missing */ + if (!is_mst && dsc) + limits->max_rate = min(limits->max_rate, 810000); limits->min_rate = min(limits->min_rate, limits->max_rate); limits->min_lane_count = intel_dp_min_lane_count(intel_dp); limits->max_lane_count = intel_dp_max_lane_count(intel_dp); limits->pipe.min_bpp = intel_dp_min_bpp(crtc_state->output_format); - limits->pipe.max_bpp = intel_dp_max_bpp(intel_dp, crtc_state, - respect_downstream_limits); + if (is_mst) { + /* + * FIXME: If all the streams can't fit into the link with their + * current pipe_bpp we should reduce pipe_bpp across the board + * until things start to fit. Until then we limit to <= 8bpc + * since that's what was hardcoded for all MST streams + * previously. This hack should be removed once we have the + * proper retry logic in place. + */ + limits->pipe.max_bpp = min(crtc_state->pipe_bpp, 24); + } else { + limits->pipe.max_bpp = intel_dp_max_bpp(intel_dp, crtc_state, + respect_downstream_limits); + } + + if (dsc) + intel_dp_dsc_compute_pipe_bpp_limits(intel_dp, limits); - if (intel_dp->use_max_params) { + if (is_mst || intel_dp->use_max_params) { /* + * For MST we always configure max link bw - the spec doesn't + * seem to suggest we should do otherwise. + * * Use the maximum clock and number of lanes the eDP panel * advertizes being capable of in case the initial fast * optimal params failed us. The panels are generally @@ -2526,6 +2564,7 @@ intel_dp_compute_config_limits(struct intel_dp *intel_dp, intel_dp_test_compute_config(intel_dp, crtc_state, limits); return intel_dp_compute_config_link_bpp_limits(intel_dp, + intel_dp->attached_connector, crtc_state, dsc, limits); @@ -2542,7 +2581,7 @@ int intel_dp_config_required_rate(const struct intel_crtc_state *crtc_state) return intel_dp_link_required(adjusted_mode->crtc_clock, bpp); } -bool intel_dp_joiner_needs_dsc(struct drm_i915_private *i915, +bool intel_dp_joiner_needs_dsc(struct intel_display *display, int num_joined_pipes) { /* @@ -2551,7 +2590,7 @@ bool intel_dp_joiner_needs_dsc(struct drm_i915_private *i915, * compression. * Ultrajoiner always needs compression. */ - return (!HAS_UNCOMPRESSED_JOINER(i915) && num_joined_pipes == 2) || + return (!HAS_UNCOMPRESSED_JOINER(display) && num_joined_pipes == 2) || num_joined_pipes == 4; } @@ -2561,7 +2600,7 @@ intel_dp_compute_link_config(struct intel_encoder *encoder, struct drm_connector_state *conn_state, bool respect_downstream_limits) { - struct drm_i915_private *i915 = to_i915(encoder->base.dev); + struct intel_display *display = to_intel_display(encoder); struct intel_crtc *crtc = to_intel_crtc(pipe_config->uapi.crtc); struct intel_connector *connector = to_intel_connector(conn_state->connector); @@ -2583,7 +2622,7 @@ intel_dp_compute_link_config(struct intel_encoder *encoder, if (num_joined_pipes > 1) pipe_config->joiner_pipes = GENMASK(crtc->pipe + num_joined_pipes - 1, crtc->pipe); - joiner_needs_dsc = intel_dp_joiner_needs_dsc(i915, num_joined_pipes); + joiner_needs_dsc = intel_dp_joiner_needs_dsc(display, num_joined_pipes); dsc_needed = joiner_needs_dsc || intel_dp->force_dsc_en || !intel_dp_compute_config_limits(intel_dp, pipe_config, @@ -2598,12 +2637,25 @@ intel_dp_compute_link_config(struct intel_encoder *encoder, */ ret = intel_dp_compute_link_config_wide(intel_dp, pipe_config, conn_state, &limits); + if (!ret && intel_dp_is_uhbr(pipe_config)) + ret = intel_dp_mtp_tu_compute_config(intel_dp, + pipe_config, + pipe_config->pipe_bpp, + pipe_config->pipe_bpp, + conn_state, + 0, false); if (ret) dsc_needed = true; } + if (dsc_needed && !intel_dp_supports_dsc(intel_dp, connector, pipe_config)) { + drm_dbg_kms(display->drm, "DSC required but not available\n"); + return -EINVAL; + } + if (dsc_needed) { - drm_dbg_kms(&i915->drm, "Try DSC (fallback=%s, joiner=%s, force=%s)\n", + drm_dbg_kms(display->drm, + "Try DSC (fallback=%s, joiner=%s, force=%s)\n", str_yes_no(ret), str_yes_no(joiner_needs_dsc), str_yes_no(intel_dp->force_dsc_en)); @@ -2619,7 +2671,7 @@ intel_dp_compute_link_config(struct intel_encoder *encoder, return ret; } - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "DP lane count %d clock %d bpp input %d compressed " FXP_Q4_FMT " link rate required %d available %d\n", pipe_config->lane_count, pipe_config->port_clock, pipe_config->pipe_bpp, @@ -2665,12 +2717,11 @@ bool intel_dp_limited_color_range(const struct intel_crtc_state *crtc_state, } } -static bool intel_dp_port_has_audio(struct drm_i915_private *dev_priv, - enum port port) +static bool intel_dp_port_has_audio(struct intel_display *display, enum port port) { - if (IS_G4X(dev_priv)) + if (display->platform.g4x) return false; - if (DISPLAY_VER(dev_priv) < 12 && port == PORT_A) + if (DISPLAY_VER(display) < 12 && port == PORT_A) return false; return true; @@ -2680,8 +2731,7 @@ static void intel_dp_compute_vsc_colorimetry(const struct intel_crtc_state *crtc const struct drm_connector_state *conn_state, struct drm_dp_vsc_sdp *vsc) { - struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc); - struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); + struct intel_display *display = to_intel_display(crtc_state); if (crtc_state->has_panel_replay) { /* @@ -2758,7 +2808,7 @@ static void intel_dp_compute_vsc_colorimetry(const struct intel_crtc_state *crtc vsc->bpc = crtc_state->pipe_bpp / 3; /* only RGB pixelformat supports 6 bpc */ - drm_WARN_ON(&dev_priv->drm, + drm_WARN_ON(display->drm, vsc->bpc == 6 && vsc->pixelformat != DP_PIXELFORMAT_RGB); /* all YCbCr are always limited range */ @@ -2778,7 +2828,6 @@ static void intel_dp_compute_as_sdp(struct intel_dp *intel_dp, crtc_state->infoframes.enable |= intel_hdmi_infoframe_enable(DP_SDP_ADAPTIVE_SYNC); - /* Currently only DP_AS_SDP_AVT_FIXED_VTOTAL mode supported */ as_sdp->sdp_type = DP_SDP_ADAPTIVE_SYNC; as_sdp->length = 0x9; as_sdp->duration_incr_ms = 0; @@ -2789,7 +2838,7 @@ static void intel_dp_compute_as_sdp(struct intel_dp *intel_dp, as_sdp->target_rr = drm_mode_vrefresh(adjusted_mode); as_sdp->target_rr_divider = true; } else { - as_sdp->mode = DP_AS_SDP_AVT_FIXED_VTOTAL; + as_sdp->mode = DP_AS_SDP_AVT_DYNAMIC_VTOTAL; as_sdp->vtotal = adjusted_mode->vtotal; as_sdp->target_rr = 0; } @@ -2848,8 +2897,8 @@ intel_dp_compute_hdr_metadata_infoframe_sdp(struct intel_dp *intel_dp, struct intel_crtc_state *crtc_state, const struct drm_connector_state *conn_state) { + struct intel_display *display = to_intel_display(intel_dp); int ret; - struct drm_i915_private *dev_priv = dp_to_i915(intel_dp); struct hdmi_drm_infoframe *drm_infoframe = &crtc_state->infoframes.drm.drm; if (!conn_state->hdr_output_metadata) @@ -2858,7 +2907,8 @@ intel_dp_compute_hdr_metadata_infoframe_sdp(struct intel_dp *intel_dp, ret = drm_hdmi_infoframe_set_hdr_metadata(drm_infoframe, conn_state); if (ret) { - drm_dbg_kms(&dev_priv->drm, "couldn't set HDR metadata in infoframe\n"); + drm_dbg_kms(display->drm, + "couldn't set HDR metadata in infoframe\n"); return; } @@ -2900,6 +2950,7 @@ intel_dp_drrs_compute_config(struct intel_connector *connector, struct intel_crtc_state *pipe_config, int link_bpp_x16) { + struct intel_display *display = to_intel_display(connector); struct drm_i915_private *i915 = to_i915(connector->base.dev); const struct drm_display_mode *downclock_mode = intel_panel_downclock_mode(connector, &pipe_config->hw.adjusted_mode); @@ -2918,7 +2969,8 @@ intel_dp_drrs_compute_config(struct intel_connector *connector, return; } - if (IS_IRONLAKE(i915) || IS_SANDYBRIDGE(i915) || IS_IVYBRIDGE(i915)) + if (display->platform.ironlake || display->platform.sandybridge || + display->platform.ivybridge) pipe_config->msa_timing_delay = connector->panel.vbt.edp.drrs_msa_timing_delay; pipe_config->has_drrs = true; @@ -2940,13 +2992,13 @@ intel_dp_drrs_compute_config(struct intel_connector *connector, static bool intel_dp_has_audio(struct intel_encoder *encoder, const struct drm_connector_state *conn_state) { - struct drm_i915_private *i915 = to_i915(encoder->base.dev); + struct intel_display *display = to_intel_display(encoder); const struct intel_digital_connector_state *intel_conn_state = to_intel_digital_connector_state(conn_state); struct intel_connector *connector = to_intel_connector(conn_state->connector); - if (!intel_dp_port_has_audio(i915, encoder->port)) + if (!intel_dp_port_has_audio(display, encoder->port)) return false; if (intel_conn_state->force_audio == HDMI_AUDIO_AUTO) @@ -2961,7 +3013,7 @@ intel_dp_compute_output_format(struct intel_encoder *encoder, struct drm_connector_state *conn_state, bool respect_downstream_limits) { - struct drm_i915_private *i915 = to_i915(encoder->base.dev); + struct intel_display *display = to_intel_display(encoder); struct intel_dp *intel_dp = enc_to_intel_dp(encoder); struct intel_connector *connector = intel_dp->attached_connector; const struct drm_display_info *info = &connector->base.display_info; @@ -2972,7 +3024,7 @@ intel_dp_compute_output_format(struct intel_encoder *encoder, ycbcr_420_only = drm_mode_is_420_only(info, adjusted_mode); if (ycbcr_420_only && !connector->base.ycbcr_420_allowed) { - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "YCbCr 4:2:0 mode but YCbCr 4:2:0 output not possible. Falling back to RGB.\n"); crtc_state->sink_format = INTEL_OUTPUT_FORMAT_RGB; } else { @@ -3056,7 +3108,7 @@ intel_dp_compute_config(struct intel_encoder *encoder, struct intel_crtc_state *pipe_config, struct drm_connector_state *conn_state) { - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); + struct intel_display *display = to_intel_display(encoder); struct intel_atomic_state *state = to_intel_atomic_state(conn_state->state); struct drm_display_mode *adjusted_mode = &pipe_config->hw.adjusted_mode; struct intel_dp *intel_dp = enc_to_intel_dp(encoder); @@ -3064,9 +3116,6 @@ intel_dp_compute_config(struct intel_encoder *encoder, struct intel_connector *connector = intel_dp->attached_connector; int ret = 0, link_bpp_x16; - if (HAS_PCH_SPLIT(dev_priv) && !HAS_DDI(dev_priv) && encoder->port != PORT_A) - pipe_config->has_pch_encoder = true; - fixed_mode = intel_panel_fixed_mode(connector, adjusted_mode); if (intel_dp_is_edp(intel_dp) && fixed_mode) { ret = intel_panel_compute_config(connector, adjusted_mode); @@ -3084,7 +3133,7 @@ intel_dp_compute_config(struct intel_encoder *encoder, if (adjusted_mode->flags & DRM_MODE_FLAG_DBLCLK) return -EINVAL; - if (intel_dp_hdisplay_bad(dev_priv, adjusted_mode->crtc_hdisplay)) + if (intel_dp_hdisplay_bad(display, adjusted_mode->crtc_hdisplay)) return -EINVAL; /* @@ -3107,8 +3156,13 @@ intel_dp_compute_config(struct intel_encoder *encoder, pipe_config->limited_color_range = intel_dp_limited_color_range(pipe_config, conn_state); - pipe_config->enhanced_framing = - drm_dp_enhanced_frame_cap(intel_dp->dpcd); + if (intel_dp_is_uhbr(pipe_config)) { + /* 128b/132b SST also needs this */ + pipe_config->mst_master_transcoder = pipe_config->cpu_transcoder; + } else { + pipe_config->enhanced_framing = + drm_dp_enhanced_frame_cap(intel_dp->dpcd); + } if (pipe_config->dsc.compression_enable) link_bpp_x16 = pipe_config->dsc.compressed_bpp_x16; @@ -3124,7 +3178,8 @@ intel_dp_compute_config(struct intel_encoder *encoder, pipe_config->splitter.link_count = n; pipe_config->splitter.pixel_overlap = overlap; - drm_dbg_kms(&dev_priv->drm, "MSO link count %d, pixel overlap %d\n", + drm_dbg_kms(display->drm, + "MSO link count %d, pixel overlap %d\n", n, overlap); adjusted_mode->crtc_hdisplay = adjusted_mode->crtc_hdisplay / n + overlap; @@ -3138,20 +3193,19 @@ intel_dp_compute_config(struct intel_encoder *encoder, intel_dp_audio_compute_config(encoder, pipe_config, conn_state); - intel_link_compute_m_n(link_bpp_x16, - pipe_config->lane_count, - adjusted_mode->crtc_clock, - pipe_config->port_clock, - intel_dp_bw_fec_overhead(pipe_config->fec_enable), - &pipe_config->dp_m_n); + if (!intel_dp_is_uhbr(pipe_config)) { + intel_link_compute_m_n(link_bpp_x16, + pipe_config->lane_count, + adjusted_mode->crtc_clock, + pipe_config->port_clock, + intel_dp_bw_fec_overhead(pipe_config->fec_enable), + &pipe_config->dp_m_n); + } /* FIXME: abstract this better */ if (pipe_config->splitter.enable) pipe_config->dp_m_n.data_m *= pipe_config->splitter.link_count; - if (!HAS_DDI(dev_priv)) - g4x_dp_set_clock(encoder, pipe_config); - intel_vrr_compute_config(pipe_config, conn_state); intel_dp_compute_as_sdp(intel_dp, pipe_config); intel_psr_compute_config(intel_dp, pipe_config, conn_state); @@ -3188,13 +3242,13 @@ void intel_dp_reset_link_params(struct intel_dp *intel_dp) void intel_edp_backlight_on(const struct intel_crtc_state *crtc_state, const struct drm_connector_state *conn_state) { + struct intel_display *display = to_intel_display(crtc_state); struct intel_dp *intel_dp = enc_to_intel_dp(to_intel_encoder(conn_state->best_encoder)); - struct drm_i915_private *i915 = dp_to_i915(intel_dp); if (!intel_dp_is_edp(intel_dp)) return; - drm_dbg_kms(&i915->drm, "\n"); + drm_dbg_kms(display->drm, "\n"); intel_backlight_enable(crtc_state, conn_state); intel_pps_backlight_on(intel_dp); @@ -3204,12 +3258,12 @@ void intel_edp_backlight_on(const struct intel_crtc_state *crtc_state, void intel_edp_backlight_off(const struct drm_connector_state *old_conn_state) { struct intel_dp *intel_dp = enc_to_intel_dp(to_intel_encoder(old_conn_state->best_encoder)); - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); if (!intel_dp_is_edp(intel_dp)) return; - drm_dbg_kms(&i915->drm, "\n"); + drm_dbg_kms(display->drm, "\n"); intel_pps_backlight_off(intel_dp); intel_backlight_disable(old_conn_state); @@ -3252,11 +3306,11 @@ static void intel_dp_sink_set_dsc_decompression(struct intel_connector *connector, bool enable) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); if (write_dsc_decompression_flag(connector->dp.dsc_decompression_aux, DP_DECOMPRESSION_EN, enable) < 0) - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "Failed to %s sink decompression state\n", str_enable_disable(enable)); } @@ -3265,7 +3319,7 @@ static void intel_dp_sink_set_dsc_passthrough(const struct intel_connector *connector, bool enable) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); struct drm_dp_aux *aux = connector->port ? connector->port->passthrough_aux : NULL; @@ -3274,7 +3328,7 @@ intel_dp_sink_set_dsc_passthrough(const struct intel_connector *connector, if (write_dsc_decompression_flag(aux, DP_DSC_PASSTHROUGH_EN, enable) < 0) - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "Failed to %s sink compression passthrough state\n", str_enable_disable(enable)); } @@ -3283,7 +3337,7 @@ static int intel_dp_dsc_aux_ref_count(struct intel_atomic_state *state, const struct intel_connector *connector, bool for_get_ref) { - struct drm_i915_private *i915 = to_i915(state->base.dev); + struct intel_display *display = to_intel_display(state); struct drm_connector *_connector_iter; struct drm_connector_state *old_conn_state; struct drm_connector_state *new_conn_state; @@ -3308,7 +3362,7 @@ static int intel_dp_dsc_aux_ref_count(struct intel_atomic_state *state, if (!connector_iter->dp.dsc_decompression_enabled) continue; - drm_WARN_ON(&i915->drm, + drm_WARN_ON(display->drm, (for_get_ref && !new_conn_state->crtc) || (!for_get_ref && !old_conn_state->crtc)); @@ -3355,12 +3409,12 @@ void intel_dp_sink_enable_decompression(struct intel_atomic_state *state, struct intel_connector *connector, const struct intel_crtc_state *new_crtc_state) { - struct drm_i915_private *i915 = to_i915(state->base.dev); + struct intel_display *display = to_intel_display(state); if (!new_crtc_state->dsc.compression_enable) return; - if (drm_WARN_ON(&i915->drm, + if (drm_WARN_ON(display->drm, !connector->dp.dsc_decompression_aux || connector->dp.dsc_decompression_enabled)) return; @@ -3386,12 +3440,12 @@ void intel_dp_sink_disable_decompression(struct intel_atomic_state *state, struct intel_connector *connector, const struct intel_crtc_state *old_crtc_state) { - struct drm_i915_private *i915 = to_i915(state->base.dev); + struct intel_display *display = to_intel_display(state); if (!old_crtc_state->dsc.compression_enable) return; - if (drm_WARN_ON(&i915->drm, + if (drm_WARN_ON(display->drm, !connector->dp.dsc_decompression_aux || !connector->dp.dsc_decompression_enabled)) return; @@ -3406,7 +3460,7 @@ void intel_dp_sink_disable_decompression(struct intel_atomic_state *state, static void intel_dp_init_source_oui(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); u8 oui[] = { 0x00, 0xaa, 0x01 }; u8 buf[3] = {}; @@ -3420,7 +3474,7 @@ intel_dp_init_source_oui(struct intel_dp *intel_dp) * already set to what we want, so as to avoid clearing any state by accident */ if (drm_dp_dpcd_read(&intel_dp->aux, DP_SOURCE_OUI, buf, sizeof(buf)) < 0) - drm_err(&i915->drm, "Failed to read source OUI\n"); + drm_dbg_kms(display->drm, "Failed to read source OUI\n"); if (memcmp(oui, buf, sizeof(oui)) == 0) { /* Assume the OUI was written now. */ @@ -3429,7 +3483,7 @@ intel_dp_init_source_oui(struct intel_dp *intel_dp) } if (drm_dp_dpcd_write(&intel_dp->aux, DP_SOURCE_OUI, oui, sizeof(oui)) < 0) { - drm_info(&i915->drm, "Failed to write source OUI\n"); + drm_dbg_kms(display->drm, "Failed to write source OUI\n"); WRITE_ONCE(intel_dp->oui_valid, false); } @@ -3443,10 +3497,11 @@ void intel_dp_invalidate_source_oui(struct intel_dp *intel_dp) void intel_dp_wait_source_oui(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; - struct drm_i915_private *i915 = dp_to_i915(intel_dp); - drm_dbg_kms(&i915->drm, "[CONNECTOR:%d:%s] Performing OUI wait (%u ms)\n", + drm_dbg_kms(display->drm, + "[CONNECTOR:%d:%s] Performing OUI wait (%u ms)\n", connector->base.base.id, connector->base.name, connector->panel.vbt.backlight.hdr_dpcd_refresh_timeout); @@ -3457,8 +3512,8 @@ void intel_dp_wait_source_oui(struct intel_dp *intel_dp) /* If the device supports it, try to set the power state appropriately */ void intel_dp_set_power(struct intel_dp *intel_dp, u8 mode) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_encoder *encoder = &dp_to_dig_port(intel_dp)->base; - struct drm_i915_private *i915 = to_i915(encoder->base.dev); int ret, i; /* Should have a valid DPCD by this point */ @@ -3494,7 +3549,8 @@ void intel_dp_set_power(struct intel_dp *intel_dp, u8 mode) } if (ret != 1) - drm_dbg_kms(&i915->drm, "[ENCODER:%d:%s] Set power to %s failed\n", + drm_dbg_kms(display->drm, + "[ENCODER:%d:%s] Set power to %s failed\n", encoder->base.base.id, encoder->base.name, mode == DP_SET_POWER_D0 ? "D0" : "D3"); } @@ -3537,7 +3593,7 @@ void intel_dp_sync_state(struct intel_encoder *encoder, bool intel_dp_initial_fastset_check(struct intel_encoder *encoder, struct intel_crtc_state *crtc_state) { - struct drm_i915_private *i915 = to_i915(encoder->base.dev); + struct intel_display *display = to_intel_display(encoder); struct intel_dp *intel_dp = enc_to_intel_dp(encoder); bool fastset = true; @@ -3547,7 +3603,8 @@ bool intel_dp_initial_fastset_check(struct intel_encoder *encoder, */ if (intel_dp_rate_index(intel_dp->source_rates, intel_dp->num_source_rates, crtc_state->port_clock) < 0) { - drm_dbg_kms(&i915->drm, "[ENCODER:%d:%s] Forcing full modeset due to unsupported link rate\n", + drm_dbg_kms(display->drm, + "[ENCODER:%d:%s] Forcing full modeset due to unsupported link rate\n", encoder->base.base.id, encoder->base.name); crtc_state->uapi.connectors_changed = true; fastset = false; @@ -3561,14 +3618,15 @@ bool intel_dp_initial_fastset_check(struct intel_encoder *encoder, * Remove once we have readout for DSC. */ if (crtc_state->dsc.compression_enable) { - drm_dbg_kms(&i915->drm, "[ENCODER:%d:%s] Forcing full modeset due to DSC being enabled\n", + drm_dbg_kms(display->drm, + "[ENCODER:%d:%s] Forcing full modeset due to DSC being enabled\n", encoder->base.base.id, encoder->base.name); crtc_state->uapi.mode_changed = true; fastset = false; } if (CAN_PANEL_REPLAY(intel_dp)) { - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "[ENCODER:%d:%s] Forcing full modeset to compute panel replay state\n", encoder->base.base.id, encoder->base.name); crtc_state->uapi.mode_changed = true; @@ -3580,7 +3638,7 @@ bool intel_dp_initial_fastset_check(struct intel_encoder *encoder, static void intel_dp_get_pcon_dsc_cap(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); /* Clear the cached register set to avoid using stale values */ @@ -3589,10 +3647,10 @@ static void intel_dp_get_pcon_dsc_cap(struct intel_dp *intel_dp) if (drm_dp_dpcd_read(&intel_dp->aux, DP_PCON_DSC_ENCODER, intel_dp->pcon_dsc_dpcd, sizeof(intel_dp->pcon_dsc_dpcd)) < 0) - drm_err(&i915->drm, "Failed to read DPCD register 0x%x\n", + drm_err(display->drm, "Failed to read DPCD register 0x%x\n", DP_PCON_DSC_ENCODER); - drm_dbg_kms(&i915->drm, "PCON ENCODER DSC DPCD: %*ph\n", + drm_dbg_kms(display->drm, "PCON ENCODER DSC DPCD: %*ph\n", (int)sizeof(intel_dp->pcon_dsc_dpcd), intel_dp->pcon_dsc_dpcd); } @@ -3630,19 +3688,19 @@ static int intel_dp_pcon_set_frl_mask(int max_frl) static int intel_dp_hdmi_sink_max_frl(struct intel_dp *intel_dp) { - struct intel_connector *intel_connector = intel_dp->attached_connector; - struct drm_connector *connector = &intel_connector->base; + struct intel_connector *connector = intel_dp->attached_connector; + const struct drm_display_info *info = &connector->base.display_info; int max_frl_rate; int max_lanes, rate_per_lane; int max_dsc_lanes, dsc_rate_per_lane; - max_lanes = connector->display_info.hdmi.max_lanes; - rate_per_lane = connector->display_info.hdmi.max_frl_rate_per_lane; + max_lanes = info->hdmi.max_lanes; + rate_per_lane = info->hdmi.max_frl_rate_per_lane; max_frl_rate = max_lanes * rate_per_lane; - if (connector->display_info.hdmi.dsc_cap.v_1p2) { - max_dsc_lanes = connector->display_info.hdmi.dsc_cap.max_lanes; - dsc_rate_per_lane = connector->display_info.hdmi.dsc_cap.max_frl_rate_per_lane; + if (info->hdmi.dsc_cap.v_1p2) { + max_dsc_lanes = info->hdmi.dsc_cap.max_lanes; + dsc_rate_per_lane = info->hdmi.dsc_cap.max_frl_rate_per_lane; if (max_dsc_lanes && dsc_rate_per_lane) max_frl_rate = min(max_frl_rate, max_dsc_lanes * dsc_rate_per_lane); } @@ -3664,19 +3722,19 @@ intel_dp_pcon_is_frl_trained(struct intel_dp *intel_dp, static int intel_dp_pcon_start_frl_training(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); #define TIMEOUT_FRL_READY_MS 500 #define TIMEOUT_HDMI_LINK_ACTIVE_MS 1000 - - struct drm_i915_private *i915 = dp_to_i915(intel_dp); int max_frl_bw, max_pcon_frl_bw, max_edid_frl_bw, ret; u8 max_frl_bw_mask = 0, frl_trained_mask; bool is_active; max_pcon_frl_bw = intel_dp->dfp.pcon_max_frl_bw; - drm_dbg(&i915->drm, "PCON max rate = %d Gbps\n", max_pcon_frl_bw); + drm_dbg(display->drm, "PCON max rate = %d Gbps\n", max_pcon_frl_bw); max_edid_frl_bw = intel_dp_hdmi_sink_max_frl(intel_dp); - drm_dbg(&i915->drm, "Sink max rate from EDID = %d Gbps\n", max_edid_frl_bw); + drm_dbg(display->drm, "Sink max rate from EDID = %d Gbps\n", + max_edid_frl_bw); max_frl_bw = min(max_edid_frl_bw, max_pcon_frl_bw); @@ -3684,7 +3742,7 @@ static int intel_dp_pcon_start_frl_training(struct intel_dp *intel_dp) return -EINVAL; max_frl_bw_mask = intel_dp_pcon_set_frl_mask(max_frl_bw); - drm_dbg(&i915->drm, "MAX_FRL_BW_MASK = %u\n", max_frl_bw_mask); + drm_dbg(display->drm, "MAX_FRL_BW_MASK = %u\n", max_frl_bw_mask); if (intel_dp_pcon_is_frl_trained(intel_dp, max_frl_bw_mask, &frl_trained_mask)) goto frl_trained; @@ -3721,10 +3779,11 @@ static int intel_dp_pcon_start_frl_training(struct intel_dp *intel_dp) return -ETIMEDOUT; frl_trained: - drm_dbg(&i915->drm, "FRL_TRAINED_MASK = %u\n", frl_trained_mask); + drm_dbg(display->drm, "FRL_TRAINED_MASK = %u\n", frl_trained_mask); intel_dp->frl.trained_rate_gbps = intel_dp_pcon_get_frl_mask(frl_trained_mask); intel_dp->frl.is_trained = true; - drm_dbg(&i915->drm, "FRL trained with : %d Gbps\n", intel_dp->frl.trained_rate_gbps); + drm_dbg(display->drm, "FRL trained with : %d Gbps\n", + intel_dp->frl.trained_rate_gbps); return 0; } @@ -3763,7 +3822,7 @@ int intel_dp_pcon_set_tmds_mode(struct intel_dp *intel_dp) void intel_dp_check_frl_training(struct intel_dp *intel_dp) { - struct drm_i915_private *dev_priv = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); /* * Always go for FRL training if: @@ -3778,14 +3837,16 @@ void intel_dp_check_frl_training(struct intel_dp *intel_dp) if (intel_dp_pcon_start_frl_training(intel_dp) < 0) { int ret, mode; - drm_dbg(&dev_priv->drm, "Couldn't set FRL mode, continuing with TMDS mode\n"); + drm_dbg(display->drm, + "Couldn't set FRL mode, continuing with TMDS mode\n"); ret = intel_dp_pcon_set_tmds_mode(intel_dp); mode = drm_dp_pcon_hdmi_link_mode(&intel_dp->aux, NULL); if (ret < 0 || mode != DP_PCON_HDMI_MODE_TMDS) - drm_dbg(&dev_priv->drm, "Issue with PCON, cannot set TMDS mode\n"); + drm_dbg(display->drm, + "Issue with PCON, cannot set TMDS mode\n"); } else { - drm_dbg(&dev_priv->drm, "FRL training Completed\n"); + drm_dbg(display->drm, "FRL training Completed\n"); } } @@ -3801,10 +3862,10 @@ static int intel_dp_pcon_dsc_enc_slices(struct intel_dp *intel_dp, const struct intel_crtc_state *crtc_state) { - struct intel_connector *intel_connector = intel_dp->attached_connector; - struct drm_connector *connector = &intel_connector->base; - int hdmi_throughput = connector->display_info.hdmi.dsc_cap.clk_per_slice; - int hdmi_max_slices = connector->display_info.hdmi.dsc_cap.max_slices; + struct intel_connector *connector = intel_dp->attached_connector; + const struct drm_display_info *info = &connector->base.display_info; + int hdmi_throughput = info->hdmi.dsc_cap.clk_per_slice; + int hdmi_max_slices = info->hdmi.dsc_cap.max_slices; int pcon_max_slices = drm_dp_pcon_dsc_max_slices(intel_dp->pcon_dsc_dpcd); int pcon_max_slice_width = drm_dp_pcon_dsc_max_slice_width(intel_dp->pcon_dsc_dpcd); @@ -3818,13 +3879,13 @@ intel_dp_pcon_dsc_enc_bpp(struct intel_dp *intel_dp, const struct intel_crtc_state *crtc_state, int num_slices, int slice_width) { - struct intel_connector *intel_connector = intel_dp->attached_connector; - struct drm_connector *connector = &intel_connector->base; + struct intel_connector *connector = intel_dp->attached_connector; + const struct drm_display_info *info = &connector->base.display_info; int output_format = crtc_state->output_format; - bool hdmi_all_bpp = connector->display_info.hdmi.dsc_cap.all_bpp; + bool hdmi_all_bpp = info->hdmi.dsc_cap.all_bpp; int pcon_fractional_bpp = drm_dp_pcon_dsc_bpp_incr(intel_dp->pcon_dsc_dpcd); int hdmi_max_chunk_bytes = - connector->display_info.hdmi.dsc_cap.total_chunk_kbytes * 1024; + info->hdmi.dsc_cap.total_chunk_kbytes * 1024; return intel_hdmi_dsc_get_bpp(pcon_fractional_bpp, slice_width, num_slices, output_format, hdmi_all_bpp, @@ -3835,24 +3896,26 @@ void intel_dp_pcon_dsc_configure(struct intel_dp *intel_dp, const struct intel_crtc_state *crtc_state) { + struct intel_display *display = to_intel_display(intel_dp); + struct intel_connector *connector = intel_dp->attached_connector; + const struct drm_display_info *info; u8 pps_param[6]; int slice_height; int slice_width; int num_slices; int bits_per_pixel; int ret; - struct intel_connector *intel_connector = intel_dp->attached_connector; - struct drm_i915_private *i915 = dp_to_i915(intel_dp); - struct drm_connector *connector; bool hdmi_is_dsc_1_2; if (!intel_dp_is_hdmi_2_1_sink(intel_dp)) return; - if (!intel_connector) + if (!connector) return; - connector = &intel_connector->base; - hdmi_is_dsc_1_2 = connector->display_info.hdmi.dsc_cap.v_1p2; + + info = &connector->base.display_info; + + hdmi_is_dsc_1_2 = info->hdmi.dsc_cap.v_1p2; if (!drm_dp_pcon_enc_is_dsc_1_2(intel_dp->pcon_dsc_dpcd) || !hdmi_is_dsc_1_2) @@ -3883,13 +3946,13 @@ intel_dp_pcon_dsc_configure(struct intel_dp *intel_dp, ret = drm_dp_pcon_pps_override_param(&intel_dp->aux, pps_param); if (ret < 0) - drm_dbg_kms(&i915->drm, "Failed to set pcon DSC\n"); + drm_dbg_kms(display->drm, "Failed to set pcon DSC\n"); } void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp, const struct intel_crtc_state *crtc_state) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); bool ycbcr444_to_420 = false; bool rgb_to_ycbcr = false; u8 tmp; @@ -3904,7 +3967,8 @@ void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp, if (drm_dp_dpcd_writeb(&intel_dp->aux, DP_PROTOCOL_CONVERTER_CONTROL_0, tmp) != 1) - drm_dbg_kms(&i915->drm, "Failed to %s protocol converter HDMI mode\n", + drm_dbg_kms(display->drm, + "Failed to %s protocol converter HDMI mode\n", str_enable_disable(intel_dp_has_hdmi_sink(intel_dp))); if (crtc_state->sink_format == INTEL_OUTPUT_FORMAT_YCBCR420) { @@ -3939,14 +4003,14 @@ void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp, if (drm_dp_dpcd_writeb(&intel_dp->aux, DP_PROTOCOL_CONVERTER_CONTROL_1, tmp) != 1) - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "Failed to %s protocol converter YCbCr 4:2:0 conversion mode\n", str_enable_disable(intel_dp->dfp.ycbcr_444_to_420)); tmp = rgb_to_ycbcr ? DP_CONVERSION_BT709_RGB_YCBCR_ENABLE : 0; if (drm_dp_pcon_convert_rgb_to_ycbcr(&intel_dp->aux, tmp) < 0) - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "Failed to %s protocol converter RGB->YCbCr conversion mode\n", str_enable_disable(tmp)); } @@ -3979,7 +4043,7 @@ static void intel_dp_read_dsc_dpcd(struct drm_dp_aux *aux, void intel_dp_get_dsc_sink_cap(u8 dpcd_rev, struct intel_connector *connector) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); /* * Clear the cached register set to avoid using stale values @@ -3998,11 +4062,11 @@ void intel_dp_get_dsc_sink_cap(u8 dpcd_rev, struct intel_connector *connector) if (drm_dp_dpcd_readb(connector->dp.dsc_decompression_aux, DP_FEC_CAPABILITY, &connector->dp.fec_capability) < 0) { - drm_err(&i915->drm, "Failed to read FEC DPCD register\n"); + drm_err(display->drm, "Failed to read FEC DPCD register\n"); return; } - drm_dbg_kms(&i915->drm, "FEC CAPABILITY: %x\n", + drm_dbg_kms(display->drm, "FEC CAPABILITY: %x\n", connector->dp.fec_capability); } @@ -4017,10 +4081,10 @@ static void intel_edp_get_dsc_sink_cap(u8 edp_dpcd_rev, struct intel_connector * static void intel_dp_detect_dsc_caps(struct intel_dp *intel_dp, struct intel_connector *connector) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); /* Read DP Sink DSC Cap DPCD regs for DP v1.4 */ - if (!HAS_DSC(i915)) + if (!HAS_DSC(display)) return; if (intel_dp_is_edp(intel_dp)) @@ -4034,8 +4098,8 @@ intel_dp_detect_dsc_caps(struct intel_dp *intel_dp, struct intel_connector *conn static void intel_edp_mso_mode_fixup(struct intel_connector *connector, struct drm_display_mode *mode) { + struct intel_display *display = to_intel_display(connector); struct intel_dp *intel_dp = intel_attached_dp(connector); - struct drm_i915_private *i915 = to_i915(connector->base.dev); int n = intel_dp->mso_link_count; int overlap = intel_dp->mso_pixel_overlap; @@ -4050,7 +4114,7 @@ static void intel_edp_mso_mode_fixup(struct intel_connector *connector, drm_mode_set_name(mode); - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s] using generated MSO mode: " DRM_MODE_FMT "\n", connector->base.base.id, connector->base.name, DRM_MODE_ARG(mode)); @@ -4058,7 +4122,7 @@ static void intel_edp_mso_mode_fixup(struct intel_connector *connector, void intel_edp_fixup_vbt_bpp(struct intel_encoder *encoder, int pipe_bpp) { - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); + struct intel_display *display = to_intel_display(encoder); struct intel_dp *intel_dp = enc_to_intel_dp(encoder); struct intel_connector *connector = intel_dp->attached_connector; @@ -4076,7 +4140,7 @@ void intel_edp_fixup_vbt_bpp(struct intel_encoder *encoder, int pipe_bpp) * up by the BIOS, and thus we can't get the mode at module * load. */ - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "pipe has %d bpp for eDP panel, overriding BIOS-provided max %d bpp\n", pipe_bpp, connector->panel.vbt.edp.bpp); connector->panel.vbt.edp.bpp = pipe_bpp; @@ -4085,7 +4149,7 @@ void intel_edp_fixup_vbt_bpp(struct intel_encoder *encoder, int pipe_bpp) static void intel_edp_mso_init(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; struct drm_display_info *info = &connector->base.display_info; u8 mso; @@ -4094,23 +4158,25 @@ static void intel_edp_mso_init(struct intel_dp *intel_dp) return; if (drm_dp_dpcd_readb(&intel_dp->aux, DP_EDP_MSO_LINK_CAPABILITIES, &mso) != 1) { - drm_err(&i915->drm, "Failed to read MSO cap\n"); + drm_err(display->drm, "Failed to read MSO cap\n"); return; } /* Valid configurations are SST or MSO 2x1, 2x2, 4x1 */ mso &= DP_EDP_MSO_NUMBER_OF_LINKS_MASK; if (mso % 2 || mso > drm_dp_max_lane_count(intel_dp->dpcd)) { - drm_err(&i915->drm, "Invalid MSO link count cap %u\n", mso); + drm_err(display->drm, "Invalid MSO link count cap %u\n", mso); mso = 0; } if (mso) { - drm_dbg_kms(&i915->drm, "Sink MSO %ux%u configuration, pixel overlap %u\n", + drm_dbg_kms(display->drm, + "Sink MSO %ux%u configuration, pixel overlap %u\n", mso, drm_dp_max_lane_count(intel_dp->dpcd) / mso, info->mso_pixel_overlap); - if (!HAS_MSO(i915)) { - drm_err(&i915->drm, "No source MSO support, disabling\n"); + if (!HAS_MSO(display)) { + drm_err(display->drm, + "No source MSO support, disabling\n"); mso = 0; } } @@ -4161,11 +4227,10 @@ intel_edp_set_sink_rates(struct intel_dp *intel_dp) static bool intel_edp_init_dpcd(struct intel_dp *intel_dp, struct intel_connector *connector) { - struct drm_i915_private *dev_priv = - to_i915(dp_to_dig_port(intel_dp)->base.base.dev); + struct intel_display *display = to_intel_display(intel_dp); /* this function is meant to be called only once */ - drm_WARN_ON(&dev_priv->drm, intel_dp->dpcd[DP_DPCD_REV] != 0); + drm_WARN_ON(display->drm, intel_dp->dpcd[DP_DPCD_REV] != 0); if (drm_dp_read_dpcd_caps(&intel_dp->aux, intel_dp->dpcd) != 0) return false; @@ -4189,7 +4254,7 @@ intel_edp_init_dpcd(struct intel_dp *intel_dp, struct intel_connector *connector if (drm_dp_dpcd_read(&intel_dp->aux, DP_EDP_DPCD_REV, intel_dp->edp_dpcd, sizeof(intel_dp->edp_dpcd)) == sizeof(intel_dp->edp_dpcd)) { - drm_dbg_kms(&dev_priv->drm, "eDP DPCD: %*ph\n", + drm_dbg_kms(display->drm, "eDP DPCD: %*ph\n", (int)sizeof(intel_dp->edp_dpcd), intel_dp->edp_dpcd); @@ -4300,9 +4365,9 @@ static enum drm_dp_mst_mode intel_dp_mst_mode_choose(struct intel_dp *intel_dp, enum drm_dp_mst_mode sink_mst_mode) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); - if (!i915->display.params.enable_dp_mst) + if (!display->params.enable_dp_mst) return DRM_DP_SST; if (!intel_dp_mst_source_support(intel_dp)) @@ -4318,7 +4383,7 @@ intel_dp_mst_mode_choose(struct intel_dp *intel_dp, static enum drm_dp_mst_mode intel_dp_mst_detect(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_encoder *encoder = &dp_to_dig_port(intel_dp)->base; enum drm_dp_mst_mode sink_mst_mode; enum drm_dp_mst_mode mst_detect; @@ -4327,12 +4392,12 @@ intel_dp_mst_detect(struct intel_dp *intel_dp) mst_detect = intel_dp_mst_mode_choose(intel_dp, sink_mst_mode); - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "[ENCODER:%d:%s] MST support: port: %s, sink: %s, modparam: %s -> enable: %s\n", encoder->base.base.id, encoder->base.name, str_yes_no(intel_dp_mst_source_support(intel_dp)), intel_dp_mst_mode_str(sink_mst_mode), - str_yes_no(i915->display.params.enable_dp_mst), + str_yes_no(display->params.enable_dp_mst), intel_dp_mst_mode_str(mst_detect)); return mst_detect; @@ -4358,12 +4423,13 @@ intel_dp_mst_configure(struct intel_dp *intel_dp) static void intel_dp_mst_disconnect(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); if (!intel_dp->is_mst) return; - drm_dbg_kms(&i915->drm, "MST device may have disappeared %d vs %d\n", + drm_dbg_kms(display->drm, + "MST device may have disappeared %d vs %d\n", intel_dp->is_mst, intel_dp->mst_mgr.mst_state); intel_dp->is_mst = false; drm_dp_mst_topology_mgr_set_mst(&intel_dp->mst_mgr, intel_dp->is_mst); @@ -4444,7 +4510,7 @@ static ssize_t intel_dp_as_sdp_pack(const struct drm_dp_as_sdp *as_sdp, } static ssize_t -intel_dp_hdr_metadata_infoframe_sdp_pack(struct drm_i915_private *i915, +intel_dp_hdr_metadata_infoframe_sdp_pack(struct intel_display *display, const struct hdmi_drm_infoframe *drm_infoframe, struct dp_sdp *sdp, size_t size) @@ -4461,12 +4527,13 @@ intel_dp_hdr_metadata_infoframe_sdp_pack(struct drm_i915_private *i915, len = hdmi_drm_infoframe_pack_only(drm_infoframe, buf, sizeof(buf)); if (len < 0) { - drm_dbg_kms(&i915->drm, "buffer size is smaller than hdr metadata infoframe\n"); + drm_dbg_kms(display->drm, + "buffer size is smaller than hdr metadata infoframe\n"); return -ENOSPC; } if (len != infoframe_size) { - drm_dbg_kms(&i915->drm, "wrong static hdr metadata size\n"); + drm_dbg_kms(display->drm, "wrong static hdr metadata size\n"); return -ENOSPC; } @@ -4524,8 +4591,8 @@ static void intel_write_dp_sdp(struct intel_encoder *encoder, const struct intel_crtc_state *crtc_state, unsigned int type) { + struct intel_display *display = to_intel_display(encoder); struct intel_digital_port *dig_port = enc_to_dig_port(encoder); - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); struct dp_sdp sdp = {}; ssize_t len; @@ -4538,7 +4605,7 @@ static void intel_write_dp_sdp(struct intel_encoder *encoder, len = drm_dp_vsc_sdp_pack(&crtc_state->infoframes.vsc, &sdp); break; case HDMI_PACKET_TYPE_GAMUT_METADATA: - len = intel_dp_hdr_metadata_infoframe_sdp_pack(dev_priv, + len = intel_dp_hdr_metadata_infoframe_sdp_pack(display, &crtc_state->infoframes.drm.drm, &sdp, sizeof(sdp)); break; @@ -4551,7 +4618,7 @@ static void intel_write_dp_sdp(struct intel_encoder *encoder, return; } - if (drm_WARN_ON(&dev_priv->drm, len < 0)) + if (drm_WARN_ON(display->drm, len < 0)) return; dig_port->write_infoframe(encoder, crtc_state, type, &sdp, len); @@ -4562,20 +4629,19 @@ void intel_dp_set_infoframes(struct intel_encoder *encoder, const struct intel_crtc_state *crtc_state, const struct drm_connector_state *conn_state) { - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); - i915_reg_t reg = HSW_TVIDEO_DIP_CTL(dev_priv, - crtc_state->cpu_transcoder); + struct intel_display *display = to_intel_display(encoder); + i915_reg_t reg = HSW_TVIDEO_DIP_CTL(display, crtc_state->cpu_transcoder); u32 dip_enable = VIDEO_DIP_ENABLE_AVI_HSW | VIDEO_DIP_ENABLE_GCP_HSW | VIDEO_DIP_ENABLE_VS_HSW | VIDEO_DIP_ENABLE_GMP_HSW | VIDEO_DIP_ENABLE_SPD_HSW | VIDEO_DIP_ENABLE_DRM_GLK; - if (HAS_AS_SDP(dev_priv)) + if (HAS_AS_SDP(display)) dip_enable |= VIDEO_DIP_ENABLE_AS_ADL; - u32 val = intel_de_read(dev_priv, reg) & ~dip_enable; + u32 val = intel_de_read(display, reg) & ~dip_enable; /* TODO: Sanitize DSC enabling wrt. intel_dsc_dp_pps_write(). */ - if (!enable && HAS_DSC(dev_priv)) + if (!enable && HAS_DSC(display)) val &= ~VDIP_ENABLE_PPS; /* @@ -4585,8 +4651,8 @@ void intel_dp_set_infoframes(struct intel_encoder *encoder, if (!enable || !crtc_state->has_psr) val &= ~VIDEO_DIP_ENABLE_VSC_HSW; - intel_de_write(dev_priv, reg, val); - intel_de_posting_read(dev_priv, reg); + intel_de_write(display, reg, val); + intel_de_posting_read(display, reg); if (!enable) return; @@ -4707,8 +4773,8 @@ intel_read_dp_as_sdp(struct intel_encoder *encoder, struct intel_crtc_state *crtc_state, struct drm_dp_as_sdp *as_sdp) { + struct intel_display *display = to_intel_display(encoder); struct intel_digital_port *dig_port = enc_to_dig_port(encoder); - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); unsigned int type = DP_SDP_ADAPTIVE_SYNC; struct dp_sdp sdp = {}; int ret; @@ -4722,7 +4788,7 @@ intel_read_dp_as_sdp(struct intel_encoder *encoder, ret = intel_dp_as_sdp_unpack(as_sdp, &sdp, sizeof(sdp)); if (ret) - drm_dbg_kms(&dev_priv->drm, "Failed to unpack DP AS SDP\n"); + drm_dbg_kms(display->drm, "Failed to unpack DP AS SDP\n"); } static int @@ -4775,8 +4841,8 @@ static void intel_read_dp_vsc_sdp(struct intel_encoder *encoder, struct intel_crtc_state *crtc_state, struct drm_dp_vsc_sdp *vsc) { + struct intel_display *display = to_intel_display(encoder); struct intel_digital_port *dig_port = enc_to_dig_port(encoder); - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); unsigned int type = DP_SDP_VSC; struct dp_sdp sdp = {}; int ret; @@ -4790,15 +4856,15 @@ static void intel_read_dp_vsc_sdp(struct intel_encoder *encoder, ret = intel_dp_vsc_sdp_unpack(vsc, &sdp, sizeof(sdp)); if (ret) - drm_dbg_kms(&dev_priv->drm, "Failed to unpack DP VSC SDP\n"); + drm_dbg_kms(display->drm, "Failed to unpack DP VSC SDP\n"); } static void intel_read_dp_hdr_metadata_infoframe_sdp(struct intel_encoder *encoder, struct intel_crtc_state *crtc_state, struct hdmi_drm_infoframe *drm_infoframe) { + struct intel_display *display = to_intel_display(encoder); struct intel_digital_port *dig_port = enc_to_dig_port(encoder); - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); unsigned int type = HDMI_PACKET_TYPE_GAMUT_METADATA; struct dp_sdp sdp = {}; int ret; @@ -4814,7 +4880,7 @@ static void intel_read_dp_hdr_metadata_infoframe_sdp(struct intel_encoder *encod sizeof(sdp)); if (ret) - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "Failed to unpack DP HDR Metadata Infoframe SDP\n"); } @@ -4844,8 +4910,8 @@ void intel_read_dp_sdp(struct intel_encoder *encoder, static bool intel_dp_link_ok(struct intel_dp *intel_dp, u8 link_status[DP_LINK_STATUS_SIZE]) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_encoder *encoder = &dp_to_dig_port(intel_dp)->base; - struct drm_i915_private *i915 = to_i915(encoder->base.dev); bool uhbr = intel_dp->link_rate >= 1000000; bool ok; @@ -4859,7 +4925,7 @@ static bool intel_dp_link_ok(struct intel_dp *intel_dp, return true; intel_dp_dump_link_status(intel_dp, DP_PHY_DPRX, link_status); - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "[ENCODER:%d:%s] %s link not ok, retraining\n", encoder->base.base.id, encoder->base.name, uhbr ? "128b/132b" : "8b/10b"); @@ -4882,14 +4948,14 @@ intel_dp_mst_hpd_irq(struct intel_dp *intel_dp, u8 *esi, u8 *ack) static bool intel_dp_mst_link_status(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_encoder *encoder = &dp_to_dig_port(intel_dp)->base; - struct drm_i915_private *i915 = to_i915(encoder->base.dev); u8 link_status[DP_LINK_STATUS_SIZE] = {}; const size_t esi_link_status_size = DP_LINK_STATUS_SIZE - 2; if (drm_dp_dpcd_read(&intel_dp->aux, DP_LANE0_1_STATUS_ESI, link_status, esi_link_status_size) != esi_link_status_size) { - drm_err(&i915->drm, + drm_err(display->drm, "[ENCODER:%d:%s] Failed to read link status\n", encoder->base.base.id, encoder->base.name); return false; @@ -4915,27 +4981,27 @@ static bool intel_dp_mst_link_status(struct intel_dp *intel_dp) static bool intel_dp_check_mst_status(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); struct intel_encoder *encoder = &dig_port->base; bool link_ok = true; bool reprobe_needed = false; - drm_WARN_ON_ONCE(&i915->drm, intel_dp->active_mst_links < 0); + drm_WARN_ON_ONCE(display->drm, intel_dp->active_mst_links < 0); for (;;) { u8 esi[4] = {}; u8 ack[4] = {}; if (!intel_dp_get_sink_irq_esi(intel_dp, esi)) { - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "failed to get ESI - device may have failed\n"); link_ok = false; break; } - drm_dbg_kms(&i915->drm, "DPRX ESI: %4ph\n", esi); + drm_dbg_kms(display->drm, "DPRX ESI: %4ph\n", esi); if (intel_dp->active_mst_links > 0 && link_ok && esi[3] & LINK_STATUS_CHANGED) { @@ -4947,7 +5013,7 @@ intel_dp_check_mst_status(struct intel_dp *intel_dp) intel_dp_mst_hpd_irq(intel_dp, esi, ack); if (esi[3] & DP_TUNNELING_IRQ) { - if (drm_dp_tunnel_handle_irq(i915->display.dp_tunnel_mgr, + if (drm_dp_tunnel_handle_irq(display->dp_tunnel_mgr, &intel_dp->aux)) reprobe_needed = true; ack[3] |= DP_TUNNELING_IRQ; @@ -4957,7 +5023,7 @@ intel_dp_check_mst_status(struct intel_dp *intel_dp) break; if (!intel_dp_ack_sink_irq_esi(intel_dp, ack)) - drm_dbg_kms(&i915->drm, "Failed to ack ESI\n"); + drm_dbg_kms(display->drm, "Failed to ack ESI\n"); if (ack[1] & (DP_DOWN_REP_MSG_RDY | DP_UP_REQ_MSG_RDY)) drm_dp_mst_hpd_irq_send_new_request(&intel_dp->mst_mgr); @@ -5045,7 +5111,7 @@ intel_dp_needs_link_retrain(struct intel_dp *intel_dp) bool intel_dp_has_connector(struct intel_dp *intel_dp, const struct drm_connector_state *conn_state) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_encoder *encoder; enum pipe pipe; @@ -5058,7 +5124,7 @@ bool intel_dp_has_connector(struct intel_dp *intel_dp, return true; /* MST */ - for_each_pipe(i915, pipe) { + for_each_pipe(display, pipe) { encoder = &intel_dp->mst_encoders[pipe]->base; if (conn_state->best_encoder == &encoder->base) return true; @@ -5086,14 +5152,14 @@ int intel_dp_get_active_pipes(struct intel_dp *intel_dp, struct drm_modeset_acquire_ctx *ctx, u8 *pipe_mask) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct drm_connector_list_iter conn_iter; struct intel_connector *connector; int ret = 0; *pipe_mask = 0; - drm_connector_list_iter_begin(&i915->drm, &conn_iter); + drm_connector_list_iter_begin(display->drm, &conn_iter); for_each_intel_connector_iter(connector, &conn_iter) { struct drm_connector_state *conn_state = connector->base.state; @@ -5113,7 +5179,8 @@ int intel_dp_get_active_pipes(struct intel_dp *intel_dp, crtc_state = to_intel_crtc_state(crtc->base.state); - drm_WARN_ON(&i915->drm, !intel_crtc_has_dp_encoder(crtc_state)); + drm_WARN_ON(display->drm, + !intel_crtc_has_dp_encoder(crtc_state)); if (!crtc_state->hw.active) continue; @@ -5143,6 +5210,7 @@ static bool intel_dp_is_connected(struct intel_dp *intel_dp) static int intel_dp_retrain_link(struct intel_encoder *encoder, struct drm_modeset_acquire_ctx *ctx) { + struct intel_display *display = to_intel_display(encoder); struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); struct intel_dp *intel_dp = enc_to_intel_dp(encoder); u8 pipe_mask; @@ -5151,7 +5219,7 @@ static int intel_dp_retrain_link(struct intel_encoder *encoder, if (!intel_dp_is_connected(intel_dp)) return 0; - ret = drm_modeset_lock(&dev_priv->drm.mode_config.connection_mutex, + ret = drm_modeset_lock(&display->drm->mode_config.connection_mutex, ctx); if (ret) return ret; @@ -5169,7 +5237,8 @@ static int intel_dp_retrain_link(struct intel_encoder *encoder, if (!intel_dp_needs_link_retrain(intel_dp)) return 0; - drm_dbg_kms(&dev_priv->drm, "[ENCODER:%d:%s] retraining link (forced %s)\n", + drm_dbg_kms(display->drm, + "[ENCODER:%d:%s] retraining link (forced %s)\n", encoder->base.base.id, encoder->base.name, str_yes_no(intel_dp->link.force_retrain)); @@ -5180,7 +5249,7 @@ static int intel_dp_retrain_link(struct intel_encoder *encoder, intel_dp->link.force_retrain = false; if (ret) - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "[ENCODER:%d:%s] link retraining failed: %pe\n", encoder->base.base.id, encoder->base.name, ERR_PTR(ret)); @@ -5213,7 +5282,7 @@ void intel_dp_check_link_state(struct intel_dp *intel_dp) static void intel_dp_check_device_service_irq(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); u8 val; if (intel_dp->dpcd[DP_DPCD_REV] < 0x11) @@ -5232,12 +5301,12 @@ static void intel_dp_check_device_service_irq(struct intel_dp *intel_dp) intel_hdcp_handle_cp_irq(intel_dp->attached_connector); if (val & DP_SINK_SPECIFIC_IRQ) - drm_dbg_kms(&i915->drm, "Sink specific irq unhandled\n"); + drm_dbg_kms(display->drm, "Sink specific irq unhandled\n"); } static bool intel_dp_check_link_service_irq(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); bool reprobe_needed = false; u8 val; @@ -5249,7 +5318,7 @@ static bool intel_dp_check_link_service_irq(struct intel_dp *intel_dp) return false; if ((val & DP_TUNNELING_IRQ) && - drm_dp_tunnel_handle_irq(i915->display.dp_tunnel_mgr, + drm_dp_tunnel_handle_irq(display->dp_tunnel_mgr, &intel_dp->aux)) reprobe_needed = true; @@ -5318,12 +5387,12 @@ intel_dp_short_pulse(struct intel_dp *intel_dp) static enum drm_connector_status intel_dp_detect_dpcd(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); u8 *dpcd = intel_dp->dpcd; u8 type; - if (drm_WARN_ON(&i915->drm, intel_dp_is_edp(intel_dp))) + if (drm_WARN_ON(display->drm, intel_dp_is_edp(intel_dp))) return connector_status_connected; lspcon_resume(dig_port); @@ -5366,7 +5435,7 @@ intel_dp_detect_dpcd(struct intel_dp *intel_dp) } /* Anything else is out of spec, warn and ignore */ - drm_dbg_kms(&i915->drm, "Broken DP branch device, ignoring\n"); + drm_dbg_kms(display->drm, "Broken DP branch device, ignoring\n"); return connector_status_disconnected; } @@ -5461,7 +5530,7 @@ static void intel_dp_update_dfp(struct intel_dp *intel_dp, const struct drm_edid *drm_edid) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; intel_dp->dfp.max_bpc = @@ -5485,7 +5554,7 @@ intel_dp_update_dfp(struct intel_dp *intel_dp, drm_dp_get_pcon_max_frl_bw(intel_dp->dpcd, intel_dp->downstream_ports); - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s] DFP max bpc %d, max dotclock %d, TMDS clock %d-%d, PCON Max FRL BW %dGbps\n", connector->base.base.id, connector->base.name, intel_dp->dfp.max_bpc, @@ -5518,7 +5587,7 @@ intel_dp_can_ycbcr420(struct intel_dp *intel_dp) static void intel_dp_update_420(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; intel_dp->dfp.ycbcr420_passthrough = @@ -5536,7 +5605,7 @@ intel_dp_update_420(struct intel_dp *intel_dp) connector->base.ycbcr_420_allowed = intel_dp_can_ycbcr420(intel_dp); - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s] RGB->YcbCr conversion? %s, YCbCr 4:2:0 allowed? %s, YCbCr 4:4:4->4:2:0 conversion? %s\n", connector->base.base.id, connector->base.name, str_yes_no(intel_dp->dfp.rgb_to_ycbcr), @@ -5547,7 +5616,7 @@ intel_dp_update_420(struct intel_dp *intel_dp) static void intel_dp_set_edid(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; const struct drm_edid *drm_edid; bool vrr_capable; @@ -5560,7 +5629,7 @@ intel_dp_set_edid(struct intel_dp *intel_dp) drm_edid_connector_update(&connector->base, drm_edid); vrr_capable = intel_vrr_is_capable(connector); - drm_dbg_kms(&i915->drm, "[CONNECTOR:%d:%s] VRR capable: %s\n", + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s] VRR capable: %s\n", connector->base.base.id, connector->base.name, str_yes_no(vrr_capable)); drm_connector_set_vrr_capable_property(&connector->base, vrr_capable); @@ -5597,38 +5666,37 @@ intel_dp_unset_edid(struct intel_dp *intel_dp) static void intel_dp_detect_sdp_caps(struct intel_dp *intel_dp) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); - intel_dp->as_sdp_supported = HAS_AS_SDP(i915) && + intel_dp->as_sdp_supported = HAS_AS_SDP(display) && drm_dp_as_sdp_supported(&intel_dp->aux, intel_dp->dpcd); } static int -intel_dp_detect(struct drm_connector *connector, +intel_dp_detect(struct drm_connector *_connector, struct drm_modeset_acquire_ctx *ctx, bool force) { - struct drm_i915_private *dev_priv = to_i915(connector->dev); - struct intel_connector *intel_connector = - to_intel_connector(connector); - struct intel_dp *intel_dp = intel_attached_dp(intel_connector); + struct intel_display *display = to_intel_display(_connector->dev); + struct intel_connector *connector = to_intel_connector(_connector); + struct intel_dp *intel_dp = intel_attached_dp(connector); struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); struct intel_encoder *encoder = &dig_port->base; enum drm_connector_status status; int ret; - drm_dbg_kms(&dev_priv->drm, "[CONNECTOR:%d:%s]\n", - connector->base.id, connector->name); - drm_WARN_ON(&dev_priv->drm, - !drm_modeset_is_locked(&dev_priv->drm.mode_config.connection_mutex)); + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s]\n", + connector->base.base.id, connector->base.name); + drm_WARN_ON(display->drm, + !drm_modeset_is_locked(&display->drm->mode_config.connection_mutex)); - if (!intel_display_device_enabled(dev_priv)) + if (!intel_display_device_enabled(display)) return connector_status_disconnected; - if (!intel_display_driver_check_access(dev_priv)) - return connector->status; + if (!intel_display_driver_check_access(display)) + return connector->base.status; - intel_dp_flush_connector_commits(intel_connector); + intel_dp_flush_connector_commits(connector); intel_pps_vdd_on(intel_dp); @@ -5654,7 +5722,7 @@ intel_dp_detect(struct drm_connector *connector, if (status == connector_status_disconnected) { intel_dp_test_reset(intel_dp); - memset(intel_connector->dp.dsc_dpcd, 0, sizeof(intel_connector->dp.dsc_dpcd)); + memset(connector->dp.dsc_dpcd, 0, sizeof(connector->dp.dsc_dpcd)); intel_dp->psr.sink_panel_replay_support = false; intel_dp->psr.sink_panel_replay_su_support = false; @@ -5675,12 +5743,12 @@ intel_dp_detect(struct drm_connector *connector, } if (ret == 1) - intel_connector->base.epoch_counter++; + connector->base.epoch_counter++; if (!intel_dp_is_edp(intel_dp)) intel_psr_init_dpcd(intel_dp); - intel_dp_detect_dsc_caps(intel_dp, intel_connector); + intel_dp_detect_dsc_caps(intel_dp, connector); intel_dp_detect_sdp_caps(intel_dp); @@ -5723,8 +5791,7 @@ intel_dp_detect(struct drm_connector *connector, intel_dp->aux.i2c_defer_count = 0; intel_dp_set_edid(intel_dp); - if (intel_dp_is_edp(intel_dp) || - to_intel_connector(connector)->detect_edid) + if (intel_dp_is_edp(intel_dp) || connector->detect_edid) status = connector_status_connected; intel_dp_check_device_service_irq(intel_dp); @@ -5734,7 +5801,7 @@ out_unset_edid: intel_dp_unset_edid(intel_dp); if (!intel_dp_is_edp(intel_dp)) - drm_dp_set_subconnector_property(connector, + drm_dp_set_subconnector_property(&connector->base, status, intel_dp->dpcd, intel_dp->downstream_ports); @@ -5747,15 +5814,13 @@ out_vdd_off: static void intel_dp_force(struct drm_connector *connector) { + struct intel_display *display = to_intel_display(connector->dev); struct intel_dp *intel_dp = intel_attached_dp(to_intel_connector(connector)); - struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); - struct intel_encoder *intel_encoder = &dig_port->base; - struct drm_i915_private *dev_priv = to_i915(intel_encoder->base.dev); - drm_dbg_kms(&dev_priv->drm, "[CONNECTOR:%d:%s]\n", + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s]\n", connector->base.id, connector->name); - if (!intel_display_driver_check_access(dev_priv)) + if (!intel_display_driver_check_access(display)) return; intel_dp_unset_edid(intel_dp); @@ -5766,30 +5831,31 @@ intel_dp_force(struct drm_connector *connector) intel_dp_set_edid(intel_dp); } -static int intel_dp_get_modes(struct drm_connector *connector) +static int intel_dp_get_modes(struct drm_connector *_connector) { - struct intel_connector *intel_connector = to_intel_connector(connector); + struct intel_display *display = to_intel_display(_connector->dev); + struct intel_connector *connector = to_intel_connector(_connector); + struct intel_dp *intel_dp = intel_attached_dp(connector); int num_modes; /* drm_edid_connector_update() done in ->detect() or ->force() */ - num_modes = drm_edid_connector_add_modes(connector); + num_modes = drm_edid_connector_add_modes(&connector->base); /* Also add fixed mode, which may or may not be present in EDID */ - if (intel_dp_is_edp(intel_attached_dp(intel_connector))) - num_modes += intel_panel_get_modes(intel_connector); + if (intel_dp_is_edp(intel_dp)) + num_modes += intel_panel_get_modes(connector); if (num_modes) return num_modes; - if (!intel_connector->detect_edid) { - struct intel_dp *intel_dp = intel_attached_dp(intel_connector); + if (!connector->detect_edid) { struct drm_display_mode *mode; - mode = drm_dp_downstream_mode(connector->dev, + mode = drm_dp_downstream_mode(display->drm, intel_dp->dpcd, intel_dp->downstream_ports); if (mode) { - drm_mode_probed_add(connector, mode); + drm_mode_probed_add(&connector->base, mode); num_modes++; } } @@ -5800,7 +5866,7 @@ static int intel_dp_get_modes(struct drm_connector *connector) static int intel_dp_connector_register(struct drm_connector *connector) { - struct drm_i915_private *i915 = to_i915(connector->dev); + struct intel_display *display = to_intel_display(connector->dev); struct intel_dp *intel_dp = intel_attached_dp(to_intel_connector(connector)); struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); struct intel_lspcon *lspcon = &dig_port->lspcon; @@ -5810,7 +5876,7 @@ intel_dp_connector_register(struct drm_connector *connector) if (ret) return ret; - drm_dbg_kms(&i915->drm, "registering %s bus for %s\n", + drm_dbg_kms(display->drm, "registering %s bus for %s\n", intel_dp->aux.name, connector->kdev->kobj.name); intel_dp->aux.dev = connector->kdev; @@ -5847,10 +5913,11 @@ intel_dp_connector_unregister(struct drm_connector *connector) void intel_dp_connector_sync_state(struct intel_connector *connector, const struct intel_crtc_state *crtc_state) { - struct drm_i915_private *i915 = to_i915(connector->base.dev); + struct intel_display *display = to_intel_display(connector); if (crtc_state && crtc_state->dsc.compression_enable) { - drm_WARN_ON(&i915->drm, !connector->dp.dsc_decompression_aux); + drm_WARN_ON(display->drm, + !connector->dp.dsc_decompression_aux); connector->dp.dsc_decompression_enabled = true; } else { connector->dp.dsc_decompression_enabled = false; @@ -5880,18 +5947,18 @@ void intel_dp_encoder_flush_work(struct drm_encoder *_encoder) intel_dp_aux_fini(intel_dp); } -void intel_dp_encoder_suspend(struct intel_encoder *intel_encoder) +void intel_dp_encoder_suspend(struct intel_encoder *encoder) { - struct intel_dp *intel_dp = enc_to_intel_dp(intel_encoder); + struct intel_dp *intel_dp = enc_to_intel_dp(encoder); intel_pps_vdd_off_sync(intel_dp); intel_dp_tunnel_suspend(intel_dp); } -void intel_dp_encoder_shutdown(struct intel_encoder *intel_encoder) +void intel_dp_encoder_shutdown(struct intel_encoder *encoder) { - struct intel_dp *intel_dp = enc_to_intel_dp(intel_encoder); + struct intel_dp *intel_dp = enc_to_intel_dp(encoder); intel_pps_wait_power_cycle(intel_dp); } @@ -5899,12 +5966,12 @@ void intel_dp_encoder_shutdown(struct intel_encoder *intel_encoder) static int intel_modeset_tile_group(struct intel_atomic_state *state, int tile_group_id) { - struct drm_i915_private *dev_priv = to_i915(state->base.dev); + struct intel_display *display = to_intel_display(state); struct drm_connector_list_iter conn_iter; struct drm_connector *connector; int ret = 0; - drm_connector_list_iter_begin(&dev_priv->drm, &conn_iter); + drm_connector_list_iter_begin(display->drm, &conn_iter); drm_for_each_connector_iter(connector, &conn_iter) { struct drm_connector_state *conn_state; struct intel_crtc_state *crtc_state; @@ -5940,13 +6007,13 @@ static int intel_modeset_tile_group(struct intel_atomic_state *state, static int intel_modeset_affected_transcoders(struct intel_atomic_state *state, u8 transcoders) { - struct drm_i915_private *dev_priv = to_i915(state->base.dev); + struct intel_display *display = to_intel_display(state); struct intel_crtc *crtc; if (transcoders == 0) return 0; - for_each_intel_crtc(&dev_priv->drm, crtc) { + for_each_intel_crtc(display->drm, crtc) { struct intel_crtc_state *crtc_state; int ret; @@ -5973,7 +6040,7 @@ static int intel_modeset_affected_transcoders(struct intel_atomic_state *state, transcoders &= ~BIT(crtc_state->cpu_transcoder); } - drm_WARN_ON(&dev_priv->drm, transcoders != 0); + drm_WARN_ON(display->drm, transcoders != 0); return 0; } @@ -6007,7 +6074,7 @@ static int intel_modeset_synced_crtcs(struct intel_atomic_state *state, static int intel_dp_connector_atomic_check(struct drm_connector *conn, struct drm_atomic_state *_state) { - struct drm_i915_private *dev_priv = to_i915(conn->dev); + struct intel_display *display = to_intel_display(conn->dev); struct intel_atomic_state *state = to_intel_atomic_state(_state); struct drm_connector_state *conn_state = drm_atomic_get_new_connector_state(_state, conn); struct intel_connector *intel_conn = to_intel_connector(conn); @@ -6037,7 +6104,7 @@ static int intel_dp_connector_atomic_check(struct drm_connector *conn, * We don't enable port sync on BDW due to missing w/as and * due to not having adjusted the modeset sequence appropriately. */ - if (DISPLAY_VER(dev_priv) < 9) + if (DISPLAY_VER(display) < 9) return 0; if (conn->has_tile) { @@ -6052,6 +6119,7 @@ static int intel_dp_connector_atomic_check(struct drm_connector *conn, static void intel_dp_oob_hotplug_event(struct drm_connector *connector, enum drm_connector_status hpd_state) { + struct intel_display *display = to_intel_display(connector->dev); struct intel_encoder *encoder = intel_attached_encoder(to_intel_connector(connector)); struct drm_i915_private *i915 = to_i915(connector->dev); bool hpd_high = hpd_state == connector_status_connected; @@ -6059,10 +6127,12 @@ static void intel_dp_oob_hotplug_event(struct drm_connector *connector, bool need_work = false; spin_lock_irq(&i915->irq_lock); - if (hpd_high != test_bit(hpd_pin, &i915->display.hotplug.oob_hotplug_last_state)) { - i915->display.hotplug.event_bits |= BIT(hpd_pin); + if (hpd_high != test_bit(hpd_pin, &display->hotplug.oob_hotplug_last_state)) { + display->hotplug.event_bits |= BIT(hpd_pin); - __assign_bit(hpd_pin, &i915->display.hotplug.oob_hotplug_last_state, hpd_high); + __assign_bit(hpd_pin, + &display->hotplug.oob_hotplug_last_state, + hpd_high); need_work = true; } spin_unlock_irq(&i915->irq_lock); @@ -6094,6 +6164,7 @@ static const struct drm_connector_helper_funcs intel_dp_connector_helper_funcs = enum irqreturn intel_dp_hpd_pulse(struct intel_digital_port *dig_port, bool long_hpd) { + struct intel_display *display = to_intel_display(dig_port); struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev); struct intel_dp *intel_dp = &dig_port->dp; u8 dpcd[DP_RECEIVER_CAP_SIZE]; @@ -6108,7 +6179,7 @@ intel_dp_hpd_pulse(struct intel_digital_port *dig_port, bool long_hpd) * would end up in an endless cycle of * "vdd off -> long/short hpd -> vdd on -> detect -> vdd off -> ..." */ - drm_dbg_kms(&i915->drm, + drm_dbg_kms(display->drm, "ignoring %s hpd on eDP [ENCODER:%d:%s]\n", long_hpd ? "long" : "short", dig_port->base.base.base.id, @@ -6116,7 +6187,7 @@ intel_dp_hpd_pulse(struct intel_digital_port *dig_port, bool long_hpd) return IRQ_HANDLED; } - drm_dbg_kms(&i915->drm, "got hpd irq on [ENCODER:%d:%s] - %s\n", + drm_dbg_kms(display->drm, "got hpd irq on [ENCODER:%d:%s] - %s\n", dig_port->base.base.base.id, dig_port->base.base.name, long_hpd ? "long" : "short"); @@ -6149,7 +6220,7 @@ intel_dp_hpd_pulse(struct intel_digital_port *dig_port, bool long_hpd) return IRQ_HANDLED; } -static bool _intel_dp_is_port_edp(struct drm_i915_private *dev_priv, +static bool _intel_dp_is_port_edp(struct intel_display *display, const struct intel_bios_encoder_data *devdata, enum port port) { @@ -6157,41 +6228,40 @@ static bool _intel_dp_is_port_edp(struct drm_i915_private *dev_priv, * eDP not supported on g4x. so bail out early just * for a bit extra safety in case the VBT is bonkers. */ - if (DISPLAY_VER(dev_priv) < 5) + if (DISPLAY_VER(display) < 5) return false; - if (DISPLAY_VER(dev_priv) < 9 && port == PORT_A) + if (DISPLAY_VER(display) < 9 && port == PORT_A) return true; return devdata && intel_bios_encoder_supports_edp(devdata); } -bool intel_dp_is_port_edp(struct drm_i915_private *i915, enum port port) +bool intel_dp_is_port_edp(struct intel_display *display, enum port port) { - struct intel_display *display = &i915->display; const struct intel_bios_encoder_data *devdata = intel_bios_encoder_data_lookup(display, port); - return _intel_dp_is_port_edp(i915, devdata, port); + return _intel_dp_is_port_edp(display, devdata, port); } bool intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder) { - struct drm_i915_private *i915 = to_i915(encoder->base.dev); + struct intel_display *display = to_intel_display(encoder); enum port port = encoder->port; if (intel_bios_encoder_is_lspcon(encoder->devdata)) return false; - if (DISPLAY_VER(i915) >= 11) + if (DISPLAY_VER(display) >= 11) return true; if (port == PORT_A) return false; - if (IS_HASWELL(i915) || IS_BROADWELL(i915) || - DISPLAY_VER(i915) >= 9) + if (display->platform.haswell || display->platform.broadwell || + DISPLAY_VER(display) >= 9) return true; return false; @@ -6200,19 +6270,19 @@ intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder) static void intel_dp_add_properties(struct intel_dp *intel_dp, struct drm_connector *connector) { - struct drm_i915_private *dev_priv = to_i915(connector->dev); + struct intel_display *display = to_intel_display(intel_dp); enum port port = dp_to_dig_port(intel_dp)->base.port; if (!intel_dp_is_edp(intel_dp)) drm_connector_attach_dp_subconnector_property(connector); - if (!IS_G4X(dev_priv) && port != PORT_A) + if (!display->platform.g4x && port != PORT_A) intel_attach_force_audio_property(connector); intel_attach_broadcast_rgb_property(connector); - if (HAS_GMCH(dev_priv)) + if (HAS_GMCH(display)) drm_connector_attach_max_bpc_property(connector, 6, 10); - else if (DISPLAY_VER(dev_priv) >= 5) + else if (DISPLAY_VER(display) >= 5) drm_connector_attach_max_bpc_property(connector, 6, 12); /* Register HDMI colorspace for case of lspcon */ @@ -6226,22 +6296,22 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct drm_connector *connect if (intel_dp_has_gamut_metadata_dip(&dp_to_dig_port(intel_dp)->base)) drm_connector_attach_hdr_output_metadata_property(connector); - if (HAS_VRR(dev_priv)) + if (HAS_VRR(display)) drm_connector_attach_vrr_capable_property(connector); } static void intel_edp_add_properties(struct intel_dp *intel_dp) { + struct intel_display *display = to_intel_display(intel_dp); struct intel_connector *connector = intel_dp->attached_connector; - struct drm_i915_private *i915 = to_i915(connector->base.dev); const struct drm_display_mode *fixed_mode = intel_panel_preferred_fixed_mode(connector); intel_attach_scaling_mode_property(&connector->base); drm_connector_set_panel_orientation_with_quirk(&connector->base, - i915->display.vbt.orientation, + display->vbt.orientation, fixed_mode->hdisplay, fixed_mode->vdisplay); } @@ -6249,21 +6319,20 @@ intel_edp_add_properties(struct intel_dp *intel_dp) static void intel_edp_backlight_setup(struct intel_dp *intel_dp, struct intel_connector *connector) { - struct drm_i915_private *i915 = dp_to_i915(intel_dp); + struct intel_display *display = to_intel_display(intel_dp); enum pipe pipe = INVALID_PIPE; - if (IS_VALLEYVIEW(i915) || IS_CHERRYVIEW(i915)) + if (display->platform.valleyview || display->platform.cherryview) pipe = vlv_pps_backlight_initial_pipe(intel_dp); intel_backlight_setup(connector, pipe); } static bool intel_edp_init_connector(struct intel_dp *intel_dp, - struct intel_connector *intel_connector) + struct intel_connector *connector) { struct intel_display *display = to_intel_display(intel_dp); - struct drm_i915_private *dev_priv = dp_to_i915(intel_dp); - struct drm_connector *connector = &intel_connector->base; + struct drm_i915_private *dev_priv = to_i915(display->drm); struct drm_display_mode *fixed_mode; struct intel_encoder *encoder = &dp_to_dig_port(intel_dp)->base; bool has_dpcd; @@ -6279,19 +6348,19 @@ static bool intel_edp_init_connector(struct intel_dp *intel_dp, * with an already powered-on LVDS power sequencer. */ if (intel_get_lvds_encoder(dev_priv)) { - drm_WARN_ON(&dev_priv->drm, + drm_WARN_ON(display->drm, !(HAS_PCH_IBX(dev_priv) || HAS_PCH_CPT(dev_priv))); - drm_info(&dev_priv->drm, + drm_info(display->drm, "LVDS was detected, not registering eDP\n"); return false; } - intel_bios_init_panel_early(display, &intel_connector->panel, + intel_bios_init_panel_early(display, &connector->panel, encoder->devdata); if (!intel_pps_init(intel_dp)) { - drm_info(&dev_priv->drm, + drm_info(display->drm, "[ENCODER:%d:%s] unusable PPS, disabling eDP\n", encoder->base.base.id, encoder->base.name); /* @@ -6314,11 +6383,11 @@ static bool intel_edp_init_connector(struct intel_dp *intel_dp, intel_alpm_init_dpcd(intel_dp); /* Cache DPCD and EDID for edp. */ - has_dpcd = intel_edp_init_dpcd(intel_dp, intel_connector); + has_dpcd = intel_edp_init_dpcd(intel_dp, connector); if (!has_dpcd) { /* if this fails, presume the device is a ghost */ - drm_info(&dev_priv->drm, + drm_info(display->drm, "[ENCODER:%d:%s] failed to retrieve link info, disabling eDP\n", encoder->base.base.id, encoder->base.name); goto out_vdd_off; @@ -6341,7 +6410,7 @@ static bool intel_edp_init_connector(struct intel_dp *intel_dp, * DPCD read? Would need sort out the VDD handling... */ if (!intel_digital_port_connected(encoder)) { - drm_info(&dev_priv->drm, + drm_info(display->drm, "[ENCODER:%d:%s] HPD is down, disabling eDP\n", encoder->base.base.id, encoder->base.name); goto out_vdd_off; @@ -6353,30 +6422,30 @@ static bool intel_edp_init_connector(struct intel_dp *intel_dp, * back to checking for a VGA branch device. Only do this * on known affected platforms to minimize false positives. */ - if (DISPLAY_VER(dev_priv) == 9 && drm_dp_is_branch(intel_dp->dpcd) && + if (DISPLAY_VER(display) == 9 && drm_dp_is_branch(intel_dp->dpcd) && (intel_dp->dpcd[DP_DOWNSTREAMPORT_PRESENT] & DP_DWN_STRM_PORT_TYPE_MASK) == DP_DWN_STRM_PORT_TYPE_ANALOG) { - drm_info(&dev_priv->drm, + drm_info(display->drm, "[ENCODER:%d:%s] VGA converter detected, disabling eDP\n", encoder->base.base.id, encoder->base.name); goto out_vdd_off; } } - mutex_lock(&dev_priv->drm.mode_config.mutex); - drm_edid = drm_edid_read_ddc(connector, connector->ddc); + mutex_lock(&display->drm->mode_config.mutex); + drm_edid = drm_edid_read_ddc(&connector->base, connector->base.ddc); if (!drm_edid) { /* Fallback to EDID from ACPI OpRegion, if any */ - drm_edid = intel_opregion_get_edid(intel_connector); + drm_edid = intel_opregion_get_edid(connector); if (drm_edid) - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s] Using OpRegion EDID\n", - connector->base.id, connector->name); + connector->base.base.id, connector->base.name); } if (drm_edid) { - if (drm_edid_connector_update(connector, drm_edid) || - !drm_edid_connector_add_modes(connector)) { - drm_edid_connector_update(connector, NULL); + if (drm_edid_connector_update(&connector->base, drm_edid) || + !drm_edid_connector_add_modes(&connector->base)) { + drm_edid_connector_update(&connector->base, NULL); drm_edid_free(drm_edid); drm_edid = ERR_PTR(-EINVAL); } @@ -6384,34 +6453,34 @@ static bool intel_edp_init_connector(struct intel_dp *intel_dp, drm_edid = ERR_PTR(-ENOENT); } - intel_bios_init_panel_late(display, &intel_connector->panel, encoder->devdata, + intel_bios_init_panel_late(display, &connector->panel, encoder->devdata, IS_ERR(drm_edid) ? NULL : drm_edid); - intel_panel_add_edid_fixed_modes(intel_connector, true); + intel_panel_add_edid_fixed_modes(connector, true); /* MSO requires information from the EDID */ intel_edp_mso_init(intel_dp); /* multiply the mode clock and horizontal timings for MSO */ - list_for_each_entry(fixed_mode, &intel_connector->panel.fixed_modes, head) - intel_edp_mso_mode_fixup(intel_connector, fixed_mode); + list_for_each_entry(fixed_mode, &connector->panel.fixed_modes, head) + intel_edp_mso_mode_fixup(connector, fixed_mode); /* fallback to VBT if available for eDP */ - if (!intel_panel_preferred_fixed_mode(intel_connector)) - intel_panel_add_vbt_lfp_fixed_mode(intel_connector); + if (!intel_panel_preferred_fixed_mode(connector)) + intel_panel_add_vbt_lfp_fixed_mode(connector); - mutex_unlock(&dev_priv->drm.mode_config.mutex); + mutex_unlock(&display->drm->mode_config.mutex); - if (!intel_panel_preferred_fixed_mode(intel_connector)) { - drm_info(&dev_priv->drm, + if (!intel_panel_preferred_fixed_mode(connector)) { + drm_info(display->drm, "[ENCODER:%d:%s] failed to find fixed mode for the panel, disabling eDP\n", encoder->base.base.id, encoder->base.name); goto out_vdd_off; } - intel_panel_init(intel_connector, drm_edid); + intel_panel_init(connector, drm_edid); - intel_edp_backlight_setup(intel_dp, intel_connector); + intel_edp_backlight_setup(intel_dp, connector); intel_edp_add_properties(intel_dp); @@ -6421,34 +6490,32 @@ static bool intel_edp_init_connector(struct intel_dp *intel_dp, out_vdd_off: intel_pps_vdd_off_sync(intel_dp); - intel_bios_fini_panel(&intel_connector->panel); + intel_bios_fini_panel(&connector->panel); return false; } static void intel_dp_modeset_retry_work_fn(struct work_struct *work) { - struct intel_connector *intel_connector; - struct drm_connector *connector; + struct intel_connector *connector = container_of(work, typeof(*connector), + modeset_retry_work); + struct intel_display *display = to_intel_display(connector); - intel_connector = container_of(work, typeof(*intel_connector), - modeset_retry_work); - connector = &intel_connector->base; - drm_dbg_kms(connector->dev, "[CONNECTOR:%d:%s]\n", connector->base.id, - connector->name); + drm_dbg_kms(display->drm, "[CONNECTOR:%d:%s]\n", connector->base.base.id, + connector->base.name); /* Grab the locks before changing connector property*/ - mutex_lock(&connector->dev->mode_config.mutex); + mutex_lock(&display->drm->mode_config.mutex); /* Set connector link status to BAD and send a Uevent to notify * userspace to do a modeset. */ - drm_connector_set_link_status_property(connector, + drm_connector_set_link_status_property(&connector->base, DRM_MODE_LINK_STATUS_BAD); - mutex_unlock(&connector->dev->mode_config.mutex); + mutex_unlock(&display->drm->mode_config.mutex); /* Send Hotplug uevent so userspace can reprobe */ - drm_kms_helper_connector_hotplug_event(connector); + drm_kms_helper_connector_hotplug_event(&connector->base); - drm_connector_put(connector); + drm_connector_put(&connector->base); } void intel_dp_init_modeset_retry_work(struct intel_connector *connector) @@ -6459,45 +6526,44 @@ void intel_dp_init_modeset_retry_work(struct intel_connector *connector) bool intel_dp_init_connector(struct intel_digital_port *dig_port, - struct intel_connector *intel_connector) + struct intel_connector *connector) { struct intel_display *display = to_intel_display(dig_port); - struct drm_connector *connector = &intel_connector->base; struct intel_dp *intel_dp = &dig_port->dp; - struct intel_encoder *intel_encoder = &dig_port->base; - struct drm_device *dev = intel_encoder->base.dev; + struct intel_encoder *encoder = &dig_port->base; + struct drm_device *dev = encoder->base.dev; struct drm_i915_private *dev_priv = to_i915(dev); - enum port port = intel_encoder->port; + enum port port = encoder->port; int type; /* Initialize the work for modeset in case of link train failure */ - intel_dp_init_modeset_retry_work(intel_connector); + intel_dp_init_modeset_retry_work(connector); if (drm_WARN(dev, dig_port->max_lanes < 1, "Not enough lanes (%d) for DP on [ENCODER:%d:%s]\n", - dig_port->max_lanes, intel_encoder->base.base.id, - intel_encoder->base.name)) + dig_port->max_lanes, encoder->base.base.id, + encoder->base.name)) return false; intel_dp->reset_link_params = true; /* Preserve the current hw state. */ - intel_dp->DP = intel_de_read(dev_priv, intel_dp->output_reg); - intel_dp->attached_connector = intel_connector; + intel_dp->DP = intel_de_read(display, intel_dp->output_reg); + intel_dp->attached_connector = connector; - if (_intel_dp_is_port_edp(dev_priv, intel_encoder->devdata, port)) { + if (_intel_dp_is_port_edp(display, encoder->devdata, port)) { /* * Currently we don't support eDP on TypeC ports for DISPLAY_VER < 30, * although in theory it could work on TypeC legacy ports. */ - drm_WARN_ON(dev, intel_encoder_is_tc(intel_encoder) && - DISPLAY_VER(dev_priv) < 30); + drm_WARN_ON(dev, intel_encoder_is_tc(encoder) && + DISPLAY_VER(display) < 30); type = DRM_MODE_CONNECTOR_eDP; - intel_encoder->type = INTEL_OUTPUT_EDP; + encoder->type = INTEL_OUTPUT_EDP; /* eDP only on port B and/or C on vlv/chv */ - if (drm_WARN_ON(dev, (IS_VALLEYVIEW(dev_priv) || - IS_CHERRYVIEW(dev_priv)) && + if (drm_WARN_ON(dev, (display->platform.valleyview || + display->platform.cherryview) && port != PORT_B && port != PORT_C)) return false; } else { @@ -6507,37 +6573,37 @@ intel_dp_init_connector(struct intel_digital_port *dig_port, intel_dp_set_default_sink_rates(intel_dp); intel_dp_set_default_max_sink_lane_count(intel_dp); - if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) + if (display->platform.valleyview || display->platform.cherryview) vlv_pps_pipe_init(intel_dp); intel_dp_aux_init(intel_dp); - intel_connector->dp.dsc_decompression_aux = &intel_dp->aux; + connector->dp.dsc_decompression_aux = &intel_dp->aux; - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "Adding %s connector on [ENCODER:%d:%s]\n", type == DRM_MODE_CONNECTOR_eDP ? "eDP" : "DP", - intel_encoder->base.base.id, intel_encoder->base.name); + encoder->base.base.id, encoder->base.name); - drm_connector_init_with_ddc(dev, connector, &intel_dp_connector_funcs, + drm_connector_init_with_ddc(dev, &connector->base, &intel_dp_connector_funcs, type, &intel_dp->aux.ddc); - drm_connector_helper_add(connector, &intel_dp_connector_helper_funcs); + drm_connector_helper_add(&connector->base, &intel_dp_connector_helper_funcs); - if (!HAS_GMCH(dev_priv) && DISPLAY_VER(dev_priv) < 12) - connector->interlace_allowed = true; + if (!HAS_GMCH(display) && DISPLAY_VER(display) < 12) + connector->base.interlace_allowed = true; if (type != DRM_MODE_CONNECTOR_eDP) - intel_connector->polled = DRM_CONNECTOR_POLL_HPD; - intel_connector->base.polled = intel_connector->polled; + connector->polled = DRM_CONNECTOR_POLL_HPD; + connector->base.polled = connector->polled; - intel_connector_attach_encoder(intel_connector, intel_encoder); + intel_connector_attach_encoder(connector, encoder); - if (HAS_DDI(dev_priv)) - intel_connector->get_hw_state = intel_ddi_connector_get_hw_state; + if (HAS_DDI(display)) + connector->get_hw_state = intel_ddi_connector_get_hw_state; else - intel_connector->get_hw_state = intel_connector_get_hw_state; - intel_connector->sync_state = intel_dp_connector_sync_state; + connector->get_hw_state = intel_connector_get_hw_state; + connector->sync_state = intel_dp_connector_sync_state; - if (!intel_edp_init_connector(intel_dp, intel_connector)) { + if (!intel_edp_init_connector(intel_dp, connector)) { intel_dp_aux_fini(intel_dp); goto fail; } @@ -6547,15 +6613,14 @@ intel_dp_init_connector(struct intel_digital_port *dig_port, intel_dp_reset_link_params(intel_dp); /* init MST on ports that can support it */ - intel_dp_mst_encoder_init(dig_port, - intel_connector->base.base.id); + intel_dp_mst_encoder_init(dig_port, connector->base.base.id); - intel_dp_add_properties(intel_dp, connector); + intel_dp_add_properties(intel_dp, &connector->base); if (is_hdcp_supported(display, port) && !intel_dp_is_edp(intel_dp)) { - int ret = intel_dp_hdcp_init(dig_port, intel_connector); + int ret = intel_dp_hdcp_init(dig_port, connector); if (ret) - drm_dbg_kms(&dev_priv->drm, + drm_dbg_kms(display->drm, "HDCP init failed, skipping.\n"); } @@ -6568,19 +6633,19 @@ intel_dp_init_connector(struct intel_digital_port *dig_port, fail: intel_display_power_flush_work(dev_priv); - drm_connector_cleanup(connector); + drm_connector_cleanup(&connector->base); return false; } -void intel_dp_mst_suspend(struct drm_i915_private *dev_priv) +void intel_dp_mst_suspend(struct intel_display *display) { struct intel_encoder *encoder; - if (!HAS_DISPLAY(dev_priv)) + if (!HAS_DISPLAY(display)) return; - for_each_intel_encoder(&dev_priv->drm, encoder) { + for_each_intel_encoder(display->drm, encoder) { struct intel_dp *intel_dp; if (encoder->type != INTEL_OUTPUT_DDI) @@ -6596,14 +6661,14 @@ void intel_dp_mst_suspend(struct drm_i915_private *dev_priv) } } -void intel_dp_mst_resume(struct drm_i915_private *dev_priv) +void intel_dp_mst_resume(struct intel_display *display) { struct intel_encoder *encoder; - if (!HAS_DISPLAY(dev_priv)) + if (!HAS_DISPLAY(display)) return; - for_each_intel_encoder(&dev_priv->drm, encoder) { + for_each_intel_encoder(display->drm, encoder) { struct intel_dp *intel_dp; int ret; |