video: tegra: dc: count underflows for winD/H/T
Jon Mayo [Thu, 21 Feb 2013 22:21:18 +0000 (14:21 -0800)]
Change-Id: I16cc1e97caf1f0528f39bfdf396aa6f3d0ec6903
Signed-off-by: Jon Mayo <jmayo@nvidia.com>
Reviewed-on: http://git-master/r/203064
Reviewed-by: Simone Willett <swillett@nvidia.com>
Tested-by: Simone Willett <swillett@nvidia.com>

drivers/video/tegra/dc/dc.c
drivers/video/tegra/dc/dc_priv_defs.h
drivers/video/tegra/dc/dc_reg.h

index e6ffd94..33e1a9e 100644 (file)
@@ -598,6 +598,15 @@ static int dbg_dc_stats_show(struct seq_file *s, void *unused)
                dc->stats.underflows_a,
                dc->stats.underflows_b,
                dc->stats.underflows_c);
+#if defined(CONFIG_ARCH_TEGRA_14x_SOC)
+       seq_printf(s,
+               "underflows_d: %llu\n"
+               "underflows_h: %llu\n"
+               "underflows_t: %llu\n",
+               dc->stats.underflows_d,
+               dc->stats.underflows_h,
+               dc->stats.underflows_t);
+#endif
        mutex_unlock(&dc->lock);
 
        return 0;
@@ -1385,14 +1394,42 @@ static void tegra_dc_underflow_handler(struct tegra_dc *dc)
        if (dc->underflow_mask & WIN_C_UF_INT)
                dc->stats.underflows_c += tegra_dc_underflow_count(dc,
                        DC_WINBUF_CD_UFLOW_STATUS);
+#if defined(CONFIG_ARCH_TEGRA_14x_SOC)
+       if (dc->underflow_mask & HC_UF_INT)
+               dc->stats.underflows_h += tegra_dc_underflow_count(dc,
+                       DC_WINBUF_HD_UFLOW_STATUS);
+       if (dc->underflow_mask & WIN_D_UF_INT)
+               dc->stats.underflows_d += tegra_dc_underflow_count(dc,
+                       DC_WINBUF_DD_UFLOW_STATUS);
+       if (dc->underflow_mask & WIN_T_UF_INT)
+               dc->stats.underflows_t += tegra_dc_underflow_count(dc,
+                       DC_WINBUF_TD_UFLOW_STATUS);
+#endif
 
        /* Check for any underflow reset conditions */
        for (i = 0; i < DC_N_WINDOWS; i++) {
-               if (dc->underflow_mask & (WIN_A_UF_INT << i)) {
+               u32 masks[] = {
+                       WIN_A_UF_INT,
+                       WIN_B_UF_INT,
+                       WIN_C_UF_INT,
+#if defined(CONFIG_ARCH_TEGRA_14x_SOC)
+                       WIN_D_UF_INT,
+                       HC_UF_INT,
+                       WIN_T_UF_INT,
+#endif
+               };
+
+               if (WARN_ONCE(i >= ARRAY_SIZE(masks),
+                       "underflow stats unsupported"))
+                       break; /* bail if the table above is missing entries */
+               if (!masks[i])
+                       continue; /* skip empty entries */
+
+               if (dc->underflow_mask & masks[i]) {
                        dc->windows[i].underflows++;
 
 #ifdef CONFIG_ARCH_TEGRA_2x_SOC
-                       if (dc->windows[i].underflows > 4) {
+                       if (i < 3 && dc->windows[i].underflows > 4) {
                                schedule_work(&dc->reset_work);
                                /* reset counter */
                                dc->windows[i].underflows = 0;
@@ -1400,7 +1437,7 @@ static void tegra_dc_underflow_handler(struct tegra_dc *dc)
                        }
 #endif
 #ifdef CONFIG_ARCH_TEGRA_3x_SOC
-                       if (dc->windows[i].underflows > 4) {
+                       if (i < 3 && dc->windows[i].underflows > 4) {
                                trace_display_reset(dc);
                                tegra_dc_writel(dc, UF_LINE_FLUSH,
                                                DC_DISP_DISP_MISC_CONTROL);
index e8b135a..94ba3b0 100644 (file)
@@ -51,7 +51,12 @@ static inline u32 ALL_UF_INT(void)
 {
        if (tegra_platform_is_fpga())
                return 0;
+#if defined(CONFIG_ARCH_TEGRA_14x_SOC)
+       return WIN_A_UF_INT | WIN_B_UF_INT | WIN_C_UF_INT | HC_UF_INT |
+               WIN_D_UF_INT | WIN_T_UF_INT;
+#else
        return WIN_A_UF_INT | WIN_B_UF_INT | WIN_C_UF_INT;
+#endif
 }
 
 #if defined(CONFIG_TEGRA_EMC_TO_DDR_CLOCK)
@@ -170,6 +175,11 @@ struct tegra_dc {
                u64                     underflows_a;
                u64                     underflows_b;
                u64                     underflows_c;
+#if defined(CONFIG_ARCH_TEGRA_14x_SOC)
+               u64                     underflows_d;
+               u64                     underflows_h;
+               u64                     underflows_t;
+#endif
        } stats;
 
        struct tegra_dc_ext             *ext;
index a9705b8..f807f69 100644 (file)
 #define  WIN_A_UF_INT          (1 << 8)
 #define  WIN_B_UF_INT          (1 << 9)
 #define  WIN_C_UF_INT          (1 << 10)
+#if defined(CONFIG_ARCH_TEGRA_11x_SOC) || defined(CONFIG_ARCH_TEGRA_14x_SOC)
+#define  HC_UF_INT             (1 << 23) /* Cursor or WinH */
+#endif
+#if defined(CONFIG_ARCH_TEGRA_14x_SOC)
+#define  WIN_D_UF_INT          (1 << 24)
+#define  WIN_T_UF_INT          (1 << 25)
+#endif
 #define  MSF_INT               (1 << 12)
 #define  SSF_INT               (1 << 13)
 #define  WIN_A_OF_INT          (1 << 14)
 #define DC_WINBUF_AD_UFLOW_STATUS              0xbca
 #define DC_WINBUF_BD_UFLOW_STATUS              0xdca
 #define DC_WINBUF_CD_UFLOW_STATUS              0xfca
+#if defined(CONFIG_ARCH_TEGRA_14x_SOC)
+#define DC_WINBUF_DD_UFLOW_STATUS              0x0ca
+#define DC_WINBUF_HD_UFLOW_STATUS              0x1ca
+#define DC_WINBUF_TD_UFLOW_STATUS              0x14a
+#endif
 
 #define DC_DISP_SD_CONTROL                     0x4c2
 #define  SD_ENABLE_NORMAL              (1 << 0)