As anx7625 MIPI RX bandwidth(maximum 1.5Gbps per lane) and internal
pixel clock(maximum 300M) limitation. Anx7625 must enable DSC feature
while MIPI source want to output 4K30 resolution.

Signed-off-by: Xin Ji <[email protected]>
---
 drivers/gpu/drm/bridge/analogix/anx7625.c | 300 ++++++++++++++++++----
 drivers/gpu/drm/bridge/analogix/anx7625.h |  32 +++
 2 files changed, 284 insertions(+), 48 deletions(-)

diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
b/drivers/gpu/drm/bridge/analogix/anx7625.c
index 4be34d5c7a3b..7d86ab02f71c 100644
--- a/drivers/gpu/drm/bridge/analogix/anx7625.c
+++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
@@ -22,6 +22,7 @@
 
 #include <drm/display/drm_dp_aux_bus.h>
 #include <drm/display/drm_dp_helper.h>
+#include <drm/display/drm_dsc_helper.h>
 #include <drm/display/drm_hdcp_helper.h>
 #include <drm/drm_atomic_helper.h>
 #include <drm/drm_bridge.h>
@@ -476,6 +477,138 @@ static int anx7625_set_k_value(struct anx7625_data *ctx)
                                 MIPI_DIGITAL_ADJ_1, 0x3D);
 }
 
