[PATCH 2/2] drm/i915/hdcp: Check mst_port to determine connector type

2024-05-21 Thread Suraj Kandpal
Check mst_port field in intel_connector to check connector type
rather than rely on encoder as it may not be attached to connector
at times.

--v2
-Add closes tag [Imre]

Closes: https://gitlab.freedesktop.org/drm/i915/kernel/-/issues/10898
Signed-off-by: Suraj Kandpal 
Reviewed-by: Imre Deak 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 551c862ed7a6..2edffe62f360 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -693,7 +693,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
 
*hdcp_capable = false;
*hdcp2_capable = false;
-   if (!intel_encoder_is_mst(connector->encoder))
+   if (!connector->mst_port)
return -EINVAL;
 
aux = >port->aux;
-- 
2.43.2



[PATCH 1/2] drm/i915/hdcp: Move aux assignment after connector type check

2024-05-21 Thread Suraj Kandpal
Move assignment of aux after connector type check as port may not
exist if connector is not DPMST.

--v2
-Fix unwanted change in intel_encoder check [Jani]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Imre Deak 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 92b03073acdd..551c862ed7a6 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -687,7 +687,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
bool *hdcp2_capable)
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
-   struct drm_dp_aux *aux = >port->aux;
+   struct drm_dp_aux *aux;
u8 bcaps;
int ret;
 
@@ -696,6 +696,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
if (!intel_encoder_is_mst(connector->encoder))
return -EINVAL;
 
+   aux = >port->aux;
ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
if (ret)
drm_dbg_kms(>drm,
-- 
2.43.2



[PATCH 0/2] Fixes in hdcp remote capability

2024-05-21 Thread Suraj Kandpal
This patch series aims to avoid page fault errors caused by aux
early assignment as connector may not be mst and using encoder
to check for connector type.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (2):
  drm/i915/hdcp: Move aux assignment after connector type check
  drm/i915/hdcp: Check mst_port to determine connector type

 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

-- 
2.43.2



[PATCH 2/2] drm/i915/hdcp: Check mst_port to determine connector type

2024-05-19 Thread Suraj Kandpal
Check mst_port field in intel_connector to check connector type
rather than rely on encoder as it may not be attached to connector
at times.

--v2
-Add closes tag [Imre]

Closes: https://gitlab.freedesktop.org/drm/i915/kernel/-/issues/10898
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 551c862ed7a6..2edffe62f360 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -693,7 +693,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
 
*hdcp_capable = false;
*hdcp2_capable = false;
-   if (!intel_encoder_is_mst(connector->encoder))
+   if (!connector->mst_port)
return -EINVAL;
 
aux = >port->aux;
-- 
2.43.2



[PATCH] drm/i915/pps: Disable DPLS_GATING around pps sequence

2024-05-08 Thread Suraj Kandpal
Disable bit 29 of SCLKGATE_DIS register around pps sequence
when we turn panel power on.

--v2
-Squash two commit together [Jani]
-Use IS_DISPLAY_VER [Jani]
-Fix multiline comment [Jani]

--v3
-Define register in a more appropriate place [Mitul]

Bspec: 49304
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_pps.c | 12 
 drivers/gpu/drm/i915/i915_reg.h  |  4 
 2 files changed, 16 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_pps.c 
b/drivers/gpu/drm/i915/display/intel_pps.c
index 0ccbf9a85914..d774aeb1673e 100644
--- a/drivers/gpu/drm/i915/display/intel_pps.c
+++ b/drivers/gpu/drm/i915/display/intel_pps.c
@@ -948,6 +948,14 @@ void intel_pps_on_unlocked(struct intel_dp *intel_dp)
intel_de_posting_read(dev_priv, pp_ctrl_reg);
}
 
+   /*
+* WA: 16023567976
+* Disable DPLS gating around power sequence.
+*/
+   if (IS_DISPLAY_VER(dev_priv, 12, 14))
+   intel_de_rmw(dev_priv, SCLKGATE_DIS,
+0, DPLS_GATING_DISABLE);
+
pp |= PANEL_POWER_ON;
if (!IS_IRONLAKE(dev_priv))
pp |= PANEL_POWER_RESET;
@@ -958,6 +966,10 @@ void intel_pps_on_unlocked(struct intel_dp *intel_dp)
wait_panel_on(intel_dp);
intel_dp->pps.last_power_on = jiffies;
 
+   if (IS_DISPLAY_VER(dev_priv, 12, 14))
+   intel_de_rmw(dev_priv, SCLKGATE_DIS,
+DPLS_GATING_DISABLE, 0);
+
if (IS_IRONLAKE(dev_priv)) {
pp |= PANEL_POWER_RESET; /* restore panel reset bit */
intel_de_write(dev_priv, pp_ctrl_reg, pp);
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 5670eee4a498..4cc82360298b 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -5151,6 +5151,10 @@ enum skl_power_gate {
 
 #define _MMIO_PLANE_GAMC(plane, i, a, b)  _MMIO(_PIPE(plane, a, b) + (i) * 4)
 
+/* SCLKGATE_DIS */
+#define SCLKGATE_DIS   _MMIO(0xc2020)
+#define  DPLS_GATING_DISABLE   REG_BIT(29)
+
 /* Plane CSC Registers */
 #define _PLANE_CSC_RY_GY_1_A   0x70210
 #define _PLANE_CSC_RY_GY_2_A   0x70310
-- 
2.43.2



[PATCH] drm/i915/hdcp: Disable HDCP Line Rekeying for HDCP2.2 on HDMI

2024-05-07 Thread Suraj Kandpal
Disable HDCP Line Rekeying when HDCP ver > 1.4 and when we are
on HDMI TMDS operation for DISPLAY_VER >= 14.

--v2
-Wa to be mentioned in comments not in commit message [Jani]
-Remove blankline [Jani]

--v3
-No need to write what is being done in comments when code
is self explanatory [Jani]

--v4
-Add comment regarding need of this WA when in TMDS mode
[Chaitanya]
-Write in chicken register for MTL [CHaitanya]

--v5
-Fix comment [Chaitanya]
-Use correct set and clear value in intel_de_rmw [Chaitanya]

--v6
-No need to define C, D chicken bits it gets calculated [Animesh]

Bspec: 49273
Bspec: 69964
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 23 +++
 drivers/gpu/drm/i915/i915_reg.h   |  2 ++
 2 files changed, 25 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index d5ed4c7dfbc0..02cbbbfd8e25 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,6 +30,27 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
+/* WA: 16022217614 */
+static void
+intel_hdcp_disable_hdcp_line_rekeying(struct intel_encoder *encoder,
+ struct intel_hdcp *hdcp)
+{
+   struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
+
+   /* Here we assume HDMI is in TMDS mode of operation */
+   if (encoder->type != INTEL_OUTPUT_HDMI)
+   return;
+
+   if (DISPLAY_VER(dev_priv) >= 14) {
+   if (IS_METEORLAKE(dev_priv))
+   intel_de_rmw(dev_priv, 
MTL_CHICKEN_TRANS(hdcp->cpu_transcoder),
+0, HDCP_LINE_REKEY_DISABLE);
+   else
+   intel_de_rmw(dev_priv, 
TRANS_DDI_FUNC_CTL(hdcp->cpu_transcoder),
+0, TRANS_DDI_HDCP_LINE_REKEY_DISABLE);
+   }
+}
+
 static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
@@ -2005,6 +2026,8 @@ static int _intel_hdcp2_enable(struct intel_atomic_state 
*state,
connector->base.base.id, connector->base.name,
hdcp->content_type);
 
+   intel_hdcp_disable_hdcp_line_rekeying(connector->encoder, hdcp);
+
ret = hdcp2_authenticate_and_encrypt(state, connector);
if (ret) {
drm_dbg_kms(>drm, "HDCP2 Type%d  Enabling Failed. (%d)\n",
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index ae692f461982..9f2171f0adf8 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -3520,6 +3520,7 @@
 #define   DP_FEC_BS_JITTER_WA  REG_BIT(15)
 #define   PSR2_VSC_ENABLE_PROG_HEADER  REG_BIT(12)
 #define   DP_DSC_INSERT_SF_AT_EOL_WA   REG_BIT(4)
+#define   HDCP_LINE_REKEY_DISABLE  REG_BIT(0)
 
 #define DISP_ARB_CTL   _MMIO(0x45000)
 #define   DISP_FBC_MEMORY_WAKE REG_BIT(31)
@@ -4521,6 +4522,7 @@ enum skl_power_gate {
 #define  TRANS_DDI_EDP_INPUT_B_ONOFF   (5 << 12)
 #define  TRANS_DDI_EDP_INPUT_C_ONOFF   (6 << 12)
 #define  TRANS_DDI_EDP_INPUT_D_ONOFF   (7 << 12)
+#define  TRANS_DDI_HDCP_LINE_REKEY_DISABLE REG_BIT(12)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT_MASK   REG_GENMASK(11, 10)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT(trans) \
REG_FIELD_PREP(TRANS_DDI_MST_TRANSPORT_SELECT_MASK, trans)
-- 
2.43.2



[PATCH 7/7] drm/i915/dp: Write panel override luminance values

2024-05-06 Thread Suraj Kandpal
Write panel override luminance values which helps the TCON decide
if tone mapping needs to be enabled or not.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Sebastian Wick 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 25 +++
 1 file changed, 25 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index da42f6704930..8ce60d53dcde 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -374,6 +374,29 @@ static const char *dpcd_vs_pwm_str(bool aux)
return aux ? "DPCD" : "PWM";
 }
 
+static void
+intel_dp_aux_write_panel_luminance_override(struct intel_connector *connector)
+{
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   struct intel_panel *panel = >panel;
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   int ret;
+   u8 buf[4] = {};
+
+   buf[0] = panel->backlight.min & 0xFF;
+   buf[1] = (panel->backlight.min & 0xFF00) >> 8;
+   buf[2] = panel->backlight.max & 0xFF;
+   buf[3] = (panel->backlight.max & 0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux,
+   INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE,
+   buf, sizeof(buf));
+   if (ret < 0)
+   drm_dbg_kms(>drm,
+   "Panel Luminance DPCD reg write failed, err:-%d\n",
+   ret);
+}
+
 static int
 intel_dp_aux_hdr_setup_backlight(struct intel_connector *connector, enum pipe 
pipe)
 {
@@ -405,6 +428,8 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
panel->backlight.min = 0;
}
 
+   intel_dp_aux_write_panel_luminance_override(connector);
+
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
connector->base.base.id, connector->base.name,
panel->backlight.min, panel->backlight.max);
-- 
2.43.2



[PATCH 6/7] drm/i915/dp: Enable AUX based backlight for HDR

2024-05-06 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

--v3
-Content Luminance needs to be sent only for pre-ICL after that
it is directly picked up from hdr metadata [Ville]

--v4
-Add checks for HDR TCON cap bits [Ville]
-Check eotf of hdr_output_data and sets bits base of that value.

--v5
-Fix capability check bits.
-Check colorspace before setting BT2020

--v6
-Use intel_dp_has_gamut_dip to check if we have capability
to send sdp [Ville]
-Seprate filling of all hdr tcon related bits into it's
own function.
-Check eotf data to make sure we are in HDR mode [Sebastian]

--v7
-Fix confusion function name for hdr mode check [Jani]
-Fix the condition which tells us if we are in HDR mode or not
[Sebastian]

--v8
-Call fill_hdr_tcon_param unconditionally as some parameters may not
be dependent on the fact if we are in hdr mode or not [Sebastian]
-Fix some conditions after change in hdr mode check [Sebastian]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Sebastian Wick 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 98 ---
 1 file changed, 87 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 1ee693df0563..da42f6704930 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -127,9 +122,6 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (ret != sizeof(tcon_cap))
return false;
 
-   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
-   return false;
-
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Detected %s HDR backlight 
interface version %d\n",
connector->base.base.id, connector->base.name,
is_intel_tcon_cap(tcon_cap) ? "Intel" : "unsupported", 
tcon_cap[0]);
@@ -137,6 +129,9 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (!is_intel_tcon_cap(tcon_cap))
return false;
 
+   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
+   return false;
+
/*
 * If we don't have HDR static metadata there is no way to
 * runtime detect used range for nits based control. For now
@@ -225,13 +220,27 @@ intel_dp_aux_hdr_set_aux_backlight(const struct 
drm_connector_state *conn_state,
connector->base.base.id, connector->base.name);
 }
 
+static bool
+intel_dp_in_hdr_mode(const struct drm_connector_state *conn_state)
+{
+   struct hdr_output_metadata *hdr_metadata;
+
+   if (!conn_state->hdr_output_metadata)
+   return false;
+
+   hdr_metadata = conn_state->hdr_output_metadata->data;
+
+   return hdr_metadata->hdmi_metadata_type1.eotf == HDMI_EOTF_SMPTE_ST2084;
+}
+
 static void
 intel_dp_aux_hdr_set_backlight(const struct drm_connector_state *conn_state, 
u32 level)
 {
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel_cap.sdr_uses_aux) {
+   if (intel_dp_in_hdr_mode(conn_state) ||
+   panel->backlight.edp.intel_cap.sdr_uses_aux) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -240,6 +249,64 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
}
 }
 
+static void
+intel_dp_aux_write_content_luminance(struct intel_connector *connector,
+struct hdr_output_metadata *hdr_metadata)
+{
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   int ret;
+   u8 buf[4];
+
+   if (!intel_dp_has_gamut_metadata_dip(connector->encoder))
+   return;
+
+   buf[0] = hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF;
+   buf[1] = (hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF00) >> 8;
+   buf[2] = 

[PATCH 2/7] drm/i915/dp: Rename intel struct inside intel_panel

2024-05-06 Thread Suraj Kandpal
Rename intel to intel cap which is present inside panel.edp struct
to make it more sensible to tell us what it contains.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/i915/display/intel_display_types.h |  2 +-
 .../gpu/drm/i915/display/intel_dp_aux_backlight.c  | 14 +++---
 2 files changed, 8 insertions(+), 8 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index 00eba3fbcdc6..66cc9c97fe58 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -401,7 +401,7 @@ struct intel_panel {
} vesa;
struct {
bool sdr_uses_aux;
-   } intel;
+   } intel_cap;
} edp;
 
struct backlight_device *device;
diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..44bc6fa04332 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -156,7 +156,7 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
return false;
}
 
-   panel->backlight.edp.intel.sdr_uses_aux =
+   panel->backlight.edp.intel_cap.sdr_uses_aux =
tcon_cap[2] & INTEL_EDP_SDR_TCON_BRIGHTNESS_AUX_CAP;
 
return true;
@@ -178,7 +178,7 @@ intel_dp_aux_hdr_get_backlight(struct intel_connector 
*connector, enum pipe pipe
}
 
if (!(tmp & INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE)) {
-   if (!panel->backlight.edp.intel.sdr_uses_aux) {
+   if (!panel->backlight.edp.intel_cap.sdr_uses_aux) {
u32 pwm_level = 
panel->backlight.pwm_funcs->get(connector, pipe);
 
return intel_backlight_level_from_pwm(connector, 
pwm_level);
@@ -221,7 +221,7 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel_cap.sdr_uses_aux) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -251,7 +251,7 @@ intel_dp_aux_hdr_enable_backlight(const struct 
intel_crtc_state *crtc_state,
}
 
ctrl = old_ctrl;
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel_cap.sdr_uses_aux) {
ctrl |= INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE;
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
@@ -275,7 +275,7 @@ intel_dp_aux_hdr_disable_backlight(const struct 
drm_connector_state *conn_state,
struct intel_panel *panel = >panel;
 
/* Nothing to do for AUX based backlight controls */
-   if (panel->backlight.edp.intel.sdr_uses_aux)
+   if (panel->backlight.edp.intel_cap.sdr_uses_aux)
return;
 
/* Note we want the actual pwm_level to be 0, regardless of pwm_min */
@@ -298,9 +298,9 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
 
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] SDR backlight is controlled 
through %s\n",
connector->base.base.id, connector->base.name,
-   dpcd_vs_pwm_str(panel->backlight.edp.intel.sdr_uses_aux));
+   
dpcd_vs_pwm_str(panel->backlight.edp.intel_cap.sdr_uses_aux));
 
-   if (!panel->backlight.edp.intel.sdr_uses_aux) {
+   if (!panel->backlight.edp.intel_cap.sdr_uses_aux) {
ret = panel->backlight.pwm_funcs->setup(connector, pipe);
if (ret < 0) {
drm_err(>drm,
-- 
2.43.2



[PATCH 5/7] drm/i915/dp: Drop comments on EDP HDR DPCD registers

2024-05-06 Thread Suraj Kandpal
Drop comments for EDP HDR DPCD registers as the code and
conditions will tell us what can be written where.

--v2
-Drop the comments altogether instead of just renaming them
[Sebastian]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 85205aeb3e9a..1ee693df0563 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -69,14 +69,14 @@
 #define INTEL_EDP_HDR_GETSET_CTRL_PARAMS   0x344
 # define INTEL_EDP_HDR_TCON_2084_DECODE_ENABLEBIT(0)
 # define INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE BIT(1)
-# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2) 
/* Pre-TGL+ */
+# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2)
 # define INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLEBIT(3)
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
 # define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
-#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
+#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
 #define INTEL_EDP_SDR_LUMINANCE_LEVEL  0x352
 #define INTEL_EDP_BRIGHTNESS_NITS_LSB  0x354
-- 
2.43.2



[PATCH 4/7] drm/i915/dp: Fix Register bit naming

2024-05-06 Thread Suraj Kandpal
Change INTEL_EDP_HDR_TCON_SDP_COLORIMETRY enable to
INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX as this bit tells TCON to
ignore DPCD colorimetry values and take the one's sent through
SDP.

--v2
-Fix typo in commit message [Arun]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 63d99afba398..85205aeb3e9a 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -74,7 +74,7 @@
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
-# define INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_ENABLEBIT(7)
+# define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
 #define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
-- 
2.43.2



[PATCH 3/7] drm/i915/dp: Add TCON HDR capability checks

2024-05-06 Thread Suraj Kandpal
Add checks to see the HDR capability of TCON panel.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/i915/display/intel_display_types.h|  5 +
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 10 ++
 2 files changed, 15 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index 66cc9c97fe58..da0d003102e4 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -401,6 +401,11 @@ struct intel_panel {
} vesa;
struct {
bool sdr_uses_aux;
+   bool supports_2084_decode;
+   bool supports_2020_gamut;
+   bool supports_segmented_backlight;
+   bool supports_sdp_colorimetry;
+   bool supports_tone_mapping;
} intel_cap;
} edp;
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 44bc6fa04332..63d99afba398 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -158,6 +158,16 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
 
panel->backlight.edp.intel_cap.sdr_uses_aux =
tcon_cap[2] & INTEL_EDP_SDR_TCON_BRIGHTNESS_AUX_CAP;
+   panel->backlight.edp.intel_cap.supports_2084_decode =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2084_DECODE_CAP;
+   panel->backlight.edp.intel_cap.supports_2020_gamut =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2020_GAMUT_CAP;
+   panel->backlight.edp.intel_cap.supports_segmented_backlight =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_CAP;
+   panel->backlight.edp.intel_cap.supports_sdp_colorimetry =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_CAP;
+   panel->backlight.edp.intel_cap.supports_tone_mapping =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_TONE_MAPPING_CAP;
 
return true;
 }
-- 
2.43.2



[PATCH 0/7] Enable Aux Based EDP HDR

2024-05-06 Thread Suraj Kandpal
This series enables Aux based EDP HDR and backlight controls.
The DPCD written to are intel proprietary and are filled
based on the specs that were provided to TCON vendors.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (7):
  drm/i915/dp: Make has_gamut_metadata_dip() non static
  drm/i915/dp: Rename intel struct inside intel_panel
  drm/i915/dp: Add TCON HDR capability checks
  drm/i915/dp: Fix Register bit naming
  drm/i915/dp: Drop comments on EDP HDR DPCD registers
  drm/i915/dp: Enable AUX based backlight for HDR
  drm/i915/dp: Write panel override luminance values

 .../drm/i915/display/intel_display_types.h|   7 +-
 drivers/gpu/drm/i915/display/intel_dp.c   |   6 +-
 drivers/gpu/drm/i915/display/intel_dp.h   |   1 +
 .../drm/i915/display/intel_dp_aux_backlight.c | 149 +++---
 4 files changed, 140 insertions(+), 23 deletions(-)

-- 
2.43.2



[PATCH 1/7] drm/i915/dp: Make has_gamut_metadata_dip() non static

2024-05-06 Thread Suraj Kandpal
Make has_gamut_metadata_dip() non static so it can also be used to
at other places eg in intel_dp_aux_backlight. So that we can check
if HW is capable of sending SDP which helps us decide if we use
AUX based HDR control or via SDP.

--v2
-State reason the function is needed [Arun]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/i915/display/intel_dp.c | 6 +++---
 drivers/gpu/drm/i915/display/intel_dp.h | 1 +
 2 files changed, 4 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp.c 
b/drivers/gpu/drm/i915/display/intel_dp.c
index 486361eb0070..6b8a94d0ca99 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -6364,8 +6364,8 @@ bool intel_dp_is_port_edp(struct drm_i915_private *i915, 
enum port port)
return _intel_dp_is_port_edp(i915, devdata, port);
 }
 
-static bool
-has_gamut_metadata_dip(struct intel_encoder *encoder)
+bool
+intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder)
 {
struct drm_i915_private *i915 = to_i915(encoder->base.dev);
enum port port = encoder->port;
@@ -6412,7 +6412,7 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct 
drm_connector *connect
intel_attach_dp_colorspace_property(connector);
}
 
-   if (has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
+   if (intel_dp_has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
drm_connector_attach_hdr_output_metadata_property(connector);
 
if (HAS_VRR(dev_priv))
diff --git a/drivers/gpu/drm/i915/display/intel_dp.h 
b/drivers/gpu/drm/i915/display/intel_dp.h
index 106ecfde36d9..aad2223df2a3 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.h
+++ b/drivers/gpu/drm/i915/display/intel_dp.h
@@ -196,5 +196,6 @@ intel_dp_compute_config_link_bpp_limits(struct intel_dp 
*intel_dp,
struct link_config_limits *limits);
 
 void intel_dp_get_dsc_sink_cap(u8 dpcd_rev, struct intel_connector *connector);
+bool intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder);
 
 #endif /* __INTEL_DP_H__ */
-- 
2.43.2



[PATCH 0/2] Fixes in hdcp remote capability

2024-05-06 Thread Suraj Kandpal
This patch series aims to avoid page fault errors caused by aux
early assignment as connector may not be mst and using encoder
to check for connector type.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (2):
  drm/i915/hdcp: Move aux assignment after connector type check
  drm/i915/hdcp: Check mst_port to determine connector type

 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

-- 
2.43.2



[PATCH 2/2] drm/i915/hdcp: Check mst_port to determine connector type

2024-05-06 Thread Suraj Kandpal
Check mst_port field in intel_connector to check connector type
rather than rely on encoder as it may not be attached to connector
at times.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 551c862ed7a6..2edffe62f360 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -693,7 +693,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
 
*hdcp_capable = false;
*hdcp2_capable = false;
-   if (!intel_encoder_is_mst(connector->encoder))
+   if (!connector->mst_port)
return -EINVAL;
 
aux = >port->aux;
-- 
2.43.2



[PATCH 1/2] drm/i915/hdcp: Move aux assignment after connector type check

2024-05-06 Thread Suraj Kandpal
Move assignment of aux after connector type check as port may not
exist if connector is not DPMST.

--v2
-Fix unwanted change in intel_encoder check [Jani]

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 92b03073acdd..551c862ed7a6 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -687,7 +687,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
bool *hdcp2_capable)
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
-   struct drm_dp_aux *aux = >port->aux;
+   struct drm_dp_aux *aux;
u8 bcaps;
int ret;
 
@@ -696,6 +696,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
if (!intel_encoder_is_mst(connector->encoder))
return -EINVAL;
 
