Configure the related HDMI audio register to generate an unsolicited
response to the audio controller driver to indicate that the controller
sequence should start.

Use "pipe" way to get correct register definitions for IBX/CPT/HSW.

Signed-off-by: Wang Xingchao <xingchao.w...@intel.com>
---
 drivers/gpu/drm/i915/i915_reg.h      |   32 +++++++++++++++++++--
 drivers/gpu/drm/i915/intel_display.c |   52 +++++++++++++++++++++++++++-------
 2 files changed, 72 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
index ed87de9..9588dd4 100644
--- a/drivers/gpu/drm/i915/i915_reg.h
+++ b/drivers/gpu/drm/i915/i915_reg.h
@@ -4247,7 +4247,15 @@
 #define G4X_HDMIW_HDMIEDID             0x6210C
 
 #define IBX_HDMIW_HDMIEDID_A           0xE2050
+#define IBX_HDMIW_HDMIEDID_B           0xE2150
+#define IBX_HDMIW_HDMIEDID(pipe) _PIPE(pipe, \
+                                       IBX_HDMIW_HDMIEDID_A, \
+                                       IBX_HDMIW_HDMIEDID_B)
 #define IBX_AUD_CNTL_ST_A              0xE20B4
+#define IBX_AUD_CNTL_ST_B              0xE21B4
+#define IBX_AUD_CNTL_ST(pipe) _PIPE(pipe, \
+                                       IBX_AUD_CNTL_ST_A, \
+                                       IBX_AUD_CNTL_ST_B)
 #define IBX_ELD_BUFFER_SIZE            (0x1f << 10)
 #define IBX_ELD_ADDRESS                        (0x1f << 5)
 #define IBX_ELD_ACK                    (1 << 4)
@@ -4256,7 +4264,15 @@
 #define IBX_CP_READYB                  (1 << 1)
 
 #define CPT_HDMIW_HDMIEDID_A           0xE5050
+#define CPT_HDMIW_HDMIEDID_B           0xE5150
+#define CPT_HDMIW_HDMIEDID(pipe) _PIPE(pipe, \
+                                       CPT_HDMIW_HDMIEDID_A, \
+                                       CPT_HDMIW_HDMIEDID_B)
 #define CPT_AUD_CNTL_ST_A              0xE50B4
+#define CPT_AUD_CNTL_ST_B              0xE51B4
+#define CPT_AUD_CNTL_ST(pipe) _PIPE(pipe, \
+                                       CPT_AUD_CNTL_ST_A, \
+                                       CPT_AUD_CNTL_ST_B)
 #define CPT_AUD_CNTRL_ST2              0xE50C0
 
 /* These are the 4 32-bit write offset registers for each stream
@@ -4266,7 +4282,15 @@
 #define GEN7_SO_WRITE_OFFSET(n)                (0x5280 + (n) * 4)
 
 #define IBX_AUD_CONFIG_A                       0xe2000
+#define IBX_AUD_CONFIG_B                       0xe2100
+#define IBX_AUD_CFG(pipe) _PIPE(pipe, \
+                                       IBX_AUD_CONFIG_A, \
+                                       IBX_AUD_CONFIG_B)
 #define CPT_AUD_CONFIG_A                       0xe5000
+#define CPT_AUD_CONFIG_B                       0xe5100
+#define CPT_AUD_CFG(pipe) _PIPE(pipe, \
+                                       CPT_AUD_CONFIG_A, \
+                                       CPT_AUD_CONFIG_B)
 #define   AUD_CONFIG_N_VALUE_INDEX             (1 << 29)
 #define   AUD_CONFIG_N_PROG_ENABLE             (1 << 28)
 #define   AUD_CONFIG_UPPER_N_SHIFT             20
@@ -4296,7 +4320,7 @@
                                        HSW_AUD_DIP_ELD_CTRL_ST_B)
 
 #define   HSW_AUD_PIPE_CONV_CFG                0x6507c /*Audio pipe and 
converter configs*/
-#define   HSW_AUD_PIN_ELD_CP_VL                0x650c0 /*Audio ELD and CP 
Ready Status*/
+#define   HSW_AUD_PIN_ELD_CP_VLD       0x650c0 /*Audio ELD and CP Ready 
Status*/
 #define   AUDIO_INACTIVE_C             (1<<11)
 #define   AUDIO_INACTIVE_B             (1<<7)
 #define   AUDIO_INACTIVE_A             (1<<3)
@@ -4317,7 +4341,11 @@
                                        HSW_AUD_DIG_CNVT_1, \
                                        HSW_AUD_DIG_CNVT_2)
 
-#define   HSW_AUD_EDID_DATA            0x65050
+#define   HSW_AUD_EDID_DATA_A          0x65050
+#define   HSW_AUD_EDID_DATA_B          0x65150
+#define HSW_AUD_EDID_DATA(pipe) _PIPE(pipe, \
+                                       HSW_AUD_EDID_DATA_A, \
+                                       HSW_AUD_EDID_DATA_B)
 
 #define   TRANS_CONF_A                 0xf0008
 #define   AUD_PB_UNSL_DEV_CP           0x65fb0