+static int anx7625_set_dsc_params(struct anx7625_data *ctx)
+{
+       int ret, i;
+       u16 htotal, vtotal;
+
+       if (!ctx->dsc_en)
+               return 0;
+
+       /* Htotal */
+       htotal = ctx->dt.hactive.min + ctx->dt.hfront_porch.min +
+               ctx->dt.hback_porch.min + ctx->dt.hsync_len.min;
+       ret = anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                               HORIZONTAL_TOTAL_PIXELS_L, htotal);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_TOTAL_PIXELS_H, htotal >> 8);
+       /* Hactive */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_ACTIVE_PIXELS_L,
+                                ctx->dt.hactive.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_ACTIVE_PIXELS_H,
+                                ctx->dt.hactive.min >> 8);
+       /* HFP */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_FRONT_PORCH_L,
+                                ctx->dt.hfront_porch.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_FRONT_PORCH_H,
+                                ctx->dt.hfront_porch.min >> 8);
+       /* HWS */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_SYNC_WIDTH_L,
+                                ctx->dt.hsync_len.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_SYNC_WIDTH_H,
+                                ctx->dt.hsync_len.min >> 8);
+       /* HBP */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_BACK_PORCH_L,
+                                ctx->dt.hback_porch.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                HORIZONTAL_BACK_PORCH_H,
+                                ctx->dt.hback_porch.min >> 8);
+       /* Vtotal */
+       vtotal = ctx->dt.vactive.min + ctx->dt.vfront_porch.min +
+                ctx->dt.vback_porch.min + ctx->dt.vsync_len.min;
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client, TOTAL_LINES_L,
+                                vtotal);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client, TOTAL_LINES_H,
+                                vtotal >> 8);
+       /* Vactive */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client, ACTIVE_LINES_L,
+                                ctx->dt.vactive.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client, ACTIVE_LINES_H,
+                                ctx->dt.vactive.min >> 8);
+       /* VFP */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                VERTICAL_FRONT_PORCH, 
ctx->dt.vfront_porch.min);
+       /* VWS */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                VERTICAL_SYNC_WIDTH, ctx->dt.vsync_len.min);
+       /* VBP */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.tx_p2_client,
+                                VERTICAL_BACK_PORCH, ctx->dt.vback_porch.min);
+
+       /* Htotal */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client, TOTAL_PIXEL_L_7E,
+                                htotal);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client, TOTAL_PIXEL_H_7E,
+                                htotal >> 8);
+       /* Hactive */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                ACTIVE_PIXEL_L_7E, ctx->dt.hactive.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                ACTIVE_PIXEL_H_7E, ctx->dt.hactive.min >> 8);
+       /* HFP */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                HORIZON_FRONT_PORCH_L_7E,
+                                ctx->dt.hfront_porch.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                HORIZON_FRONT_PORCH_H_7E,
+                                ctx->dt.hfront_porch.min >> 8);
+       /* HWS */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                HORIZON_SYNC_WIDTH_L_7E,
+                                ctx->dt.hsync_len.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                HORIZON_SYNC_WIDTH_H_7E,
+                                ctx->dt.hsync_len.min >> 8);
+       /* HBP */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                HORIZON_BACK_PORCH_L_7E,
+                                ctx->dt.hback_porch.min);
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p0_client,
+                                HORIZON_BACK_PORCH_H_7E,
+                                ctx->dt.hback_porch.min >> 8);
+
+       /* Config DSC decoder internal blank timing for decoder to start */
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p1_client,
+                                H_BLANK_L,
+                                dsc_div(htotal - ctx->dt.hactive.min));
+       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p1_client,
+                                H_BLANK_H,
+                                dsc_div(htotal - ctx->dt.hactive.min) >> 8);
+
+       /* Compress ratio  RATIO bit[7:6] */
+       ret |= anx7625_write_and(ctx, ctx->i2c.rx_p0_client, R_I2C_1, 0x3F);
+       ret |= anx7625_write_or(ctx, ctx->i2c.rx_p0_client, R_I2C_1,
+                               (5 - DSC_COMPRESS_RATIO) << 6);
+       /*PPS table*/
+       for (i = 0; i < PPS_SIZE; i += PPS_BLOCK_SIZE)
+               ret |= anx7625_reg_block_write(ctx, ctx->i2c.rx_p2_client,
+                                              R_PPS_REG_0 + i, PPS_BLOCK_SIZE,
+                                              &ctx->pps_table[i]);
+
+       return ret;
+}
+
+static int anx7625_timing_write(struct anx7625_data *ctx,
+                               struct i2c_client *client,
+                               u8 reg_addr, u16 reg_val, bool high_byte)
+{
+       u8 reg_data;
+
+       if (ctx->dsc_en)
+               reg_val = dsc_div(reg_val);
+
+       reg_data = (high_byte ? (reg_val >> 8) : reg_val) & 0xFF;
+
+       return anx7625_reg_write(ctx, client, reg_addr, reg_data);
+}
+
 static int anx7625_dsi_video_timing_config(struct anx7625_data *ctx)
 {
        struct device *dev = ctx->dev;
@@ -506,34 +639,33 @@ static int anx7625_dsi_video_timing_config(struct 
anx7625_data *ctx)
        ret |= anx7625_write_or(ctx, ctx->i2c.rx_p1_client,
                                MIPI_LANE_CTRL_0, ctx->pdata.mipi_lanes - 1);
 
-       /* Htotal */
        htotal = ctx->dt.hactive.min + ctx->dt.hfront_porch.min +
-               ctx->dt.hback_porch.min + ctx->dt.hsync_len.min;
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_TOTAL_PIXELS_L, htotal & 0xFF);
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_TOTAL_PIXELS_H, htotal >> 8);
+                        ctx->dt.hback_porch.min + ctx->dt.hsync_len.min;
+       /* Htotal */
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_TOTAL_PIXELS_L, htotal, false);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_TOTAL_PIXELS_H, htotal, true);
        /* Hactive */
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_ACTIVE_PIXELS_L, ctx->dt.hactive.min & 0xFF);
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_ACTIVE_PIXELS_H, ctx->dt.hactive.min >> 8);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_ACTIVE_PIXELS_L, ctx->dt.hactive.min, false);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_ACTIVE_PIXELS_H, ctx->dt.hactive.min, true);
        /* HFP */
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_FRONT_PORCH_L, ctx->dt.hfront_porch.min);
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_FRONT_PORCH_H,
-                       ctx->dt.hfront_porch.min >> 8);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_FRONT_PORCH_L, ctx->dt.hfront_porch.min, 
false);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_FRONT_PORCH_H, ctx->dt.hfront_porch.min, 
true);
        /* HWS */
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_SYNC_WIDTH_L, ctx->dt.hsync_len.min);
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_SYNC_WIDTH_H, ctx->dt.hsync_len.min >> 8);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_SYNC_WIDTH_L, ctx->dt.hsync_len.min, false);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_SYNC_WIDTH_H, ctx->dt.hsync_len.min, true);
        /* HBP */
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_BACK_PORCH_L, ctx->dt.hback_porch.min);
-       ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client,
-                       HORIZONTAL_BACK_PORCH_H, ctx->dt.hback_porch.min >> 8);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_BACK_PORCH_L, ctx->dt.hback_porch.min, 
false);
+       ret |= anx7625_timing_write(ctx, ctx->i2c.rx_p2_client,
+                       HORIZONTAL_BACK_PORCH_H, ctx->dt.hback_porch.min, true);
        /* Vactive */
        ret |= anx7625_reg_write(ctx, ctx->i2c.rx_p2_client, ACTIVE_LINES_L,
                        ctx->dt.vactive.min);