+   aux = >port->aux;
ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
if (ret)
drm_dbg_kms(>drm,
-- 
2.43.2



[PATCH] drm/i915/hdcp: Disable HDCP Line Rekeying for HDCP2.2 on HDMI

2024-05-01 Thread Suraj Kandpal
Disable HDCP Line Rekeying when HDCP ver > 1.4 and when we are
on HDMI TMDS operation for DISPLAY_VER >= 14.

--v2
-Wa to be mentioned in comments not in commit message [Jani]
-Remove blankline [Jani]

--v3
-No need to write what is being done in comments when code
is self explanatory [Jani]

--v4
-Add comment regarding need of this WA when in TMDS mode
[Chaitanya]
-Write in chicken register for MTL [CHaitanya]

--v5
-Fix comment [Chaitanya]
-Use correct set and clear value in intel_de_rmw [Chaitanya]

Bspec: 49273
Bspec: 69964
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 23 +++
 drivers/gpu/drm/i915/i915_reg.h   |  4 
 2 files changed, 27 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index d5ed4c7dfbc0..02cbbbfd8e25 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,6 +30,27 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
+/* WA: 16022217614 */
+static void
+intel_hdcp_disable_hdcp_line_rekeying(struct intel_encoder *encoder,
+ struct intel_hdcp *hdcp)
+{
+   struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
+
+   /* Here we assume HDMI is in TMDS mode of operation */
+   if (encoder->type != INTEL_OUTPUT_HDMI)
+   return;
+
+   if (DISPLAY_VER(dev_priv) >= 14) {
+   if (IS_METEORLAKE(dev_priv))
+   intel_de_rmw(dev_priv, 
MTL_CHICKEN_TRANS(hdcp->cpu_transcoder),
+0, HDCP_LINE_REKEY_DISABLE);
+   else
+   intel_de_rmw(dev_priv, 
TRANS_DDI_FUNC_CTL(hdcp->cpu_transcoder),
+0, TRANS_DDI_HDCP_LINE_REKEY_DISABLE);
+   }
+}
+
 static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
@@ -2005,6 +2026,8 @@ static int _intel_hdcp2_enable(struct intel_atomic_state 
*state,
connector->base.base.id, connector->base.name,
hdcp->content_type);
 
+   intel_hdcp_disable_hdcp_line_rekeying(connector->encoder, hdcp);
+
ret = hdcp2_authenticate_and_encrypt(state, connector);
if (ret) {
drm_dbg_kms(>drm, "HDCP2 Type%d  Enabling Failed. (%d)\n",
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index e22a82a5ddd7..31338d825e34 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -3501,6 +3501,8 @@
[TRANSCODER_D] = _CHICKEN_TRANS_D))
 #define _MTL_CHICKEN_TRANS_A   0x604e0
 #define _MTL_CHICKEN_TRANS_B   0x614e0
+#define _MTL_CHICKEN_TRANS_C   0x624e0
+#define _MTL_CHICKEN_TRANS_D   0x634e0
 #define MTL_CHICKEN_TRANS(trans)   _MMIO_TRANS((trans), \
_MTL_CHICKEN_TRANS_A, \
_MTL_CHICKEN_TRANS_B)
@@ -3519,6 +3521,7 @@
 #define   DP_FEC_BS_JITTER_WA  REG_BIT(15)
 #define   PSR2_VSC_ENABLE_PROG_HEADER  REG_BIT(12)
 #define   DP_DSC_INSERT_SF_AT_EOL_WA   REG_BIT(4)
+#define   HDCP_LINE_REKEY_DISABLE  REG_BIT(0)
 
 #define DISP_ARB_CTL   _MMIO(0x45000)
 #define   DISP_FBC_MEMORY_WAKE REG_BIT(31)
@@ -4520,6 +4523,7 @@ enum skl_power_gate {
 #define  TRANS_DDI_EDP_INPUT_B_ONOFF   (5 << 12)
 #define  TRANS_DDI_EDP_INPUT_C_ONOFF   (6 << 12)
 #define  TRANS_DDI_EDP_INPUT_D_ONOFF   (7 << 12)
+#define  TRANS_DDI_HDCP_LINE_REKEY_DISABLE REG_BIT(12)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT_MASK   REG_GENMASK(11, 10)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT(trans) \
REG_FIELD_PREP(TRANS_DDI_MST_TRANSPORT_SELECT_MASK, trans)
-- 
2.43.2



[PATCH 2/2] drm/i915/hdcp: Check mst_port to determine connector type

2024-04-30 Thread Suraj Kandpal
Check mst_port field in intel_connector to check connector type
rather than rely on encoder as it may not be attached to connector
at times.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 92be53d7c81f..2edffe62f360 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -693,7 +693,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
 
*hdcp_capable = false;
*hdcp2_capable = false;
-   if (intel_encoder_is_mst(connector->encoder))
+   if (!connector->mst_port)
return -EINVAL;
 
aux = >port->aux;
-- 
2.43.2



[PATCH 1/2] drm/i915/hdcp: Move aux assignment after connector type check

2024-04-30 Thread Suraj Kandpal
Move assignment of aux after connector type check as port may not
exist if connector is not DPMST.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 92b03073acdd..92be53d7c81f 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -687,15 +687,16 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
bool *hdcp2_capable)
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
-   struct drm_dp_aux *aux = >port->aux;
+   struct drm_dp_aux *aux;
u8 bcaps;
int ret;
 
*hdcp_capable = false;
*hdcp2_capable = false;
-   if (!intel_encoder_is_mst(connector->encoder))
+   if (intel_encoder_is_mst(connector->encoder))
return -EINVAL;
 
+   aux = >port->aux;
ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
if (ret)
drm_dbg_kms(>drm,
-- 
2.43.2



[PATCH 0/2] Fixes in hdcp remote capability

2024-04-30 Thread Suraj Kandpal
This patch series aims to avoid page fault errors caused by aux
early assignment as connector may not be mst and using encoder
to check for connector type.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (2):
  drm/i915/hdcp: Move aux assignment after connector type check
  drm/i915/hdcp: Check mst_port to determine connector type

 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

-- 
2.43.2



[RFC 3/3] drm/i915: Schedule darkscreen detection work

2024-04-24 Thread Suraj Kandpal
Schedule darkscreen detection work whenever we hit FIFO
underrun.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_fifo_underrun.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_fifo_underrun.c 
b/drivers/gpu/drm/i915/display/intel_fifo_underrun.c
index 09a7fa6c0c37..a6acd086d924 100644
--- a/drivers/gpu/drm/i915/display/intel_fifo_underrun.c
+++ b/drivers/gpu/drm/i915/display/intel_fifo_underrun.c
@@ -27,6 +27,7 @@
 
 #include "i915_drv.h"
 #include "i915_reg.h"
+#include "intel_darkscreen.h"
 #include "intel_de.h"
 #include "intel_display_irq.h"
 #include "intel_display_trace.h"
@@ -438,6 +439,7 @@ void intel_cpu_fifo_underrun_irq_handler(struct 
drm_i915_private *dev_priv,
}
 
intel_fbc_handle_fifo_underrun_irq(dev_priv);
+   intel_darkscreen_schedule_work(crtc);
 }
 
 /**
-- 
2.43.2



[RFC 2/3] drm/i915/darkscreen: Enable darkscreen detection

2024-04-24 Thread Suraj Kandpal
Add functions to enable darkscreen detection and corresponding
additions to Makefile to build them.
The enable and detect functions will be used in case we encounter
a FIFO underrun which will help to check if a darkscreen occurred.

Signed-off-by: Suraj Kandpal 
Signed-off-by: Nemesa Garg 
---
 drivers/gpu/drm/i915/Makefile |   1 +
 .../gpu/drm/i915/display/intel_darkscreen.c   | 139 ++
 .../gpu/drm/i915/display/intel_darkscreen.h   |  25 
 .../drm/i915/display/intel_display_types.h|   3 +
 drivers/gpu/drm/xe/Makefile   |   1 +
 5 files changed, 169 insertions(+)
 create mode 100644 drivers/gpu/drm/i915/display/intel_darkscreen.c
 create mode 100644 drivers/gpu/drm/i915/display/intel_darkscreen.h

diff --git a/drivers/gpu/drm/i915/Makefile b/drivers/gpu/drm/i915/Makefile
index 7cad944b825c..00e36169a74d 100644
--- a/drivers/gpu/drm/i915/Makefile
+++ b/drivers/gpu/drm/i915/Makefile
@@ -255,6 +255,7 @@ i915-y += \
display/intel_crtc.o \
display/intel_crtc_state_dump.o \
display/intel_cursor.o \
+   display/intel_darkscreen.o \
display/intel_display.o \
display/intel_display_driver.o \
display/intel_display_irq.o \
diff --git a/drivers/gpu/drm/i915/display/intel_darkscreen.c 
b/drivers/gpu/drm/i915/display/intel_darkscreen.c
new file mode 100644
index ..3ac3e8e6c1e3
--- /dev/null
+++ b/drivers/gpu/drm/i915/display/intel_darkscreen.c
@@ -0,0 +1,139 @@
+// SPDX-License-Identifier: MIT
+/*
+ * Copyright © 2023 Intel Corporation
+ */
+
+#include "i915_reg.h"
+#include "intel_de.h"
+#include "intel_display_types.h"
+
+#define COLOR_DEPTH_6BPC 6
+#define COLOR_DEPTH_8BPC 8
+#define COLOR_DEPTH_10BPC 10
+#define COLOR_DEPTH_12BPC 12
+
+#define COMPARE_VALUE_6_BPC 4
+#define COMPARE_VALUE_8_BPC 16
+#define COMPARE_VALUE_10_BPC 64
+#define COMPARE_VALUE_12_BPC 256
+
+#define COMPARE_VALUE_CALCULATION_FACTOR 12
+
+static void intel_darkscreen_detect(struct intel_crtc *crtc);
+
+static u32 intel_darkscreen_get_comp_val(struct drm_i915_private *i915, int 
bpc)
+{
+   u32 compare_value = 0;
+
+   switch (bpc) {
+   case COLOR_DEPTH_6BPC:
+   compare_value = COMPARE_VALUE_6_BPC;
+   break;
+   case COLOR_DEPTH_8BPC:
+   compare_value = COMPARE_VALUE_8_BPC;
+   break;
+   case COLOR_DEPTH_10BPC:
+   compare_value = COMPARE_VALUE_10_BPC;
+   break;
+   case COLOR_DEPTH_12BPC:
+   compare_value = COMPARE_VALUE_12_BPC;
+   break;
+   default:
+   drm_dbg(>drm, "Bpc value is incorrect:%d\n", bpc);
+   return -EINVAL;
+   }
+
+   compare_value = compare_value << (COMPARE_VALUE_CALCULATION_FACTOR - 
bpc);
+   return DARK_SCREEN_COMPARE_VAL(compare_value);
+}
+
+static void intel_darkscreen_work_fn(struct work_struct *work)
+{
+   struct intel_darkscreen *dark_screen =
+   container_of(work, typeof(*dark_screen), 
darkscreen_detect_work);
+
+   if (!dark_screen->enable)
+   intel_darkscreen_enable(dark_screen->crtc);
+
+   intel_darkscreen_detect(dark_screen->crtc);
+}
+
+void intel_darkscreen_schedule_work(struct intel_crtc *crtc)
+{
+   struct drm_i915_private *i915 = to_i915(crtc->base.dev);
+   struct intel_darkscreen *dark_screen = >dark_screen;
+
+   dark_screen->crtc = crtc;
+   queue_work(i915->unordered_wq, _screen->darkscreen_detect_work);
+}
+
+void intel_darkscreen_setup(struct intel_crtc *crtc)
+{
+   struct intel_darkscreen *dark_screen;
+
+   dark_screen = >dark_screen;
+   dark_screen = kzalloc(sizeof(*dark_screen), GFP_KERNEL);
+   if (!dark_screen)
+   return;
+   dark_screen->enable = false;
+
+   INIT_WORK(_screen->darkscreen_detect_work, 
intel_darkscreen_work_fn);
+}
+
+/*
+ * Check the color format and compute the compare value based on bpc.
+ */
+int intel_darkscreen_enable(struct intel_crtc *crtc)
+{
+   struct intel_crtc_state *crtc_state = crtc->config;
+   enum transcoder cpu_transcoder = crtc_state->cpu_transcoder;
+   struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
+   int bpc = crtc_state->pipe_bpp / 3;
+   u32 val;
+
+   if (!crtc->dark_screen.enable)
+   return 0;
+
+   if (crtc_state->output_format != INTEL_OUTPUT_FORMAT_RGB) {
+   drm_dbg_kms(_priv->drm,
+   "YUV format not supported:%c for darkscreen 
detection\n",
+   pipe_name(crtc->pipe));
+   return -EPROTO;
+   }
+
+   val = intel_darkscreen_get_comp_val(dev_priv, bpc);
+   val |= DARK_SCREEN_ENABLE;
+   intel_de_write(dev_priv, DARK_SCREEN(cpu_transcoder), val);
+   crtc->dark_screen.enable = true;
+
+   retu

[RFC 1/3] drm/i915: Add Dark screen detection registers

2024-04-24 Thread Suraj Kandpal
Add Dark screen detection related register and field definitions.

Signed-off-by: Suraj Kandpal 
Signed-off-by: Nemesa Garg 
---
 drivers/gpu/drm/i915/i915_reg.h | 8 
 1 file changed, 8 insertions(+)

diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 8eb6c2bf4557..474b1c263517 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -1838,6 +1838,14 @@
 #define VRR_VSYNC_START_MASK   REG_GENMASK(12, 0)
 #define VRR_VSYNC_START(vsync_start)   REG_FIELD_PREP(VRR_VSYNC_START_MASK, 
(vsync_start))
 
+#define _DARK_SCREEN_PIPE_A0x60120
+#define DARK_SCREEN(trans) _MMIO_TRANS2(trans, _DARK_SCREEN_PIPE_A)
+#define   DARK_SCREEN_ENABLE   REG_BIT(31)
+#define   DARK_SCREEN_DETECT   REG_BIT(29)
+#define   DARK_SCREEN_DONE REG_BIT(28)
+#define DARK_SCREEN_COMPARE_MASK   REG_GENMASK(9, 0)
+#define DARK_SCREEN_COMPARE_VAL(x) 
REG_FIELD_PREP(DARK_SCREEN_COMPARE_MASK, (x))
+
 /* VGA port control */
 #define ADPA   _MMIO(0x61100)
 #define PCH_ADPA_MMIO(0xe1100)
-- 
2.43.2



[RFC 0/3] Enable darkscreen detection

2024-04-24 Thread Suraj Kandpal
Fifo underrun can lead to flicker, screen corruption and blank screen in
case of pipe hang.
This patch series aims to enable dark screen detection whenever
FIFO underruns are hit and in case we face a darkscreen at this point
instead of disabling irq and fbc we want to try reset the pipe on which
the underrun has occured and keep a track on the number of times
underrun occurs post reset and if this persists more than 5 times we go
ahead and reset the whole display. If this still persists we then
fallback to disabling irq and the fb.
To summarize we are using the dark screen detction feature to detect the
pipe hung scenario of FIFO underrun. After detection as corrective
measurements following is done.
1)pipe reset
2)display reset
Comments on this design and ideas on how else this can be implemented
or diffrent scenarios dark screen detection can be used are also
welcome.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (3):
  drm/i915: Add Dark screen detection registers
  drm/i915/darkscreen: Enable darkscreen detection
  drm/i915: Schedule darkscreen detection work

 drivers/gpu/drm/i915/Makefile |   1 +
 .../gpu/drm/i915/display/intel_darkscreen.c   | 139 ++
 .../gpu/drm/i915/display/intel_darkscreen.h   |  25 
 .../drm/i915/display/intel_display_types.h|   3 +
 .../drm/i915/display/intel_fifo_underrun.c|   2 +
 drivers/gpu/drm/i915/i915_reg.h   |   8 +
 drivers/gpu/drm/xe/Makefile   |   1 +
 7 files changed, 179 insertions(+)
 create mode 100644 drivers/gpu/drm/i915/display/intel_darkscreen.c
 create mode 100644 drivers/gpu/drm/i915/display/intel_darkscreen.h

-- 
2.43.2



[PATCH] drm/i915/hdcp: Disable HDCP Line Rekeying for HDCP2.2 on HDMI

2024-04-23 Thread Suraj Kandpal
Disable HDCP Line Rekeying when HDCP ver > 1.4 and when we are
on HDMI TMDS operation for DISPLAY_VER >= 14.

--v2
-Wa to be mentioned in comments not in commit message [Jani]
-Remove blankline [Jani]

--v3
-No need to write what is being done in comments when code
is self explanatory [Jani]

--v4
-Add comment regarding need of this WA when in TMDS mode
[Chaitanya]
-Write in chicken register for MTL [CHaitanya]

Bspec: 49273
Bspec: 69964
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 26 +++
 drivers/gpu/drm/i915/i915_reg.h   |  4 
 2 files changed, 30 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index d5ed4c7dfbc0..0d8ae6962d34 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,6 +30,30 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
+/*
+ * WA: 16022217614
+ * Disable HDCP line rekeying if we are using HDMI and in
+ * TMDS mode.
+ */
+static void
+intel_hdcp_disable_hdcp_line_rekeying(struct intel_encoder *encoder,
+ struct intel_hdcp *hdcp)
+{
+   struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
+
+   if (encoder->type != INTEL_OUTPUT_HDMI)
+   return;
+
+   if (DISPLAY_VER(dev_priv) >= 14) {
+   if (IS_METEORLAKE(dev_priv))
+   intel_de_rmw(dev_priv, 
MTL_CHICKEN_TRANS(hdcp->cpu_transcoder),
+HDCP_LINE_REKEY_DISABLE, 1);
+   else
+   intel_de_rmw(dev_priv, 
TRANS_DDI_FUNC_CTL(hdcp->cpu_transcoder),
+TRANS_DDI_HDCP_LINE_REKEY_DISABLE, 1);
+   }
+}
+
 static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
@@ -2005,6 +2029,8 @@ static int _intel_hdcp2_enable(struct intel_atomic_state 
*state,
connector->base.base.id, connector->base.name,
hdcp->content_type);
 
+   intel_hdcp_disable_hdcp_line_rekeying(connector->encoder, hdcp);
+
ret = hdcp2_authenticate_and_encrypt(state, connector);
if (ret) {
drm_dbg_kms(>drm, "HDCP2 Type%d  Enabling Failed. (%d)\n",
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 3f34efcd7d6c..39b1a2d516fe 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -4613,6 +4613,8 @@
[TRANSCODER_D] = _CHICKEN_TRANS_D))
 #define _MTL_CHICKEN_TRANS_A   0x604e0
 #define _MTL_CHICKEN_TRANS_B   0x614e0
+#define _MTL_CHICKEN_TRANS_C   0x624e0
+#define _MTL_CHICKEN_TRANS_D   0x634e0
 #define MTL_CHICKEN_TRANS(trans)   _MMIO_TRANS((trans), \
_MTL_CHICKEN_TRANS_A, \
_MTL_CHICKEN_TRANS_B)
@@ -4631,6 +4633,7 @@
 #define   DP_FEC_BS_JITTER_WA  REG_BIT(15)
 #define   PSR2_VSC_ENABLE_PROG_HEADER  REG_BIT(12)
 #define   DP_DSC_INSERT_SF_AT_EOL_WA   REG_BIT(4)
+#define   HDCP_LINE_REKEY_DISABLE  REG_BIT(0)
 
 #define DISP_ARB_CTL   _MMIO(0x45000)
 #define   DISP_FBC_MEMORY_WAKE REG_BIT(31)
@@ -5630,6 +5633,7 @@ enum skl_power_gate {
 #define  TRANS_DDI_EDP_INPUT_B_ONOFF   (5 << 12)
 #define  TRANS_DDI_EDP_INPUT_C_ONOFF   (6 << 12)
 #define  TRANS_DDI_EDP_INPUT_D_ONOFF   (7 << 12)
+#define  TRANS_DDI_HDCP_LINE_REKEY_DISABLE REG_BIT(12)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT_MASK   REG_GENMASK(11, 10)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT(trans) \
REG_FIELD_PREP(TRANS_DDI_MST_TRANSPORT_SELECT_MASK, trans)
-- 
2.43.2



[PATCH 6/6] drm/i915/dp: Write panel override luminance values

2024-04-21 Thread Suraj Kandpal
Write panel override luminance values which helps the TCON decide
if tone mapping needs to be enabled or not.

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 25 +++
 1 file changed, 25 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index e23694257ea5..9e885eb40805 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -374,6 +374,29 @@ static const char *dpcd_vs_pwm_str(bool aux)
return aux ? "DPCD" : "PWM";
 }
 
+static void
+intel_dp_aux_write_panel_luminance_override(struct intel_connector *connector)
+{
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   struct intel_panel *panel = >panel;
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   int ret;
+   u8 buf[4] = {};
+
+   buf[0] = panel->backlight.min & 0xFF;
+   buf[1] = (panel->backlight.min & 0xFF00) >> 8;
+   buf[2] = panel->backlight.max & 0xFF;
+   buf[3] = (panel->backlight.max & 0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux,
+   INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE,
+   buf, sizeof(buf));
+   if (ret < 0)
+   drm_dbg_kms(>drm,
+   "Panel Luminance DPCD reg write failed, err:-%d\n",
+   ret);
+}
+
 static int
 intel_dp_aux_hdr_setup_backlight(struct intel_connector *connector, enum pipe 
pipe)
 {
@@ -405,6 +428,8 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
panel->backlight.min = 0;
}
 
+   intel_dp_aux_write_panel_luminance_override(connector);
+
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
connector->base.base.id, connector->base.name,
panel->backlight.min, panel->backlight.max);
-- 
2.43.2



[PATCH 4/6] drm/i915/dp: Drop comments on EDP HDR DPCD registers

2024-04-21 Thread Suraj Kandpal
Drop comments for EDP HDR DPCD registers as the code and
conditions will tell us what can be written where.

--v2
-Drop the comments altogether instead of just renaming them
[Sebastian]

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 3d9723714c96..b61bad218994 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -69,14 +69,14 @@
 #define INTEL_EDP_HDR_GETSET_CTRL_PARAMS   0x344
 # define INTEL_EDP_HDR_TCON_2084_DECODE_ENABLEBIT(0)
 # define INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE BIT(1)
-# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2) 
/* Pre-TGL+ */
+# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2)
 # define INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLEBIT(3)
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
 # define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
-#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
+#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
 #define INTEL_EDP_SDR_LUMINANCE_LEVEL  0x352
 #define INTEL_EDP_BRIGHTNESS_NITS_LSB  0x354
-- 
2.43.2



[PATCH 5/6] drm/i915/dp: Enable AUX based backlight for HDR

2024-04-21 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

--v3
-Content Luminance needs to be sent only for pre-ICL after that
it is directly picked up from hdr metadata [Ville]

--v4
-Add checks for HDR TCON cap bits [Ville]
-Check eotf of hdr_output_data and sets bits base of that value.

--v5
-Fix capability check bits.
-Check colorspace before setting BT2020

--v6
-Use intel_dp_has_gamut_dip to check if we have capability
to send sdp [Ville]
-Seprate filling of all hdr tcon related bits into it's
own function.
-Check eotf data to make sure we are in HDR mode [Sebastian]

--v7
-Fix confusion function name for hdr mode check [Jani]
-Fix the condition which tells us if we are in HDR mode or not
[Sebastian]

--v8
-Call fill_hdr_tcon_param unconditionally as some parameters may not
be dependent on the fact if we are in hdr mode or not [Sebastian]
-Fix some conditions after change in hdr mode check [Sebastian]

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 98 ---
 1 file changed, 87 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index b61bad218994..e23694257ea5 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -127,9 +122,6 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (ret != sizeof(tcon_cap))
return false;
 
-   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
-   return false;
-
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Detected %s HDR backlight 
interface version %d\n",
connector->base.base.id, connector->base.name,
is_intel_tcon_cap(tcon_cap) ? "Intel" : "unsupported", 
tcon_cap[0]);
@@ -137,6 +129,9 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (!is_intel_tcon_cap(tcon_cap))
return false;
 
