Re: [Intel-gfx] [PATCH 14/24] drm/i915/dp: Allow big joiner modes in intel_dp_mode_valid(), v2.

2019-10-08 Thread Ville Syrjälä
On Fri, Oct 04, 2019 at 01:35:04PM +0200, Maarten Lankhorst wrote:
> Small changes to intel_dp_mode_valid(), allow listing modes that
> can only be supported in the bigjoiner configuration, which is
> not supported yet.
> 
> eDP does not support bigjoiner, so do not expose bigjoiner only
> modes on the eDP port.
> 
> Changes since v1:
> - Disallow bigjoiner on eDP.
> 
> Signed-off-by: Maarten Lankhorst 
> ---
>  drivers/gpu/drm/i915/display/intel_dp.c | 92 +++--
>  1 file changed, 72 insertions(+), 20 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_dp.c 
> b/drivers/gpu/drm/i915/display/intel_dp.c
> index 4297738655c6..5c7323af08b3 100644
> --- a/drivers/gpu/drm/i915/display/intel_dp.c
> +++ b/drivers/gpu/drm/i915/display/intel_dp.c
> @@ -244,7 +244,7 @@ intel_dp_max_data_rate(int max_link_clock, int max_lanes)
>  }
>  
>  static int
> -intel_dp_downstream_max_dotclock(struct intel_dp *intel_dp)
> +intel_dp_downstream_max_dotclock(struct intel_dp *intel_dp, bool 
> allow_bigjoiner)
>  {
>   struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp);
>   struct intel_encoder *encoder = &intel_dig_port->base;
> @@ -254,6 +254,9 @@ intel_dp_downstream_max_dotclock(struct intel_dp 
> *intel_dp)
>  
>   int type = intel_dp->downstream_ports[0] & DP_DS_PORT_TYPE_MASK;
>  
> + if (allow_bigjoiner && INTEL_GEN(dev_priv) >= 11)
> + max_dotclk *= 2;
> +

This code is now rather confusing. OK, this function is already misnamed
because it checks both the source and downstream dotclock limits.

I suspect this should all look a bit more like:

source_max_dotclock()
{
if (port_can_do_bigjoiner && dsc_supported)
return 2*max_dotclock;
else
return max_dotclock;
}

max_dotclock = source_max_dotclock();
ds_max_dotclock = ds_max_dotclock()
if (ds_max_dotclock)
max_dotclock = min(max_dotclock, ds_max_dotclock);