@@ -663,9 +795,15 @@ static int anx7625_dsi_config(struct anx7625_data *ctx)
 
        DRM_DEV_DEBUG_DRIVER(dev, "config dsi.\n");
 
-       /* DSC disable */
-       ret = anx7625_write_and(ctx, ctx->i2c.rx_p0_client,
-                               R_DSC_CTRL_0, ~DSC_EN);
+       ret = anx7625_set_dsc_params(ctx);
+       if (ctx->dsc_en)
+               /* DSC enable */
+               ret |= anx7625_write_or(ctx, ctx->i2c.rx_p0_client,
+                                       R_DSC_CTRL_0, DSC_EN);
+       else
+               /* DSC disable */
+               ret |= anx7625_write_and(ctx, ctx->i2c.rx_p0_client,
+                                        R_DSC_CTRL_0, ~DSC_EN);
 
        ret |= anx7625_api_dsi_config(ctx);
 
@@ -2083,6 +2221,7 @@ static int anx7625_setup_dsi_device(struct anx7625_data 
*ctx)
                MIPI_DSI_MODE_VIDEO_HSE |
                MIPI_DSI_HS_PKT_END_ALIGNED;
 
+       dsi->dsc = &ctx->dsc;
        ctx->dsi = dsi;
 
        return 0;