+   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
+   return false;
+
/*
 * If we don't have HDR static metadata there is no way to
 * runtime detect used range for nits based control. For now
@@ -225,13 +220,27 @@ intel_dp_aux_hdr_set_aux_backlight(const struct 
drm_connector_state *conn_state,
connector->base.base.id, connector->base.name);
 }
 
+static bool
+intel_dp_in_hdr_mode(const struct drm_connector_state *conn_state)
+{
+   struct hdr_output_metadata *hdr_metadata;
+
+   if (!conn_state->hdr_output_metadata)
+   return false;
+
+   hdr_metadata = conn_state->hdr_output_metadata->data;
+
+   return hdr_metadata->hdmi_metadata_type1.eotf == HDMI_EOTF_SMPTE_ST2084;
+}
+
 static void
 intel_dp_aux_hdr_set_backlight(const struct drm_connector_state *conn_state, 
u32 level)
 {
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (intel_dp_in_hdr_mode(conn_state) ||
+   panel->backlight.edp.intel.sdr_uses_aux) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -240,6 +249,64 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
}
 }
 
+static void
+intel_dp_aux_write_content_luminance(struct intel_connector *connector,
+struct hdr_output_metadata *hdr_metadata)
+{
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   int ret;
+   u8 buf[4];
+
+   if (!intel_dp_has_gamut_metadata_dip(connector->encoder))
+   return;
+
+   buf[0] = hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF;
+   buf[1] = (hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF00) >> 8;
+   buf[2] = hdr_metadata->hdmi_metadata_type1.max_fal

[PATCH 1/6] drm/i915/dp: Make has_gamut_metadata_dip() non static

2024-04-21 Thread Suraj Kandpal
Make has_gamut_metadata_dip() non static so it can also be used to
at other places eg in intel_dp_aux_backlight. So that we can check
if HW is capable of sending SDP which helps us decide if we use
AUX based HDR control or via SDP.

--v2
-State reason the function is needed [Arun]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/i915/display/intel_dp.c | 6 +++---
 drivers/gpu/drm/i915/display/intel_dp.h | 1 +
 2 files changed, 4 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp.c 
b/drivers/gpu/drm/i915/display/intel_dp.c
index 163da48bc406..8b105efd4de9 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -6365,8 +6365,8 @@ bool intel_dp_is_port_edp(struct drm_i915_private *i915, 
enum port port)
return _intel_dp_is_port_edp(i915, devdata, port);
 }
 
-static bool
-has_gamut_metadata_dip(struct intel_encoder *encoder)
+bool
+intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder)
 {
struct drm_i915_private *i915 = to_i915(encoder->base.dev);
enum port port = encoder->port;
@@ -6413,7 +6413,7 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct 
drm_connector *connect
intel_attach_dp_colorspace_property(connector);
}
 
-   if (has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
+   if (intel_dp_has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
drm_connector_attach_hdr_output_metadata_property(connector);
 
if (HAS_VRR(dev_priv))
diff --git a/drivers/gpu/drm/i915/display/intel_dp.h 
b/drivers/gpu/drm/i915/display/intel_dp.h
index 106ecfde36d9..aad2223df2a3 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.h
+++ b/drivers/gpu/drm/i915/display/intel_dp.h
@@ -196,5 +196,6 @@ intel_dp_compute_config_link_bpp_limits(struct intel_dp 
*intel_dp,
struct link_config_limits *limits);
 
 void intel_dp_get_dsc_sink_cap(u8 dpcd_rev, struct intel_connector *connector);
+bool intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder);
 
 #endif /* __INTEL_DP_H__ */
-- 
2.43.2



[PATCH 2/6] drm/i915/dp: Add TCON HDR capability checks

2024-04-21 Thread Suraj Kandpal
Add checks to see the HDR capability of TCON panel.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_display_types.h|  5 +
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 10 ++
 2 files changed, 15 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index 62f7a30c37dc..1cf4caf1a0a9 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -401,6 +401,11 @@ struct intel_panel {
} vesa;
struct {
bool sdr_uses_aux;
+   bool supports_2084_decode;
+   bool supports_2020_gamut;
+   bool supports_segmented_backlight;
+   bool supports_sdp_colorimetry;
+   bool supports_tone_mapping;
} intel;
} edp;
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..94edf982eff8 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -158,6 +158,16 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
 
panel->backlight.edp.intel.sdr_uses_aux =
tcon_cap[2] & INTEL_EDP_SDR_TCON_BRIGHTNESS_AUX_CAP;
+   panel->backlight.edp.intel.supports_2084_decode =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2084_DECODE_CAP;
+   panel->backlight.edp.intel.supports_2020_gamut =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2020_GAMUT_CAP;
+   panel->backlight.edp.intel.supports_segmented_backlight =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_CAP;
+   panel->backlight.edp.intel.supports_sdp_colorimetry =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_CAP;
+   panel->backlight.edp.intel.supports_tone_mapping =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_TONE_MAPPING_CAP;
 
return true;
 }
-- 
2.43.2



[PATCH 3/6] drm/i915/dp: Fix Register bit naming

2024-04-21 Thread Suraj Kandpal
Change INTEL_EDP_HDR_TCON_SDP_COLORIMETRY enable to
INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX as this bit is tells TCON to
ignore DPCD colorimetry values and take the one's sent through
SDP.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 94edf982eff8..3d9723714c96 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -74,7 +74,7 @@
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
-# define INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_ENABLEBIT(7)
+# define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
 #define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
-- 
2.43.2



[PATCH 0/6] Enable Aux Based EDP HDR

2024-04-21 Thread Suraj Kandpal
This series enables Aux based EDP HDR and backlight controls.
The DPCD written to are intel proprietary and are filled
based on the specs that were provided to TCON vendors.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (6):
  drm/i915/dp: Make has_gamut_metadata_dip() non static
  drm/i915/dp: Add TCON HDR capability checks
  drm/i915/dp: Fix Register bit naming
  drm/i915/dp: Drop comments on EDP HDR DPCD registers
  drm/i915/dp: Enable AUX based backlight for HDR
  drm/i915/dp: Write panel override luminance values

 .../drm/i915/display/intel_display_types.h|   5 +
 drivers/gpu/drm/i915/display/intel_dp.c   |   6 +-
 drivers/gpu/drm/i915/display/intel_dp.h   |   1 +
 .../drm/i915/display/intel_dp_aux_backlight.c | 139 --
 4 files changed, 134 insertions(+), 17 deletions(-)

-- 
2.43.2



[PATCH] drm/i915/hdcp: Disable HDCP Line Rekeying for HDCP2.2 on HDMI

2024-04-17 Thread Suraj Kandpal
Disable HDCP Line Rekeying when HDCP ver > 1.4 and when we are
on HDMI TMDS operation for DISPLAY_VER >= 14.

--v2
-Wa to be mentioned in comments not in commit message [Jani]
-Remove blankline [Jani]

--v3
-No need to write what is being done in comments when code
is self explanatory [Jani]

Bspec: 49273
Bspec: 69964
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 17 +
 drivers/gpu/drm/i915/i915_reg.h   |  1 +
 2 files changed, 18 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index d5ed4c7dfbc0..78b20f23a2e1 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,6 +30,21 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
+/* WA: 16022217614 */
+static void
+intel_hdcp_disable_hdcp_line_rekeying(struct intel_encoder *encoder,
+ struct intel_hdcp *hdcp)
+{
+   struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
+
+   if (encoder->type != INTEL_OUTPUT_HDMI)
+   return;
+
+   if (DISPLAY_VER(dev_priv) >= 14)
+   intel_de_rmw(dev_priv, TRANS_DDI_FUNC_CTL(hdcp->cpu_transcoder),
+TRANS_DDI_HDCP_LINE_REKEY_DISABLE, 1);
+}
+
 static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
@@ -2005,6 +2020,8 @@ static int _intel_hdcp2_enable(struct intel_atomic_state 
*state,
connector->base.base.id, connector->base.name,
hdcp->content_type);
 
+   intel_hdcp_disable_hdcp_line_rekeying(connector->encoder, hdcp);
+
ret = hdcp2_authenticate_and_encrypt(state, connector);
if (ret) {
drm_dbg_kms(>drm, "HDCP2 Type%d  Enabling Failed. (%d)\n",
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 3f34efcd7d6c..fbf4623cd536 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -5630,6 +5630,7 @@ enum skl_power_gate {
 #define  TRANS_DDI_EDP_INPUT_B_ONOFF   (5 << 12)
 #define  TRANS_DDI_EDP_INPUT_C_ONOFF   (6 << 12)
 #define  TRANS_DDI_EDP_INPUT_D_ONOFF   (7 << 12)
+#define  TRANS_DDI_HDCP_LINE_REKEY_DISABLE REG_BIT(12)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT_MASK   REG_GENMASK(11, 10)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT(trans) \
REG_FIELD_PREP(TRANS_DDI_MST_TRANSPORT_SELECT_MASK, trans)
-- 
2.43.2



[PATCH] drm/i915/pps: Disable DPLS_GATING around pps sequence

2024-04-16 Thread Suraj Kandpal
Disable bit 29 of SCLKGATE_DIS register around pps sequence
when we turn panel power on.

--v2
-Squash two commit together [Jani]
-Use IS_DISPLAY_VER [Jani]
-Fix multiline comment [Jani]

Bspec: 49304
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_pps.c | 12 
 drivers/gpu/drm/i915/i915_reg.h  |  4 
 2 files changed, 16 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_pps.c 
b/drivers/gpu/drm/i915/display/intel_pps.c
index 3078dfac7817..2b2cead22a7d 100644
--- a/drivers/gpu/drm/i915/display/intel_pps.c
+++ b/drivers/gpu/drm/i915/display/intel_pps.c
@@ -948,6 +948,14 @@ void intel_pps_on_unlocked(struct intel_dp *intel_dp)
intel_de_posting_read(dev_priv, pp_ctrl_reg);
}
 
+   /*
+* WA: 16023567976
+* Disable DPLS gating around power sequence.
+*/
+   if (IS_DISPLAY_VER(dev_priv, 12, 14))
+   intel_de_rmw(dev_priv, SCLKGATE_DIS,
+DPLS_GATING_DISABLE, 1);
+
pp |= PANEL_POWER_ON;
if (!IS_IRONLAKE(dev_priv))
pp |= PANEL_POWER_RESET;
@@ -958,6 +966,10 @@ void intel_pps_on_unlocked(struct intel_dp *intel_dp)
wait_panel_on(intel_dp);
intel_dp->pps.last_power_on = jiffies;
 
+   if (IS_DISPLAY_VER(dev_priv, 12, 14))
+   intel_de_rmw(dev_priv, SCLKGATE_DIS,
+DPLS_GATING_DISABLE, 0);
+
if (IS_IRONLAKE(dev_priv)) {
pp |= PANEL_POWER_RESET; /* restore panel reset bit */
intel_de_write(dev_priv, pp_ctrl_reg, pp);
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 3f34efcd7d6c..1c2cd6cc254f 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -6250,6 +6250,10 @@ enum skl_power_gate {
 #define  SFUSE_STRAP_DDIC_DETECTED (1 << 1)
 #define  SFUSE_STRAP_DDID_DETECTED (1 << 0)
 
+/* SCLKGATE_DIS */
+#define SCLKGATE_DIS   _MMIO(0xc2020)
+#define  DPLS_GATING_DISABLE   REG_BIT(29)
+
 #define WM_MISC_MMIO(0x45260)
 #define  WM_MISC_DATA_PARTITION_5_6(1 << 0)
 
-- 
2.43.2



[PATCH] drm/i915/hdcp: Disable HDCP Line Rekeying for HDCP2.2 on HDMI

2024-04-16 Thread Suraj Kandpal
Disable HDCP Line Rekeying when HDCP ver > 1.4 and when we are
on HDMI TMDS operation for DISPLAY_VER >= 14.

--v2
-Wa to be mentioned in comments not in commit message [Jani]
-Remove blankline [Jani]

Bspec: 49273
Bspec: 69964
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 22 ++
 drivers/gpu/drm/i915/i915_reg.h   |  1 +
 2 files changed, 23 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index d5ed4c7dfbc0..4b1833742245 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,6 +30,26 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
+/*
+ * WA: 16022217614
+ * Disable HDCP Line Rekeying when HDCP ver > 1.4
+ * and when we are on HDMI TMDS operation
+ * for DISPLAY_VEY >= 14.
+ */
+static void
+intel_hdcp_disable_hdcp_line_rekeying(struct intel_encoder *encoder,
+ struct intel_hdcp *hdcp)
+{
+   struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
+
+   if (encoder->type != INTEL_OUTPUT_HDMI)
+   return;
+
+   if (DISPLAY_VER(dev_priv) >= 14)
+   intel_de_rmw(dev_priv, TRANS_DDI_FUNC_CTL(hdcp->cpu_transcoder),
+TRANS_DDI_HDCP_LINE_REKEY_DISABLE, 1);
+}
+
 static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
@@ -2005,6 +2025,8 @@ static int _intel_hdcp2_enable(struct intel_atomic_state 
*state,
connector->base.base.id, connector->base.name,
hdcp->content_type);
 
+   intel_hdcp_disable_hdcp_line_rekeying(connector->encoder, hdcp);
+
ret = hdcp2_authenticate_and_encrypt(state, connector);
if (ret) {
drm_dbg_kms(>drm, "HDCP2 Type%d  Enabling Failed. (%d)\n",
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 3f34efcd7d6c..fbf4623cd536 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -5630,6 +5630,7 @@ enum skl_power_gate {
 #define  TRANS_DDI_EDP_INPUT_B_ONOFF   (5 << 12)
 #define  TRANS_DDI_EDP_INPUT_C_ONOFF   (6 << 12)
 #define  TRANS_DDI_EDP_INPUT_D_ONOFF   (7 << 12)
+#define  TRANS_DDI_HDCP_LINE_REKEY_DISABLE REG_BIT(12)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT_MASK   REG_GENMASK(11, 10)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT(trans) \
REG_FIELD_PREP(TRANS_DDI_MST_TRANSPORT_SELECT_MASK, trans)
-- 
2.43.2



[PATCH 0/2] Disable DPLS Gating around PPS

2024-04-16 Thread Suraj Kandpal
Disable DPLS Gating around Panel Power on Sequence.
WA:16023567976

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (2):
  drm/i915: Add SCLKGATE_DIS register definition
  drm/i915/pps: Disable DPLS_GATING around pps sequence

 drivers/gpu/drm/i915/display/intel_pps.c | 12 
 drivers/gpu/drm/i915/i915_reg.h  |  4 
 2 files changed, 16 insertions(+)

-- 
2.43.2



[PATCH 2/2] drm/i915/pps: Disable DPLS_GATING around pps sequence

2024-04-16 Thread Suraj Kandpal
Disable bit 29 of SCLKGATE_DIS register around pps sequence
when we turn panel power on.
WA: 16023567976
Bspec: 49304

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_pps.c | 12 
 1 file changed, 12 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_pps.c 
b/drivers/gpu/drm/i915/display/intel_pps.c
index 3078dfac7817..a912e712ca63 100644
--- a/drivers/gpu/drm/i915/display/intel_pps.c
+++ b/drivers/gpu/drm/i915/display/intel_pps.c
@@ -919,6 +919,7 @@ void intel_pps_on_unlocked(struct intel_dp *intel_dp)
struct drm_i915_private *dev_priv = dp_to_i915(intel_dp);
u32 pp;
i915_reg_t pp_ctrl_reg;
+   int dis_ver = DISPLAY_VER(dev_priv);
 
lockdep_assert_held(_priv->display.pps.mutex);
 
@@ -948,6 +949,13 @@ void intel_pps_on_unlocked(struct intel_dp *intel_dp)
intel_de_posting_read(dev_priv, pp_ctrl_reg);
}
 
+   /* WA: 16023567976
+* Disable DPLS gating around power sequence.
+*/
+   if (dis_ver >= 12 && dis_ver <= 14)
+   intel_de_rmw(dev_priv, SCLKGATE_DIS,
+DPLS_GATING_DISABLE, 1);
+
pp |= PANEL_POWER_ON;
if (!IS_IRONLAKE(dev_priv))
pp |= PANEL_POWER_RESET;
@@ -958,6 +966,10 @@ void intel_pps_on_unlocked(struct intel_dp *intel_dp)
wait_panel_on(intel_dp);
intel_dp->pps.last_power_on = jiffies;
 
+   if (dis_ver >= 12 && dis_ver <= 14)
+   intel_de_rmw(dev_priv, SCLKGATE_DIS,
+DPLS_GATING_DISABLE, 0);
+
if (IS_IRONLAKE(dev_priv)) {
pp |= PANEL_POWER_RESET; /* restore panel reset bit */
intel_de_write(dev_priv, pp_ctrl_reg, pp);
-- 
2.43.2



[PATCH 1/2] drm/i915: Add SCLKGATE_DIS register definition

2024-04-16 Thread Suraj Kandpal
Add SCLKGATE_DIS register and it's register definition which
will be used the next patch.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/i915_reg.h | 4 
 1 file changed, 4 insertions(+)

diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 3f34efcd7d6c..beec91a2f493 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -6250,6 +6250,10 @@ enum skl_power_gate {
 #define  SFUSE_STRAP_DDIC_DETECTED (1 << 1)
 #define  SFUSE_STRAP_DDID_DETECTED (1 << 0)
 
+/* SCLKGATE_DIS */
+#define SCLKGATE_DIS   _MMIO(0xc2014)
+#define  DPLS_GATING_DISABLE   REG_BIT(29)
+
 #define WM_MISC_MMIO(0x45260)
 #define  WM_MISC_DATA_PARTITION_5_6(1 << 0)
 
-- 
2.43.2



[PATCH] drm/i915/hdcp: Disable HDCP Line Rekeying for HDCP2.2 on HDMI

2024-04-15 Thread Suraj Kandpal
Disable HDCP Line Rekeying when HDCP ver > 1.4 and when we are
on HDMI TMDS operation for DISPLAY_VEY >= 14.
WA: 16022217614
Bspec: 49273
Bspec: 69964

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 16 
 drivers/gpu/drm/i915/i915_reg.h   |  1 +
 2 files changed, 17 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index d5ed4c7dfbc0..15af6e184ef8 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,6 +30,20 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
+static void
+intel_hdcp_disable_hdcp_line_rekeying(struct intel_encoder *encoder,
+ struct intel_hdcp *hdcp)
+{
+   struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
+
+   if (encoder->type != INTEL_OUTPUT_HDMI)
+   return;
+
+   if (DISPLAY_VER(dev_priv) >= 14)
+   intel_de_rmw(dev_priv, TRANS_DDI_FUNC_CTL(hdcp->cpu_transcoder),
+TRANS_DDI_HDCP_LINE_REKEY_DISABLE, 1);
+}
+
 static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
@@ -2005,6 +2019,8 @@ static int _intel_hdcp2_enable(struct intel_atomic_state 
*state,
connector->base.base.id, connector->base.name,
hdcp->content_type);
 
+   intel_hdcp_disable_hdcp_line_rekeying(connector->encoder, hdcp);
+
ret = hdcp2_authenticate_and_encrypt(state, connector);
if (ret) {
drm_dbg_kms(>drm, "HDCP2 Type%d  Enabling Failed. (%d)\n",
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index 3f34efcd7d6c..fbf4623cd536 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -5630,6 +5630,7 @@ enum skl_power_gate {
 #define  TRANS_DDI_EDP_INPUT_B_ONOFF   (5 << 12)
 #define  TRANS_DDI_EDP_INPUT_C_ONOFF   (6 << 12)
 #define  TRANS_DDI_EDP_INPUT_D_ONOFF   (7 << 12)
+#define  TRANS_DDI_HDCP_LINE_REKEY_DISABLE REG_BIT(12)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT_MASK   REG_GENMASK(11, 10)
 #define  TRANS_DDI_MST_TRANSPORT_SELECT(trans) \
REG_FIELD_PREP(TRANS_DDI_MST_TRANSPORT_SELECT_MASK, trans)
-- 
2.43.2



[PATCH 6/6] drm/i915/dp: Write panel override luminance values

2024-04-11 Thread Suraj Kandpal
Write panel override luminance values which helps the TCON decide
if tone mapping needs to be enabled or not.

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 25 +++
 1 file changed, 25 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index b13eee250dc4..cb6f01daae42 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -381,6 +381,29 @@ static const char *dpcd_vs_pwm_str(bool aux)
return aux ? "DPCD" : "PWM";
 }
 
+static void
+intel_dp_aux_write_panel_luminance_override(struct intel_connector *connector)
+{
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   struct intel_panel *panel = >panel;
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   int ret;
+   u8 buf[4] = {};
+
+   buf[0] = panel->backlight.min & 0xFF;
+   buf[1] = (panel->backlight.min & 0xFF00) >> 8;
+   buf[2] = panel->backlight.max & 0xFF;
+   buf[3] = (panel->backlight.max & 0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux,
+   INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE,
+   buf, sizeof(buf));
+   if (ret < 0)
+   drm_dbg_kms(>drm,
+   "Panel Luminance DPCD reg write failed, err:-%d\n",
+   ret);
+}
+
 static int
 intel_dp_aux_hdr_setup_backlight(struct intel_connector *connector, enum pipe 
pipe)
 {
@@ -412,6 +435,8 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
panel->backlight.min = 0;
}
 
+   intel_dp_aux_write_panel_luminance_override(connector);
+
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
connector->base.base.id, connector->base.name,
panel->backlight.min, panel->backlight.max);
-- 
2.43.2



[PATCH 5/6] drm/i915/dp: Enable AUX based backlight for HDR

2024-04-11 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

--v3
-Content Luminance needs to be sent only for pre-ICL after that
it is directly picked up from hdr metadata [Ville]

--v4
-Add checks for HDR TCON cap bits [Ville]
-Check eotf of hdr_output_data and sets bits base of that value.

--v5
-Fix capability check bits.
-Check colorspace before setting BT2020

--v6
-Use intel_dp_has_gamut_dip to check if we have capability
to send sdp [Ville]
-Seprate filling of all hdr tcon related bits into it's
own function.
-Check eotf data to make sure we are in HDR mode [Sebastian]

--v7
-Fix confusion function name for hdr mode check [Jani]
-Fix the condition which tells us if we are in HDR mode or not
[Sebastian]

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 105 --
 1 file changed, 94 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index b61bad218994..b13eee250dc4 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -127,9 +122,6 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (ret != sizeof(tcon_cap))
return false;
 
-   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
-   return false;
-
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Detected %s HDR backlight 
interface version %d\n",
connector->base.base.id, connector->base.name,
is_intel_tcon_cap(tcon_cap) ? "Intel" : "unsupported", 
tcon_cap[0]);
@@ -137,6 +129,9 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (!is_intel_tcon_cap(tcon_cap))
return false;
 
+   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
+   return false;
+
/*
 * If we don't have HDR static metadata there is no way to
 * runtime detect used range for nits based control. For now
@@ -225,13 +220,27 @@ intel_dp_aux_hdr_set_aux_backlight(const struct 
drm_connector_state *conn_state,
connector->base.base.id, connector->base.name);
 }
 
+static bool
+intel_dp_in_hdr_mode(const struct drm_connector_state *conn_state)
+{
+   struct hdr_output_metadata *hdr_metadata;
+
+   if (!conn_state->hdr_output_metadata)
+   return false;
+
+   hdr_metadata = conn_state->hdr_output_metadata->data;
+
+   return hdr_metadata->hdmi_metadata_type1.eotf == HDMI_EOTF_SMPTE_ST2084;
+}
+
 static void
 intel_dp_aux_hdr_set_backlight(const struct drm_connector_state *conn_state, 
u32 level)
 {
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (intel_dp_in_hdr_mode(conn_state) ||
+   panel->backlight.edp.intel.sdr_uses_aux) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -240,6 +249,70 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
}
 }
 
+static void
+intel_dp_aux_write_content_luminance(struct intel_connector *connector,
+struct hdr_output_metadata *hdr_metadata)
+{
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   int ret;
+   u8 buf[4];
+
+   if (!intel_dp_has_gamut_metadata_dip(connector->encoder))
+   return;
+
+   buf[0] = hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF;
+   buf[1] = (hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF00) >> 8;
+   buf[2] = hdr_metadata->hdmi_metadata_type1.max_fall & 0xFF;
+   buf[3] = (hdr_metadata->hdmi_metadata_type1.max_fall & 0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux,
+   INTEL_EDP_HDR_CONTENT_LUMI

[PATCH 3/6] drm/i915/dp: Fix Register bit naming

2024-04-11 Thread Suraj Kandpal
Change INTEL_EDP_HDR_TCON_SDP_COLORIMETRY enable to
INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX as this bit is tells TCON to
ignore DPCD colorimetry values and take the one's sent through
SDP.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 94edf982eff8..3d9723714c96 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -74,7 +74,7 @@
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
-# define INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_ENABLEBIT(7)
+# define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
 #define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
-- 
2.43.2



[PATCH 4/6] drm/i915/dp: Drop comments on EDP HDR DPCD registers

2024-04-11 Thread Suraj Kandpal
Drop comments for EDP HDR DPCD registers as the code and
conditions will tell us what can be written where.

--v2
-Drop the comments altogether instead of just renaming them
[Sebastian]

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 3d9723714c96..b61bad218994 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -69,14 +69,14 @@
 #define INTEL_EDP_HDR_GETSET_CTRL_PARAMS   0x344
 # define INTEL_EDP_HDR_TCON_2084_DECODE_ENABLEBIT(0)
 # define INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE BIT(1)
-# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2) 
/* Pre-TGL+ */
+# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2)
 # define INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLEBIT(3)
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
 # define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
-#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
+#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
 #define INTEL_EDP_SDR_LUMINANCE_LEVEL  0x352
 #define INTEL_EDP_BRIGHTNESS_NITS_LSB  0x354
-- 
2.43.2



[PATCH 1/6] drm/i915/dp: Make has_gamut_metadata_dip() non static

2024-04-11 Thread Suraj Kandpal
Make has_gamut_metadata_dip() non static so it can also be used to
at other places eg in intel_dp_aux_backlight.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp.c | 6 +++---
 drivers/gpu/drm/i915/display/intel_dp.h | 1 +
 2 files changed, 4 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp.c 
b/drivers/gpu/drm/i915/display/intel_dp.c
index 163da48bc406..8b105efd4de9 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -6365,8 +6365,8 @@ bool intel_dp_is_port_edp(struct drm_i915_private *i915, 
enum port port)
return _intel_dp_is_port_edp(i915, devdata, port);
 }
 
-static bool
-has_gamut_metadata_dip(struct intel_encoder *encoder)
+bool
+intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder)
 {
struct drm_i915_private *i915 = to_i915(encoder->base.dev);
enum port port = encoder->port;
@@ -6413,7 +6413,7 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct 
drm_connector *connect
intel_attach_dp_colorspace_property(connector);
}
 
-   if (has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
+   if (intel_dp_has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
drm_connector_attach_hdr_output_metadata_property(connector);
 
if (HAS_VRR(dev_priv))
diff --git a/drivers/gpu/drm/i915/display/intel_dp.h 
b/drivers/gpu/drm/i915/display/intel_dp.h
index 106ecfde36d9..aad2223df2a3 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.h
+++ b/drivers/gpu/drm/i915/display/intel_dp.h
@@ -196,5 +196,6 @@ intel_dp_compute_config_link_bpp_limits(struct intel_dp 
*intel_dp,
struct link_config_limits *limits);
 
 void intel_dp_get_dsc_sink_cap(u8 dpcd_rev, struct intel_connector *connector);
+bool intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder);
 
 #endif /* __INTEL_DP_H__ */
-- 
2.43.2



[PATCH 2/6] drm/i915/dp: Add TCON HDR capability checks

2024-04-11 Thread Suraj Kandpal
Add checks to see the HDR capability of TCON panel.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_display_types.h|  5 +
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 10 ++
 2 files changed, 15 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index 0f4bd5710796..ef28eee05ec6 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -401,6 +401,11 @@ struct intel_panel {
} vesa;
struct {
bool sdr_uses_aux;
+   bool supports_2084_decode;
+   bool supports_2020_gamut;
+   bool supports_segmented_backlight;
+   bool supports_sdp_colorimetry;
+   bool supports_tone_mapping;
} intel;
} edp;
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..94edf982eff8 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -158,6 +158,16 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
 
panel->backlight.edp.intel.sdr_uses_aux =
tcon_cap[2] & INTEL_EDP_SDR_TCON_BRIGHTNESS_AUX_CAP;
+   panel->backlight.edp.intel.supports_2084_decode =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2084_DECODE_CAP;
+   panel->backlight.edp.intel.supports_2020_gamut =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2020_GAMUT_CAP;
+   panel->backlight.edp.intel.supports_segmented_backlight =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_CAP;
+   panel->backlight.edp.intel.supports_sdp_colorimetry =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_CAP;
+   panel->backlight.edp.intel.supports_tone_mapping =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_TONE_MAPPING_CAP;
 
return true;
 }
-- 
2.43.2



[PATCH 0/6] Enable Aux Based EDP HDR

2024-04-11 Thread Suraj Kandpal
This series enables Aux based EDP HDR and backlight controls.
The DPCD written to are intel proprietary and are filled
based on the specs that were provided to TCON vendors.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (6):
  drm/i915/dp: Make has_gamut_metadata_dip() non static
  drm/i915/dp: Add TCON HDR capability checks
  drm/i915/dp: Fix Register bit naming
  drm/i915/dp: Drop comments on EDP HDR DPCD registers
  drm/i915/dp: Enable AUX based backlight for HDR
  drm/i915/dp: Write panel override luminance values

 .../drm/i915/display/intel_display_types.h|   5 +
 drivers/gpu/drm/i915/display/intel_dp.c   |   6 +-
 drivers/gpu/drm/i915/display/intel_dp.h   |   1 +
 .../drm/i915/display/intel_dp_aux_backlight.c | 146 --
 4 files changed, 141 insertions(+), 17 deletions(-)

-- 
2.43.2



[PATCH 7/7] drm/i915/dp: Limit brightness level to vbt min brightness

2024-04-05 Thread Suraj Kandpal
Limit minimum brightness to vbt min brightness when using aux
based brightness control to avoid letting the screen
from going completely blank.
Sometimes vbt can have some bogus values hence clamping the value
for sanity in case of corner case.

--v2
-Use something same mechanism to limit minimum brightness
that PWM method uses [Jani]

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 10 +-
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 20dd5a6a0f3f..eb2a7225dfaa 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -411,6 +411,8 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
struct intel_panel *panel = >panel;
struct drm_luminance_range_info *luminance_range =
>base.display_info.luminance_range;
+   u32 min_level = clamp_t(u32,
+   connector->panel.vbt.backlight.min_brightness, 
0, 64);
int ret;
 
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] SDR backlight is controlled 
through %s\n",
@@ -427,14 +429,12 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
}
}
 
-   if (luminance_range->max_luminance) {
+   if (luminance_range->max_luminance)
panel->backlight.max = luminance_range->max_luminance;
-   panel->backlight.min = luminance_range->min_luminance;
-   } else {
+   else
panel->backlight.max = 512;
-   panel->backlight.min = 0;
-   }
 
+   panel->backlight.min = min_level;
intel_dp_aux_write_panel_luminance_override(connector);
 
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
-- 
2.43.2



[PATCH 7/7] drm/i915/dp: Limit brightness level to 20

2024-04-03 Thread Suraj Kandpal
Limit minimum brightness to 20 when using aux based brightness
control to avoid letting the screen going completely blank.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 20dd5a6a0f3f..b54ea7e46954 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -211,6 +211,9 @@ intel_dp_aux_hdr_set_aux_backlight(const struct 
drm_connector_state *conn_state,
struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
u8 buf[4] = {};
 
+   if (level < 20)
+   level = 20;
+
buf[0] = level & 0xFF;
buf[1] = (level & 0xFF00) >> 8;
 
-- 
2.43.2



[PATCH 6/7] drm/i915/dp: Write panel override luminance values

2024-04-03 Thread Suraj Kandpal
Write panel override luminance values which helps the TCON decide
if tone mapping needs to be enabled or not.

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 25 +++
 1 file changed, 25 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 7af876e2d210..20dd5a6a0f3f 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -381,6 +381,29 @@ static const char *dpcd_vs_pwm_str(bool aux)
return aux ? "DPCD" : "PWM";
 }
 
+static void
+intel_dp_aux_write_panel_luminance_override(struct intel_connector *connector)
+{
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   struct intel_panel *panel = >panel;
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   int ret;
+   u8 buf[4] = {};
+
+   buf[0] = panel->backlight.min & 0xFF;
+   buf[1] = (panel->backlight.min & 0xFF00) >> 8;
+   buf[2] = panel->backlight.max & 0xFF;
+   buf[3] = (panel->backlight.max & 0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux,
+   INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE,
+   buf, sizeof(buf));
+   if (ret < 0)
+   drm_dbg_kms(>drm,
+   "Panel Luminance DPCD reg write failed, err:-%d\n",
+   ret);
+}
+
 static int
 intel_dp_aux_hdr_setup_backlight(struct intel_connector *connector, enum pipe 
pipe)
 {
@@ -412,6 +435,8 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
panel->backlight.min = 0;
}
 
+   intel_dp_aux_write_panel_luminance_override(connector);
+
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
connector->base.base.id, connector->base.name,
panel->backlight.min, panel->backlight.max);
-- 
2.43.2



[PATCH 5/7] drm/i915/dp: Enable AUX based backlight for HDR

2024-04-03 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

--v3
-Content Luminance needs to be sent only for pre-ICL after that
it is directly picked up from hdr metadata [Ville]

--v4
-Add checks for HDR TCON cap bits [Ville]
-Check eotf of hdr_output_data and sets bits base of that value.

--v5
-Fix capability check bits.
-Check colorspace before setting BT2020

--v6
-Use intel_dp_has_gamut_dip to check if we have capability
to send sdp [Ville]
-Seprate filling of all hdr tcon related bits into it's
own function.
-Check eotf data to make sure we are in HDR mode [Sebastian]

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 105 --
 1 file changed, 94 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 2d50a4734823..7af876e2d210 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -127,9 +122,6 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (ret != sizeof(tcon_cap))
return false;
 
-   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
-   return false;
-
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Detected %s HDR backlight 
interface version %d\n",
connector->base.base.id, connector->base.name,
is_intel_tcon_cap(tcon_cap) ? "Intel" : "unsupported", 
tcon_cap[0]);
@@ -137,6 +129,9 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
if (!is_intel_tcon_cap(tcon_cap))
return false;
 
