video: tegra: dc: Add quick for Vizio P series rel-24-uda-r1
Aly Hirani [Wed, 11 Jan 2017 07:29:58 +0000 (23:29 -0800)]
The Vizio SmartCast P series 4K TVs fail 1/3 hotplugs with "No Signal".
Experiments showed that enabling HDMI 2.0 scrambling and HDCP at the
same time causes this failure from Vizio's side.

This change adds a WAR to introduce a 5 second delay after modeset to
start the hdcp (instead of the standard 100ms delay).

This change also adds edid quirks to limit the 5 second delay to only
the P cast series.

Bug ??

Change-Id: I96d1200afa20401d09ab5d1d2966ab24ac761b2b
Signed-off-by: Aly Hirani <ahirani@nvidia.com>
Reviewed-on: http://git-master/r/1283347
Reviewed-by: Mandar Padmawar <mpadmawar@nvidia.com>
Tested-by: Mandar Padmawar <mpadmawar@nvidia.com>

drivers/video/tegra/dc/edid.h
drivers/video/tegra/dc/edid_quirks.c
drivers/video/tegra/dc/hdmihdcp.c

index 9faaec0..7547ac3 100644 (file)
@@ -129,9 +129,11 @@ enum {
 /* Flag fallback edid is in use. */
 #define EDID_ERRORS_USING_FALLBACK     0x04
 
-#define TEGRA_EDID_QUIRK_NONE      (0)
+#define TEGRA_EDID_QUIRK_NONE       (0)
 /* TV doesn't support YUV420, but declares support */
-#define TEGRA_EDID_QUIRK_NO_YUV (1 << 0)
+#define TEGRA_EDID_QUIRK_NO_YUV     (1 << 0)
+/* TV needs us to delay HDCP by a few seconds */
+#define TEGRA_EDID_QUIRK_DELAY_HDCP (1 << 1)
 
 struct tegra_edid {
        struct tegra_edid_pvt   *data;
index 9dcb9af..74a6a26 100644 (file)
@@ -24,6 +24,11 @@ static const struct hdmi_blacklist {
 } edid_blacklist[] = {
        /* Bauhn ATVS65-815 65" 4K TV */
        { "CTV", 48, "Tempo 4K TV", TEGRA_EDID_QUIRK_NO_YUV },
+       /* Vizio SmartCast P-Series 4K TV */
+       { "VIZ", 4120, "P50-C1",    TEGRA_EDID_QUIRK_DELAY_HDCP },
+       { "VIZ", 4120, "P55-C1",    TEGRA_EDID_QUIRK_DELAY_HDCP },
+       { "VIZ", 4120, "P65-C1",    TEGRA_EDID_QUIRK_DELAY_HDCP },
+       { "VIZ", 4120, "P75-C1",    TEGRA_EDID_QUIRK_DELAY_HDCP },
 };
 
 u32 tegra_edid_lookup_quirks(const char *manufacturer, u32 model,
index 90c1d15..ce9d45e 100644 (file)
@@ -1806,6 +1806,8 @@ static int tegra_nvhdcp_on(struct tegra_nvhdcp *nvhdcp)
        u8 hdcp2version = 0;
        int e;
        int val;
+       int delay = tegra_edid_get_quirks(nvhdcp->hdmi->edid) &
+                   TEGRA_EDID_QUIRK_DELAY_HDCP ? 5000 : 100;
        nvhdcp->state = STATE_UNAUTHENTICATED;
        if (nvhdcp_is_plugged(nvhdcp) &&
                atomic_read(&nvhdcp->policy) !=
@@ -1826,7 +1828,7 @@ static int tegra_nvhdcp_on(struct tegra_nvhdcp *nvhdcp)
                                nvhdcp->hdcp22 = HDCP1X_PROTOCOL;
                                queue_delayed_work(nvhdcp->downstream_wq,
                                        &nvhdcp->hdcp1x_work,
-                                       msecs_to_jiffies(100));
+                                       msecs_to_jiffies(delay));
                        } else {
                                val = HDCP_EESS_ENABLE<<31|
                                        HDCP22_EESS_START<<16|
@@ -1836,7 +1838,7 @@ static int tegra_nvhdcp_on(struct tegra_nvhdcp *nvhdcp)
                                nvhdcp->hdcp22 = HDCP22_PROTOCOL;
                                queue_delayed_work(nvhdcp->downstream_wq,
                                        &nvhdcp->hdcp22_work,
-                                       msecs_to_jiffies(100));
+                                       msecs_to_jiffies(delay));
                        }
                } else {
                        val = HDCP_EESS_ENABLE<<31|
@@ -1847,7 +1849,7 @@ static int tegra_nvhdcp_on(struct tegra_nvhdcp *nvhdcp)
                        nvhdcp->hdcp22 = HDCP1X_PROTOCOL;
                        queue_delayed_work(nvhdcp->downstream_wq,
                                &nvhdcp->hdcp1x_work,
-                               msecs_to_jiffies(100));
+                               msecs_to_jiffies(delay));
                }
        }
        return 0;