@@ -2186,20 +2325,68 @@ anx7625_bridge_mode_valid(struct drm_bridge *bridge,
        struct anx7625_data *ctx = bridge_to_anx7625(bridge);
        struct device *dev = ctx->dev;
 
-       DRM_DEV_DEBUG_DRIVER(dev, "drm mode checking\n");
+       dev_dbg(dev, "drm mode checking\n");
+       if (mode->clock > SUPPORT_PIXEL_CLOCK)
+               return MODE_CLOCK_HIGH;
+
+       if (mode->clock < SUPPORT_MIN_PIXEL_CLOCK)
+               return MODE_CLOCK_LOW;
 
-       /* Max 1200p at 5.4 Ghz, one lane, pixel clock 300M */
-       if (mode->clock > SUPPORT_PIXEL_CLOCK) {
-               DRM_DEV_DEBUG_DRIVER(dev,
-                                    "drm mode invalid, pixelclock too 
high.\n");
+       if (mode->clock > DSC_PIXEL_CLOCK && (mode->hdisplay % 3 != 0))
                return MODE_CLOCK_HIGH;
-       }
 
-       DRM_DEV_DEBUG_DRIVER(dev, "drm mode valid.\n");
+       dev_dbg(dev, "drm mode valid.\n");
 
        return MODE_OK;
 }
 
+static void anx7625_dsc_enable(struct anx7625_data *ctx, bool en)
+{
+       int ret;
+       struct device *dev = ctx->dev;
+
+       ctx->dsc_en = en;
+
+       if (en) {
+               ctx->dsc.dsc_version_major = 1;
+               ctx->dsc.dsc_version_minor = 1;
+               ctx->dsc.slice_height = 8;
+               ctx->dsc.slice_width = ctx->dt.hactive.min / DSC_SLICE_NUM;
+               ctx->dsc.slice_count = DSC_SLICE_NUM;
+               ctx->dsc.bits_per_component = 8;
+               ctx->dsc.bits_per_pixel = 8 << 4; /* 4 fractional bits */
+               ctx->dsc.block_pred_enable = true;
+               ctx->dsc.native_420 = false;
+               ctx->dsc.native_422 = false;
+               ctx->dsc.simple_422 = false;
+               ctx->dsc.vbr_enable = false;
+               ctx->dsc.rc_model_size = DSC_RC_MODEL_SIZE_CONST;
+               ctx->dsc.pic_width = ctx->dt.hactive.min;
+               ctx->dsc.pic_height = ctx->dt.vactive.min;
+               ctx->dsc.convert_rgb = 1;
+               ctx->dsc.vbr_enable = 0;
+
+               drm_dsc_set_rc_buf_thresh(&ctx->dsc);
+               drm_dsc_set_const_params(&ctx->dsc);
+
+               ctx->dsc.initial_scale_value = 
drm_dsc_initial_scale_value(&ctx->dsc);
+               ctx->dsc.line_buf_depth = ctx->dsc.bits_per_component + 1;
+               ret = drm_dsc_setup_rc_params(&ctx->dsc, DRM_DSC_1_2_444);
+               if (ret < 0)
+                       dev_warn(dev, "drm_dsc_setup_rc_params ret %d\n", ret);
+
+               drm_dsc_compute_rc_parameters(&ctx->dsc);
+
+               drm_dsc_pps_payload_pack((struct drm_dsc_picture_parameter_set 
*)&ctx->pps_table,
+                                        &ctx->dsc);
+               dev_dbg(dev, "anx7625 enable dsc\n");
+       } else {
+               ctx->dsc.dsc_version_major = 0;
+               ctx->dsc.dsc_version_minor = 0;
+               dev_dbg(dev, "anx7625 disable dsc\n");
+       }
+}
+
 static void anx7625_bridge_mode_set(struct drm_bridge *bridge,
                                    const struct drm_display_mode *old_mode,
                                    const struct drm_display_mode *mode)
@@ -2244,6 +2431,11 @@ static void anx7625_bridge_mode_set(struct drm_bridge 
*bridge,
        DRM_DEV_DEBUG_DRIVER(dev, "vsync_end(%d),vtotal(%d).\n",
                             mode->vsync_end,
                             mode->vtotal);
+
+       if (mode->clock > DSC_PIXEL_CLOCK)
+               anx7625_dsc_enable(ctx, true);
+       else
+               anx7625_dsc_enable(ctx, false);
 }
 
 static bool anx7625_bridge_mode_fixup(struct drm_bridge *bridge,
@@ -2258,26 +2450,33 @@ static bool anx7625_bridge_mode_fixup(struct drm_bridge 
*bridge,
 
        DRM_DEV_DEBUG_DRIVER(dev, "drm mode fixup set\n");
 
-       /* No need fixup for external monitor */
-       if (!ctx->pdata.panel_bridge)
-               return true;
-
        hsync = mode->hsync_end - mode->hsync_start;
        hfp = mode->hsync_start - mode->hdisplay;
        hbp = mode->htotal - mode->hsync_end;
        hblanking = mode->htotal - mode->hdisplay;
 
-       DRM_DEV_DEBUG_DRIVER(dev, "before mode fixup\n");
-       DRM_DEV_DEBUG_DRIVER(dev, "hsync(%d), hfp(%d), hbp(%d), clock(%d)\n",
-                            hsync, hfp, hbp, adj->clock);
-       DRM_DEV_DEBUG_DRIVER(dev, "hsync_start(%d), hsync_end(%d), htot(%d)\n",
-                            adj->hsync_start, adj->hsync_end, adj->htotal);
-
+       dev_dbg(dev, "before mode fixup\n");
+       dev_dbg(dev, "hsync(%d), hfp(%d), hbp(%d), clock(%d)\n",
+               hsync, hfp, hbp, adj->clock);
+       dev_dbg(dev, "hsync_start(%d), hsync_end(%d), htot(%d)\n",
+               adj->hsync_start, adj->hsync_end, adj->htotal);
        adj_hfp = hfp;
        adj_hsync = hsync;
        adj_hbp = hbp;
        adj_hblanking = hblanking;
 
+       if (mode->clock > DSC_PIXEL_CLOCK) {
+               adj_hsync = DSC_HSYNC_LEN;
+               adj_hfp = DSC_HFP_LEN;
+               adj_hbp = DSC_HBP_LEN;
+               vref = (u64)adj->clock * 1000 * 1000 / (adj->htotal * 
adj->vtotal);
+               goto calculate_timing;
+       }
+
+       /* No need fixup for external monitor */
+       if (!ctx->pdata.panel_bridge)
+               return true;
+
        /* HFP needs to be even */
        if (hfp & 0x1) {
                adj_hfp += 1;
@@ -2349,16 +2548,21 @@ static bool anx7625_bridge_mode_fixup(struct drm_bridge 
*bridge,
                        adj_hfp -= delta_adj;
        }
 
-       DRM_DEV_DEBUG_DRIVER(dev, "after mode fixup\n");
-       DRM_DEV_DEBUG_DRIVER(dev, "hsync(%d), hfp(%d), hbp(%d), clock(%d)\n",
-                            adj_hsync, adj_hfp, adj_hbp, adj->clock);
+calculate_timing:
+
+       dev_dbg(dev, "after mode fixup\n");
+       dev_dbg(dev, "hsync(%d), hfp(%d), hbp(%d), clock(%d)\n",
+               adj_hsync, adj_hfp, adj_hbp, adj->clock);
 
        /* Reconstruct timing */
        adj->hsync_start = adj->hdisplay + adj_hfp;
        adj->hsync_end = adj->hsync_start + adj_hsync;
        adj->htotal = adj->hsync_end + adj_hbp;
-       DRM_DEV_DEBUG_DRIVER(dev, "hsync_start(%d), hsync_end(%d), htot(%d)\n",
-                            adj->hsync_start, adj->hsync_end, adj->htotal);
+       if (mode->clock > DSC_PIXEL_CLOCK)
+               adj->clock = (u64)vref * adj->htotal * adj->vtotal / 1000 / 
1000;
+
+       dev_dbg(dev, "hsync_start(%d), hsync_end(%d), htot(%d), clock(%d)\n",
+               adj->hsync_start, adj->hsync_end, adj->htotal, adj->clock);
 
        return true;
 }
diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.h 
b/drivers/gpu/drm/bridge/analogix/anx7625.h
index eb5580f1ab2f..db931f5800b1 100644
--- a/drivers/gpu/drm/bridge/analogix/anx7625.h
+++ b/drivers/gpu/drm/bridge/analogix/anx7625.h
@@ -149,6 +149,8 @@
 #define HFP_HBP_DEF            ((HBLANKING_MIN - SYNC_LEN_DEF) / 2)
 #define VIDEO_CONTROL_0        0x08
 
+#define  TOTAL_LINES_L          0x12
+#define  TOTAL_LINES_H          0x13
 #define  ACTIVE_LINES_L         0x14
 #define  ACTIVE_LINES_H         0x15  /* Bit[7:6] are reserved */
 #define  VERTICAL_FRONT_PORCH   0x16
@@ -166,6 +168,32 @@
 #define  HORIZONTAL_BACK_PORCH_L      0x21
 #define  HORIZONTAL_BACK_PORCH_H      0x22  /* Bit[7:4] are reserved */
 
+#define  H_BLANK_L                    0x3E
+#define  H_BLANK_H                    0x3F
+#define  DSC_COMPRESS_RATIO           3
+#define  dsc_div(X)                   ((X) / DSC_COMPRESS_RATIO)
+#define  DSC_SLICE_NUM                2
+#define  DSC_PIXEL_CLOCK              250000
+#define  DSC_HSYNC_LEN                90
+#define  DSC_HFP_LEN                  177
+#define  DSC_HBP_LEN                  297
+
+#define  TOTAL_PIXEL_L_7E             0x50
+#define  TOTAL_PIXEL_H_7E             0x51  /* bit[7:6] are reserved */
+#define  ACTIVE_PIXEL_L_7E            0x52
+#define  ACTIVE_PIXEL_H_7E            0x53  /* bit[7:6] are reserved */
+#define  HORIZON_FRONT_PORCH_L_7E     0x54
+#define  HORIZON_FRONT_PORCH_H_7E     0x55
+#define  HORIZON_SYNC_WIDTH_L_7E      0x56
+#define  HORIZON_SYNC_WIDTH_H_7E      0x57
+#define  HORIZON_BACK_PORCH_L_7E      0x58
+#define  HORIZON_BACK_PORCH_H_7E      0x59
+
+#define  PPS_SIZE                     128
+#define  PPS_BLOCK_SIZE               32
+#define  R_PPS_REG_0                  0x80
+#define  R_I2C_1                      0x81
+
 /******** END of I2C Address 0x72 *********/
 
 /***************************************************************/
@@ -415,6 +443,7 @@ enum audio_wd_len {
 #define MAX_EDID_BLOCK 3
 #define EDID_TRY_CNT   3
 #define SUPPORT_PIXEL_CLOCK    300000
+#define SUPPORT_MIN_PIXEL_CLOCK        50000
 
 /***************** Display End *****************/
 
@@ -454,6 +483,7 @@ struct anx7625_data {
        int hpd_high_cnt;
        int dp_en;
        int hdcp_cp;
+       bool dsc_en;
        /* Lock for work queue */
        struct mutex lock;
        struct device *dev;
@@ -479,6 +509,8 @@ struct anx7625_data {
        struct drm_connector *connector;
        struct mipi_dsi_device *dsi;
        struct drm_dp_aux aux;
+       struct drm_dsc_config dsc;
+       char pps_table[PPS_SIZE];
 };
 
 #endif  /* __ANX7625_H__ */
-- 
2.25.1

Reply via email to