+   if (!(tcon_cap[1] & INTEL_EDP_HDR_TCON_BRIGHTNESS_NITS_CAP))
+   return false;
+
/*
 * If we don't have HDR static metadata there is no way to
 * runtime detect used range for nits based control. For now
@@ -225,13 +220,27 @@ intel_dp_aux_hdr_set_aux_backlight(const struct 
drm_connector_state *conn_state,
connector->base.base.id, connector->base.name);
 }
 
+static bool
+intel_dp_aux_in_hdr_mode(const struct drm_connector_state *conn_state)
+{
+   struct hdr_output_metadata *hdr_metadata;
+
+   if (!conn_state->hdr_output_metadata)
+   return false;
+
+   hdr_metadata = conn_state->hdr_output_metadata->data;
+
+   return hdr_metadata->hdmi_metadata_type1.eotf != 
HDMI_EOTF_TRADITIONAL_GAMMA_SDR;
+}
+
 static void
 intel_dp_aux_hdr_set_backlight(const struct drm_connector_state *conn_state, 
u32 level)
 {
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (intel_dp_aux_in_hdr_mode(conn_state) ||
+   panel->backlight.edp.intel.sdr_uses_aux) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -240,6 +249,70 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
}
 }
 
+static void
+intel_dp_aux_write_content_luminance(struct intel_connector *connector,
+struct hdr_output_metadata *hdr_metadata)
+{
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   int ret;
+   u8 buf[4];
+
+   if (!intel_dp_has_gamut_metadata_dip(connector->encoder))
+   return;
+
+   buf[0] = hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF;
+   buf[1] = (hdr_metadata->hdmi_metadata_type1.max_cll & 0xFF00) >> 8;
+   buf[2] = hdr_metadata->hdmi_metadata_type1.max_fall & 0xFF;
+   buf[3] = (hdr_metadata->hdmi_metadata_type1.max_fall & 0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux,
+   INTEL_EDP_HDR_CONTENT_LUMINANCE,
+   buf, sizeof(buf));
+   if (ret < 0)
+   

[PATCH 4/7] drm/i915/dp: Fix comments on EDP HDR DPCD registers

2024-04-03 Thread Suraj Kandpal
Change comments from Pre-TGL+ to Pre-ICL as mentioned in specs

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 3d9723714c96..2d50a4734823 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -69,14 +69,14 @@
 #define INTEL_EDP_HDR_GETSET_CTRL_PARAMS   0x344
 # define INTEL_EDP_HDR_TCON_2084_DECODE_ENABLEBIT(0)
 # define INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE BIT(1)
-# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2) 
/* Pre-TGL+ */
+# define INTEL_EDP_HDR_TCON_TONE_MAPPING_ENABLE   BIT(2) 
/* Pre-ICL */
 # define INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLEBIT(3)
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
 # define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
-#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
+#define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-ICL */
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
 #define INTEL_EDP_SDR_LUMINANCE_LEVEL  0x352
 #define INTEL_EDP_BRIGHTNESS_NITS_LSB  0x354
-- 
2.43.2



[PATCH 3/7] drm/i915/dp: Fix Register bit naming

2024-04-03 Thread Suraj Kandpal
Change INTEL_EDP_HDR_TCON_SDP_COLORIMETRY enable to
INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX as this bit is tells TCON to
ignore DPCD colorimetry values and take the one's sent through
SDP.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 94edf982eff8..3d9723714c96 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -74,7 +74,7 @@
 # define INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE BIT(4)
 # define INTEL_EDP_HDR_TCON_SRGB_TO_PANEL_GAMUT_ENABLEBIT(5)
 /* Bit 6 is reserved */
-# define INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_ENABLEBIT(7)
+# define INTEL_EDP_HDR_TCON_SDP_OVERRIDE_AUX BIT(7)
 
 #define INTEL_EDP_HDR_CONTENT_LUMINANCE0x346 
/* Pre-TGL+ */
 #define INTEL_EDP_HDR_PANEL_LUMINANCE_OVERRIDE 0x34A
-- 
2.43.2



[PATCH 2/7] drm/i915/dp: Add TCON HDR capability checks

2024-04-03 Thread Suraj Kandpal
Add checks to see the HDR capability of TCON panel.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_display_types.h|  5 +
 drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c | 10 ++
 2 files changed, 15 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index 4ef1f5f709d8..ebee6ebf1fdb 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -401,6 +401,11 @@ struct intel_panel {
} vesa;
struct {
bool sdr_uses_aux;
+   bool supports_2084_decode;
+   bool supports_2020_gamut;
+   bool supports_segmented_backlight;
+   bool supports_sdp_colorimetry;
+   bool supports_tone_mapping;
} intel;
} edp;
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..94edf982eff8 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -158,6 +158,16 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
 
panel->backlight.edp.intel.sdr_uses_aux =
tcon_cap[2] & INTEL_EDP_SDR_TCON_BRIGHTNESS_AUX_CAP;
+   panel->backlight.edp.intel.supports_2084_decode =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2084_DECODE_CAP;
+   panel->backlight.edp.intel.supports_2020_gamut =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2020_GAMUT_CAP;
+   panel->backlight.edp.intel.supports_segmented_backlight =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_CAP;
+   panel->backlight.edp.intel.supports_sdp_colorimetry =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SDP_COLORIMETRY_CAP;
+   panel->backlight.edp.intel.supports_tone_mapping =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_TONE_MAPPING_CAP;
 
return true;
 }
-- 
2.43.2



[PATCH 1/7] drm/i915/dp: Make has_gamut_metadata_dip() non static

2024-04-03 Thread Suraj Kandpal
Make has_gamut_metadata_dip() non static so it can also be used to
at other places eg in intel_dp_aux_backlight.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp.c | 6 +++---
 drivers/gpu/drm/i915/display/intel_dp.h | 1 +
 2 files changed, 4 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp.c 
b/drivers/gpu/drm/i915/display/intel_dp.c
index a11bc4fd3d65..26ccd4cc0d48 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -6226,8 +6226,8 @@ bool intel_dp_is_port_edp(struct drm_i915_private *i915, 
enum port port)
return _intel_dp_is_port_edp(i915, devdata, port);
 }
 
-static bool
-has_gamut_metadata_dip(struct intel_encoder *encoder)
+bool
+intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder)
 {
struct drm_i915_private *i915 = to_i915(encoder->base.dev);
enum port port = encoder->port;
@@ -6274,7 +6274,7 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct 
drm_connector *connect
intel_attach_dp_colorspace_property(connector);
}
 