diff --git a/drivers/gpu/drm/i915/intel_display.c 
b/drivers/gpu/drm/i915/intel_display.c
index 17020cd..103de56 100644
--- a/drivers/gpu/drm/i915/intel_display.c
+++ b/drivers/gpu/drm/i915/intel_display.c
@@ -5071,6 +5071,7 @@ static void ironlake_write_eld(struct drm_connector 
*connector,
                                     struct drm_crtc *crtc)
 {
        struct drm_i915_private *dev_priv = connector->dev->dev_private;
+       struct drm_device *dev = crtc->dev;
        uint8_t *eld = connector->eld;
        uint32_t eldv;
        uint32_t i;
@@ -5079,23 +5080,52 @@ static void ironlake_write_eld(struct drm_connector 
*connector,
        int aud_config;
        int aud_cntl_st;
        int aud_cntrl_st2;
+       int pipe = to_intel_crtc(crtc)->pipe;
 
        if (HAS_PCH_IBX(connector->dev)) {
-               hdmiw_hdmiedid = IBX_HDMIW_HDMIEDID_A;
-               aud_config = IBX_AUD_CONFIG_A;
-               aud_cntl_st = IBX_AUD_CNTL_ST_A;
+               hdmiw_hdmiedid = IBX_HDMIW_HDMIEDID(pipe);
+               aud_config = IBX_AUD_CFG(pipe);
+               aud_cntl_st = IBX_AUD_CNTL_ST(pipe);
                aud_cntrl_st2 = IBX_AUD_CNTL_ST2;
+       } else if (IS_HASWELL(dev)) {
+               hdmiw_hdmiedid = HSW_AUD_EDID_DATA(pipe);
+               aud_cntl_st = HSW_AUD_DIP_ELD_CTRL(pipe);
+               aud_config = HSW_AUD_CFG(pipe);
+               aud_cntrl_st2 = HSW_AUD_PIN_ELD_CP_VLD;
        } else {
-               hdmiw_hdmiedid = CPT_HDMIW_HDMIEDID_A;
-               aud_config = CPT_AUD_CONFIG_A;
-               aud_cntl_st = CPT_AUD_CNTL_ST_A;
+               hdmiw_hdmiedid = CPT_HDMIW_HDMIEDID(pipe);
+               aud_config = CPT_AUD_CFG(pipe);
+               aud_cntl_st = CPT_AUD_CNTL_ST(pipe);
                aud_cntrl_st2 = CPT_AUD_CNTRL_ST2;
        }
 
-       i = to_intel_crtc(crtc)->pipe;
-       hdmiw_hdmiedid += i * 0x100;
-       aud_cntl_st += i * 0x100;
-       aud_config += i * 0x100;
+       if (IS_HASWELL(dev)) {
+               int tmp;
+               int aud_vld = HSW_AUD_PIN_ELD_CP_VLD;
+
+               DRM_DEBUG_DRIVER("HDMI: Haswell Audio initialize....\n");
+
+               /* Audio output enable */
+               DRM_DEBUG_DRIVER("HDMI audio: enable codec\n");
+               tmp = I915_READ(aud_vld);
+               tmp |= (AUDIO_OUTPUT_ENABLE_A | AUDIO_OUTPUT_ENABLE_B | 
AUDIO_OUTPUT_ENABLE_C);
+               I915_WRITE(aud_vld, tmp);
+
+               /* Set ELD valid state */
+               tmp = I915_READ(aud_vld);
+               DRM_DEBUG_DRIVER("HDMI audio: pin eld vld status=0x%8x\n", tmp);
+               tmp |= (AUDIO_ELD_VALID_A | AUDIO_ELD_VALID_B | 
AUDIO_ELD_VALID_C);
+               I915_WRITE(aud_vld, tmp);
+               tmp = I915_READ(aud_vld);
+               DRM_DEBUG_DRIVER("HDMI audio: eld vld status=0x%8x\n", tmp);
+
+               /* Enable HDMI mode */
+               tmp = I915_READ(aud_config);
+               DRM_DEBUG_DRIVER("HDMI audio: audio conf: 0x%8x\n", tmp);
+               /* clear N_programing_enable and N_value_index */
+               tmp &= ~(AUD_CONFIG_N_VALUE_INDEX | AUD_CONFIG_N_PROG_ENABLE);
+               I915_WRITE(aud_config, tmp);
+       }
 
        DRM_DEBUG_DRIVER("ELD on pipe %c\n", pipe_name(i));
 
@@ -5135,6 +5165,8 @@ static void ironlake_write_eld(struct drm_connector 
*connector,
        i = I915_READ(aud_cntl_st);
        i &= ~IBX_ELD_ADDRESS;
        I915_WRITE(aud_cntl_st, i);
+       i = (i >> 29) & 0x3;            /* DIP_Port_Select, 0x1 = PortB */
+       DRM_DEBUG_DRIVER("port num:%d\n", i);
 
        len = min_t(uint8_t, eld[2], 21);       /* 84 bytes of hw ELD buffer */
        DRM_DEBUG_DRIVER("ELD size %d\n", len);
-- 
1.7.9.5

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/intel-gfx

Reply via email to