>   if (type != DP_DS_PORT_TYPE_VGA)
>   return max_dotclk;
>  
> @@ -506,7 +509,8 @@ small_joiner_ram_size_bits(struct drm_i915_private *i915)
>  
>  static u16 intel_dp_dsc_get_output_bpp(struct drm_i915_private *i915,
>  u32 link_clock, u32 lane_count,
> -u32 mode_clock, u32 mode_hdisplay)
> +u32 mode_clock, u32 mode_hdisplay,
> +bool bigjoiner)
>  {
>   u32 bits_per_pixel, max_bpp_small_joiner_ram;
>   int i;
> @@ -524,6 +528,10 @@ static u16 intel_dp_dsc_get_output_bpp(struct 
> drm_i915_private *i915,
>   /* Small Joiner Check: output bpp <= joiner RAM (bits) / Horiz. width */
>   max_bpp_small_joiner_ram = small_joiner_ram_size_bits(i915) /
>   mode_hdisplay;
> +
> + if (bigjoiner)
> + max_bpp_small_joiner_ram *= 2;
> +
>   DRM_DEBUG_KMS("Max small joiner bpp: %u\n", max_bpp_small_joiner_ram);
>  
>   /*
> @@ -532,6 +540,15 @@ static u16 intel_dp_dsc_get_output_bpp(struct 
> drm_i915_private *i915,
>*/
>   bits_per_pixel = min(bits_per_pixel, max_bpp_small_joiner_ram);
>  
> + if (bigjoiner) {
> + u32 max_bpp_bigjoiner =
> + i915->max_cdclk_freq * 48 /
> + intel_dp_mode_to_fec_clock(mode_clock);
> +
> + DRM_DEBUG_KMS("Max big joiner bpp: %u\n", max_bpp_bigjoiner);
> + bits_per_pixel = min(bits_per_pixel, max_bpp_bigjoiner);
> + }
> +
>   /* Error out if the max bpp is less than smallest allowed valid bpp */
>   if (bits_per_pixel < valid_dsc_bpp[0]) {
>   DRM_DEBUG_KMS("Unsupported BPP %u, min %u\n",
> @@ -554,7 +571,8 @@ static u16 intel_dp_dsc_get_output_bpp(struct 
> drm_i915_private *i915,
>  }
>  
>  static u8 intel_dp_dsc_get_slice_count(struct intel_dp *intel_dp,
> -int mode_clock, int mode_hdisplay)
> +int mode_clock, int mode_hdisplay,
> +bool bigjoiner)
>  {
>   u8 min_slice_count, i;
>   int max_slice_width;
> @@ -579,12 +597,20 @@ static u8 intel_dp_dsc_get_slice_count(struct intel_dp 
> *intel_dp,
>  
>   /* Find the closest match to the valid slice count values */
>   for (i = 0; i < ARRAY_SIZE(valid_dsc_slicecount); i++) {
> - if (valid_dsc_slicecount[i] >
> - drm_dp_dsc_sink_max_slice_count(intel_dp->dsc_dpcd,
> - false))
> + u8 test_slice_count = bigjoiner ?
> + 2 * valid_dsc_slicecount[i] :
> + valid_dsc_slicecount[i];
> +
> + if (test_slice_count >
> + drm_dp_dsc_sink_max_slice_count(intel_dp->dsc_dpcd, false))
>   break;
> - if (min_slice_count  <= valid_dsc_slicecount[i])
> - return valid_dsc_slicecount[i];
> +
> 

[Intel-gfx] [PATCH 14/24] drm/i915/dp: Allow big joiner modes in intel_dp_mode_valid(), v2.

2019-10-04 Thread Maarten Lankhorst
Small changes to intel_dp_mode_valid(), allow listing modes that
can only be supported in the bigjoiner configuration, which is
not supported yet.

eDP does not support bigjoiner, so do not expose bigjoiner only
modes on the eDP port.

Changes since v1:
- Disallow bigjoiner on eDP.

Signed-off-by: Maarten Lankhorst 
---
 drivers/gpu/drm/i915/display/intel_dp.c | 92 +++--
 1 file changed, 72 insertions(+), 20 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp.c 
b/drivers/gpu/drm/i915/display/intel_dp.c
index 4297738655c6..5c7323af08b3 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -244,7 +244,7 @@ intel_dp_max_data_rate(int max_link_clock, int max_lanes)
 }
 
 static int
-intel_dp_downstream_max_dotclock(struct intel_dp *intel_dp)
+intel_dp_downstream_max_dotclock(struct intel_dp *intel_dp, bool 
allow_bigjoiner)
 {
struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp);
struct intel_encoder *encoder = &intel_dig_port->base;
@@ -254,6 +254,9 @@ intel_dp_downstream_max_dotclock(struct intel_dp *intel_dp)
 
int type = intel_dp->downstream_ports[0] & DP_DS_PORT_TYPE_MASK;
 
+   if (allow_bigjoiner && INTEL_GEN(dev_priv) >= 11)
+   max_dotclk *= 2;
+
if (type != DP_DS_PORT_TYPE_VGA)
return max_dotclk;
 
@@ -506,7 +509,8 @@ small_joiner_ram_size_bits(struct drm_i915_private *i915)
 
 static u16 intel_dp_dsc_get_output_bpp(struct drm_i915_private *i915,
   u32 link_clock, u32 lane_count,
-  u32 mode_clock, u32 mode_hdisplay)
+  u32 mode_clock, u32 mode_hdisplay,
+  bool bigjoiner)
 {
u32 bits_per_pixel, max_bpp_small_joiner_ram;
int i;
@@ -524,6 +528,10 @@ static u16 intel_dp_dsc_get_output_bpp(struct 
drm_i915_private *i915,
/* Small Joiner Check: output bpp <= joiner RAM (bits) / Horiz. width */
max_bpp_small_joiner_ram = small_joiner_ram_size_bits(i915) /
mode_hdisplay;
+
+   if (bigjoiner)
+   max_bpp_small_joiner_ram *= 2;
+
DRM_DEBUG_KMS("Max small joiner bpp: %u\n", max_bpp_small_joiner_ram);
 
/*
@@ -532,6 +540,15 @@ static u16 intel_dp_dsc_get_output_bpp(struct 
drm_i915_private *i915,
 */
bits_per_pixel = min(bits_per_pixel, max_bpp_small_joiner_ram);
 
+   if (bigjoiner) {
+   u32 max_bpp_bigjoiner =
+   i915->max_cdclk_freq * 48 /
+   intel_dp_mode_to_fec_clock(mode_clock);
+
+   DRM_DEBUG_KMS("Max big joiner bpp: %u\n", max_bpp_bigjoiner);
+   bits_per_pixel = min(bits_per_pixel, max_bpp_bigjoiner);
+   }
+
/* Error out if the max bpp is less than smallest allowed valid bpp */
if (bits_per_pixel < valid_dsc_bpp[0]) {
DRM_DEBUG_KMS("Unsupported BPP %u, min %u\n",
@@ -554,7 +571,8 @@ static u16 intel_dp_dsc_get_output_bpp(struct 
drm_i915_private *i915,
 }
 
 static u8 intel_dp_dsc_get_slice_count(struct intel_dp *intel_dp,
-  int mode_clock, int mode_hdisplay)
+  int mode_clock, int mode_hdisplay,
+  bool bigjoiner)
 {
u8 min_slice_count, i;
int max_slice_width;
@@ -579,12 +597,20 @@ static u8 intel_dp_dsc_get_slice_count(struct intel_dp 
*intel_dp,
 
/* Find the closest match to the valid slice count values */
for (i = 0; i < ARRAY_SIZE(valid_dsc_slicecount); i++) {
-   if (valid_dsc_slicecount[i] >
-   drm_dp_dsc_sink_max_slice_count(intel_dp->dsc_dpcd,
-   false))
+   u8 test_slice_count = bigjoiner ?
+   2 * valid_dsc_slicecount[i] :
+   valid_dsc_slicecount[i];
+
+   if (test_slice_count >
+   drm_dp_dsc_sink_max_slice_count(intel_dp->dsc_dpcd, false))
break;
-   if (min_slice_count  <= valid_dsc_slicecount[i])
-   return valid_dsc_slicecount[i];
+
+   /* big joiner needs small joiner to be enabled */
+   if (bigjoiner && test_slice_count < 4)
+   continue;
+
+   if (min_slice_count <= test_slice_count)
+   return test_slice_count;
}
 
DRM_DEBUG_KMS("Unsupported Slice Count %d\n", min_slice_count);
@@ -604,11 +630,15 @@ intel_dp_mode_valid(struct drm_connector *connector,
int max_dotclk;
u16 dsc_max_output_bpp = 0;
u8 dsc_slice_count = 0;
+   bool dsc = false, bigjoiner = false;
 
if (mode->flags & DRM_MODE_FLAG_DBLSCAN)
return MODE_NO_DBLESCAN;
 
-   max_dotclk = intel_dp_downstream_max_dotc