-   if (has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
+   if (intel_dp_has_gamut_metadata_dip(_to_dig_port(intel_dp)->base))
drm_connector_attach_hdr_output_metadata_property(connector);
 
if (HAS_VRR(dev_priv))
diff --git a/drivers/gpu/drm/i915/display/intel_dp.h 
b/drivers/gpu/drm/i915/display/intel_dp.h
index c540d3a73fe7..bbd61cbedc4f 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.h
+++ b/drivers/gpu/drm/i915/display/intel_dp.h
@@ -193,5 +193,6 @@ intel_dp_compute_config_link_bpp_limits(struct intel_dp 
*intel_dp,
struct link_config_limits *limits);
 
 void intel_dp_get_dsc_sink_cap(u8 dpcd_rev, struct intel_connector *connector);
+bool intel_dp_has_gamut_metadata_dip(struct intel_encoder *encoder);
 
 #endif /* __INTEL_DP_H__ */
-- 
2.43.2



[PATCH 0/7] Enable Aux Based EDP HDR

2024-04-03 Thread Suraj Kandpal
This series enables Aux based EDP HDR and backlight controls.
The DPCD written to are intel proprietary and are filled
based on the specs that were provided to TCON vendors.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (7):
  drm/i915/dp: Make has_gamut_metadata_dip() non static
  drm/i915/dp: Add TCON HDR capability checks
  drm/i915/dp: Fix Register bit naming
  drm/i915/dp: Fix comments on EDP HDR DPCD registers
  drm/i915/dp: Enable AUX based backlight for HDR
  drm/i915/dp: Write panel override luminance values
  drm/i915/dp: Limit brightness level to 20

 .../drm/i915/display/intel_display_types.h|   5 +
 drivers/gpu/drm/i915/display/intel_dp.c   |   6 +-
 drivers/gpu/drm/i915/display/intel_dp.h   |   1 +
 .../drm/i915/display/intel_dp_aux_backlight.c | 149 --
 4 files changed, 144 insertions(+), 17 deletions(-)

-- 
2.43.2



[PATCH 2/2] drm/i915/hdcp: Fix get remote hdcp capability function

2024-03-31 Thread Suraj Kandpal
HDCP 1.x capability needs to be checked even if setup is not
HDCP 2.x capable.

--v2
-Assign hdcp_capable and hdcp2_capable to false [Chaitanya]

--v3
-Fix variable assignment [Chaitanya]

Fixes: 813cca96e4ac ("drm/i915/hdcp: Add new remote capability check shim 
function")
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 5 -
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 179e754e5c30..92b03073acdd 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -691,12 +691,15 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
u8 bcaps;
int ret;
 
+   *hdcp_capable = false;
+   *hdcp2_capable = false;
if (!intel_encoder_is_mst(connector->encoder))
return -EINVAL;
 
ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
if (ret)
-   return ret;
+   drm_dbg_kms(>drm,
+   "HDCP2 DPCD capability read failed err: %d\n", ret);
 
ret = intel_dp_hdcp_read_bcaps(aux, i915, );
if (ret)
-- 
2.43.2



[PATCH 2/2] drm/i915/hdcp: Fix get remote hdcp capability function

2024-03-31 Thread Suraj Kandpal
HDCP 1.x capability needs to be checked even if setup is not
HDCP 2.x capable.

--v2
-Assign hdcp_capable and hdcp2_capable to false [Chaitanya]

Fixes: 813cca96e4ac ("drm/i915/hdcp: Add new remote capability check shim 
function")
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 5 -
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 179e754e5c30..bd2cd7417136 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -694,9 +694,12 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
if (!intel_encoder_is_mst(connector->encoder))
return -EINVAL;
 
+   hdcp_capable = false;
+   hdcp2_capable = false;
ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
if (ret)
-   return ret;
+   drm_dbg_kms(>drm,
+   "HDCP2 DPCD capability read failed err: %d\n", ret);
 
ret = intel_dp_hdcp_read_bcaps(aux, i915, );
if (ret)
-- 
2.43.2



[PATCH 1/2] drm/i915/display: Initialize capability variables

2024-03-31 Thread Suraj Kandpal
Initialize HDCP capability variables to false to avoid UBSAN
warning in boolean value as some functions invoking this could
return without filling the two capability values.

--v2
-Fix Typo [Chaitanya]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Chaitanya Kumar Borah 
---
 drivers/gpu/drm/i915/display/intel_display_debugfs.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_debugfs.c 
b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
index b99c024b0934..95d14dab089e 100644
--- a/drivers/gpu/drm/i915/display/intel_display_debugfs.c
+++ b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
@@ -191,7 +191,7 @@ static void intel_hdcp_info(struct seq_file *m,
struct intel_connector *intel_connector,
bool remote_req)
 {
-   bool hdcp_cap, hdcp2_cap;
+   bool hdcp_cap = false, hdcp2_cap = false;
 
if (!intel_connector->hdcp.shim) {
seq_puts(m, "No Connector Support");
-- 
2.43.2



[PATCH 0/2] Fix UBSAN warning in hdcp_info

2024-03-31 Thread Suraj Kandpal
This patch series fixes the UBSAN warning which gets called
when hdcp_info is invoked accompanied by some other logical fixes
required in the hdcp capability function.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (2):
  drm/i915/display: Initialize capability variables
  drm/i915/hdcp: Fix get remote hdcp capability function

 drivers/gpu/drm/i915/display/intel_display_debugfs.c | 2 +-
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 5 -
 2 files changed, 5 insertions(+), 2 deletions(-)

-- 
2.43.2



[PATCH 2/2] drm/i915/hdcp: Fix get remote hdcp capability function

2024-03-26 Thread Suraj Kandpal
HDCP 1.x capability needs to be checked even if setup is not
HDCP 2.x capable.

Fixes: 813cca96e4ac ("drm/i915/hdcp: Add new remote capability check shim 
function")
Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 9 -
 1 file changed, 4 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index b98a87883fef..7f52043b0f9f 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -688,7 +688,7 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
struct drm_dp_aux *aux = >port->aux;
-   u8 bcaps;
+   u8 bcaps = 0;
int ret;
 
if (!intel_encoder_is_mst(connector->encoder))
@@ -696,15 +696,14 @@ int intel_dp_hdcp_get_remote_capability(struct 
intel_connector *connector,
 
ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
if (ret)
-   return ret;
+   drm_dbg_kms(>drm,
+   "HDCP2 DPCD capability read failed err: %d\n", ret);
 
ret = intel_dp_hdcp_read_bcaps(aux, i915, );
-   if (ret)
-   return ret;
 
*hdcp_capable = bcaps & DP_BCAPS_HDCP_CAPABLE;
 
-   return 0;
+   return ret;
 }
 
 static const struct intel_hdcp_shim intel_dp_hdcp_shim = {
-- 
2.43.2



[PATCH 1/2] drm/i915/display: Initialize capability variables

2024-03-26 Thread Suraj Kandpal
Initialize HDCP capability variables to false to avoid UBSAN
warning in boolean value.

--v2
-Fix Typo [Chaitanya]

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_display_debugfs.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_debugfs.c 
b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
index b99c024b0934..95d14dab089e 100644
--- a/drivers/gpu/drm/i915/display/intel_display_debugfs.c
+++ b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
@@ -191,7 +191,7 @@ static void intel_hdcp_info(struct seq_file *m,
struct intel_connector *intel_connector,
bool remote_req)
 {
-   bool hdcp_cap, hdcp2_cap;
+   bool hdcp_cap = false, hdcp2_cap = false;
 
if (!intel_connector->hdcp.shim) {
seq_puts(m, "No Connector Support");
-- 
2.43.2



[PATCH 0/2] Fix UBSAN warning in hdcp_info

2024-03-26 Thread Suraj Kandpal
This patch series fixes the UBSAN warning which gets called
when hdcp_info is invoked accompanied by some other logical fixes
required in the hdcp capability function.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (2):
  drm/i915/display: Initialize capability variables
  drm/i915/hdcp: Fix get remote hdcp capability function

 drivers/gpu/drm/i915/display/intel_display_debugfs.c | 2 +-
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 9 -
 2 files changed, 5 insertions(+), 6 deletions(-)

-- 
2.43.2



[PATCH] drm/i915/display: Initalizalize capability variables

2024-03-25 Thread Suraj Kandpal
Initialize HDCP capability variables to false to avoid UBSAN
warning in boolean value.

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_display_debugfs.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_debugfs.c 
b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
index b99c024b0934..95d14dab089e 100644
--- a/drivers/gpu/drm/i915/display/intel_display_debugfs.c
+++ b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
@@ -191,7 +191,7 @@ static void intel_hdcp_info(struct seq_file *m,
struct intel_connector *intel_connector,
bool remote_req)
 {
-   bool hdcp_cap, hdcp2_cap;
+   bool hdcp_cap = false, hdcp2_cap = false;
 
if (!intel_connector->hdcp.shim) {
seq_puts(m, "No Connector Support");
-- 
2.43.2



[PATCH] drm/i915/dp: Enable AUX based backlight for HDR

2024-03-14 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

--v3
-Content Luminance needs to be sent only for pre-ICL after that
it is directly picked up from hdr metadata [Ville]

--v4
-Add checks for HDR TCON cap bits [Ville]
-Check eotf of hdr_output_data and sets bits base of that value.

--v5
-Fix capability check bits.
-Check colorspace before setting BT2020

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_display_types.h|  3 +
 .../drm/i915/display/intel_dp_aux_backlight.c | 57 ---
 2 files changed, 52 insertions(+), 8 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index e67cd5b02e84..271bb609106d 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -401,6 +401,9 @@ struct intel_panel {
} vesa;
struct {
bool sdr_uses_aux;
+   bool supports_2084_decode;
+   bool supports_2020_gamut;
+   bool supports_segmented_backlight;
} intel;
} edp;
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..f927e259b540 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -158,6 +153,12 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
 
panel->backlight.edp.intel.sdr_uses_aux =
tcon_cap[2] & INTEL_EDP_SDR_TCON_BRIGHTNESS_AUX_CAP;
+   panel->backlight.edp.intel.supports_2084_decode =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2084_DECODE_CAP;
+   panel->backlight.edp.intel.supports_2020_gamut =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_2020_GAMUT_CAP;
+   panel->backlight.edp.intel.supports_segmented_backlight =
+   tcon_cap[1] & INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_CAP;
 
return true;
 }
@@ -206,6 +207,9 @@ intel_dp_aux_hdr_set_aux_backlight(const struct 
drm_connector_state *conn_state,
struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
u8 buf[4] = {};
 
+   if (level < 20)
+   level = 20;
+
buf[0] = level & 0xFF;
buf[1] = (level & 0xFF00) >> 8;
 
@@ -221,7 +225,7 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -251,8 +255,30 @@ intel_dp_aux_hdr_enable_backlight(const struct 
intel_crtc_state *crtc_state,
}
 
ctrl = old_ctrl;
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
ctrl |= INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE;
+
+   if (conn_state->hdr_output_metadata) {
+   struct hdr_output_metadata *hdr_metadata =
+   conn_state->hdr_output_metadata->data;
+
+   if 
(panel->backlight.edp.intel.supports_segmented_backlight &&
+   hdr_metadata->hdmi_metadata_type1.eotf >=
+   HDMI_EOTF_TRADITIONAL_GAMMA_HDR)
+   ctrl |= 
INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLE;
+   if (panel->backlight.edp.intel.supports_2084_decode &&
+   hdr_metadata->hdmi_metadata_type1.eotf ==
+   HDMI_EOTF_SMPTE_ST2084)
+   ctrl |= INTEL_EDP_HDR_TCON_2084_D

[PATCH] drm/i915/dp: Enable AUX based backlight for HDR

2024-03-10 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

--v3
-Content Luminance needs to be sent only for pre-ICL after that
it is directly picked up from hdr metadata [Ville]

--v4
-Add checks for HDR TCON cap bits [Ville]
-Check eotf of hdr_output_data and sets bits base of that value.

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_display_types.h|  3 ++
 .../drm/i915/display/intel_dp_aux_backlight.c | 51 ---
 2 files changed, 46 insertions(+), 8 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index e67cd5b02e84..271bb609106d 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -401,6 +401,9 @@ struct intel_panel {
} vesa;
struct {
bool sdr_uses_aux;
+   bool supports_2084_decode;
+   bool supports_2020_gamut;
+   bool supports_segmented_backlight;
} intel;
} edp;
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..74270c4755e7 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -158,6 +153,12 @@ intel_dp_aux_supports_hdr_backlight(struct intel_connector 
*connector)
 
panel->backlight.edp.intel.sdr_uses_aux =
tcon_cap[2] & INTEL_EDP_SDR_TCON_BRIGHTNESS_AUX_CAP;
+   panel->backlight.edp.intel.supports_2084_decode =
+   tcon_cap[2] & INTEL_EDP_HDR_TCON_2084_DECODE_CAP;
+   panel->backlight.edp.intel.supports_2020_gamut =
+   tcon_cap[2] & INTEL_EDP_HDR_TCON_2020_GAMUT_CAP;
+   panel->backlight.edp.intel.supports_segmented_backlight =
+   tcon_cap[2] & INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_CAP;
 
return true;
 }
@@ -221,7 +222,7 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -251,8 +252,27 @@ intel_dp_aux_hdr_enable_backlight(const struct 
intel_crtc_state *crtc_state,
}
 
ctrl = old_ctrl;
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
ctrl |= INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE;
+
+   if (conn_state->hdr_output_metadata) {
+   struct hdr_output_metadata *hdr_metadata =
+   conn_state->hdr_output_metadata->data;
+
+   if 
(panel->backlight.edp.intel.supports_segmented_backlight &&
+   hdr_metadata->hdmi_metadata_type1.eotf >=
+   HDMI_EOTF_TRADITIONAL_GAMMA_HDR)
+   ctrl |= 
INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLE;
+   if (panel->backlight.edp.intel.supports_2084_decode &&
+   hdr_metadata->hdmi_metadata_type1.eotf ==
+   HDMI_EOTF_SMPTE_ST2084)
+   ctrl |= INTEL_EDP_HDR_TCON_2084_DECODE_ENABLE;
+   if (panel->backlight.edp.intel.supports_2020_gamut &&
+   hdr_metadata->hdmi_metadata_type1.eotf >=
+   HDMI_EOTF_TRADITIONAL_GAMMA_HDR)
+   ctrl |= INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE;
+   }
+
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {

[PATCH] drm/i915/dp: Enable AUX based backlight for HDR

2024-03-07 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

--v3
-Content Luminance needs to be sent only for pre-ICL after that
it is directly picked up from hdr metadata [Ville]

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 33 ++-
 1 file changed, 25 insertions(+), 8 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..cba7b8f5dad4 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -221,7 +216,7 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -251,8 +246,15 @@ intel_dp_aux_hdr_enable_backlight(const struct 
intel_crtc_state *crtc_state,
}
 
ctrl = old_ctrl;
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
ctrl |= INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE;
+
+   if (conn_state->hdr_output_metadata) {
+   ctrl |= INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLE;
+   ctrl |= INTEL_EDP_HDR_TCON_2084_DECODE_ENABLE;
+   ctrl |= INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE;
+   }
+
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
u32 pwm_level = intel_backlight_level_to_pwm(connector, level);
@@ -292,9 +294,11 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
struct intel_panel *panel = >panel;
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
struct drm_luminance_range_info *luminance_range =
>base.display_info.luminance_range;
int ret;
+   u8 buf[4];
 
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] SDR backlight is controlled 
through %s\n",
connector->base.base.id, connector->base.name,
@@ -318,11 +322,24 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
panel->backlight.min = 0;
}
 
+   if (DISPLAY_VER(i915) < 11) {
+   buf[0] = connector->base.hdr_sink_metadata.hdmi_type1.max_cll & 
0xFF;
+   buf[1] = (connector->base.hdr_sink_metadata.hdmi_type1.max_cll 
& 0xFF00) >> 8;
+   buf[2] = connector->base.hdr_sink_metadata.hdmi_type1.max_fall 
& 0xFF;
+   buf[3] = (connector->base.hdr_sink_metadata.hdmi_type1.max_fall 
& 0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux, 
INTEL_EDP_HDR_CONTENT_LUMINANCE, buf,
+   sizeof(buf));
+   if (ret < 0)
+   drm_dbg_kms(>drm,
+   "Content Luminance DPCD reg write failed, 
err:-%d\n",
+   ret);
+   }
+
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
connector->base.base.id, connector->base.name,
panel->backlight.min, panel->backlight.max);
 
-
panel->backlight.level = intel_dp_aux_hdr_get_backlight(connector, 
pipe);
panel->backlight.enabled = panel->backlight.level != 0;
 
-- 
2.43.2



[PATCH] drm/i915/dp: Enable AUX based backlight for HDR

2024-03-06 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

--v2
-Fix max_cll and max_fall assignment [Jani]
-Fix the size sent in drm_dpcd_write [Jani]

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 30 ++-
 1 file changed, 22 insertions(+), 8 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..1b6f14dacf3b 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -221,7 +216,7 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -251,8 +246,15 @@ intel_dp_aux_hdr_enable_backlight(const struct 
intel_crtc_state *crtc_state,
}
 
ctrl = old_ctrl;
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
ctrl |= INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE;
+
+   if (conn_state->hdr_output_metadata) {
+   ctrl |= INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLE;
+   ctrl |= INTEL_EDP_HDR_TCON_2084_DECODE_ENABLE;
+   ctrl |= INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE;
+   }
+
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
u32 pwm_level = intel_backlight_level_to_pwm(connector, level);
@@ -292,9 +294,11 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
struct intel_panel *panel = >panel;
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
struct drm_luminance_range_info *luminance_range =
>base.display_info.luminance_range;
int ret;
+   u8 buf[4];
 
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] SDR backlight is controlled 
through %s\n",
connector->base.base.id, connector->base.name,
@@ -318,11 +322,21 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
panel->backlight.min = 0;
}
 
+   buf[0] = connector->base.hdr_sink_metadata.hdmi_type1.max_cll & 0xFF;
+   buf[1] = (connector->base.hdr_sink_metadata.hdmi_type1.max_cll & 
0xFF00) >> 8;
+   buf[2] = connector->base.hdr_sink_metadata.hdmi_type1.max_fall & 0xFF;
+   buf[3] = (connector->base.hdr_sink_metadata.hdmi_type1.max_fall & 
0xFF00) >> 8;
+
+   ret = drm_dp_dpcd_write(_dp->aux, 
INTEL_EDP_HDR_CONTENT_LUMINANCE, buf,
+   sizeof(buf));
+   if (ret < 0)
+   drm_dbg_kms(>drm,
+   "Not able to write content luminence to DPCD 
register err:-%d\n", ret);
+
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
connector->base.base.id, connector->base.name,
panel->backlight.min, panel->backlight.max);
 
-
panel->backlight.level = intel_dp_aux_hdr_get_backlight(connector, 
pipe);
panel->backlight.enabled = panel->backlight.level != 0;
 
-- 
2.43.2



[PATCH 1/4] drm/i915/hdcp: Move intel_hdcp_gsc_message def away from header file

2024-03-05 Thread Suraj Kandpal
Move intel_hdcp_gsc_message definition into intel_hdcp_gsc.c
so that intel_hdcp_gsc_message can be redefined for xe as needed.

--v2
-Correct commit message to reflect what patch is actually doing [Arun]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
Acked-by: Jani Nikula 
---
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.c | 6 ++
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.h | 7 +--
 2 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
index 302bff75b06c..35823e1f65d6 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
@@ -13,6 +13,12 @@
 #include "intel_hdcp_gsc.h"
 #include "intel_hdcp_gsc_message.h"
 
+struct intel_hdcp_gsc_message {
+   struct i915_vma *vma;
+   void *hdcp_cmd_in;
+   void *hdcp_cmd_out;
+};
+
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915)
 {
return DISPLAY_VER(i915) >= 14;
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
index eba2057c5a9e..5f610df61cc9 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
@@ -10,12 +10,7 @@
 #include 
 
 struct drm_i915_private;
-
-struct intel_hdcp_gsc_message {
-   struct i915_vma *vma;
-   void *hdcp_cmd_in;
-   void *hdcp_cmd_out;
-};
+struct intel_hdcp_gsc_message;
 
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915);
 ssize_t intel_hdcp_gsc_msg_send(struct drm_i915_private *i915, u8 *msg_in,
-- 
2.43.2



[PATCH 2/4] drm/xe/hdcp: Use xe_device struct

2024-03-05 Thread Suraj Kandpal
Use xe_device struct instead of drm_i915_private so as to not
cause confusion and comply with Xe standards as drm_i915_private is
xe_device under the hood.

--v2
-Fix commit message [Daniele]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c | 15 ---
 1 file changed, 8 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c 
b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
index 0f11a39333e2..5d1d0054b578 100644
--- a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
+++ b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
@@ -3,30 +3,31 @@
  * Copyright 2023, Intel Corporation.
  */
 
-#include "i915_drv.h"
+#include 
 #include "intel_hdcp_gsc.h"
+#include "xe_device_types.h"
 
-bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915)
+bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 {
return true;
 }
 
-bool intel_hdcp_gsc_check_status(struct drm_i915_private *i915)
+bool intel_hdcp_gsc_check_status(struct xe_device *xe)
 {
return false;
 }
 
-int intel_hdcp_gsc_init(struct drm_i915_private *i915)
+int intel_hdcp_gsc_init(struct xe_device *xe)
 {
-   drm_info(>drm, "HDCP support not yet implemented\n");
+   drm_dbg_kms(>drm, "HDCP support not yet implemented\n");
return -ENODEV;
 }
 
-void intel_hdcp_gsc_fini(struct drm_i915_private *i915)
+void intel_hdcp_gsc_fini(struct xe_device *xe)
 {
 }
 
-ssize_t intel_hdcp_gsc_msg_send(struct drm_i915_private *i915, u8 *msg_in,
+ssize_t intel_hdcp_gsc_msg_send(struct xe_device *xe, u8 *msg_in,
size_t msg_in_len, u8 *msg_out,
size_t msg_out_len)
 {
-- 
2.43.2



[PATCH 4/4] drm/xe/hdcp: Enable HDCP for XE

2024-03-05 Thread Suraj Kandpal
Enable HDCP for Xe by defining functions which take care of
interaction of HDCP as a client with the GSC CS interface.
Add intel_hdcp_gsc_message to Makefile and add corresponding
changes to xe_hdcp_gsc.c to make it build.

--v2
-add kfree at appropriate place [Daniele]
-remove useless define [Daniele]
-move host session logic to xe_gsc_submit.c [Daniele]
-call xe_gsc_check_and_update_pending directly in an if condition
[Daniele]
-use xe_device instead of drm_i915_private [Daniele]

--v3
-use xe prefix for newly exposed function [Daniele]
-remove client specific defines from intel_gsc_mtl_header [Daniele]
-add missing kfree() [Daniele]
-have NULL check for hdcp_message in finish function [Daniele]
-dont have too many variable declarations in the same line [Daniele]

--v4
-don't point the hdcp_message structure in xe_device to anything
until it properly gets initialized [Daniele]

--v5
-Squash commits for buildability

--v6
-Order includes alphabetically [Lucas]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/xe/Makefile  |   1 +
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c | 202 ++-
 drivers/gpu/drm/xe/xe_gsc_submit.c   |  15 ++
 drivers/gpu/drm/xe/xe_gsc_submit.h   |   1 +
 4 files changed, 214 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/xe/Makefile b/drivers/gpu/drm/xe/Makefile
index c531210695db..2b654c908ff3 100644
--- a/drivers/gpu/drm/xe/Makefile
+++ b/drivers/gpu/drm/xe/Makefile
@@ -254,6 +254,7 @@ xe-$(CONFIG_DRM_XE_DISPLAY) += \
i915-display/intel_global_state.o \
i915-display/intel_gmbus.o \
i915-display/intel_hdcp.o \
+   i915-display/intel_hdcp_gsc_message.o \
i915-display/intel_hdmi.o \
i915-display/intel_hotplug.o \
i915-display/intel_hotplug_irq.o \
diff --git a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c 
b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
index 3af5a86db3aa..dcde1d0ac1f8 100644
--- a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
+++ b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
@@ -4,15 +4,32 @@
  */
 
 #include 
+#include 
+#include 
 
+#include "abi/gsc_command_header_abi.h"
 #include "intel_hdcp_gsc.h"
-#include "xe_device_types.h"
+#include "intel_hdcp_gsc_message.h"
+#include "xe_bo.h"
 #include "xe_device.h"
-#include "xe_gt.h"
+#include "xe_device_types.h"
 #include "xe_gsc_proxy.h"
+#include "xe_gsc_submit.h"
+#include "xe_gt.h"
+#include "xe_map.h"
 #include "xe_pm.h"
 #include "xe_uc_fw.h"
 
+#define HECI_MEADDRESS_HDCP 18
+
+struct intel_hdcp_gsc_message {
+   struct xe_bo *hdcp_bo;
+   u64 hdcp_cmd_in;
+   u64 hdcp_cmd_out;
+};
+
+#define HDCP_GSC_HEADER_SIZE sizeof(struct intel_gsc_mtl_header)
+
 bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 {
return true;
@@ -44,19 +61,194 @@ bool intel_hdcp_gsc_check_status(struct xe_device *xe)
return ret;
 }
 
+/*This function helps allocate memory for the command that we will send to gsc 
cs */
+static int intel_hdcp_gsc_initialize_message(struct xe_device *xe,
+struct intel_hdcp_gsc_message 
*hdcp_message)
+{
+   struct xe_bo *bo = NULL;
+   u64 cmd_in, cmd_out;
+   int ret = 0;
+
+   /* allocate object of two page for HDCP command memory and store it */
+   xe_device_mem_access_get(xe);
+   bo = xe_bo_create_pin_map(xe, xe_device_get_root_tile(xe), NULL, 
PAGE_SIZE * 2,
+ ttm_bo_type_kernel,
+ XE_BO_CREATE_SYSTEM_BIT |
+ XE_BO_CREATE_GGTT_BIT);
+
+   if (IS_ERR(bo)) {
+   drm_err(>drm, "Failed to allocate bo for HDCP streaming 
command!\n");
+   ret = PTR_ERR(bo);
+   goto out;
+   }
+
+   cmd_in = xe_bo_ggtt_addr(bo);
+   cmd_out = cmd_in + PAGE_SIZE;
+   xe_map_memset(xe, >vmap, 0, 0, bo->size);
+
+   hdcp_message->hdcp_bo = bo;
+   hdcp_message->hdcp_cmd_in = cmd_in;
+   hdcp_message->hdcp_cmd_out = cmd_out;
+out:
+   xe_device_mem_access_put(xe);
+   return ret;
+}
+
+static int intel_hdcp_gsc_hdcp2_init(struct xe_device *xe)
+{
+   struct intel_hdcp_gsc_message *hdcp_message;
+   int ret;
+
+   hdcp_message = kzalloc(sizeof(*hdcp_message), GFP_KERNEL);
+
+   if (!hdcp_message)
+   return -ENOMEM;
+
+   /*
+* NOTE: No need to lock the comp mutex here as it is already
+* going to be taken before this function called
+*/
+   ret = intel_hdcp_gsc_initialize_message(xe, hdcp_message);
+   if (ret) {
+   drm_err(>drm, "Could not initialize hdcp_message\n");
+   kfree(hdcp_message);
+   return ret;
+   }
+
+   xe->

[PATCH 3/4] drm/xe: Use gsc_proxy_init_done to check proxy status

2024-03-05 Thread Suraj Kandpal
Expose gsc_proxy_init_done so that we can check if gsc proxy has
been initialized or not.

--v2
-Check if GSC FW is enabled before taking forcewake ref [Daniele]

--v3
-Directly call proxy check function inside if condition

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
Reviewed-by: Daniele Ceraolo Spurio 
---
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c | 29 +++-
 drivers/gpu/drm/xe/xe_gsc_proxy.c|  4 ++--
 drivers/gpu/drm/xe/xe_gsc_proxy.h|  1 +
 3 files changed, 31 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c 
b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
index 5d1d0054b578..3af5a86db3aa 100644
--- a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
+++ b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
@@ -4,8 +4,14 @@
  */
 
 #include 
+
 #include "intel_hdcp_gsc.h"
 #include "xe_device_types.h"
+#include "xe_device.h"
+#include "xe_gt.h"
+#include "xe_gsc_proxy.h"
+#include "xe_pm.h"
+#include "xe_uc_fw.h"
 
 bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 {
@@ -14,7 +20,28 @@ bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 
 bool intel_hdcp_gsc_check_status(struct xe_device *xe)
 {
-   return false;
+   struct xe_tile *tile = xe_device_get_root_tile(xe);
+   struct xe_gt *gt = tile->media_gt;
+   bool ret = true;
+
+   if (!xe_uc_fw_is_enabled(>uc.gsc.fw))
+   return false;
+
+   xe_pm_runtime_get(xe);
+   if (xe_force_wake_get(gt_to_fw(gt), XE_FW_GSC)) {
+   drm_dbg_kms(>drm,
+   "failed to get forcewake to check proxy status\n");
+   ret = false;
+   goto out;
+   }
+
+   if (!xe_gsc_proxy_init_done(>uc.gsc))
+   ret = false;
+
+   xe_force_wake_put(gt_to_fw(gt), XE_FW_GSC);
+out:
+   xe_pm_runtime_put(xe);
+   return ret;
 }
 
 int intel_hdcp_gsc_init(struct xe_device *xe)
diff --git a/drivers/gpu/drm/xe/xe_gsc_proxy.c 
b/drivers/gpu/drm/xe/xe_gsc_proxy.c
index 309ef80e3b95..1ced6b4d4946 100644
--- a/drivers/gpu/drm/xe/xe_gsc_proxy.c
+++ b/drivers/gpu/drm/xe/xe_gsc_proxy.c
@@ -66,7 +66,7 @@ static inline struct xe_device *kdev_to_xe(struct device 
*kdev)
return dev_get_drvdata(kdev);
 }
 
-static bool gsc_proxy_init_done(struct xe_gsc *gsc)
+bool xe_gsc_proxy_init_done(struct xe_gsc *gsc)
 {
struct xe_gt *gt = gsc_to_gt(gsc);
u32 fwsts1 = xe_mmio_read32(gt, HECI_FWSTS1(MTL_GSC_HECI1_BASE));
@@ -528,7 +528,7 @@ int xe_gsc_proxy_start(struct xe_gsc *gsc)
if (err)
return err;
 
-   if (!gsc_proxy_init_done(gsc)) {
+   if (!xe_gsc_proxy_init_done(gsc)) {
xe_gt_err(gsc_to_gt(gsc), "GSC FW reports proxy init not 
completed\n");
return -EIO;
}
diff --git a/drivers/gpu/drm/xe/xe_gsc_proxy.h 
b/drivers/gpu/drm/xe/xe_gsc_proxy.h
index 908f9441f093..c511ade6b863 100644
--- a/drivers/gpu/drm/xe/xe_gsc_proxy.h
+++ b/drivers/gpu/drm/xe/xe_gsc_proxy.h
@@ -11,6 +11,7 @@
 struct xe_gsc;
 
 int xe_gsc_proxy_init(struct xe_gsc *gsc);
+bool xe_gsc_proxy_init_done(struct xe_gsc *gsc);
 void xe_gsc_proxy_remove(struct xe_gsc *gsc);
 int xe_gsc_proxy_start(struct xe_gsc *gsc);
 
-- 
2.43.2



[PATCH 1/4] drm/i915/hdcp: Move intel_hdcp_gsc_message def away from header file

2024-03-05 Thread Suraj Kandpal
Move intel_hdcp_gsc_message definition into intel_hdcp_gsc.c
so that intel_hdcp_gsc_message can be redefined for xe as needed.

--v2
-Correct commit message to reflect what patch is actually doing [Arun]

Signed-off-by: Suraj Kandpal 
Acked-by: Jani Nikula 
---
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.c | 6 ++
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.h | 7 +--
 2 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
index 302bff75b06c..35823e1f65d6 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
@@ -13,6 +13,12 @@
 #include "intel_hdcp_gsc.h"
 #include "intel_hdcp_gsc_message.h"
 
+struct intel_hdcp_gsc_message {
+   struct i915_vma *vma;
+   void *hdcp_cmd_in;
+   void *hdcp_cmd_out;
+};
+
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915)
 {
return DISPLAY_VER(i915) >= 14;
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
index eba2057c5a9e..5f610df61cc9 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
@@ -10,12 +10,7 @@
 #include 
 
 struct drm_i915_private;
-
-struct intel_hdcp_gsc_message {
-   struct i915_vma *vma;
-   void *hdcp_cmd_in;
-   void *hdcp_cmd_out;
-};
+struct intel_hdcp_gsc_message;
 
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915);
 ssize_t intel_hdcp_gsc_msg_send(struct drm_i915_private *i915, u8 *msg_in,
-- 
2.43.2



[PATCH 0/4] XE HDCP Enablement

2024-03-05 Thread Suraj Kandpal
This patch series enables HDCP on XE.
Mainly includes rewriting functions that were responsible for
sending hdcp messages via gsc cs.

Signed-off-by: Suraj Kandpal 
Acked-by: Lucas De Marchi 

Suraj Kandpal (4):
  drm/i915/hdcp: Move intel_hdcp_gsc_message def away from header file
  drm/xe/hdcp: Use xe_device struct
  drm/xe: Use gsc_proxy_init_done to check proxy status
  drm/xe/hdcp: Enable HDCP for XE

 drivers/gpu/drm/i915/display/intel_hdcp_gsc.c |   6 +
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.h |   7 +-
 drivers/gpu/drm/xe/Makefile   |   1 +
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c  | 240 +-
 drivers/gpu/drm/xe/xe_gsc_proxy.c |   4 +-
 drivers/gpu/drm/xe/xe_gsc_proxy.h |   1 +
 drivers/gpu/drm/xe/xe_gsc_submit.c|  15 ++
 drivers/gpu/drm/xe/xe_gsc_submit.h|   1 +
 8 files changed, 257 insertions(+), 18 deletions(-)

-- 
2.43.2



[PATCH] drm/i915/dp: Enable AUX based backlight for HDR

2024-03-05 Thread Suraj Kandpal
As of now whenerver HDR is switched on we use the PWM to change the
backlight as opposed to AUX based backlight changes in terms of nits.
This patch writes to the appropriate DPCD registers to enable aux
based backlight using values in nits.

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_dp_aux_backlight.c | 29 ++-
 1 file changed, 21 insertions(+), 8 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c 
b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
index 4f58efdc688a..14144347f13f 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_aux_backlight.c
@@ -40,11 +40,6 @@
 #include "intel_dp.h"
 #include "intel_dp_aux_backlight.h"
 
-/* TODO:
- * Implement HDR, right now we just implement the bare minimum to bring us 
back into SDR mode so we
- * can make people's backlights work in the mean time
- */
-
 /*
  * DP AUX registers for Intel's proprietary HDR backlight interface. We define
  * them here since we'll likely be the only driver to ever use these.
@@ -221,7 +216,7 @@ intel_dp_aux_hdr_set_backlight(const struct 
drm_connector_state *conn_state, u32
struct intel_connector *connector = 
to_intel_connector(conn_state->connector);
struct intel_panel *panel = >panel;
 
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
const u32 pwm_level = intel_backlight_level_to_pwm(connector, 
level);
@@ -251,8 +246,15 @@ intel_dp_aux_hdr_enable_backlight(const struct 
intel_crtc_state *crtc_state,
}
 
ctrl = old_ctrl;
-   if (panel->backlight.edp.intel.sdr_uses_aux) {
+   if (panel->backlight.edp.intel.sdr_uses_aux || 
conn_state->hdr_output_metadata) {
ctrl |= INTEL_EDP_HDR_TCON_BRIGHTNESS_AUX_ENABLE;
+
+   if (conn_state->hdr_output_metadata) {
+   ctrl |= INTEL_EDP_HDR_TCON_SEGMENTED_BACKLIGHT_ENABLE;
+   ctrl |= INTEL_EDP_HDR_TCON_2084_DECODE_ENABLE;
+   ctrl |= INTEL_EDP_HDR_TCON_2020_GAMUT_ENABLE;
+   }
+
intel_dp_aux_hdr_set_aux_backlight(conn_state, level);
} else {
u32 pwm_level = intel_backlight_level_to_pwm(connector, level);
@@ -292,9 +294,11 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
struct intel_panel *panel = >panel;
+   struct intel_dp *intel_dp = enc_to_intel_dp(connector->encoder);
struct drm_luminance_range_info *luminance_range =
>base.display_info.luminance_range;
int ret;
+   u8 buf[4];
 
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] SDR backlight is controlled 
through %s\n",
connector->base.base.id, connector->base.name,
@@ -318,11 +322,20 @@ intel_dp_aux_hdr_setup_backlight(struct intel_connector 
*connector, enum pipe pi
panel->backlight.min = 0;
}
 
+   buf[0] = panel->backlight.max & 0xFF;
+   buf[1] = (panel->backlight.max & 0xFF00) >> 8;
+   buf[2] = (connector->base.hdr_sink_metadata.hdmi_type1.max_fall & 0xFF) 
>> 16;
+   buf[3] = (connector->base.hdr_sink_metadata.hdmi_type1.max_fall & 
0xFF00) >> 24;
+
+   ret = drm_dp_dpcd_write(_dp->aux, 
INTEL_EDP_HDR_CONTENT_LUMINANCE, buf,
+   sizeof(buf) != sizeof(buf));
+   if (ret)
+   drm_dbg_kms(>drm, "Not able to write content luminence to 
DPCD register\n");
+
drm_dbg_kms(>drm, "[CONNECTOR:%d:%s] Using AUX HDR interface for 
backlight control (range %d..%d)\n",
connector->base.base.id, connector->base.name,
panel->backlight.min, panel->backlight.max);
 
-
panel->backlight.level = intel_dp_aux_hdr_get_backlight(connector, 
pipe);
panel->backlight.enabled = panel->backlight.level != 0;
 
-- 
2.43.2



[PATCH 3/4] drm/xe: Use gsc_proxy_init_done to check proxy status

2024-02-27 Thread Suraj Kandpal
Expose gsc_proxy_init_done so that we can check if gsc proxy has
been initialized or not.

--v2
-Check if GSC FW is enabled before taking forcewake ref [Daniele]

--v3
-Directly call forcewake get function inside if condition

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
Reviewed-by: Daniele Ceraolo Spurio 
---
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c | 29 +++-
 drivers/gpu/drm/xe/xe_gsc_proxy.c|  4 ++--
 drivers/gpu/drm/xe/xe_gsc_proxy.h|  1 +
 3 files changed, 31 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c 
b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
index 5d1d0054b578..3af5a86db3aa 100644
--- a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
+++ b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
@@ -4,8 +4,14 @@
  */
 
 #include 
+
 #include "intel_hdcp_gsc.h"
 #include "xe_device_types.h"
+#include "xe_device.h"
+#include "xe_gt.h"
+#include "xe_gsc_proxy.h"
+#include "xe_pm.h"
+#include "xe_uc_fw.h"
 
 bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 {
@@ -14,7 +20,28 @@ bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 
 bool intel_hdcp_gsc_check_status(struct xe_device *xe)
 {
-   return false;
+   struct xe_tile *tile = xe_device_get_root_tile(xe);
+   struct xe_gt *gt = tile->media_gt;
+   bool ret = true;
+
+   if (!xe_uc_fw_is_enabled(>uc.gsc.fw))
+   return false;
+
+   xe_pm_runtime_get(xe);
+   if (xe_force_wake_get(gt_to_fw(gt), XE_FW_GSC)) {
+   drm_dbg_kms(>drm,
+   "failed to get forcewake to check proxy status\n");
+   ret = false;
+   goto out;
+   }
+
+   if (!xe_gsc_proxy_init_done(>uc.gsc))
+   ret = false;
+
+   xe_force_wake_put(gt_to_fw(gt), XE_FW_GSC);
+out:
+   xe_pm_runtime_put(xe);
+   return ret;
 }
 
 int intel_hdcp_gsc_init(struct xe_device *xe)
diff --git a/drivers/gpu/drm/xe/xe_gsc_proxy.c 
b/drivers/gpu/drm/xe/xe_gsc_proxy.c
index 309ef80e3b95..1ced6b4d4946 100644
--- a/drivers/gpu/drm/xe/xe_gsc_proxy.c
+++ b/drivers/gpu/drm/xe/xe_gsc_proxy.c
@@ -66,7 +66,7 @@ static inline struct xe_device *kdev_to_xe(struct device 
*kdev)
return dev_get_drvdata(kdev);
 }
 
-static bool gsc_proxy_init_done(struct xe_gsc *gsc)
+bool xe_gsc_proxy_init_done(struct xe_gsc *gsc)
 {
struct xe_gt *gt = gsc_to_gt(gsc);
u32 fwsts1 = xe_mmio_read32(gt, HECI_FWSTS1(MTL_GSC_HECI1_BASE));
@@ -528,7 +528,7 @@ int xe_gsc_proxy_start(struct xe_gsc *gsc)
if (err)
return err;
 
-   if (!gsc_proxy_init_done(gsc)) {
+   if (!xe_gsc_proxy_init_done(gsc)) {
xe_gt_err(gsc_to_gt(gsc), "GSC FW reports proxy init not 
completed\n");
return -EIO;
}
diff --git a/drivers/gpu/drm/xe/xe_gsc_proxy.h 
b/drivers/gpu/drm/xe/xe_gsc_proxy.h
index 908f9441f093..c511ade6b863 100644
--- a/drivers/gpu/drm/xe/xe_gsc_proxy.h
+++ b/drivers/gpu/drm/xe/xe_gsc_proxy.h
@@ -11,6 +11,7 @@
 struct xe_gsc;
 
 int xe_gsc_proxy_init(struct xe_gsc *gsc);
+bool xe_gsc_proxy_init_done(struct xe_gsc *gsc);
 void xe_gsc_proxy_remove(struct xe_gsc *gsc);
 int xe_gsc_proxy_start(struct xe_gsc *gsc);
 
-- 
2.43.2



[PATCH 1/4] drm/i915/hdcp: Move intel_hdcp_gsc_message def away from header file

2024-02-26 Thread Suraj Kandpal
Move intel_hdcp_gsc_message definition into intel_hdcp_gsc.c
so that intel_hdcp_gsc_message can be redefined for xe as needed.

--v2
-Correct commit message to reflect what patch is actually doing [Arun]

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.c | 6 ++
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.h | 7 +--
 2 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
index 302bff75b06c..35823e1f65d6 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
@@ -13,6 +13,12 @@
 #include "intel_hdcp_gsc.h"
 #include "intel_hdcp_gsc_message.h"
 
+struct intel_hdcp_gsc_message {
+   struct i915_vma *vma;
+   void *hdcp_cmd_in;
+   void *hdcp_cmd_out;
+};
+
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915)
 {
return DISPLAY_VER(i915) >= 14;
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
index eba2057c5a9e..5f610df61cc9 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
@@ -10,12 +10,7 @@
 #include 
 
 struct drm_i915_private;
-
-struct intel_hdcp_gsc_message {
-   struct i915_vma *vma;
-   void *hdcp_cmd_in;
-   void *hdcp_cmd_out;
-};
+struct intel_hdcp_gsc_message;
 
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915);
 ssize_t intel_hdcp_gsc_msg_send(struct drm_i915_private *i915, u8 *msg_in,
-- 
2.43.2



[PATCH 1/4] drm/i915/hdcp: Move intel_hdcp_gsc_message def away from header file

2024-02-26 Thread Suraj Kandpal
Move intel_hdcp_gsc_message definition into intel_hdcp_gsc.h
so that intel_hdcp_gsc_message can be redefined for xe as needed.

--v2
-Correct commit message to reflect what patch is actually doing [Arun]

Signed-off-by: Suraj Kandpal 
---
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.c | 6 ++
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.h | 7 +--
 2 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
index 302bff75b06c..35823e1f65d6 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.c
@@ -13,6 +13,12 @@
 #include "intel_hdcp_gsc.h"
 #include "intel_hdcp_gsc_message.h"
 
+struct intel_hdcp_gsc_message {
+   struct i915_vma *vma;
+   void *hdcp_cmd_in;
+   void *hdcp_cmd_out;
+};
+
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915)
 {
return DISPLAY_VER(i915) >= 14;
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h 
b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
index eba2057c5a9e..5f610df61cc9 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
+++ b/drivers/gpu/drm/i915/display/intel_hdcp_gsc.h
@@ -10,12 +10,7 @@
 #include 
 
 struct drm_i915_private;
-
-struct intel_hdcp_gsc_message {
-   struct i915_vma *vma;
-   void *hdcp_cmd_in;
-   void *hdcp_cmd_out;
-};
+struct intel_hdcp_gsc_message;
 
 bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915);
 ssize_t intel_hdcp_gsc_msg_send(struct drm_i915_private *i915, u8 *msg_in,
-- 
2.43.2



[PATCH 4/4] drm/xe/hdcp: Enable HDCP for XE

2024-02-26 Thread Suraj Kandpal
Enable HDCP for Xe by defining functions which take care of
interaction of HDCP as a client with the GSC CS interface.
Add intel_hdcp_gsc_message to Makefile and add corresponding
changes to xe_hdcp_gsc.c to make it build.

--v2
-add kfree at appropriate place [Daniele]
-remove useless define [Daniele]
-move host session logic to xe_gsc_submit.c [Daniele]
-call xe_gsc_check_and_update_pending directly in an if condition
[Daniele]
-use xe_device instead of drm_i915_private [Daniele]

--v3
-use xe prefix for newly exposed function [Daniele]
-remove client specific defines from intel_gsc_mtl_header [Daniele]
-add missing kfree() [Daniele]
-have NULL check for hdcp_message in finish function [Daniele]
-dont have too many variable declarations in the same line [Daniele]

--v4
-don't point the hdcp_message structure in xe_device to anything
until it properly gets initialized [Daniele]

--v5
-Squash commits for buildability

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/xe/Makefile  |   1 +
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c | 198 ++-
 drivers/gpu/drm/xe/xe_gsc_submit.c   |  15 ++
 drivers/gpu/drm/xe/xe_gsc_submit.h   |   1 +
 4 files changed, 212 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/xe/Makefile b/drivers/gpu/drm/xe/Makefile
index c531210695db..2b654c908ff3 100644
--- a/drivers/gpu/drm/xe/Makefile
+++ b/drivers/gpu/drm/xe/Makefile
@@ -254,6 +254,7 @@ xe-$(CONFIG_DRM_XE_DISPLAY) += \
i915-display/intel_global_state.o \
i915-display/intel_gmbus.o \
i915-display/intel_hdcp.o \
+   i915-display/intel_hdcp_gsc_message.o \
i915-display/intel_hdmi.o \
i915-display/intel_hotplug.o \
i915-display/intel_hotplug_irq.o \
diff --git a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c 
b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
index 0de06e0373ef..bb3bddcd5747 100644
--- a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
+++ b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
@@ -4,14 +4,31 @@
  */
 
 #include 
+#include 
+#include 
 
+#include "abi/gsc_command_header_abi.h"
 #include "intel_hdcp_gsc.h"
+#include "intel_hdcp_gsc_message.h"
 #include "xe_device_types.h"
 #include "xe_device.h"
 #include "xe_gt.h"
 #include "xe_gsc_proxy.h"
 #include "xe_pm.h"
 #include "xe_uc_fw.h"
+#include "xe_bo.h"
+#include "xe_map.h"
+#include "xe_gsc_submit.h"
+
+#define HECI_MEADDRESS_HDCP 18
+
+struct intel_hdcp_gsc_message {
+   struct xe_bo *hdcp_bo;
+   u64 hdcp_cmd_in;
+   u64 hdcp_cmd_out;
+};
+
+#define HDCP_GSC_HEADER_SIZE sizeof(struct intel_gsc_mtl_header)
 
 bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 {
@@ -45,19 +62,194 @@ bool intel_hdcp_gsc_check_status(struct xe_device *xe)
return ret;
 }
 
+/*This function helps allocate memory for the command that we will send to gsc 
cs */
+static int intel_hdcp_gsc_initialize_message(struct xe_device *xe,
+struct intel_hdcp_gsc_message 
*hdcp_message)
+{
+   struct xe_bo *bo = NULL;
+   u64 cmd_in, cmd_out;
+   int ret = 0;
+
+   /* allocate object of two page for HDCP command memory and store it */
+   xe_device_mem_access_get(xe);
+   bo = xe_bo_create_pin_map(xe, xe_device_get_root_tile(xe), NULL, 
PAGE_SIZE * 2,
+ ttm_bo_type_kernel,
+ XE_BO_CREATE_SYSTEM_BIT |
+ XE_BO_CREATE_GGTT_BIT);
+
+   if (IS_ERR(bo)) {
+   drm_err(>drm, "Failed to allocate bo for HDCP streaming 
command!\n");
+   ret = PTR_ERR(bo);
+   goto out;
+   }
+
+   cmd_in = xe_bo_ggtt_addr(bo);
+   cmd_out = cmd_in + PAGE_SIZE;
+   xe_map_memset(xe, >vmap, 0, 0, bo->size);
+
+   hdcp_message->hdcp_bo = bo;
+   hdcp_message->hdcp_cmd_in = cmd_in;
+   hdcp_message->hdcp_cmd_out = cmd_out;
+out:
+   xe_device_mem_access_put(xe);
+   return ret;
+}
+
+static int intel_hdcp_gsc_hdcp2_init(struct xe_device *xe)
+{
+   struct intel_hdcp_gsc_message *hdcp_message;
+   int ret;
+
+   hdcp_message = kzalloc(sizeof(*hdcp_message), GFP_KERNEL);
+
+   if (!hdcp_message)
+   return -ENOMEM;
+
+   /*
+* NOTE: No need to lock the comp mutex here as it is already
+* going to be taken before this function called
+*/
+   ret = intel_hdcp_gsc_initialize_message(xe, hdcp_message);
+   if (ret) {
+   drm_err(>drm, "Could not initialize hdcp_message\n");
+   kfree(hdcp_message);
+   return ret;
+   }
+
+   xe->display.hdcp.hdcp_message = hdcp_message;
+   return ret;
+}
+
+static const struct i915_hdcp_ops gsc_hdcp_ops = {
+   .initiate_hdcp2_session = intel_hdcp_gsc

[PATCH 2/4] drm/xe/hdcp: Use xe_device struct

2024-02-26 Thread Suraj Kandpal
Use xe_device struct instead of drm_i915_private so as to not
cause confusion and comply with Xe standards as drm_i915_private is
xe_device under the hood.

--v2
-Fix commit message [Daniele]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
---
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c | 15 ---
 1 file changed, 8 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c 
b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
index 0f11a39333e2..5d1d0054b578 100644
--- a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
+++ b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
@@ -3,30 +3,31 @@
  * Copyright 2023, Intel Corporation.
  */
 
-#include "i915_drv.h"
+#include 
 #include "intel_hdcp_gsc.h"
+#include "xe_device_types.h"
 
-bool intel_hdcp_gsc_cs_required(struct drm_i915_private *i915)
+bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 {
return true;
 }
 
-bool intel_hdcp_gsc_check_status(struct drm_i915_private *i915)
+bool intel_hdcp_gsc_check_status(struct xe_device *xe)
 {
return false;
 }
 
-int intel_hdcp_gsc_init(struct drm_i915_private *i915)
+int intel_hdcp_gsc_init(struct xe_device *xe)
 {
-   drm_info(>drm, "HDCP support not yet implemented\n");
+   drm_dbg_kms(>drm, "HDCP support not yet implemented\n");
return -ENODEV;
 }
 
-void intel_hdcp_gsc_fini(struct drm_i915_private *i915)
+void intel_hdcp_gsc_fini(struct xe_device *xe)
 {
 }
 
-ssize_t intel_hdcp_gsc_msg_send(struct drm_i915_private *i915, u8 *msg_in,
+ssize_t intel_hdcp_gsc_msg_send(struct xe_device *xe, u8 *msg_in,
size_t msg_in_len, u8 *msg_out,
size_t msg_out_len)
 {
-- 
2.43.2



[PATCH 3/4] drm/xe: Use gsc_proxy_init_done to check proxy status

2024-02-26 Thread Suraj Kandpal
Expose gsc_proxy_init_done so that we can check if gsc proxy has
been initialized or not.

--v2
-Check if GSC FW is enabled before taking forcewake ref [Daniele]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Arun R Murthy 
Reviewed-by: Daniele Ceraolo Spurio 
---
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c | 30 +++-
 drivers/gpu/drm/xe/xe_gsc_proxy.c|  4 ++--
 drivers/gpu/drm/xe/xe_gsc_proxy.h|  1 +
 3 files changed, 32 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c 
b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
index 5d1d0054b578..0de06e0373ef 100644
--- a/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
+++ b/drivers/gpu/drm/xe/display/xe_hdcp_gsc.c
@@ -4,8 +4,14 @@
  */
 
 #include 
+
 #include "intel_hdcp_gsc.h"
 #include "xe_device_types.h"
+#include "xe_device.h"
+#include "xe_gt.h"
+#include "xe_gsc_proxy.h"
+#include "xe_pm.h"
+#include "xe_uc_fw.h"
 
 bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 {
@@ -14,7 +20,29 @@ bool intel_hdcp_gsc_cs_required(struct xe_device *xe)
 
 bool intel_hdcp_gsc_check_status(struct xe_device *xe)
 {
-   return false;
+   struct xe_tile *tile = xe_device_get_root_tile(xe);
+   struct xe_gt *gt = tile->media_gt;
+   bool ret = true;
+
+   if (!xe_uc_fw_is_enabled(>uc.gsc.fw))
+   return false;
+
+   xe_pm_runtime_get(xe);
+   ret = xe_force_wake_get(gt_to_fw(gt), XE_FW_GSC);
+   if (ret) {
+   drm_dbg_kms(>drm,
+   "failed to get forcewake to check proxy status\n");
+   ret = false;
+   goto out;
+   }
+
+   if (!xe_gsc_proxy_init_done(>uc.gsc))
+   ret = false;
+
+   xe_force_wake_put(gt_to_fw(gt), XE_FW_GSC);
+out:
+   xe_pm_runtime_put(xe);
+   return ret;
 }
 
 int intel_hdcp_gsc_init(struct xe_device *xe)
diff --git a/drivers/gpu/drm/xe/xe_gsc_proxy.c 
b/drivers/gpu/drm/xe/xe_gsc_proxy.c
index 309ef80e3b95..1ced6b4d4946 100644
--- a/drivers/gpu/drm/xe/xe_gsc_proxy.c
+++ b/drivers/gpu/drm/xe/xe_gsc_proxy.c
@@ -66,7 +66,7 @@ static inline struct xe_device *kdev_to_xe(struct device 
*kdev)
return dev_get_drvdata(kdev);
 }
 
-static bool gsc_proxy_init_done(struct xe_gsc *gsc)
+bool xe_gsc_proxy_init_done(struct xe_gsc *gsc)
 {
struct xe_gt *gt = gsc_to_gt(gsc);
u32 fwsts1 = xe_mmio_read32(gt, HECI_FWSTS1(MTL_GSC_HECI1_BASE));
@@ -528,7 +528,7 @@ int xe_gsc_proxy_start(struct xe_gsc *gsc)
if (err)
return err;
 
-   if (!gsc_proxy_init_done(gsc)) {
+   if (!xe_gsc_proxy_init_done(gsc)) {
xe_gt_err(gsc_to_gt(gsc), "GSC FW reports proxy init not 
completed\n");
return -EIO;
}
diff --git a/drivers/gpu/drm/xe/xe_gsc_proxy.h 
b/drivers/gpu/drm/xe/xe_gsc_proxy.h
index 908f9441f093..c511ade6b863 100644
--- a/drivers/gpu/drm/xe/xe_gsc_proxy.h
+++ b/drivers/gpu/drm/xe/xe_gsc_proxy.h
@@ -11,6 +11,7 @@
 struct xe_gsc;
 
 int xe_gsc_proxy_init(struct xe_gsc *gsc);
+bool xe_gsc_proxy_init_done(struct xe_gsc *gsc);
 void xe_gsc_proxy_remove(struct xe_gsc *gsc);
 int xe_gsc_proxy_start(struct xe_gsc *gsc);
 
-- 
2.43.2



[PATCH 0/4] XE HDCP Enablement

2024-02-26 Thread Suraj Kandpal
This patch series enables HDCP on XE.
Mainly includes rewriting functions that were responsible for
sending hdcp messages via gsc cs.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (4):
  drm/i915/hdcp: Move intel_hdcp_gsc_message def away from header file
  drm/xe/hdcp: Use xe_device struct
  drm/xe: Use gsc_proxy_init_done to check proxy status
  drm/xe/hdcp: Enable HDCP for XE

 drivers/gpu/drm/i915/display/intel_hdcp_gsc.c |   6 +
 drivers/gpu/drm/i915/display/intel_hdcp_gsc.h |   7 +-
 drivers/gpu/drm/xe/Makefile   |   1 +
 drivers/gpu/drm/xe/display/xe_hdcp_gsc.c  | 241 +-
 drivers/gpu/drm/xe/xe_gsc_proxy.c |   4 +-
 drivers/gpu/drm/xe/xe_gsc_proxy.h |   1 +
 drivers/gpu/drm/xe/xe_gsc_submit.c|  15 ++
 drivers/gpu/drm/xe/xe_gsc_submit.h|   1 +
 8 files changed, 258 insertions(+), 18 deletions(-)

-- 
2.43.2



[PATCH 5/5] drm/i915/hdcp: Read Rxcaps for robustibility

2024-02-25 Thread Suraj Kandpal
We see some monitors and docks report incorrect hdcp version
and capability in first few reads so we read rx_caps three times
before we conclude the monitor's or docks HDCP capability

--v2
-Add comment to justify the 3 time read loop for hdcp capability[Ankit]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 29 ++--
 1 file changed, 20 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 99220f970039..b98a87883fef 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -644,18 +644,29 @@ int _intel_dp_hdcp2_get_capability(struct drm_dp_aux *aux,
   bool *capable)
 {
u8 rx_caps[3];
-   int ret;
+   int ret, i;
 
*capable = false;
-   ret = drm_dp_dpcd_read(aux,
-  DP_HDCP_2_2_REG_RX_CAPS_OFFSET,
-  rx_caps, HDCP_2_2_RXCAPS_LEN);
-   if (ret != HDCP_2_2_RXCAPS_LEN)
-   return ret >= 0 ? -EIO : ret;
 
-   if (rx_caps[0] == HDCP_2_2_RX_CAPS_VERSION_VAL &&
-   HDCP_2_2_DP_HDCP_CAPABLE(rx_caps[2]))
-   *capable = true;
+   /*
+* Some HDCP monitors act really shady by not giving the correct hdcp
+* capability on the first rx_caps read and usually take an extra read
+* to give the capability. We read rx_caps three times before we
+* declare a monitor not capable of HDCP 2.2.
+*/
+   for (i = 0; i < 3; i++) {
+   ret = drm_dp_dpcd_read(aux,
+  DP_HDCP_2_2_REG_RX_CAPS_OFFSET,
+  rx_caps, HDCP_2_2_RXCAPS_LEN);
+   if (ret != HDCP_2_2_RXCAPS_LEN)
+   return ret >= 0 ? -EIO : ret;
+
+   if (rx_caps[0] == HDCP_2_2_RX_CAPS_VERSION_VAL &&
+   HDCP_2_2_DP_HDCP_CAPABLE(rx_caps[2])) {
+   *capable = true;
+   break;
+   }
+   }
 
return 0;
 }
-- 
2.43.2



[PATCH 3/5] drm/i915/hdcp: Don't enable HDCP1.4 directly from check_link

2024-02-25 Thread Suraj Kandpal
Whenever LIC fails instead of moving from ENABLED to DESIRED
CP property we directly enable HDCP1.4 without informing the userspace
of this failure in link integrity check.
Now we will just update the value to DESIRED send the event to
userspace and then continue with the normal flow of HDCP enablement.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 12 +++-
 1 file changed, 3 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index 1023153ba9d4..321c6dd8dbf5 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -1088,15 +1088,9 @@ static int intel_hdcp_check_link(struct intel_connector 
*connector)
goto out;
}
 
-   ret = intel_hdcp1_enable(connector);
-   if (ret) {
-   drm_err(>drm, "Failed to enable hdcp (%d)\n", ret);
-   intel_hdcp_update_value(connector,
-   DRM_MODE_CONTENT_PROTECTION_DESIRED,
-   true);
-   goto out;
-   }
-
+   intel_hdcp_update_value(connector,
+   DRM_MODE_CONTENT_PROTECTION_DESIRED,
+   true);
 out:
mutex_unlock(_port->hdcp_mutex);
mutex_unlock(>mutex);
-- 
2.43.2



[PATCH 4/5] drm/i915/hdcp: Allocate stream id after HDCP AKE stage

2024-02-25 Thread Suraj Kandpal
Allocate stream id after HDCP AKE stage and not before so that it
can also be done during link integrity check.
Right now for MST scenarios LIC fails after hdcp enablement for this
reason.

--v2
-no need for else block in prepare_streams function [Ankit]

--v3
-remove intel_hdcp argument from required_content_stream function
[Ankit]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 137 ++
 1 file changed, 65 insertions(+), 72 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index 321c6dd8dbf5..9edac27bab26 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,7 +30,7 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
-static int intel_conn_to_vcpi(struct drm_atomic_state *state,
+static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
struct drm_dp_mst_topology_mgr *mgr;
@@ -43,7 +43,7 @@ static int intel_conn_to_vcpi(struct drm_atomic_state *state,
return 0;
mgr = connector->port->mgr;
 
-   drm_modeset_lock(>base.lock, state->acquire_ctx);
+   drm_modeset_lock(>base.lock, state->base.acquire_ctx);
mst_state = to_drm_dp_mst_topology_state(mgr->base.state);
payload = drm_atomic_get_mst_payload_state(mst_state, connector->port);
if (drm_WARN_ON(mgr->dev, !payload))
@@ -68,19 +68,51 @@ static int intel_conn_to_vcpi(struct drm_atomic_state 
*state,
  * DP MST topology. Though it is not compulsory, security fw should change its
  * policy to mark different content_types for different streams.
  */
-static void
-intel_hdcp_required_content_stream(struct intel_digital_port *dig_port)
+static int
+intel_hdcp_required_content_stream(struct intel_atomic_state *state,
+  struct intel_digital_port *dig_port)
 {
+   struct drm_connector_list_iter conn_iter;
+   struct intel_digital_port *conn_dig_port;
+   struct intel_connector *connector;
+   struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
struct hdcp_port_data *data = _port->hdcp_port_data;
bool enforce_type0 = false;
int k;
 
if (dig_port->hdcp_auth_status)
-   return;
+   return 0;
+
+   data->k = 0;
 
if (!dig_port->hdcp_mst_type1_capable)
enforce_type0 = true;
 
+   drm_connector_list_iter_begin(>drm, _iter);
+   for_each_intel_connector_iter(connector, _iter) {
+   if (connector->base.status == connector_status_disconnected)
+   continue;
+
+   if (!intel_encoder_is_mst(intel_attached_encoder(connector)))
+   continue;
+
+   conn_dig_port = intel_attached_dig_port(connector);
+   if (conn_dig_port != dig_port)
+   continue;
+
+   data->streams[data->k].stream_id =
+   intel_conn_to_vcpi(state, connector);
+   data->k++;
+
+   /* if there is only one active stream */
+   if (dig_port->dp.active_mst_links <= 1)
+   break;
+   }
+   drm_connector_list_iter_end(_iter);
+
+   if (drm_WARN_ON(>drm, data->k > INTEL_NUM_PIPES(i915) || data->k 
== 0))
+   return -EINVAL;
+
/*
 * Apply common protection level across all streams in DP MST Topology.
 * Use highest supported content type for all streams in DP MST 
Topology.
@@ -88,19 +120,25 @@ intel_hdcp_required_content_stream(struct 
intel_digital_port *dig_port)
for (k = 0; k < data->k; k++)
data->streams[k].stream_type =
enforce_type0 ? DRM_MODE_HDCP_CONTENT_TYPE0 : 
DRM_MODE_HDCP_CONTENT_TYPE1;
+
+   return 0;
 }
 
-static void intel_hdcp_prepare_streams(struct intel_connector *connector)
+static int intel_hdcp_prepare_streams(struct intel_atomic_state *state,
+ struct intel_connector *connector)
 {
struct intel_digital_port *dig_port = 
intel_attached_dig_port(connector);
struct hdcp_port_data *data = _port->hdcp_port_data;
struct intel_hdcp *hdcp = >hdcp;
 
-   if (!intel_encoder_is_mst(intel_attached_encoder(connector))) {
-   data->streams[0].stream_type = hdcp->content_type;
-   } else {
-   intel_hdcp_required_content_stream(dig_port);
-   }
+   if (intel_encoder_is_mst(intel_attached_encoder(connector)))
+   return intel_hdcp_required_content_stream(state, dig_port);
+
+   data->k = 1;
+   data->streams[0].stream_id = 0;
+   data->streams[0].stream_type = hdcp->conten

[PATCH 2/5] drm/i915/hdcp: Don't enable HDCP2.2 directly from check_link

2024-02-25 Thread Suraj Kandpal
Whenever LIC fails instead of moving from ENABLED to DESIRED
CP property we directly enable HDCP2.2 without informing the userspace
of this failure in link integrity check.
Now we will just update the value to DESIRED send the event to
userspace and then continue with the normal flow of HDCP enablement.

--v2
-Don't change the function prototype in this function [Ankit]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 25 ++-
 1 file changed, 2 insertions(+), 23 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index 801b8f0495bb..1023153ba9d4 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -2068,17 +2068,6 @@ static int intel_hdcp2_check_link(struct intel_connector 
*connector)
 
drm_dbg_kms(>drm,
"HDCP2.2 Downstream topology change\n");
-   ret = hdcp2_authenticate_repeater_topology(connector);
-   if (!ret) {
-   intel_hdcp_update_value(connector,
-   DRM_MODE_CONTENT_PROTECTION_ENABLED,
-   true);
-   goto out;
-   }
-   drm_dbg_kms(>drm,
-   "[CONNECTOR:%d:%s] Repeater topology auth 
failed.(%d)\n",
-   connector->base.base.id, connector->base.name,
-   ret);
} else {
drm_dbg_kms(>drm,
"[CONNECTOR:%d:%s] HDCP2.2 link failed, retrying 
auth\n",
@@ -2095,18 +2084,8 @@ static int intel_hdcp2_check_link(struct intel_connector 
*connector)
goto out;
}
 
-   ret = _intel_hdcp2_enable(connector);
-   if (ret) {
-   drm_dbg_kms(>drm,
-   "[CONNECTOR:%d:%s] Failed to enable hdcp2.2 (%d)\n",
-   connector->base.base.id, connector->base.name,
-   ret);
-   intel_hdcp_update_value(connector,
-   DRM_MODE_CONTENT_PROTECTION_DESIRED,
-   true);
-   goto out;
-   }
-
+   intel_hdcp_update_value(connector,
+   DRM_MODE_CONTENT_PROTECTION_DESIRED, true);
 out:
mutex_unlock(_port->hdcp_mutex);
mutex_unlock(>mutex);
-- 
2.43.2



[PATCH 1/5] drm/i915/hdcp: Extract hdcp structure from correct connector

2024-02-25 Thread Suraj Kandpal
Currently intel_hdcp is not being extracted from primary connector
this patch fixes that.

Fixes: 524240b231ea ("drm/i915/hdcp: Propagate aux info in DP HDCP functions")
Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 7 +--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 16ed489e09ec..99220f970039 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -395,7 +395,9 @@ intel_dp_hdcp2_wait_for_msg(struct intel_connector 
*connector,
const struct hdcp2_dp_msg_data *hdcp2_msg_data)
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
-   struct intel_hdcp *hdcp = >hdcp;
+   struct intel_digital_port *dig_port = 
intel_attached_dig_port(connector);
+   struct intel_dp *dp = _port->dp;
+   struct intel_hdcp *hdcp = >attached_connector->hdcp;
u8 msg_id = hdcp2_msg_data->msg_id;
int ret, timeout;
bool msg_ready = false;
@@ -511,8 +513,9 @@ int intel_dp_hdcp2_read_msg(struct intel_connector 
*connector,
 {
struct intel_digital_port *dig_port = 
intel_attached_dig_port(connector);
struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
-   struct intel_hdcp *hdcp = >hdcp;
struct drm_dp_aux *aux = _port->dp.aux;
+   struct intel_dp *dp = _port->dp;
+   struct intel_hdcp *hdcp = >attached_connector->hdcp;
unsigned int offset;
u8 *byte = buf;
ssize_t ret, bytes_to_recv, len;
-- 
2.43.2



[PATCH 0/5] HDCP MST Type1 fixes

2024-02-25 Thread Suraj Kandpal
We were seeing a blank screen whenever Type1 content was played.
This was due to extra timing which was taken as we had moved to
remote read and writes previously for MST scenario, which in turn
was done as we were not able to do direct read and writes to the
immediate downstream device.
The correct flow should be that we talk only to the immediate
downstream device and the rest needs to be taken care by that device.
With this patch series we move back to direct reads and writes,
fix the fastset setting because of which direct reads and writes to
HDCP related DPCD register stopped working, derive hdcp structure
correctly and increase robustability if rxcaps HDCP capability
reporting.
Rebased on latest commits.

Signed-off-by: Suraj Kandpal 

Suraj Kandpal (5):
  drm/i915/hdcp: Extract hdcp structure from correct connector
  drm/i915/hdcp: Don't enable HDCP2.2 directly from check_link
  drm/i915/hdcp: Don't enable HDCP1.4 directly from check_link
  drm/i915/hdcp: Allocate stream id after HDCP AKE stage
  drm/i915/hdcp: Read Rxcaps for robustibility

 drivers/gpu/drm/i915/display/intel_dp_hdcp.c |  36 ++--
 drivers/gpu/drm/i915/display/intel_hdcp.c| 174 ---
 2 files changed, 95 insertions(+), 115 deletions(-)

-- 
2.43.2



[PATCH 06/13] drm/i915/hdcp: Add new remote capability check shim function

2024-02-25 Thread Suraj Kandpal
Create a remote HDCP capability shim function which can read the
remote monitor HDCP capability when in MST configuration.

--v2
-Add an assertion to make sure only mst encoder call this remote_cap
function [Ankit]

--v3
-rename remote_hdcp_cap to remote_hdcp_capability [Jani]

--v4
-fix hdcp2_prerequisite check condition
-Move intel_dp_hdcp_get_remote_capability to dp_mst shim instead of
having it in dp shim [Ankit]

Signed-off-by: Suraj Kandpal 
---
 .../drm/i915/display/intel_display_types.h|  4 +++
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c  | 27 +++
 drivers/gpu/drm/i915/display/intel_hdcp.c | 16 +++
 drivers/gpu/drm/i915/display/intel_hdcp.h |  3 +++
 4 files changed, 50 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index b6f86129c0bc..8ce986fadd9a 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -531,6 +531,10 @@ struct intel_hdcp_shim {
/* HDCP2.2 Link Integrity Check */
int (*check_2_2_link)(struct intel_digital_port *dig_port,
  struct intel_connector *connector);
+
+   /* HDCP remote sink cap */
+   int (*get_remote_hdcp_capability)(struct intel_connector *connector,
+ bool *hdcp_capable, bool 
*hdcp2_capable);
 };
 
 struct intel_hdcp {
diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index bf90e9024feb..eab6e9fab4e6 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -672,6 +672,32 @@ int intel_dp_hdcp2_get_capability(struct intel_connector 
*connector,
return _intel_dp_hdcp2_get_capability(aux, capable);
 }
 
+static
+int intel_dp_hdcp_get_remote_capability(struct intel_connector *connector,
+   bool *hdcp_capable,
+   bool *hdcp2_capable)
+{
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   struct drm_dp_aux *aux = >port->aux;
+   u8 bcaps;
+   int ret;
+
+   if (!intel_encoder_is_mst(connector->encoder))
+   return -EINVAL;
+
+   ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
+   if (ret)
+   return ret;
+
+   ret = intel_dp_hdcp_read_bcaps(aux, i915, );
+   if (ret)
+   return ret;
+
+   *hdcp_capable = bcaps & DP_BCAPS_HDCP_CAPABLE;
+
+   return 0;
+}
+
 static const struct intel_hdcp_shim intel_dp_hdcp_shim = {
.write_an_aksv = intel_dp_hdcp_write_an_aksv,
.read_bksv = intel_dp_hdcp_read_bksv,
@@ -820,6 +846,7 @@ static const struct intel_hdcp_shim intel_dp_mst_hdcp_shim 
= {
.stream_2_2_encryption = intel_dp_mst_hdcp2_stream_encryption,
.check_2_2_link = intel_dp_mst_hdcp2_check_link,
.hdcp_2_2_get_capability = intel_dp_hdcp2_get_capability,
+   .get_remote_hdcp_capability = intel_dp_hdcp_get_remote_capability,
.protocol = HDCP_PROTOCOL_DP,
 };
 
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index c1a32f9f1199..801b8f0495bb 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -205,6 +205,22 @@ bool intel_hdcp2_get_capability(struct intel_connector 
*connector)
return capable;
 }
 
+void intel_hdcp_get_remote_capability(struct intel_connector *connector,
+ bool *hdcp_capable,
+ bool *hdcp2_capable)
+{
+   struct intel_hdcp *hdcp = >hdcp;
+
+   if (!hdcp->shim->get_remote_hdcp_capability)
+   return;
+
+   hdcp->shim->get_remote_hdcp_capability(connector, hdcp_capable,
+  hdcp2_capable);
+
+   if (!intel_hdcp2_prerequisite(connector))
+   *hdcp2_capable = false;
+}
+
 static bool intel_hdcp_in_use(struct drm_i915_private *i915,
  enum transcoder cpu_transcoder, enum port port)
 {
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.h 
b/drivers/gpu/drm/i915/display/intel_hdcp.h
index aeefb3c13d2c..477f2d2bb120 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.h
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.h
@@ -40,6 +40,9 @@ void intel_hdcp_update_pipe(struct intel_atomic_state *state,
 bool is_hdcp_supported(struct drm_i915_private *i915, enum port port);
 bool intel_hdcp_get_capability(struct intel_connector *connector);
 bool intel_hdcp2_get_capability(struct intel_connector *connector);
+void intel_hdcp_get_remote_capability(struct intel_connector *connector,
+ bool *hdcp_capable,
+ bool *hdcp2_capable);
 void intel_hdcp_component_init(struct

[PATCH 12/13] drm/i915/hdcp: Allocate stream id after HDCP AKE stage

2024-02-23 Thread Suraj Kandpal
Allocate stream id after HDCP AKE stage and not before so that it
can also be done during link integrity check.
Right now for MST scenarios LIC fails after hdcp enablement for this
reason.

--v2
-no need for else block in prepare_streams function [Ankit]

--v3
-remove intel_hdcp argument from required_content_stream function
[Ankit]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 137 ++
 1 file changed, 65 insertions(+), 72 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index 321c6dd8dbf5..9edac27bab26 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -30,7 +30,7 @@
 #define KEY_LOAD_TRIES 5
 #define HDCP2_LC_RETRY_CNT 3
 
-static int intel_conn_to_vcpi(struct drm_atomic_state *state,
+static int intel_conn_to_vcpi(struct intel_atomic_state *state,
  struct intel_connector *connector)
 {
struct drm_dp_mst_topology_mgr *mgr;
@@ -43,7 +43,7 @@ static int intel_conn_to_vcpi(struct drm_atomic_state *state,
return 0;
mgr = connector->port->mgr;
 
-   drm_modeset_lock(>base.lock, state->acquire_ctx);
+   drm_modeset_lock(>base.lock, state->base.acquire_ctx);
mst_state = to_drm_dp_mst_topology_state(mgr->base.state);
payload = drm_atomic_get_mst_payload_state(mst_state, connector->port);
if (drm_WARN_ON(mgr->dev, !payload))
@@ -68,19 +68,51 @@ static int intel_conn_to_vcpi(struct drm_atomic_state 
*state,
  * DP MST topology. Though it is not compulsory, security fw should change its
  * policy to mark different content_types for different streams.
  */
-static void
-intel_hdcp_required_content_stream(struct intel_digital_port *dig_port)
+static int
+intel_hdcp_required_content_stream(struct intel_atomic_state *state,
+  struct intel_digital_port *dig_port)
 {
+   struct drm_connector_list_iter conn_iter;
+   struct intel_digital_port *conn_dig_port;
+   struct intel_connector *connector;
+   struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
struct hdcp_port_data *data = _port->hdcp_port_data;
bool enforce_type0 = false;
int k;
 
if (dig_port->hdcp_auth_status)
-   return;
+   return 0;
+
+   data->k = 0;
 
if (!dig_port->hdcp_mst_type1_capable)
enforce_type0 = true;
 
+   drm_connector_list_iter_begin(>drm, _iter);
+   for_each_intel_connector_iter(connector, _iter) {
+   if (connector->base.status == connector_status_disconnected)
+   continue;
+
+   if (!intel_encoder_is_mst(intel_attached_encoder(connector)))
+   continue;
+
+   conn_dig_port = intel_attached_dig_port(connector);
+   if (conn_dig_port != dig_port)
+   continue;
+
+   data->streams[data->k].stream_id =
+   intel_conn_to_vcpi(state, connector);
+   data->k++;
+
+   /* if there is only one active stream */
+   if (dig_port->dp.active_mst_links <= 1)
+   break;
+   }
+   drm_connector_list_iter_end(_iter);
+
+   if (drm_WARN_ON(>drm, data->k > INTEL_NUM_PIPES(i915) || data->k 
== 0))
+   return -EINVAL;
+
/*
 * Apply common protection level across all streams in DP MST Topology.
 * Use highest supported content type for all streams in DP MST 
Topology.
@@ -88,19 +120,25 @@ intel_hdcp_required_content_stream(struct 
intel_digital_port *dig_port)
for (k = 0; k < data->k; k++)
data->streams[k].stream_type =
enforce_type0 ? DRM_MODE_HDCP_CONTENT_TYPE0 : 
DRM_MODE_HDCP_CONTENT_TYPE1;
+
+   return 0;
 }
 
-static void intel_hdcp_prepare_streams(struct intel_connector *connector)
+static int intel_hdcp_prepare_streams(struct intel_atomic_state *state,
+ struct intel_connector *connector)
 {
struct intel_digital_port *dig_port = 
intel_attached_dig_port(connector);
struct hdcp_port_data *data = _port->hdcp_port_data;
struct intel_hdcp *hdcp = >hdcp;
 
-   if (!intel_encoder_is_mst(intel_attached_encoder(connector))) {
-   data->streams[0].stream_type = hdcp->content_type;
-   } else {
-   intel_hdcp_required_content_stream(dig_port);
-   }
+   if (intel_encoder_is_mst(intel_attached_encoder(connector)))
+   return intel_hdcp_required_content_stream(state, dig_port);
+
+   data->k = 1;
+   data->streams[0].stream_id = 0;
+   data->streams[0].stream_type = hdcp->conten

[PATCH 07/13] drm/i915/hdcp: HDCP Capability for the downstream device

2024-02-23 Thread Suraj Kandpal
Currently we are only checking capability of remote device and not
immediate downstream device but during capability check we need are
concerned with only the HDCP capability of downstream device.
During i915_display_info reporting we need HDCP Capability for both
the monitors and downstream branch device if any this patch adds that.

--v2
-Use MST Hub HDCP version [Ankit]

--v3
-Redefined how we seprate remote and direct read to make sure HDMI
shim functions are not touched [Ankit]

--v4
- Fix the conditions so that hdcp_info with remote_req true is sent
only when encoder is mst [Ankit]

--v5
-No need to have the MST Hub version in i915_hdcp_sink_capability[Ankit]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 .../drm/i915/display/intel_display_debugfs.c  | 21 ++-
 1 file changed, 16 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_debugfs.c 
b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
index d8f1a23ac2b1..b99c024b0934 100644
--- a/drivers/gpu/drm/i915/display/intel_display_debugfs.c
+++ b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
@@ -188,7 +188,8 @@ static void intel_panel_info(struct seq_file *m,
 }
 
 static void intel_hdcp_info(struct seq_file *m,
-   struct intel_connector *intel_connector)
+   struct intel_connector *intel_connector,
+   bool remote_req)
 {
bool hdcp_cap, hdcp2_cap;
 
@@ -197,8 +198,14 @@ static void intel_hdcp_info(struct seq_file *m,
goto out;
}
 
-   hdcp_cap = intel_hdcp_get_capability(intel_connector);
-   hdcp2_cap = intel_hdcp2_get_capability(intel_connector);
+   if (remote_req) {
+   intel_hdcp_get_remote_capability(intel_connector,
+_cap,
+_cap);
+   } else {
+   hdcp_cap = intel_hdcp_get_capability(intel_connector);
+   hdcp2_cap = intel_hdcp2_get_capability(intel_connector);
+   }
 
if (hdcp_cap)
seq_puts(m, "HDCP1.4 ");
@@ -285,7 +292,11 @@ static void intel_connector_info(struct seq_file *m,
}
 
seq_puts(m, "\tHDCP version: ");
-   intel_hdcp_info(m, intel_connector);
+   if (intel_encoder_is_mst(encoder)) {
+   intel_hdcp_info(m, intel_connector, true);
+   seq_puts(m, "\tMST Hub HDCP version: ");
+   }
+   intel_hdcp_info(m, intel_connector, false);
 
seq_printf(m, "\tmax bpc: %u\n", connector->display_info.bpc);
 
@@ -1131,7 +1142,7 @@ static int i915_hdcp_sink_capability_show(struct seq_file 
*m, void *data)
 
seq_printf(m, "%s:%d HDCP version: ", connector->base.name,
   connector->base.base.id);
-   intel_hdcp_info(m, connector);
+   intel_hdcp_info(m, connector, false);
 
 out:
drm_modeset_unlock(>drm.mode_config.connection_mutex);
-- 
2.43.2



[PATCH 11/13] drm/i915/hdcp: Don't enable HDCP1.4 directly from check_link

2024-02-23 Thread Suraj Kandpal
Whenever LIC fails instead of moving from ENABLED to DESIRED
CP property we directly enable HDCP1.4 without informing the userspace
of this failure in link integrity check.
Now we will just update the value to DESIRED send the event to
userspace and then continue with the normal flow of HDCP enablement.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 12 +++-
 1 file changed, 3 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index 1023153ba9d4..321c6dd8dbf5 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -1088,15 +1088,9 @@ static int intel_hdcp_check_link(struct intel_connector 
*connector)
goto out;
}
 
-   ret = intel_hdcp1_enable(connector);
-   if (ret) {
-   drm_err(>drm, "Failed to enable hdcp (%d)\n", ret);
-   intel_hdcp_update_value(connector,
-   DRM_MODE_CONTENT_PROTECTION_DESIRED,
-   true);
-   goto out;
-   }
-
+   intel_hdcp_update_value(connector,
+   DRM_MODE_CONTENT_PROTECTION_DESIRED,
+   true);
 out:
mutex_unlock(_port->hdcp_mutex);
mutex_unlock(>mutex);
-- 
2.43.2



[PATCH 13/13] drm/i915/hdcp: Read Rxcaps for robustibility

2024-02-23 Thread Suraj Kandpal
We see some monitors and docks report incorrect hdcp version
and capability in first few reads so we read rx_caps three times
before we conclude the monitor's or docks HDCP capability

--v2
-Add comment to justify the 3 time read loop for hdcp capability[Ankit]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 29 ++--
 1 file changed, 20 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 99220f970039..b98a87883fef 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -644,18 +644,29 @@ int _intel_dp_hdcp2_get_capability(struct drm_dp_aux *aux,
   bool *capable)
 {
u8 rx_caps[3];
-   int ret;
+   int ret, i;
 
*capable = false;
-   ret = drm_dp_dpcd_read(aux,
-  DP_HDCP_2_2_REG_RX_CAPS_OFFSET,
-  rx_caps, HDCP_2_2_RXCAPS_LEN);
-   if (ret != HDCP_2_2_RXCAPS_LEN)
-   return ret >= 0 ? -EIO : ret;
 
-   if (rx_caps[0] == HDCP_2_2_RX_CAPS_VERSION_VAL &&
-   HDCP_2_2_DP_HDCP_CAPABLE(rx_caps[2]))
-   *capable = true;
+   /*
+* Some HDCP monitors act really shady by not giving the correct hdcp
+* capability on the first rx_caps read and usually take an extra read
+* to give the capability. We read rx_caps three times before we
+* declare a monitor not capable of HDCP 2.2.
+*/
+   for (i = 0; i < 3; i++) {
+   ret = drm_dp_dpcd_read(aux,
+  DP_HDCP_2_2_REG_RX_CAPS_OFFSET,
+  rx_caps, HDCP_2_2_RXCAPS_LEN);
+   if (ret != HDCP_2_2_RXCAPS_LEN)
+   return ret >= 0 ? -EIO : ret;
+
+   if (rx_caps[0] == HDCP_2_2_RX_CAPS_VERSION_VAL &&
+   HDCP_2_2_DP_HDCP_CAPABLE(rx_caps[2])) {
+   *capable = true;
+   break;
+   }
+   }
 
return 0;
 }
-- 
2.43.2



[PATCH 09/13] drm/i915/hdcp: Extract hdcp structure from correct connector

2024-02-23 Thread Suraj Kandpal
Currently intel_hdcp is not being extracted from primary connector
this patch fixes that.

Fixes: 524240b231ea ("drm/i915/hdcp: Propagate aux info in DP HDCP functions")
Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 7 +--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 16ed489e09ec..99220f970039 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -395,7 +395,9 @@ intel_dp_hdcp2_wait_for_msg(struct intel_connector 
*connector,
const struct hdcp2_dp_msg_data *hdcp2_msg_data)
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
-   struct intel_hdcp *hdcp = >hdcp;
+   struct intel_digital_port *dig_port = 
intel_attached_dig_port(connector);
+   struct intel_dp *dp = _port->dp;
+   struct intel_hdcp *hdcp = >attached_connector->hdcp;
u8 msg_id = hdcp2_msg_data->msg_id;
int ret, timeout;
bool msg_ready = false;
@@ -511,8 +513,9 @@ int intel_dp_hdcp2_read_msg(struct intel_connector 
*connector,
 {
struct intel_digital_port *dig_port = 
intel_attached_dig_port(connector);
struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
-   struct intel_hdcp *hdcp = >hdcp;
struct drm_dp_aux *aux = _port->dp.aux;
+   struct intel_dp *dp = _port->dp;
+   struct intel_hdcp *hdcp = >attached_connector->hdcp;
unsigned int offset;
u8 *byte = buf;
ssize_t ret, bytes_to_recv, len;
-- 
2.43.2



[PATCH 10/13] drm/i915/hdcp: Don't enable HDCP2.2 directly from check_link

2024-02-23 Thread Suraj Kandpal
Whenever LIC fails instead of moving from ENABLED to DESIRED
CP property we directly enable HDCP2.2 without informing the userspace
of this failure in link integrity check.
Now we will just update the value to DESIRED send the event to
userspace and then continue with the normal flow of HDCP enablement.

--v2
-Don't change the function prototype in this function [Ankit]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 25 ++-
 1 file changed, 2 insertions(+), 23 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index 801b8f0495bb..1023153ba9d4 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -2068,17 +2068,6 @@ static int intel_hdcp2_check_link(struct intel_connector 
*connector)
 
drm_dbg_kms(>drm,
"HDCP2.2 Downstream topology change\n");
-   ret = hdcp2_authenticate_repeater_topology(connector);
-   if (!ret) {
-   intel_hdcp_update_value(connector,
-   DRM_MODE_CONTENT_PROTECTION_ENABLED,
-   true);
-   goto out;
-   }
-   drm_dbg_kms(>drm,
-   "[CONNECTOR:%d:%s] Repeater topology auth 
failed.(%d)\n",
-   connector->base.base.id, connector->base.name,
-   ret);
} else {
drm_dbg_kms(>drm,
"[CONNECTOR:%d:%s] HDCP2.2 link failed, retrying 
auth\n",
@@ -2095,18 +2084,8 @@ static int intel_hdcp2_check_link(struct intel_connector 
*connector)
goto out;
}
 
-   ret = _intel_hdcp2_enable(connector);
-   if (ret) {
-   drm_dbg_kms(>drm,
-   "[CONNECTOR:%d:%s] Failed to enable hdcp2.2 (%d)\n",
-   connector->base.base.id, connector->base.name,
-   ret);
-   intel_hdcp_update_value(connector,
-   DRM_MODE_CONTENT_PROTECTION_DESIRED,
-   true);
-   goto out;
-   }
-
+   intel_hdcp_update_value(connector,
+   DRM_MODE_CONTENT_PROTECTION_DESIRED, true);
 out:
mutex_unlock(_port->hdcp_mutex);
mutex_unlock(>mutex);
-- 
2.43.2



[PATCH 08/13] drm/i915/hdcp: Remove additional timing for reading mst hdcp message

2024-02-23 Thread Suraj Kandpal
Now that we have moved back to direct reads the additional timing
is not required hence this can be removed.

--v2
-Add Fixes tag [Ankit]

Fixes: 3974f9c17bb9 ("drm/i915/hdcp: Adjust timeout for read in DPMST Scenario")
Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 9 ++---
 1 file changed, 2 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index eab6e9fab4e6..16ed489e09ec 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -555,13 +555,8 @@ int intel_dp_hdcp2_read_msg(struct intel_connector 
*connector,
 
/* Entire msg read timeout since initiate of msg read */
if (bytes_to_recv == size - 1 && 
hdcp2_msg_data->msg_read_timeout > 0) {
-   if (intel_encoder_is_mst(connector->encoder))
-   msg_end = ktime_add_ms(ktime_get_raw(),
-  
hdcp2_msg_data->msg_read_timeout *
-  
connector->port->parent->num_ports);
-   else
-   msg_end = ktime_add_ms(ktime_get_raw(),
-  
hdcp2_msg_data->msg_read_timeout);
+   msg_end = ktime_add_ms(ktime_get_raw(),
+  
hdcp2_msg_data->msg_read_timeout);
}
 
ret = drm_dp_dpcd_read(aux, offset,
-- 
2.43.2



[PATCH 05/13] drm/i915/hdcp: Rename hdcp capable functions

2024-02-23 Thread Suraj Kandpal
Rename hdcp_capable and hdcp_2_2_capable to hdcp_get_capability
and hdcp_2_2_get_capability to properly reflect what these functions
are doing.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 .../drm/i915/display/intel_display_debugfs.c  |  4 ++--
 .../drm/i915/display/intel_display_types.h|  8 +++
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c  | 22 +--
 drivers/gpu/drm/i915/display/intel_hdcp.c | 18 +++
 drivers/gpu/drm/i915/display/intel_hdcp.h |  4 ++--
 drivers/gpu/drm/i915/display/intel_hdmi.c |  6 ++---
 6 files changed, 31 insertions(+), 31 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_debugfs.c 
b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
index a962b48bcf13..d8f1a23ac2b1 100644
--- a/drivers/gpu/drm/i915/display/intel_display_debugfs.c
+++ b/drivers/gpu/drm/i915/display/intel_display_debugfs.c
@@ -197,8 +197,8 @@ static void intel_hdcp_info(struct seq_file *m,
goto out;
}
 
-   hdcp_cap = intel_hdcp_capable(intel_connector);
-   hdcp2_cap = intel_hdcp2_capable(intel_connector);
+   hdcp_cap = intel_hdcp_get_capability(intel_connector);
+   hdcp2_cap = intel_hdcp2_get_capability(intel_connector);
 
if (hdcp_cap)
seq_puts(m, "HDCP1.4 ");
diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index 578763e202c0..b6f86129c0bc 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -498,15 +498,15 @@ struct intel_hdcp_shim {
   struct intel_connector *connector);
 
/* Detects panel's hdcp capability. This is optional for HDMI. */
-   int (*hdcp_capable)(struct intel_digital_port *dig_port,
-   bool *hdcp_capable);
+   int (*hdcp_get_capability)(struct intel_digital_port *dig_port,
+  bool *hdcp_capable);
 
/* HDCP adaptation(DP/HDMI) required on the port */
enum hdcp_wired_protocol protocol;
 
/* Detects whether sink is HDCP2.2 capable */
-   int (*hdcp_2_2_capable)(struct intel_connector *connector,
-   bool *capable);
+   int (*hdcp_2_2_get_capability)(struct intel_connector *connector,
+  bool *capable);
 
/* Write HDCP2.2 messages */
int (*write_2_2_msg)(struct intel_connector *connector,
diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 5394391acbe1..bf90e9024feb 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -269,8 +269,8 @@ bool intel_dp_hdcp_check_link(struct intel_digital_port 
*dig_port,
 }
 
 static
-int intel_dp_hdcp_capable(struct intel_digital_port *dig_port,
- bool *hdcp_capable)
+int intel_dp_hdcp_get_capability(struct intel_digital_port *dig_port,
+bool *hdcp_capable)
 {
struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
ssize_t ret;
@@ -642,8 +642,8 @@ int intel_dp_hdcp2_check_link(struct intel_digital_port 
*dig_port,
 }
 
 static
-int _intel_dp_hdcp2_capable(struct drm_dp_aux *aux,
-   bool *capable)
+int _intel_dp_hdcp2_get_capability(struct drm_dp_aux *aux,
+  bool *capable)
 {
u8 rx_caps[3];
int ret;
@@ -663,13 +663,13 @@ int _intel_dp_hdcp2_capable(struct drm_dp_aux *aux,
 }
 
 static
-int intel_dp_hdcp2_capable(struct intel_connector *connector,
-  bool *capable)
+int intel_dp_hdcp2_get_capability(struct intel_connector *connector,
+ bool *capable)
 {
struct intel_digital_port *dig_port = 
intel_attached_dig_port(connector);
struct drm_dp_aux *aux = _port->dp.aux;
 
-   return _intel_dp_hdcp2_capable(aux, capable);
+   return _intel_dp_hdcp2_get_capability(aux, capable);
 }
 
 static const struct intel_hdcp_shim intel_dp_hdcp_shim = {
@@ -683,12 +683,12 @@ static const struct intel_hdcp_shim intel_dp_hdcp_shim = {
.read_v_prime_part = intel_dp_hdcp_read_v_prime_part,
.toggle_signalling = intel_dp_hdcp_toggle_signalling,
.check_link = intel_dp_hdcp_check_link,
-   .hdcp_capable = intel_dp_hdcp_capable,
+   .hdcp_get_capability = intel_dp_hdcp_get_capability,
.write_2_2_msg = intel_dp_hdcp2_write_msg,
.read_2_2_msg = intel_dp_hdcp2_read_msg,
.config_stream_type = intel_dp_hdcp2_config_stream_type,
.check_2_2_link = intel_dp_hdcp2_check_link,
-   .hdcp_2_2_capable = intel_dp_hdcp2_capable,
+   .hdcp_2_2_get_capability = intel_dp_hdcp2_get_capability,
.protocol = HDCP_PROTOCOL_DP,
 };
 
@@ -813,13 +813,13 @@ static const struct

[PATCH 02/13] drm/i915/hdcp: Move source hdcp2 checks into its own function

2024-02-23 Thread Suraj Kandpal
Move checks on the source side for HDCP2.2 into its own function
so that they can be used in the HDCP remote capability check
function.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_hdcp.c | 20 +---
 1 file changed, 17 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index c3e692e7f790..4593ac10e2fa 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -160,12 +160,14 @@ bool intel_hdcp_capable(struct intel_connector *connector)
return capable;
 }
 
-/* Is HDCP2.2 capable on Platform and Sink */
-bool intel_hdcp2_capable(struct intel_connector *connector)
+/*
+ * Check if the source has all the building blocks ready to make
+ * HDCP 2.2 work
+ */
+static bool intel_hdcp2_prerequisite(struct intel_connector *connector)
 {
struct drm_i915_private *i915 = to_i915(connector->base.dev);
struct intel_hdcp *hdcp = >hdcp;
-   bool capable = false;
 
/* I915 support for HDCP2.2 */
if (!hdcp->hdcp2_supported)
@@ -185,6 +187,18 @@ bool intel_hdcp2_capable(struct intel_connector *connector)
}
mutex_unlock(>display.hdcp.hdcp_mutex);
 
+   return true;
+}
+
+/* Is HDCP2.2 capable on Platform and Sink */
+bool intel_hdcp2_capable(struct intel_connector *connector)
+{
+   struct intel_hdcp *hdcp = >hdcp;
+   bool capable = false;
+
+   if (!intel_hdcp2_prerequisite(connector))
+   return false;
+
/* Sink's capability for HDCP2.2 */
hdcp->shim->hdcp_2_2_capable(connector, );
 
-- 
2.43.2



[PATCH 06/13] drm/i915/hdcp: Add new remote capability check shim function

2024-02-23 Thread Suraj Kandpal
Create a remote HDCP capability shim function which can read the
remote monitor HDCP capability when in MST configuration.

--v2
-Add an assertion to make sure only mst encoder call this remote_cap
function [Ankit]

--v3
-rename remote_hdcp_cap to remote_hdcp_capability [Jani]

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 .../drm/i915/display/intel_display_types.h|  4 +++
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c  | 27 +++
 drivers/gpu/drm/i915/display/intel_hdcp.c | 16 +++
 drivers/gpu/drm/i915/display/intel_hdcp.h |  3 +++
 4 files changed, 50 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h 
b/drivers/gpu/drm/i915/display/intel_display_types.h
index b6f86129c0bc..8ce986fadd9a 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -531,6 +531,10 @@ struct intel_hdcp_shim {
/* HDCP2.2 Link Integrity Check */
int (*check_2_2_link)(struct intel_digital_port *dig_port,
  struct intel_connector *connector);
+
+   /* HDCP remote sink cap */
+   int (*get_remote_hdcp_capability)(struct intel_connector *connector,
+ bool *hdcp_capable, bool 
*hdcp2_capable);
 };
 
 struct intel_hdcp {
diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index bf90e9024feb..eab6e9fab4e6 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -672,6 +672,32 @@ int intel_dp_hdcp2_get_capability(struct intel_connector 
*connector,
return _intel_dp_hdcp2_get_capability(aux, capable);
 }
 
+static
+int intel_dp_hdcp_get_remote_capability(struct intel_connector *connector,
+   bool *hdcp_capable,
+   bool *hdcp2_capable)
+{
+   struct drm_i915_private *i915 = to_i915(connector->base.dev);
+   struct drm_dp_aux *aux = >port->aux;
+   u8 bcaps;
+   int ret;
+
+   if (!intel_encoder_is_mst(connector->encoder))
+   return -EINVAL;
+
+   ret =  _intel_dp_hdcp2_get_capability(aux, hdcp2_capable);
+   if (ret)
+   return ret;
+
+   ret = intel_dp_hdcp_read_bcaps(aux, i915, );
+   if (ret)
+   return ret;
+
+   *hdcp_capable = bcaps & DP_BCAPS_HDCP_CAPABLE;
+
+   return 0;
+}
+
 static const struct intel_hdcp_shim intel_dp_hdcp_shim = {
.write_an_aksv = intel_dp_hdcp_write_an_aksv,
.read_bksv = intel_dp_hdcp_read_bksv,
@@ -820,6 +846,7 @@ static const struct intel_hdcp_shim intel_dp_mst_hdcp_shim 
= {
.stream_2_2_encryption = intel_dp_mst_hdcp2_stream_encryption,
.check_2_2_link = intel_dp_mst_hdcp2_check_link,
.hdcp_2_2_get_capability = intel_dp_hdcp2_get_capability,
+   .get_remote_hdcp_capability = intel_dp_hdcp_get_remote_capability,
.protocol = HDCP_PROTOCOL_DP,
 };
 
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_hdcp.c
index c1a32f9f1199..801b8f0495bb 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.c
@@ -205,6 +205,22 @@ bool intel_hdcp2_get_capability(struct intel_connector 
*connector)
return capable;
 }
 
+void intel_hdcp_get_remote_capability(struct intel_connector *connector,
+ bool *hdcp_capable,
+ bool *hdcp2_capable)
+{
+   struct intel_hdcp *hdcp = >hdcp;
+
+   if (!hdcp->shim->get_remote_hdcp_capability)
+   return;
+
+   hdcp->shim->get_remote_hdcp_capability(connector, hdcp_capable,
+  hdcp2_capable);
+
+   if (!intel_hdcp2_prerequisite(connector))
+   *hdcp2_capable = false;
+}
+
 static bool intel_hdcp_in_use(struct drm_i915_private *i915,
  enum transcoder cpu_transcoder, enum port port)
 {
diff --git a/drivers/gpu/drm/i915/display/intel_hdcp.h 
b/drivers/gpu/drm/i915/display/intel_hdcp.h
index aeefb3c13d2c..477f2d2bb120 100644
--- a/drivers/gpu/drm/i915/display/intel_hdcp.h
+++ b/drivers/gpu/drm/i915/display/intel_hdcp.h
@@ -40,6 +40,9 @@ void intel_hdcp_update_pipe(struct intel_atomic_state *state,
 bool is_hdcp_supported(struct drm_i915_private *i915, enum port port);
 bool intel_hdcp_get_capability(struct intel_connector *connector);
 bool intel_hdcp2_get_capability(struct intel_connector *connector);
+void intel_hdcp_get_remote_capability(struct intel_connector *connector,
+ bool *hdcp_capable,
+ bool *hdcp2_capable);
 void intel_hdcp_component_init(struct drm_i915_private *i915);
 void intel_hdcp_component_fini(struct drm_i915_private *i915);
 void intel_hdcp

[PATCH 04/13] drm/i915/hdcp: Pass drm_dp_aux to read_bcaps function

2024-02-23 Thread Suraj Kandpal
Pass drm_dp_aux to intel_dp_hdcp_read_bcaps function
so as to aid in reading the bcaps for the remote monitor
later on.

Signed-off-by: Suraj Kandpal 
Reviewed-by: Ankit Nautiyal 
---
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c | 12 +++-
 1 file changed, 7 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c 
b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
index 6767b5338ae7..5394391acbe1 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp_hdcp.c
@@ -125,13 +125,13 @@ static int intel_dp_hdcp_read_bstatus(struct 
intel_digital_port *dig_port,
 }
 
 static
-int intel_dp_hdcp_read_bcaps(struct intel_digital_port *dig_port,
+int intel_dp_hdcp_read_bcaps(struct drm_dp_aux *aux,
+struct drm_i915_private *i915,
 u8 *bcaps)
 {
-   struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
ssize_t ret;
 
-   ret = drm_dp_dpcd_read(_port->dp.aux, DP_AUX_HDCP_BCAPS,
+   ret = drm_dp_dpcd_read(aux, DP_AUX_HDCP_BCAPS,
   bcaps, 1);
if (ret != 1) {
drm_dbg_kms(>drm,
@@ -146,10 +146,11 @@ static
 int intel_dp_hdcp_repeater_present(struct intel_digital_port *dig_port,
   bool *repeater_present)
 {
+   struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
ssize_t ret;
u8 bcaps;
 
-   ret = intel_dp_hdcp_read_bcaps(dig_port, );
+   ret = intel_dp_hdcp_read_bcaps(_port->dp.aux, i915,  );
if (ret)
return ret;
 
@@ -271,10 +272,11 @@ static
 int intel_dp_hdcp_capable(struct intel_digital_port *dig_port,
  bool *hdcp_capable)
 {
+   struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
ssize_t ret;
u8 bcaps;
 
-   ret = intel_dp_hdcp_read_bcaps(dig_port, );
+   ret = intel_dp_hdcp_read_bcaps(_port->dp.aux, i915, );
if (ret)
return ret;
 
-- 
2.43.2



  1   2   3   4   5   6   7   8   >