diff options
Diffstat (limited to 'drivers/gpu/drm/panel')
-rw-r--r-- | drivers/gpu/drm/panel/Kconfig | 3 | ||||
-rw-r--r-- | drivers/gpu/drm/panel/panel-ilitek-ili9341.c | 14 | ||||
-rw-r--r-- | drivers/gpu/drm/panel/panel-jadard-jd9365da-h3.c | 137 | ||||
-rw-r--r-- | drivers/gpu/drm/panel/panel-jdi-fhd-r63452.c | 149 | ||||
-rw-r--r-- | drivers/gpu/drm/panel/panel-mantix-mlaf057we51.c | 79 | ||||
-rw-r--r-- | drivers/gpu/drm/panel/panel-simple.c | 71 | ||||
-rw-r--r-- | drivers/gpu/drm/panel/panel-sitronix-st7701.c | 1122 |
7 files changed, 918 insertions, 657 deletions
diff --git a/drivers/gpu/drm/panel/Kconfig b/drivers/gpu/drm/panel/Kconfig index 9f49b0189d3b..5d83ddc06ece 100644 --- a/drivers/gpu/drm/panel/Kconfig +++ b/drivers/gpu/drm/panel/Kconfig @@ -784,7 +784,8 @@ config DRM_PANEL_SHARP_LS060T1SX01 config DRM_PANEL_SITRONIX_ST7701 tristate "Sitronix ST7701 panel driver" depends on OF - depends on DRM_MIPI_DSI + depends on SPI || DRM_MIPI_DSI + select DRM_MIPI_DBI if SPI depends on BACKLIGHT_CLASS_DEVICE help Say Y here if you want to enable support for the Sitronix diff --git a/drivers/gpu/drm/panel/panel-ilitek-ili9341.c b/drivers/gpu/drm/panel/panel-ilitek-ili9341.c index 775d5d5e828c..1fbc5d433d75 100644 --- a/drivers/gpu/drm/panel/panel-ilitek-ili9341.c +++ b/drivers/gpu/drm/panel/panel-ilitek-ili9341.c @@ -121,19 +121,19 @@ struct ili9341_config { const struct drm_display_mode mode; /* ca: TODO: need comments for this register */ u8 ca[ILI9341_CA_LEN]; - /* power_b: TODO: need comments for this register */ + /* power_b: Power control B (CFh) */ u8 power_b[ILI9341_POWER_B_LEN]; - /* power_seq: TODO: need comments for this register */ + /* power_seq: Power on sequence control (EDh) */ u8 power_seq[ILI9341_POWER_SEQ_LEN]; - /* dtca: TODO: need comments for this register */ + /* dtca: Driver timing control A (E8h) */ u8 dtca[ILI9341_DTCA_LEN]; - /* dtcb: TODO: need comments for this register */ + /* dtcb: Driver timing control B (EAh) */ u8 dtcb[ILI9341_DTCB_LEN]; - /* power_a: TODO: need comments for this register */ + /* power_a: Power control A (CBh) */ u8 power_a[ILI9341_POWER_A_LEN]; /* frc: Frame Rate Control (In Normal Mode/Full Colors) (B1h) */ u8 frc[ILI9341_FRC_LEN]; - /* prc: TODO: need comments for this register */ + /* prc: Pump ratio control (F7h) */ u8 prc; /* dfc_1: B6h DISCTRL (Display Function Control) */ u8 dfc_1[ILI9341_DFC_1_LEN]; @@ -147,7 +147,7 @@ struct ili9341_config { u8 vcom_2; /* address_mode: Memory Access Control (36h) */ u8 address_mode; - /* g3amma_en: TODO: need comments for this register */ + /* g3amma_en: Enable 3G (F2h) */ u8 g3amma_en; /* rgb_interface: RGB Interface Signal Control (B0h) */ u8 rgb_interface; diff --git a/drivers/gpu/drm/panel/panel-jadard-jd9365da-h3.c b/drivers/gpu/drm/panel/panel-jadard-jd9365da-h3.c index 04d315d96bff..44897e5218a6 100644 --- a/drivers/gpu/drm/panel/panel-jadard-jd9365da-h3.c +++ b/drivers/gpu/drm/panel/panel-jadard-jd9365da-h3.c @@ -31,8 +31,6 @@ struct jadard_panel_desc { bool reset_before_power_off_vcioo; unsigned int vcioo_to_lp11_delay_ms; unsigned int lp11_to_reset_delay_ms; - unsigned int exit_sleep_to_display_on_delay_ms; - unsigned int display_on_delay_ms; unsigned int backlight_off_to_display_off_delay_ms; unsigned int display_off_to_enter_sleep_delay_ms; unsigned int enter_sleep_to_reset_down_delay_ms; @@ -66,26 +64,6 @@ static inline struct jadard *panel_to_jadard(struct drm_panel *panel) return container_of(panel, struct jadard, panel); } -static int jadard_enable(struct drm_panel *panel) -{ - struct jadard *jadard = panel_to_jadard(panel); - struct mipi_dsi_multi_context dsi_ctx = { .dsi = jadard->dsi }; - - msleep(120); - - mipi_dsi_dcs_exit_sleep_mode_multi(&dsi_ctx); - - if (jadard->desc->exit_sleep_to_display_on_delay_ms) - mipi_dsi_msleep(&dsi_ctx, jadard->desc->exit_sleep_to_display_on_delay_ms); - - mipi_dsi_dcs_set_display_on_multi(&dsi_ctx); - - if (jadard->desc->display_on_delay_ms) - mipi_dsi_msleep(&dsi_ctx, jadard->desc->display_on_delay_ms); - - return dsi_ctx.accum_err; -} - static int jadard_disable(struct drm_panel *panel) { struct jadard *jadard = panel_to_jadard(panel); @@ -202,7 +180,6 @@ static const struct drm_panel_funcs jadard_funcs = { .disable = jadard_disable, .unprepare = jadard_unprepare, .prepare = jadard_prepare, - .enable = jadard_enable, .get_modes = jadard_get_modes, .get_orientation = jadard_panel_get_orientation, }; @@ -382,6 +359,12 @@ static int radxa_display_8hd_ad002_init_cmds(struct jadard *jadard) jd9365da_switch_page(&dsi_ctx, 0x00); + mipi_dsi_msleep(&dsi_ctx, 120); + + mipi_dsi_dcs_exit_sleep_mode_multi(&dsi_ctx); + + mipi_dsi_dcs_set_display_on_multi(&dsi_ctx); + return dsi_ctx.accum_err; }; @@ -608,6 +591,12 @@ static int cz101b4001_init_cmds(struct jadard *jadard) mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0xE6, 0x02); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0xE7, 0x0C); + mipi_dsi_msleep(&dsi_ctx, 120); + + mipi_dsi_dcs_exit_sleep_mode_multi(&dsi_ctx); + + mipi_dsi_dcs_set_display_on_multi(&dsi_ctx); + return dsi_ctx.accum_err; }; @@ -831,6 +820,16 @@ static int kingdisplay_kd101ne3_init_cmds(struct jadard *jadard) jd9365da_switch_page(&dsi_ctx, 0x00); + mipi_dsi_msleep(&dsi_ctx, 120); + + mipi_dsi_dcs_exit_sleep_mode_multi(&dsi_ctx); + + mipi_dsi_msleep(&dsi_ctx, 120); + + mipi_dsi_dcs_set_display_on_multi(&dsi_ctx); + + mipi_dsi_msleep(&dsi_ctx, 20); + return dsi_ctx.accum_err; }; @@ -859,8 +858,6 @@ static const struct jadard_panel_desc kingdisplay_kd101ne3_40ti_desc = { .reset_before_power_off_vcioo = true, .vcioo_to_lp11_delay_ms = 5, .lp11_to_reset_delay_ms = 10, - .exit_sleep_to_display_on_delay_ms = 120, - .display_on_delay_ms = 20, .backlight_off_to_display_off_delay_ms = 100, .display_off_to_enter_sleep_delay_ms = 50, .enter_sleep_to_reset_down_delay_ms = 100, @@ -876,22 +873,22 @@ static int melfas_lmfbx101117480_init_cmds(struct jadard *jadard) jd9365da_switch_page(&dsi_ctx, 0x01); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x0c, 0x74); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x17, 0x00); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x18, 0xbf); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x19, 0x00); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x18, 0xd7); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x19, 0x01); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x1a, 0x00); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x1b, 0xbf); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x1c, 0x00); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x1b, 0xd7); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x1c, 0x01); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x1f, 0x70); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x20, 0x2d); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x21, 0x2d); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x22, 0x7e); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x24, 0xfe); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x24, 0xfd); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x37, 0x19); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x35, 0x28); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x38, 0x05); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x39, 0x08); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x3a, 0x12); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x3c, 0x78); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x3c, 0x7e); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x3d, 0xff); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x3e, 0xff); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x3f, 0x7f); @@ -902,47 +899,47 @@ static int melfas_lmfbx101117480_init_cmds(struct jadard *jadard) mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x0c, 0x74); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x55, 0x02); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x56, 0x01); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x57, 0x8e); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x57, 0x6a); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x58, 0x09); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x59, 0x0a); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5a, 0x2e); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5b, 0x1a); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5c, 0x15); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5d, 0x7f); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5e, 0x69); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5f, 0x59); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x60, 0x4e); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x61, 0x4c); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x62, 0x40); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x63, 0x45); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x64, 0x30); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x65, 0x4a); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x66, 0x49); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x67, 0x4a); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x68, 0x68); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x69, 0x57); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6a, 0x5b); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6b, 0x4e); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6c, 0x49); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5d, 0x73); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5e, 0x56); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x5f, 0x43); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x60, 0x38); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x61, 0x36); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x62, 0x28); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x63, 0x2f); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x64, 0x19); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x65, 0x32); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x66, 0x31); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x67, 0x31); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x68, 0x4f); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x69, 0x3e); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6a, 0x47); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6b, 0x36); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6c, 0x31); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6d, 0x24); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6e, 0x12); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x6f, 0x02); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x70, 0x7f); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x71, 0x69); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x72, 0x59); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x73, 0x4e); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x74, 0x4c); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x75, 0x40); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x76, 0x45); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x77, 0x30); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x78, 0x4a); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x79, 0x49); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7a, 0x4a); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7b, 0x68); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7c, 0x57); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7d, 0x5b); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7e, 0x4e); - mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7f, 0x49); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x70, 0x73); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x71, 0x56); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x72, 0x43); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x73, 0x38); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x74, 0x36); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x75, 0x28); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x76, 0x2f); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x77, 0x19); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x78, 0x32); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x79, 0x31); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7a, 0x31); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7b, 0x4f); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7c, 0x3e); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7d, 0x47); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7e, 0x36); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x7f, 0x31); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x80, 0x24); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x81, 0x12); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x82, 0x02); @@ -1074,6 +1071,16 @@ static int melfas_lmfbx101117480_init_cmds(struct jadard *jadard) mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0xe6, 0x02); mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0xe7, 0x06); + mipi_dsi_msleep(&dsi_ctx, 120); + + mipi_dsi_dcs_exit_sleep_mode_multi(&dsi_ctx); + + mipi_dsi_msleep(&dsi_ctx, 120); + + mipi_dsi_dcs_set_display_on_multi(&dsi_ctx); + + mipi_dsi_msleep(&dsi_ctx, 20); + return dsi_ctx.accum_err; }; @@ -1102,8 +1109,6 @@ static const struct jadard_panel_desc melfas_lmfbx101117480_desc = { .reset_before_power_off_vcioo = true, .vcioo_to_lp11_delay_ms = 5, .lp11_to_reset_delay_ms = 10, - .exit_sleep_to_display_on_delay_ms = 120, - .display_on_delay_ms = 20, .backlight_off_to_display_off_delay_ms = 100, .display_off_to_enter_sleep_delay_ms = 50, .enter_sleep_to_reset_down_delay_ms = 100, diff --git a/drivers/gpu/drm/panel/panel-jdi-fhd-r63452.c b/drivers/gpu/drm/panel/panel-jdi-fhd-r63452.c index 483dc88d16d8..4eb71e85e9e9 100644 --- a/drivers/gpu/drm/panel/panel-jdi-fhd-r63452.c +++ b/drivers/gpu/drm/panel/panel-jdi-fhd-r63452.c @@ -41,142 +41,89 @@ static void jdi_fhd_r63452_reset(struct jdi_fhd_r63452 *ctx) static int jdi_fhd_r63452_on(struct jdi_fhd_r63452 *ctx) { struct mipi_dsi_device *dsi = ctx->dsi; - struct device *dev = &dsi->dev; - int ret; + struct mipi_dsi_multi_context dsi_ctx = { .dsi = dsi }; dsi->mode_flags |= MIPI_DSI_MODE_LPM; - mipi_dsi_generic_write_seq(dsi, 0xb0, 0x00); - mipi_dsi_generic_write_seq(dsi, 0xd6, 0x01); - mipi_dsi_generic_write_seq(dsi, 0xec, - 0x64, 0xdc, 0xec, 0x3b, 0x52, 0x00, 0x0b, 0x0b, - 0x13, 0x15, 0x68, 0x0b, 0xb5); - mipi_dsi_generic_write_seq(dsi, 0xb0, 0x03); - - ret = mipi_dsi_dcs_set_tear_on(dsi, MIPI_DSI_DCS_TEAR_MODE_VBLANK); - if (ret < 0) { - dev_err(dev, "Failed to set tear on: %d\n", ret); - return ret; - } - - mipi_dsi_dcs_write_seq(dsi, MIPI_DCS_SET_ADDRESS_MODE, 0x00); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xb0, 0x00); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xd6, 0x01); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xec, + 0x64, 0xdc, 0xec, 0x3b, 0x52, 0x00, 0x0b, 0x0b, + 0x13, 0x15, 0x68, 0x0b, 0xb5); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xb0, 0x03); - ret = mipi_dsi_dcs_set_pixel_format(dsi, 0x77); - if (ret < 0) { - dev_err(dev, "Failed to set pixel format: %d\n", ret); - return ret; - } - - ret = mipi_dsi_dcs_set_column_address(dsi, 0x0000, 0x0437); - if (ret < 0) { - dev_err(dev, "Failed to set column address: %d\n", ret); - return ret; - } + mipi_dsi_dcs_set_tear_on_multi(&dsi_ctx, MIPI_DSI_DCS_TEAR_MODE_VBLANK); - ret = mipi_dsi_dcs_set_page_address(dsi, 0x0000, 0x077f); - if (ret < 0) { - dev_err(dev, "Failed to set page address: %d\n", ret); - return ret; - } + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, MIPI_DCS_SET_ADDRESS_MODE, 0x00); - ret = mipi_dsi_dcs_set_tear_scanline(dsi, 0x0000); - if (ret < 0) { - dev_err(dev, "Failed to set tear scanline: %d\n", ret); - return ret; - } + mipi_dsi_dcs_set_pixel_format_multi(&dsi_ctx, 0x77); + mipi_dsi_dcs_set_column_address_multi(&dsi_ctx, 0x0000, 0x0437); + mipi_dsi_dcs_set_page_address_multi(&dsi_ctx, 0x0000, 0x077f); + mipi_dsi_dcs_set_tear_scanline_multi(&dsi_ctx, 0x0000); + mipi_dsi_dcs_set_display_brightness_multi(&dsi_ctx, 0x00ff); - ret = mipi_dsi_dcs_set_display_brightness(dsi, 0x00ff); - if (ret < 0) { - dev_err(dev, "Failed to set display brightness: %d\n", ret); - return ret; - } + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, MIPI_DCS_WRITE_CONTROL_DISPLAY, 0x24); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, MIPI_DCS_WRITE_POWER_SAVE, 0x00); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, MIPI_DCS_SET_CABC_MIN_BRIGHTNESS, 0x00); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x84, 0x00); - mipi_dsi_dcs_write_seq(dsi, MIPI_DCS_WRITE_CONTROL_DISPLAY, 0x24); - mipi_dsi_dcs_write_seq(dsi, MIPI_DCS_WRITE_POWER_SAVE, 0x00); - mipi_dsi_dcs_write_seq(dsi, MIPI_DCS_SET_CABC_MIN_BRIGHTNESS, 0x00); - mipi_dsi_dcs_write_seq(dsi, 0x84, 0x00); + mipi_dsi_dcs_set_display_on_multi(&dsi_ctx); + mipi_dsi_msleep(&dsi_ctx, 20); + mipi_dsi_dcs_exit_sleep_mode_multi(&dsi_ctx); + mipi_dsi_msleep(&dsi_ctx, 80); - ret = mipi_dsi_dcs_set_display_on(dsi); - if (ret < 0) { - dev_err(dev, "Failed to set display on: %d\n", ret); - return ret; - } - msleep(20); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xb0, 0x04); + mipi_dsi_dcs_write_seq_multi(&dsi_ctx, 0x84, 0x00); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xc8, 0x11); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xb0, 0x03); - ret = mipi_dsi_dcs_exit_sleep_mode(dsi); - if (ret < 0) { - dev_err(dev, "Failed to exit sleep mode: %d\n", ret); - return ret; - } - msleep(80); - - mipi_dsi_generic_write_seq(dsi, 0xb0, 0x04); - mipi_dsi_dcs_write_seq(dsi, 0x84, 0x00); - mipi_dsi_generic_write_seq(dsi, 0xc8, 0x11); - mipi_dsi_generic_write_seq(dsi, 0xb0, 0x03); - - return 0; + return dsi_ctx.accum_err; } -static int jdi_fhd_r63452_off(struct jdi_fhd_r63452 *ctx) +static void jdi_fhd_r63452_off(struct jdi_fhd_r63452 *ctx) { struct mipi_dsi_device *dsi = ctx->dsi; - struct device *dev = &dsi->dev; - int ret; + struct mipi_dsi_multi_context dsi_ctx = { .dsi = dsi }; dsi->mode_flags &= ~MIPI_DSI_MODE_LPM; - mipi_dsi_generic_write_seq(dsi, 0xb0, 0x00); - mipi_dsi_generic_write_seq(dsi, 0xd6, 0x01); - mipi_dsi_generic_write_seq(dsi, 0xec, - 0x64, 0xdc, 0xec, 0x3b, 0x52, 0x00, 0x0b, 0x0b, - 0x13, 0x15, 0x68, 0x0b, 0x95); - mipi_dsi_generic_write_seq(dsi, 0xb0, 0x03); - - ret = mipi_dsi_dcs_set_display_off(dsi); - if (ret < 0) { - dev_err(dev, "Failed to set display off: %d\n", ret); - return ret; - } - usleep_range(2000, 3000); - - ret = mipi_dsi_dcs_enter_sleep_mode(dsi); - if (ret < 0) { - dev_err(dev, "Failed to enter sleep mode: %d\n", ret); - return ret; - } - msleep(120); - - return 0; + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xb0, 0x00); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xd6, 0x01); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xec, + 0x64, 0xdc, 0xec, 0x3b, 0x52, 0x00, 0x0b, 0x0b, + 0x13, 0x15, 0x68, 0x0b, 0x95); + mipi_dsi_generic_write_seq_multi(&dsi_ctx, 0xb0, 0x03); + + mipi_dsi_dcs_set_display_off_multi(&dsi_ctx); + mipi_dsi_usleep_range(&dsi_ctx, 2000, 3000); + mipi_dsi_dcs_enter_sleep_mode_multi(&dsi_ctx); + mipi_dsi_msleep(&dsi_ctx, 120); } static int jdi_fhd_r63452_prepare(struct drm_panel *panel) { struct jdi_fhd_r63452 *ctx = to_jdi_fhd_r63452(panel); - struct device *dev = &ctx->dsi->dev; int ret; jdi_fhd_r63452_reset(ctx); ret = jdi_fhd_r63452_on(ctx); - if (ret < 0) { - dev_err(dev, "Failed to initialize panel: %d\n", ret); + if (ret < 0) gpiod_set_value_cansleep(ctx->reset_gpio, 1); - return ret; - } - return 0; + return ret; } static int jdi_fhd_r63452_unprepare(struct drm_panel *panel) { struct jdi_fhd_r63452 *ctx = to_jdi_fhd_r63452(panel); - struct device *dev = &ctx->dsi->dev; - int ret; - ret = jdi_fhd_r63452_off(ctx); - if (ret < 0) - dev_err(dev, "Failed to un-initialize panel: %d\n", ret); + /* + * NOTE: We don't return an error here as while the panel won't have + * been cleanly turned off at least we've asserted the reset signal + * so it should be safe to power it back on again later + */ + jdi_fhd_r63452_off(ctx); gpiod_set_value_cansleep(ctx->reset_gpio, 1); diff --git a/drivers/gpu/drm/panel/panel-mantix-mlaf057we51.c b/drivers/gpu/drm/panel/panel-mantix-mlaf057we51.c index ea4a6bf6d35b..4db852ffb0f6 100644 --- a/drivers/gpu/drm/panel/panel-mantix-mlaf057we51.c +++ b/drivers/gpu/drm/panel/panel-mantix-mlaf057we51.c @@ -23,7 +23,7 @@ /* Manufacturer specific Commands send via DSI */ #define MANTIX_CMD_OTP_STOP_RELOAD_MIPI 0x41 -#define MANTIX_CMD_INT_CANCEL 0x4C +#define MANTIX_CMD_INT_CANCEL 0x4c #define MANTIX_CMD_SPI_FINISH 0x90 struct mantix { @@ -45,82 +45,57 @@ static inline struct mantix *panel_to_mantix(struct drm_panel *panel) return container_of(panel, struct mantix, panel); } -static int mantix_init_sequence(struct mantix *ctx) +static void mantix_init_sequence(struct mipi_dsi_multi_context *dsi_ctx) { - struct mipi_dsi_device *dsi = to_mipi_dsi_device(ctx->dev); - struct device *dev = ctx->dev; - /* * Init sequence was supplied by the panel vendor. */ - mipi_dsi_generic_write_seq(dsi, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x5A); - - mipi_dsi_generic_write_seq(dsi, MANTIX_CMD_INT_CANCEL, 0x03); - mipi_dsi_generic_write_seq(dsi, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x5A, 0x03); - mipi_dsi_generic_write_seq(dsi, 0x80, 0xA9, 0x00); + mipi_dsi_generic_write_seq_multi(dsi_ctx, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x5a); - mipi_dsi_generic_write_seq(dsi, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x5A, 0x09); - mipi_dsi_generic_write_seq(dsi, 0x80, 0x64, 0x00, 0x64, 0x00, 0x00); - msleep(20); + mipi_dsi_generic_write_seq_multi(dsi_ctx, MANTIX_CMD_INT_CANCEL, 0x03); + mipi_dsi_generic_write_seq_multi(dsi_ctx, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x5a, 0x03); + mipi_dsi_generic_write_seq_multi(dsi_ctx, 0x80, 0xa9, 0x00); - mipi_dsi_generic_write_seq(dsi, MANTIX_CMD_SPI_FINISH, 0xA5); - mipi_dsi_generic_write_seq(dsi, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x00, 0x2F); - msleep(20); + mipi_dsi_generic_write_seq_multi(dsi_ctx, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x5a, 0x09); + mipi_dsi_generic_write_seq_multi(dsi_ctx, 0x80, 0x64, 0x00, 0x64, 0x00, 0x00); + mipi_dsi_msleep(dsi_ctx, 20); - dev_dbg(dev, "Panel init sequence done\n"); - return 0; + mipi_dsi_generic_write_seq_multi(dsi_ctx, MANTIX_CMD_SPI_FINISH, 0xa5); + mipi_dsi_generic_write_seq_multi(dsi_ctx, MANTIX_CMD_OTP_STOP_RELOAD_MIPI, 0x00, 0x2f); + mipi_dsi_msleep(dsi_ctx, 20); } static int mantix_enable(struct drm_panel *panel) { struct mantix *ctx = panel_to_mantix(panel); - struct device *dev = ctx->dev; - struct mipi_dsi_device *dsi = to_mipi_dsi_device(dev); - int ret; + struct mipi_dsi_device *dsi = to_mipi_dsi_device(ctx->dev); + struct mipi_dsi_multi_context dsi_ctx = { .dsi = dsi }; - ret = mantix_init_sequence(ctx); - if (ret < 0) { - dev_err(ctx->dev, "Panel init sequence failed: %d\n", ret); - return ret; - } + mantix_init_sequence(&dsi_ctx); + if (!dsi_ctx.accum_err) + dev_dbg(ctx->dev, "Panel init sequence done\n"); - ret = mipi_dsi_dcs_exit_sleep_mode(dsi); - if (ret < 0) { - dev_err(dev, "Failed to exit sleep mode\n"); - return ret; - } - msleep(20); + mipi_dsi_dcs_exit_sleep_mode_multi(&dsi_ctx); + mipi_dsi_msleep(&dsi_ctx, 20); - ret = mipi_dsi_dcs_set_display_on(dsi); - if (ret) - return ret; - usleep_range(10000, 12000); + mipi_dsi_dcs_set_display_on_multi(&dsi_ctx); + mipi_dsi_usleep_range(&dsi_ctx, 10000, 12000); - ret = mipi_dsi_turn_on_peripheral(dsi); - if (ret < 0) { - dev_err(dev, "Failed to turn on peripheral\n"); - return ret; - } + mipi_dsi_turn_on_peripheral_multi(&dsi_ctx); - return 0; + return dsi_ctx.accum_err; } static int mantix_disable(struct drm_panel *panel) { struct mantix *ctx = panel_to_mantix(panel); struct mipi_dsi_device *dsi = to_mipi_dsi_device(ctx->dev); - int ret; - - ret = mipi_dsi_dcs_set_display_off(dsi); - if (ret < 0) - dev_err(ctx->dev, "Failed to turn off the display: %d\n", ret); + struct mipi_dsi_multi_context dsi_ctx = { .dsi = dsi }; - ret = mipi_dsi_dcs_enter_sleep_mode(dsi); - if (ret < 0) - dev_err(ctx->dev, "Failed to enter sleep mode: %d\n", ret); + mipi_dsi_dcs_set_display_off_multi(&dsi_ctx); + mipi_dsi_dcs_enter_sleep_mode_multi(&dsi_ctx); - - return 0; + return dsi_ctx.accum_err; } static int mantix_unprepare(struct drm_panel *panel) diff --git a/drivers/gpu/drm/panel/panel-simple.c b/drivers/gpu/drm/panel/panel-simple.c index 1b78248cbe4f..86735430462f 100644 --- a/drivers/gpu/drm/panel/panel-simple.c +++ b/drivers/gpu/drm/panel/panel-simple.c @@ -2527,6 +2527,38 @@ static const struct panel_desc innolux_g070y2_l01 = { .connector_type = DRM_MODE_CONNECTOR_LVDS, }; +static const struct display_timing innolux_g070ace_lh3_timing = { + .pixelclock = { 25200000, 25400000, 35700000 }, + .hactive = { 800, 800, 800 }, + .hfront_porch = { 30, 32, 87 }, + .hback_porch = { 29, 31, 86 }, + .hsync_len = { 1, 1, 1 }, + .vactive = { 480, 480, 480 }, + .vfront_porch = { 4, 5, 65 }, + .vback_porch = { 3, 4, 65 }, + .vsync_len = { 1, 1, 1 }, + .flags = DISPLAY_FLAGS_DE_HIGH, +}; + +static const struct panel_desc innolux_g070ace_lh3 = { + .timings = &innolux_g070ace_lh3_timing, + .num_timings = 1, + .bpc = 8, + .size = { + .width = 152, + .height = 91, + }, + .delay = { + .prepare = 10, + .enable = 450, + .disable = 200, + .unprepare = 510, + }, + .bus_format = MEDIA_BUS_FMT_RGB888_1X7X4_SPWG, + .bus_flags = DRM_BUS_FLAG_DE_HIGH, + .connector_type = DRM_MODE_CONNECTOR_LVDS, +}; + static const struct drm_display_mode innolux_g070y2_t02_mode = { .clock = 33333, .hdisplay = 800, @@ -3486,6 +3518,39 @@ static const struct panel_desc olimex_lcd_olinuxino_43ts = { .bus_format = MEDIA_BUS_FMT_RGB888_1X24, }; +static const struct display_timing ontat_kd50g21_40nt_a1_timing = { + .pixelclock = { 30000000, 30000000, 50000000 }, + .hactive = { 800, 800, 800 }, + .hfront_porch = { 1, 40, 255 }, + .hback_porch = { 1, 40, 87 }, + .hsync_len = { 1, 48, 87 }, + .vactive = { 480, 480, 480 }, + .vfront_porch = { 1, 13, 255 }, + .vback_porch = { 1, 29, 29 }, + .vsync_len = { 3, 3, 31 }, + .flags = DISPLAY_FLAGS_HSYNC_LOW | DISPLAY_FLAGS_VSYNC_LOW | + DISPLAY_FLAGS_DE_HIGH | DISPLAY_FLAGS_PIXDATA_POSEDGE, +}; + +static const struct panel_desc ontat_kd50g21_40nt_a1 = { + .timings = &ontat_kd50g21_40nt_a1_timing, + .num_timings = 1, + .bpc = 8, + .size = { + .width = 108, + .height = 65, + }, + .delay = { + .prepare = 147, /* 5 VSDs */ + .enable = 147, /* 5 VSDs */ + .disable = 88, /* 3 VSDs */ + .unprepare = 117, /* 4 VSDs */ + }, + .bus_format = MEDIA_BUS_FMT_RGB888_1X24, + .bus_flags = DRM_BUS_FLAG_DE_HIGH | DRM_BUS_FLAG_PIXDATA_SAMPLE_NEGEDGE, + .connector_type = DRM_MODE_CONNECTOR_DPI, +}; + /* * 800x480 CVT. The panel appears to be quite accepting, at least as far as * pixel clocks, but this is the timing that was being used in the Adafruit @@ -4735,6 +4800,9 @@ static const struct of_device_id platform_of_match[] = { .compatible = "innolux,g070ace-l01", .data = &innolux_g070ace_l01, }, { + .compatible = "innolux,g070ace-lh3", + .data = &innolux_g070ace_lh3, + }, { .compatible = "innolux,g070y2-l01", .data = &innolux_g070y2_l01, }, { @@ -4846,6 +4914,9 @@ static const struct of_device_id platform_of_match[] = { .compatible = "olimex,lcd-olinuxino-43-ts", .data = &olimex_lcd_olinuxino_43ts, }, { + .compatible = "ontat,kd50g21-40nt-a1", + .data = &ontat_kd50g21_40nt_a1, + }, { .compatible = "ontat,yx700wv03", .data = &ontat_yx700wv03, }, { diff --git a/drivers/gpu/drm/panel/panel-sitronix-st7701.c b/drivers/gpu/drm/panel/panel-sitronix-st7701.c index 421eb4592b61..eef03d04e0cd 100644 --- a/drivers/gpu/drm/panel/panel-sitronix-st7701.c +++ b/drivers/gpu/drm/panel/panel-sitronix-st7701.c @@ -4,6 +4,7 @@ * Author: Jagan Teki <jagan@amarulasolutions.com> */ +#include <drm/drm_mipi_dbi.h> #include <drm/drm_mipi_dsi.h> #include <drm/drm_modes.h> #include <drm/drm_panel.h> @@ -14,79 +15,80 @@ #include <linux/module.h> #include <linux/of.h> #include <linux/regulator/consumer.h> +#include <linux/spi/spi.h> #include <video/mipi_display.h> /* Command2 BKx selection command */ -#define DSI_CMD2BKX_SEL 0xFF -#define DSI_CMD1 0 -#define DSI_CMD2 BIT(4) -#define DSI_CMD2BK_MASK GENMASK(3, 0) +#define ST7701_CMD2BKX_SEL 0xFF +#define ST7701_CMD1 0 +#define ST7701_CMD2 BIT(4) +#define ST7701_CMD2BK_MASK GENMASK(3, 0) /* Command2, BK0 commands */ -#define DSI_CMD2_BK0_PVGAMCTRL 0xB0 /* Positive Voltage Gamma Control */ -#define DSI_CMD2_BK0_NVGAMCTRL 0xB1 /* Negative Voltage Gamma Control */ -#define DSI_CMD2_BK0_LNESET 0xC0 /* Display Line setting */ -#define DSI_CMD2_BK0_PORCTRL 0xC1 /* Porch control */ -#define DSI_CMD2_BK0_INVSEL 0xC2 /* Inversion selection, Frame Rate Control */ +#define ST7701_CMD2_BK0_PVGAMCTRL 0xB0 /* Positive Voltage Gamma Control */ +#define ST7701_CMD2_BK0_NVGAMCTRL 0xB1 /* Negative Voltage Gamma Control */ +#define ST7701_CMD2_BK0_LNESET 0xC0 /* Display Line setting */ +#define ST7701_CMD2_BK0_PORCTRL 0xC1 /* Porch control */ +#define ST7701_CMD2_BK0_INVSEL 0xC2 /* Inversion selection, Frame Rate Control */ /* Command2, BK1 commands */ -#define DSI_CMD2_BK1_VRHS 0xB0 /* Vop amplitude setting */ -#define DSI_CMD2_BK1_VCOM 0xB1 /* VCOM amplitude setting */ -#define DSI_CMD2_BK1_VGHSS 0xB2 /* VGH Voltage setting */ -#define DSI_CMD2_BK1_TESTCMD 0xB3 /* TEST Command Setting */ -#define DSI_CMD2_BK1_VGLS 0xB5 /* VGL Voltage setting */ -#define DSI_CMD2_BK1_PWCTLR1 0xB7 /* Power Control 1 */ -#define DSI_CMD2_BK1_PWCTLR2 0xB8 /* Power Control 2 */ -#define DSI_CMD2_BK1_SPD1 0xC1 /* Source pre_drive timing set1 */ -#define DSI_CMD2_BK1_SPD2 0xC2 /* Source EQ2 Setting */ -#define DSI_CMD2_BK1_MIPISET1 0xD0 /* MIPI Setting 1 */ +#define ST7701_CMD2_BK1_VRHS 0xB0 /* Vop amplitude setting */ +#define ST7701_CMD2_BK1_VCOM 0xB1 /* VCOM amplitude setting */ +#define ST7701_CMD2_BK1_VGHSS 0xB2 /* VGH Voltage setting */ +#define ST7701_CMD2_BK1_TESTCMD 0xB3 /* TEST Command Setting */ +#define ST7701_CMD2_BK1_VGLS 0xB5 /* VGL Voltage setting */ +#define ST7701_CMD2_BK1_PWCTLR1 0xB7 /* Power Control 1 */ +#define ST7701_CMD2_BK1_PWCTLR2 0xB8 /* Power Control 2 */ +#define ST7701_CMD2_BK1_SPD1 0xC1 /* Source pre_drive timing set1 */ +#define ST7701_CMD2_BK1_SPD2 0xC2 /* Source EQ2 Setting */ +#define ST7701_CMD2_BK1_MIPISET1 0xD0 /* MIPI Setting 1 */ /* Command2, BK0 bytes */ -#define DSI_CMD2_BK0_GAMCTRL_AJ_MASK GENMASK(7, 6) -#define DSI_CMD2_BK0_GAMCTRL_VC0_MASK GENMASK(3, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC4_MASK GENMASK(5, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC8_MASK GENMASK(5, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC16_MASK GENMASK(4, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC24_MASK GENMASK(4, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC52_MASK GENMASK(3, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC80_MASK GENMASK(5, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC108_MASK GENMASK(3, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC147_MASK GENMASK(3, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC175_MASK GENMASK(5, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC203_MASK GENMASK(3, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC231_MASK GENMASK(4, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC239_MASK GENMASK(4, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC247_MASK GENMASK(5, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC251_MASK GENMASK(5, 0) -#define DSI_CMD2_BK0_GAMCTRL_VC255_MASK GENMASK(4, 0) -#define DSI_CMD2_BK0_LNESET_LINE_MASK GENMASK(6, 0) -#define DSI_CMD2_BK0_LNESET_LDE_EN BIT(7) -#define DSI_CMD2_BK0_LNESET_LINEDELTA GENMASK(1, 0) -#define DSI_CMD2_BK0_PORCTRL_VBP_MASK GENMASK(7, 0) -#define DSI_CMD2_BK0_PORCTRL_VFP_MASK GENMASK(7, 0) -#define DSI_CMD2_BK0_INVSEL_ONES_MASK GENMASK(5, 4) -#define DSI_CMD2_BK0_INVSEL_NLINV_MASK GENMASK(2, 0) -#define DSI_CMD2_BK0_INVSEL_RTNI_MASK GENMASK(4, 0) +#define ST7701_CMD2_BK0_GAMCTRL_AJ_MASK GENMASK(7, 6) +#define ST7701_CMD2_BK0_GAMCTRL_VC0_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC4_MASK GENMASK(5, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC8_MASK GENMASK(5, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC16_MASK GENMASK(4, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC24_MASK GENMASK(4, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC52_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC80_MASK GENMASK(5, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC108_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC147_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC175_MASK GENMASK(5, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC203_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC231_MASK GENMASK(4, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC239_MASK GENMASK(4, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC247_MASK GENMASK(5, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC251_MASK GENMASK(5, 0) +#define ST7701_CMD2_BK0_GAMCTRL_VC255_MASK GENMASK(4, 0) +#define ST7701_CMD2_BK0_LNESET_LINE_MASK GENMASK(6, 0) +#define ST7701_CMD2_BK0_LNESET_LDE_EN BIT(7) +#define ST7701_CMD2_BK0_LNESET_LINEDELTA GENMASK(1, 0) +#define ST7701_CMD2_BK0_PORCTRL_VBP_MASK GENMASK(7, 0) +#define ST7701_CMD2_BK0_PORCTRL_VFP_MASK GENMASK(7, 0) +#define ST7701_CMD2_BK0_INVSEL_ONES_MASK GENMASK(5, 4) +#define ST7701_CMD2_BK0_INVSEL_NLINV_MASK GENMASK(2, 0) +#define ST7701_CMD2_BK0_INVSEL_RTNI_MASK GENMASK(4, 0) /* Command2, BK1 bytes */ -#define DSI_CMD2_BK1_VRHA_MASK GENMASK(7, 0) -#define DSI_CMD2_BK1_VCOM_MASK GENMASK(7, 0) -#define DSI_CMD2_BK1_VGHSS_MASK GENMASK(3, 0) -#define DSI_CMD2_BK1_TESTCMD_VAL BIT(7) -#define DSI_CMD2_BK1_VGLS_ONES BIT(6) -#define DSI_CMD2_BK1_VGLS_MASK GENMASK(3, 0) -#define DSI_CMD2_BK1_PWRCTRL1_AP_MASK GENMASK(7, 6) -#define DSI_CMD2_BK1_PWRCTRL1_APIS_MASK GENMASK(3, 2) -#define DSI_CMD2_BK1_PWRCTRL1_APOS_MASK GENMASK(1, 0) -#define DSI_CMD2_BK1_PWRCTRL2_AVDD_MASK GENMASK(5, 4) -#define DSI_CMD2_BK1_PWRCTRL2_AVCL_MASK GENMASK(1, 0) -#define DSI_CMD2_BK1_SPD1_ONES_MASK GENMASK(6, 4) -#define DSI_CMD2_BK1_SPD1_T2D_MASK GENMASK(3, 0) -#define DSI_CMD2_BK1_SPD2_ONES_MASK GENMASK(6, 4) -#define DSI_CMD2_BK1_SPD2_T3D_MASK GENMASK(3, 0) -#define DSI_CMD2_BK1_MIPISET1_ONES BIT(7) -#define DSI_CMD2_BK1_MIPISET1_EOT_EN BIT(3) +#define ST7701_CMD2_BK1_VRHA_MASK GENMASK(7, 0) +#define ST7701_CMD2_BK1_VCOM_MASK GENMASK(7, 0) +#define ST7701_CMD2_BK1_VGHSS_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK1_TESTCMD_VAL BIT(7) +#define ST7701_CMD2_BK1_VGLS_ONES BIT(6) +#define ST7701_CMD2_BK1_VGLS_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK1_PWRCTRL1_AP_MASK GENMASK(7, 6) +#define ST7701_CMD2_BK1_PWRCTRL1_APIS_MASK GENMASK(3, 2) +#define ST7701_CMD2_BK1_PWRCTRL1_APOS_MASK GENMASK(1, 0) +#define ST7701_CMD2_BK1_PWRCTRL2_AVDD_MASK GENMASK(5, 4) +#define ST7701_CMD2_BK1_PWRCTRL2_AVCL_MASK GENMASK(1, 0) +#define ST7701_CMD2_BK1_SPD1_ONES_MASK GENMASK(6, 4) +#define ST7701_CMD2_BK1_SPD1_T2D_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK1_SPD2_ONES_MASK GENMASK(6, 4) +#define ST7701_CMD2_BK1_SPD2_T3D_MASK GENMASK(3, 0) +#define ST7701_CMD2_BK1_MIPISET1_ONES BIT(7) +#define ST7701_CMD2_BK1_MIPISET1_EOT_EN BIT(3) #define CFIELD_PREP(_mask, _val) \ (((typeof(_mask))(_val) << (__builtin_ffsll(_mask) - 1)) & (_mask)) @@ -130,12 +132,16 @@ struct st7701_panel_desc { struct st7701 { struct drm_panel panel; struct mipi_dsi_device *dsi; + struct mipi_dbi dbi; const struct st7701_panel_desc *desc; struct regulator_bulk_data supplies[2]; struct gpio_desc *reset; unsigned int sleep_delay; enum drm_panel_orientation orientation; + + int (*write_command)(struct st7701 *st7701, u8 cmd, const u8 *seq, + size_t len); }; static inline struct st7701 *panel_to_st7701(struct drm_panel *panel) @@ -143,16 +149,22 @@ static inline struct st7701 *panel_to_st7701(struct drm_panel *panel) return container_of(panel, struct st7701, panel); } -static inline int st7701_dsi_write(struct st7701 *st7701, const void *seq, - size_t len) +static int st7701_dsi_write(struct st7701 *st7701, u8 cmd, const u8 *seq, + size_t len) +{ + return mipi_dsi_dcs_write(st7701->dsi, cmd, seq, len); +} + +static int st7701_dbi_write(struct st7701 *st7701, u8 cmd, const u8 *seq, + size_t len) { - return mipi_dsi_dcs_write_buffer(st7701->dsi, seq, len); + return mipi_dbi_command_stackbuf(&st7701->dbi, cmd, seq, len); } -#define ST7701_DSI(st7701, seq...) \ - { \ - const u8 d[] = { seq }; \ - st7701_dsi_write(st7701, d, ARRAY_SIZE(d)); \ +#define ST7701_WRITE(st7701, cmd, seq...) \ + { \ + const u8 d[] = { seq }; \ + st7701->write_command(st7701, cmd, d, ARRAY_SIZE(d)); \ } static u8 st7701_vgls_map(struct st7701 *st7701) @@ -185,11 +197,11 @@ static void st7701_switch_cmd_bkx(struct st7701 *st7701, bool cmd2, u8 bkx) u8 val; if (cmd2) - val = DSI_CMD2 | FIELD_PREP(DSI_CMD2BK_MASK, bkx); + val = ST7701_CMD2 | FIELD_PREP(ST7701_CMD2BK_MASK, bkx); else - val = DSI_CMD1; + val = ST7701_CMD1; - ST7701_DSI(st7701, DSI_CMD2BKX_SEL, 0x77, 0x01, 0x00, 0x00, val); + ST7701_WRITE(st7701, ST7701_CMD2BKX_SEL, 0x77, 0x01, 0x00, 0x00, val); } static void st7701_init_sequence(struct st7701 *st7701) @@ -199,22 +211,22 @@ static void st7701_init_sequence(struct st7701 *st7701) const u8 linecount8 = mode->vdisplay / 8; const u8 linecountrem2 = (mode->vdisplay % 8) / 2; - ST7701_DSI(st7701, MIPI_DCS_SOFT_RESET, 0x00); + ST7701_WRITE(st7701, MIPI_DCS_SOFT_RESET, 0x00); /* We need to wait 5ms before sending new commands */ msleep(5); - ST7701_DSI(st7701, MIPI_DCS_EXIT_SLEEP_MODE, 0x00); + ST7701_WRITE(st7701, MIPI_DCS_EXIT_SLEEP_MODE, 0x00); msleep(st7701->sleep_delay); /* Command2, BK0 */ st7701_switch_cmd_bkx(st7701, true, 0); - mipi_dsi_dcs_write(st7701->dsi, DSI_CMD2_BK0_PVGAMCTRL, - desc->pv_gamma, ARRAY_SIZE(desc->pv_gamma)); - mipi_dsi_dcs_write(st7701->dsi, DSI_CMD2_BK0_NVGAMCTRL, - desc->nv_gamma, ARRAY_SIZE(desc->nv_gamma)); + st7701->write_command(st7701, ST7701_CMD2_BK0_PVGAMCTRL, desc->pv_gamma, + ARRAY_SIZE(desc->pv_gamma)); + st7701->write_command(st7701, ST7701_CMD2_BK0_NVGAMCTRL, desc->nv_gamma, + ARRAY_SIZE(desc->nv_gamma)); /* * Vertical line count configuration: * Line[6:0]: select number of vertical lines of the TFT matrix in @@ -226,14 +238,14 @@ static void st7701_init_sequence(struct st7701 *st7701) * Total number of vertical lines: * LN = ((Line[6:0] + 1) * 8) + (LDE_EN ? Line_delta[1:0] * 2 : 0) */ - ST7701_DSI(st7701, DSI_CMD2_BK0_LNESET, - FIELD_PREP(DSI_CMD2_BK0_LNESET_LINE_MASK, linecount8 - 1) | - (linecountrem2 ? DSI_CMD2_BK0_LNESET_LDE_EN : 0), - FIELD_PREP(DSI_CMD2_BK0_LNESET_LINEDELTA, linecountrem2)); - ST7701_DSI(st7701, DSI_CMD2_BK0_PORCTRL, - FIELD_PREP(DSI_CMD2_BK0_PORCTRL_VBP_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK0_LNESET, + FIELD_PREP(ST7701_CMD2_BK0_LNESET_LINE_MASK, linecount8 - 1) | + (linecountrem2 ? ST7701_CMD2_BK0_LNESET_LDE_EN : 0), + FIELD_PREP(ST7701_CMD2_BK0_LNESET_LINEDELTA, linecountrem2)); + ST7701_WRITE(st7701, ST7701_CMD2_BK0_PORCTRL, + FIELD_PREP(ST7701_CMD2_BK0_PORCTRL_VBP_MASK, mode->vtotal - mode->vsync_end), - FIELD_PREP(DSI_CMD2_BK0_PORCTRL_VFP_MASK, + FIELD_PREP(ST7701_CMD2_BK0_PORCTRL_VFP_MASK, mode->vsync_start - mode->vdisplay)); /* * Horizontal pixel count configuration: @@ -241,70 +253,70 @@ static void st7701_init_sequence(struct st7701 *st7701) * The PCLK is number of pixel clock per line, which matches * mode htotal. The minimum is 512 PCLK. */ - ST7701_DSI(st7701, DSI_CMD2_BK0_INVSEL, - DSI_CMD2_BK0_INVSEL_ONES_MASK | - FIELD_PREP(DSI_CMD2_BK0_INVSEL_NLINV_MASK, desc->nlinv), - FIELD_PREP(DSI_CMD2_BK0_INVSEL_RTNI_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK0_INVSEL, + ST7701_CMD2_BK0_INVSEL_ONES_MASK | + FIELD_PREP(ST7701_CMD2_BK0_INVSEL_NLINV_MASK, desc->nlinv), + FIELD_PREP(ST7701_CMD2_BK0_INVSEL_RTNI_MASK, (clamp((u32)mode->htotal, 512U, 1008U) - 512) / 16)); /* Command2, BK1 */ st7701_switch_cmd_bkx(st7701, true, 1); /* Vop = 3.5375V + (VRHA[7:0] * 0.0125V) */ - ST7701_DSI(st7701, DSI_CMD2_BK1_VRHS, - FIELD_PREP(DSI_CMD2_BK1_VRHA_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK1_VRHS, + FIELD_PREP(ST7701_CMD2_BK1_VRHA_MASK, DIV_ROUND_CLOSEST(desc->vop_uv - 3537500, 12500))); /* Vcom = 0.1V + (VCOM[7:0] * 0.0125V) */ - ST7701_DSI(st7701, DSI_CMD2_BK1_VCOM, - FIELD_PREP(DSI_CMD2_BK1_VCOM_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK1_VCOM, + FIELD_PREP(ST7701_CMD2_BK1_VCOM_MASK, DIV_ROUND_CLOSEST(desc->vcom_uv - 100000, 12500))); /* Vgh = 11.5V + (VGHSS[7:0] * 0.5V) */ - ST7701_DSI(st7701, DSI_CMD2_BK1_VGHSS, - FIELD_PREP(DSI_CMD2_BK1_VGHSS_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK1_VGHSS, + FIELD_PREP(ST7701_CMD2_BK1_VGHSS_MASK, DIV_ROUND_CLOSEST(clamp(desc->vgh_mv, (u16)11500, (u16)17000) - 11500, 500))); - ST7701_DSI(st7701, DSI_CMD2_BK1_TESTCMD, DSI_CMD2_BK1_TESTCMD_VAL); + ST7701_WRITE(st7701, ST7701_CMD2_BK1_TESTCMD, ST7701_CMD2_BK1_TESTCMD_VAL); /* Vgl is non-linear */ - ST7701_DSI(st7701, DSI_CMD2_BK1_VGLS, - DSI_CMD2_BK1_VGLS_ONES | - FIELD_PREP(DSI_CMD2_BK1_VGLS_MASK, st7701_vgls_map(st7701))); + ST7701_WRITE(st7701, ST7701_CMD2_BK1_VGLS, + ST7701_CMD2_BK1_VGLS_ONES | + FIELD_PREP(ST7701_CMD2_BK1_VGLS_MASK, st7701_vgls_map(st7701))); - ST7701_DSI(st7701, DSI_CMD2_BK1_PWCTLR1, - FIELD_PREP(DSI_CMD2_BK1_PWRCTRL1_AP_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK1_PWCTLR1, + FIELD_PREP(ST7701_CMD2_BK1_PWRCTRL1_AP_MASK, desc->gamma_op_bias) | - FIELD_PREP(DSI_CMD2_BK1_PWRCTRL1_APIS_MASK, + FIELD_PREP(ST7701_CMD2_BK1_PWRCTRL1_APIS_MASK, desc->input_op_bias) | - FIELD_PREP(DSI_CMD2_BK1_PWRCTRL1_APOS_MASK, + FIELD_PREP(ST7701_CMD2_BK1_PWRCTRL1_APOS_MASK, desc->output_op_bias)); /* Avdd = 6.2V + (AVDD[1:0] * 0.2V) , Avcl = -4.4V - (AVCL[1:0] * 0.2V) */ - ST7701_DSI(st7701, DSI_CMD2_BK1_PWCTLR2, - FIELD_PREP(DSI_CMD2_BK1_PWRCTRL2_AVDD_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK1_PWCTLR2, + FIELD_PREP(ST7701_CMD2_BK1_PWRCTRL2_AVDD_MASK, DIV_ROUND_CLOSEST(desc->avdd_mv - 6200, 200)) | - FIELD_PREP(DSI_CMD2_BK1_PWRCTRL2_AVCL_MASK, + FIELD_PREP(ST7701_CMD2_BK1_PWRCTRL2_AVCL_MASK, DIV_ROUND_CLOSEST(-4400 - desc->avcl_mv, 200))); /* T2D = 0.2us * T2D[3:0] */ - ST7701_DSI(st7701, DSI_CMD2_BK1_SPD1, - DSI_CMD2_BK1_SPD1_ONES_MASK | - FIELD_PREP(DSI_CMD2_BK1_SPD1_T2D_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK1_SPD1, + ST7701_CMD2_BK1_SPD1_ONES_MASK | + FIELD_PREP(ST7701_CMD2_BK1_SPD1_T2D_MASK, DIV_ROUND_CLOSEST(desc->t2d_ns, 200))); /* T3D = 4us + (0.8us * T3D[3:0]) */ - ST7701_DSI(st7701, DSI_CMD2_BK1_SPD2, - DSI_CMD2_BK1_SPD2_ONES_MASK | - FIELD_PREP(DSI_CMD2_BK1_SPD2_T3D_MASK, + ST7701_WRITE(st7701, ST7701_CMD2_BK1_SPD2, + ST7701_CMD2_BK1_SPD2_ONES_MASK | + FIELD_PREP(ST7701_CMD2_BK1_SPD2_T3D_MASK, DIV_ROUND_CLOSEST(desc->t3d_ns - 4000, 800))); - ST7701_DSI(st7701, DSI_CMD2_BK1_MIPISET1, - DSI_CMD2_BK1_MIPISET1_ONES | - (desc->eot_en ? DSI_CMD2_BK1_MIPISET1_EOT_EN : 0)); + ST7701_WRITE(st7701, ST7701_CMD2_BK1_MIPISET1, + ST7701_CMD2_BK1_MIPISET1_ONES | + (desc->eot_en ? ST7701_CMD2_BK1_MIPISET1_EOT_EN : 0)); } static void ts8550b_gip_sequence(struct st7701 *st7701) @@ -313,89 +325,89 @@ static void ts8550b_gip_sequence(struct st7701 *st7701) * ST7701_SPEC_V1.2 is unable to provide enough information above this * specific command sequence, so grab the same from vendor BSP driver. */ - ST7701_DSI(st7701, 0xE0, 0x00, 0x00, 0x02); - ST7701_DSI(st7701, 0xE1, 0x0B, 0x00, 0x0D, 0x00, 0x0C, 0x00, 0x0E, + ST7701_WRITE(st7701, 0xE0, 0x00, 0x00, 0x02); + ST7701_WRITE(st7701, 0xE1, 0x0B, 0x00, 0x0D, 0x00, 0x0C, 0x00, 0x0E, 0x00, 0x00, 0x44, 0x44); - ST7701_DSI(st7701, 0xE2, 0x33, 0x33, 0x44, 0x44, 0x64, 0x00, 0x66, + ST7701_WRITE(st7701, 0xE2, 0x33, 0x33, 0x44, 0x44, 0x64, 0x00, 0x66, 0x00, 0x65, 0x00, 0x67, 0x00, 0x00); - ST7701_DSI(st7701, 0xE3, 0x00, 0x00, 0x33, 0x33); - ST7701_DSI(st7701, 0xE4, 0x44, 0x44); - ST7701_DSI(st7701, 0xE5, 0x0C, 0x78, 0x3C, 0xA0, 0x0E, 0x78, 0x3C, + ST7701_WRITE(st7701, 0xE3, 0x00, 0x00, 0x33, 0x33); + ST7701_WRITE(st7701, 0xE4, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE5, 0x0C, 0x78, 0x3C, 0xA0, 0x0E, 0x78, 0x3C, 0xA0, 0x10, 0x78, 0x3C, 0xA0, 0x12, 0x78, 0x3C, 0xA0); - ST7701_DSI(st7701, 0xE6, 0x00, 0x00, 0x33, 0x33); - ST7701_DSI(st7701, 0xE7, 0x44, 0x44); - ST7701_DSI(st7701, 0xE8, 0x0D, 0x78, 0x3C, 0xA0, 0x0F, 0x78, 0x3C, + ST7701_WRITE(st7701, 0xE6, 0x00, 0x00, 0x33, 0x33); + ST7701_WRITE(st7701, 0xE7, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE8, 0x0D, 0x78, 0x3C, 0xA0, 0x0F, 0x78, 0x3C, 0xA0, 0x11, 0x78, 0x3C, 0xA0, 0x13, 0x78, 0x3C, 0xA0); - ST7701_DSI(st7701, 0xEB, 0x02, 0x02, 0x39, 0x39, 0xEE, 0x44, 0x00); - ST7701_DSI(st7701, 0xEC, 0x00, 0x00); - ST7701_DSI(st7701, 0xED, 0xFF, 0xF1, 0x04, 0x56, 0x72, 0x3F, 0xFF, + ST7701_WRITE(st7701, 0xEB, 0x02, 0x02, 0x39, 0x39, 0xEE, 0x44, 0x00); + ST7701_WRITE(st7701, 0xEC, 0x00, 0x00); + ST7701_WRITE(st7701, 0xED, 0xFF, 0xF1, 0x04, 0x56, 0x72, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0xF3, 0x27, 0x65, 0x40, 0x1F, 0xFF); } static void dmt028vghmcmi_1a_gip_sequence(struct st7701 *st7701) { - ST7701_DSI(st7701, 0xEE, 0x42); - ST7701_DSI(st7701, 0xE0, 0x00, 0x00, 0x02); + ST7701_WRITE(st7701, 0xEE, 0x42); + ST7701_WRITE(st7701, 0xE0, 0x00, 0x00, 0x02); - ST7701_DSI(st7701, 0xE1, + ST7701_WRITE(st7701, 0xE1, 0x04, 0xA0, 0x06, 0xA0, 0x05, 0xA0, 0x07, 0xA0, 0x00, 0x44, 0x44); - ST7701_DSI(st7701, 0xE2, + ST7701_WRITE(st7701, 0xE2, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - ST7701_DSI(st7701, 0xE3, + ST7701_WRITE(st7701, 0xE3, 0x00, 0x00, 0x22, 0x22); - ST7701_DSI(st7701, 0xE4, 0x44, 0x44); - ST7701_DSI(st7701, 0xE5, + ST7701_WRITE(st7701, 0xE4, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE5, 0x0C, 0x90, 0xA0, 0xA0, 0x0E, 0x92, 0xA0, 0xA0, 0x08, 0x8C, 0xA0, 0xA0, 0x0A, 0x8E, 0xA0, 0xA0); - ST7701_DSI(st7701, 0xE6, + ST7701_WRITE(st7701, 0xE6, 0x00, 0x00, 0x22, 0x22); - ST7701_DSI(st7701, 0xE7, 0x44, 0x44); - ST7701_DSI(st7701, 0xE8, + ST7701_WRITE(st7701, 0xE7, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE8, 0x0D, 0x91, 0xA0, 0xA0, 0x0F, 0x93, 0xA0, 0xA0, 0x09, 0x8D, 0xA0, 0xA0, 0x0B, 0x8F, 0xA0, 0xA0); - ST7701_DSI(st7701, 0xEB, + ST7701_WRITE(st7701, 0xEB, 0x00, 0x00, 0xE4, 0xE4, 0x44, 0x00, 0x00); - ST7701_DSI(st7701, 0xED, + ST7701_WRITE(st7701, 0xED, 0xFF, 0xF5, 0x47, 0x6F, 0x0B, 0xA1, 0xAB, 0xFF, 0xFF, 0xBA, 0x1A, 0xB0, 0xF6, 0x74, 0x5F, 0xFF); - ST7701_DSI(st7701, 0xEF, + ST7701_WRITE(st7701, 0xEF, 0x08, 0x08, 0x08, 0x40, 0x3F, 0x64); st7701_switch_cmd_bkx(st7701, false, 0); st7701_switch_cmd_bkx(st7701, true, 3); - ST7701_DSI(st7701, 0xE6, 0x7C); - ST7701_DSI(st7701, 0xE8, 0x00, 0x0E); + ST7701_WRITE(st7701, 0xE6, 0x7C); + ST7701_WRITE(st7701, 0xE8, 0x00, 0x0E); st7701_switch_cmd_bkx(st7701, false, 0); - ST7701_DSI(st7701, 0x11); + ST7701_WRITE(st7701, 0x11); msleep(120); st7701_switch_cmd_bkx(st7701, true, 3); - ST7701_DSI(st7701, 0xE8, 0x00, 0x0C); + ST7701_WRITE(st7701, 0xE8, 0x00, 0x0C); msleep(10); - ST7701_DSI(st7701, 0xE8, 0x00, 0x00); + ST7701_WRITE(st7701, 0xE8, 0x00, 0x00); st7701_switch_cmd_bkx(st7701, false, 0); - ST7701_DSI(st7701, 0x11); + ST7701_WRITE(st7701, 0x11); msleep(120); - ST7701_DSI(st7701, 0xE8, 0x00, 0x00); + ST7701_WRITE(st7701, 0xE8, 0x00, 0x00); st7701_switch_cmd_bkx(st7701, false, 0); - ST7701_DSI(st7701, 0x3A, 0x70); + ST7701_WRITE(st7701, 0x3A, 0x70); } static void kd50t048a_gip_sequence(struct st7701 *st7701) @@ -404,59 +416,108 @@ static void kd50t048a_gip_sequence(struct st7701 *st7701) * ST7701_SPEC_V1.2 is unable to provide enough information above this * specific command sequence, so grab the same from vendor BSP driver. */ - ST7701_DSI(st7701, 0xE0, 0x00, 0x00, 0x02); - ST7701_DSI(st7701, 0xE1, 0x08, 0x00, 0x0A, 0x00, 0x07, 0x00, 0x09, + ST7701_WRITE(st7701, 0xE0, 0x00, 0x00, 0x02); + ST7701_WRITE(st7701, 0xE1, 0x08, 0x00, 0x0A, 0x00, 0x07, 0x00, 0x09, 0x00, 0x00, 0x33, 0x33); - ST7701_DSI(st7701, 0xE2, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + ST7701_WRITE(st7701, 0xE2, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - ST7701_DSI(st7701, 0xE3, 0x00, 0x00, 0x33, 0x33); - ST7701_DSI(st7701, 0xE4, 0x44, 0x44); - ST7701_DSI(st7701, 0xE5, 0x0E, 0x60, 0xA0, 0xA0, 0x10, 0x60, 0xA0, + ST7701_WRITE(st7701, 0xE3, 0x00, 0x00, 0x33, 0x33); + ST7701_WRITE(st7701, 0xE4, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE5, 0x0E, 0x60, 0xA0, 0xA0, 0x10, 0x60, 0xA0, 0xA0, 0x0A, 0x60, 0xA0, 0xA0, 0x0C, 0x60, 0xA0, 0xA0); - ST7701_DSI(st7701, 0xE6, 0x00, 0x00, 0x33, 0x33); - ST7701_DSI(st7701, 0xE7, 0x44, 0x44); - ST7701_DSI(st7701, 0xE8, 0x0D, 0x60, 0xA0, 0xA0, 0x0F, 0x60, 0xA0, + ST7701_WRITE(st7701, 0xE6, 0x00, 0x00, 0x33, 0x33); + ST7701_WRITE(st7701, 0xE7, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE8, 0x0D, 0x60, 0xA0, 0xA0, 0x0F, 0x60, 0xA0, 0xA0, 0x09, 0x60, 0xA0, 0xA0, 0x0B, 0x60, 0xA0, 0xA0); - ST7701_DSI(st7701, 0xEB, 0x02, 0x01, 0xE4, 0xE4, 0x44, 0x00, 0x40); - ST7701_DSI(st7701, 0xEC, 0x02, 0x01); - ST7701_DSI(st7701, 0xED, 0xAB, 0x89, 0x76, 0x54, 0x01, 0xFF, 0xFF, + ST7701_WRITE(st7701, 0xEB, 0x02, 0x01, 0xE4, 0xE4, 0x44, 0x00, 0x40); + ST7701_WRITE(st7701, 0xEC, 0x02, 0x01); + ST7701_WRITE(st7701, 0xED, 0xAB, 0x89, 0x76, 0x54, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x10, 0x45, 0x67, 0x98, 0xBA); } static void rg_arc_gip_sequence(struct st7701 *st7701) { st7701_switch_cmd_bkx(st7701, true, 3); - ST7701_DSI(st7701, 0xEF, 0x08); + ST7701_WRITE(st7701, 0xEF, 0x08); st7701_switch_cmd_bkx(st7701, true, 0); - ST7701_DSI(st7701, 0xC7, 0x04); - ST7701_DSI(st7701, 0xCC, 0x38); + ST7701_WRITE(st7701, 0xC7, 0x04); + ST7701_WRITE(st7701, 0xCC, 0x38); st7701_switch_cmd_bkx(st7701, true, 1); - ST7701_DSI(st7701, 0xB9, 0x10); - ST7701_DSI(st7701, 0xBC, 0x03); - ST7701_DSI(st7701, 0xC0, 0x89); - ST7701_DSI(st7701, 0xE0, 0x00, 0x00, 0x02); - ST7701_DSI(st7701, 0xE1, 0x04, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, + ST7701_WRITE(st7701, 0xB9, 0x10); + ST7701_WRITE(st7701, 0xBC, 0x03); + ST7701_WRITE(st7701, 0xC0, 0x89); + ST7701_WRITE(st7701, 0xE0, 0x00, 0x00, 0x02); + ST7701_WRITE(st7701, 0xE1, 0x04, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x00, 0x20, 0x20); - ST7701_DSI(st7701, 0xE2, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + ST7701_WRITE(st7701, 0xE2, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - ST7701_DSI(st7701, 0xE3, 0x00, 0x00, 0x33, 0x00); - ST7701_DSI(st7701, 0xE4, 0x22, 0x00); - ST7701_DSI(st7701, 0xE5, 0x04, 0x5C, 0xA0, 0xA0, 0x06, 0x5C, 0xA0, + ST7701_WRITE(st7701, 0xE3, 0x00, 0x00, 0x33, 0x00); + ST7701_WRITE(st7701, 0xE4, 0x22, 0x00); + ST7701_WRITE(st7701, 0xE5, 0x04, 0x5C, 0xA0, 0xA0, 0x06, 0x5C, 0xA0, 0xA0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - ST7701_DSI(st7701, 0xE6, 0x00, 0x00, 0x33, 0x00); - ST7701_DSI(st7701, 0xE7, 0x22, 0x00); - ST7701_DSI(st7701, 0xE8, 0x05, 0x5C, 0xA0, 0xA0, 0x07, 0x5C, 0xA0, + ST7701_WRITE(st7701, 0xE6, 0x00, 0x00, 0x33, 0x00); + ST7701_WRITE(st7701, 0xE7, 0x22, 0x00); + ST7701_WRITE(st7701, 0xE8, 0x05, 0x5C, 0xA0, 0xA0, 0x07, 0x5C, 0xA0, 0xA0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - ST7701_DSI(st7701, 0xEB, 0x02, 0x00, 0x40, 0x40, 0x00, 0x00, 0x00); - ST7701_DSI(st7701, 0xEC, 0x00, 0x00); - ST7701_DSI(st7701, 0xED, 0xFA, 0x45, 0x0B, 0xFF, 0xFF, 0xFF, 0xFF, + ST7701_WRITE(st7701, 0xEB, 0x02, 0x00, 0x40, 0x40, 0x00, 0x00, 0x00); + ST7701_WRITE(st7701, 0xEC, 0x00, 0x00); + ST7701_WRITE(st7701, 0xED, 0xFA, 0x45, 0x0B, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xB0, 0x54, 0xAF); - ST7701_DSI(st7701, 0xEF, 0x08, 0x08, 0x08, 0x45, 0x3F, 0x54); + ST7701_WRITE(st7701, 0xEF, 0x08, 0x08, 0x08, 0x45, 0x3F, 0x54); + st7701_switch_cmd_bkx(st7701, false, 0); + ST7701_WRITE(st7701, MIPI_DCS_SET_ADDRESS_MODE, 0x17); + ST7701_WRITE(st7701, MIPI_DCS_SET_PIXEL_FORMAT, 0x77); + ST7701_WRITE(st7701, MIPI_DCS_EXIT_SLEEP_MODE, 0x00); + msleep(120); +} + +static void rg28xx_gip_sequence(struct st7701 *st7701) +{ + st7701_switch_cmd_bkx(st7701, true, 3); + ST7701_WRITE(st7701, 0xEF, 0x08); + + st7701_switch_cmd_bkx(st7701, true, 0); + ST7701_WRITE(st7701, 0xC3, 0x02, 0x10, 0x02); + ST7701_WRITE(st7701, 0xC7, 0x04); + ST7701_WRITE(st7701, 0xCC, 0x10); + + st7701_switch_cmd_bkx(st7701, true, 1); + ST7701_WRITE(st7701, 0xEE, 0x42); + ST7701_WRITE(st7701, 0xE0, 0x00, 0x00, 0x02); + + ST7701_WRITE(st7701, 0xE1, 0x04, 0xA0, 0x06, 0xA0, 0x05, 0xA0, 0x07, 0xA0, + 0x00, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE2, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00); + ST7701_WRITE(st7701, 0xE3, 0x00, 0x00, 0x22, 0x22); + ST7701_WRITE(st7701, 0xE4, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE5, 0x0C, 0x90, 0xA0, 0xA0, 0x0E, 0x92, 0xA0, 0xA0, + 0x08, 0x8C, 0xA0, 0xA0, 0x0A, 0x8E, 0xA0, 0xA0); + ST7701_WRITE(st7701, 0xE6, 0x00, 0x00, 0x22, 0x22); + ST7701_WRITE(st7701, 0xE7, 0x44, 0x44); + ST7701_WRITE(st7701, 0xE8, 0x0D, 0x91, 0xA0, 0xA0, 0x0F, 0x93, 0xA0, 0xA0, + 0x09, 0x8D, 0xA0, 0xA0, 0x0B, 0x8F, 0xA0, 0xA0); + ST7701_WRITE(st7701, 0xEB, 0x00, 0x00, 0xE4, 0xE4, 0x44, 0x00, 0x40); + ST7701_WRITE(st7701, 0xED, 0xFF, 0xF5, 0x47, 0x6F, 0x0B, 0xA1, 0xBA, 0xFF, + 0xFF, 0xAB, 0x1A, 0xB0, 0xF6, 0x74, 0x5F, 0xFF); + ST7701_WRITE(st7701, 0xEF, 0x08, 0x08, 0x08, 0x45, 0x3F, 0x54); + st7701_switch_cmd_bkx(st7701, false, 0); - ST7701_DSI(st7701, MIPI_DCS_SET_ADDRESS_MODE, 0x17); - ST7701_DSI(st7701, MIPI_DCS_SET_PIXEL_FORMAT, 0x77); - ST7701_DSI(st7701, MIPI_DCS_EXIT_SLEEP_MODE, 0x00); + + st7701_switch_cmd_bkx(st7701, true, 3); + ST7701_WRITE(st7701, 0xE6, 0x16); + ST7701_WRITE(st7701, 0xE8, 0x00, 0x0E); + + st7701_switch_cmd_bkx(st7701, false, 0); + ST7701_WRITE(st7701, MIPI_DCS_SET_ADDRESS_MODE, 0x10); + ST7701_WRITE(st7701, MIPI_DCS_EXIT_SLEEP_MODE); msleep(120); + + st7701_switch_cmd_bkx(st7701, true, 3); + ST7701_WRITE(st7701, 0xE8, 0x00, 0x0C); + msleep(10); + ST7701_WRITE(st7701, 0xE8, 0x00, 0x00); + st7701_switch_cmd_bkx(st7701, false, 0); } static int st7701_prepare(struct drm_panel *panel) @@ -490,7 +551,7 @@ static int st7701_enable(struct drm_panel *panel) { struct st7701 *st7701 = panel_to_st7701(panel); - ST7701_DSI(st7701, MIPI_DCS_SET_DISPLAY_ON, 0x00); + ST7701_WRITE(st7701, MIPI_DCS_SET_DISPLAY_ON, 0x00); return 0; } @@ -499,7 +560,7 @@ static int st7701_disable(struct drm_panel *panel) { struct st7701 *st7701 = panel_to_st7701(panel); - ST7701_DSI(st7701, MIPI_DCS_SET_DISPLAY_OFF, 0x00); + ST7701_WRITE(st7701, MIPI_DCS_SET_DISPLAY_OFF, 0x00); return 0; } @@ -508,7 +569,7 @@ static int st7701_unprepare(struct drm_panel *panel) { struct st7701 *st7701 = panel_to_st7701(panel); - ST7701_DSI(st7701, MIPI_DCS_ENTER_SLEEP_MODE, 0x00); + ST7701_WRITE(st7701, MIPI_DCS_ENTER_SLEEP_MODE, 0x00); msleep(st7701->sleep_delay); @@ -539,7 +600,7 @@ static int st7701_get_modes(struct drm_panel *panel, mode = drm_mode_duplicate(connector->dev, desc_mode); if (!mode) { - dev_err(&st7701->dsi->dev, "failed to add mode %ux%u@%u\n", + dev_err(panel->dev, "failed to add mode %ux%u@%u\n", desc_mode->hdisplay, desc_mode->vdisplay, drm_mode_vrefresh(desc_mode)); return -ENOMEM; @@ -602,62 +663,62 @@ static const struct st7701_panel_desc ts8550b_desc = { .panel_sleep_delay = 80, /* panel need extra 80ms for sleep out cmd */ .pv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0xe), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x15), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0xf), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x8), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x8), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x23), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x4), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0x12), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x2b), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x34), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0xe), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x15), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xf), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x8), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x8), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x23), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x4), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0x12), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x2b), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x34), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) }, .nv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0xe), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0x2) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x15), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0xf), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x13), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x7), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x9), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x22), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x4), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x10), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0xe), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x2c), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x34), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0xe), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0x2) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x15), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xf), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x13), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x7), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x9), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x22), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x4), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x10), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0xe), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x2c), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x34), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) }, .nlinv = 7, .vop_uv = 4400000, @@ -703,62 +764,62 @@ static const struct st7701_panel_desc dmt028vghmcmi_1a_desc = { .panel_sleep_delay = 5, /* panel need extra 5ms for sleep out cmd */ .pv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0x10), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x17), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0xd), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x6), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x5), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x7), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x1f), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x4), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x11), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0xe), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x29), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x30), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0x10), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x17), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xd), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x6), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x7), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x1f), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x4), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x11), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0xe), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x29), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x30), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) }, .nv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0xd), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x14), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0xe), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x6), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x4), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x20), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x5), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0x13), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x26), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x30), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0xd), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x14), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xe), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x6), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x4), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x20), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0x13), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x26), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x30), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) }, .nlinv = 1, .vop_uv = 4800000, @@ -802,62 +863,62 @@ static const struct st7701_panel_desc kd50t048a_desc = { .panel_sleep_delay = 0, .pv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0xd), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x14), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0xd), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x10), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x5), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x2), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x1e), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x5), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0x11), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 2) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x23), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x29), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x18) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0xd), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x14), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xd), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x10), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x2), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x1e), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 2) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x23), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x29), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x18) }, .nv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0xc), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x14), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0xc), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x10), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x5), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x3), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x7), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x20), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x5), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0x11), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 2) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x24), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x29), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x18) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0xc), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x14), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xc), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x10), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x3), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x7), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x20), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 2) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x24), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x29), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x18) }, .nlinv = 1, .vop_uv = 4887500, @@ -901,62 +962,62 @@ static const struct st7701_panel_desc rg_arc_desc = { .panel_sleep_delay = 80, .pv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0x01) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0x16), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x1d), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0x0e), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x12), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x06), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x0c), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x0a), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x09), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x25), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x00), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x03), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0x00), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x3f), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x3f), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1c) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0x01) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0x16), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x1d), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0x0e), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x12), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x06), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x0c), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x0a), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x09), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x25), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x00), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x03), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0x00), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x3f), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x3f), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1c) }, .nv_gamma = { - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0x01) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC0_MASK, 0), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC4_MASK, 0x16), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC8_MASK, 0x1e), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC16_MASK, 0x0e), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC52_MASK, 0x06), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC80_MASK, 0x0c), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC108_MASK, 0x08), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC147_MASK, 0x09), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC175_MASK, 0x26), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC203_MASK, 0x00), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC231_MASK, 0x15), - - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC239_MASK, 0x00), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC247_MASK, 0x3f), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC251_MASK, 0x3f), - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | - CFIELD_PREP(DSI_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1c) + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0x01) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0x16), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x1e), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0x0e), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x06), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x0c), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x08), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x09), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x26), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x00), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x15), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0x00), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x3f), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x3f), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1c) }, .nlinv = 0, .vop_uv = 4500000, @@ -974,42 +1035,148 @@ static const struct st7701_panel_desc rg_arc_desc = { .gip_sequence = rg_arc_gip_sequence, }; -static int st7701_dsi_probe(struct mipi_dsi_device *dsi) +static const struct drm_display_mode rg28xx_mode = { + .clock = 22325, + + .hdisplay = 480, + .hsync_start = 480 + 40, + .hsync_end = 480 + 40 + 4, + .htotal = 480 + 40 + 4 + 20, + + .vdisplay = 640, + .vsync_start = 640 + 2, + .vsync_end = 640 + 2 + 40, + .vtotal = 640 + 2 + 40 + 16, + + .width_mm = 44, + .height_mm = 58, + + .flags = DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC, + + .type = DRM_MODE_TYPE_DRIVER | DRM_MODE_TYPE_PREFERRED, +}; + +static const struct st7701_panel_desc rg28xx_desc = { + .mode = &rg28xx_mode, + + .panel_sleep_delay = 80, + + .pv_gamma = { + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0x10), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x17), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xd), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x6), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x7), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x1f), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x4), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x11), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0xe), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x29), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x30), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) + }, + .nv_gamma = { + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC0_MASK, 0), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC4_MASK, 0xd), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC8_MASK, 0x14), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC16_MASK, 0xe), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC24_MASK, 0x11), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC52_MASK, 0x6), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC80_MASK, 0x4), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC108_MASK, 0x8), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC147_MASK, 0x8), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC175_MASK, 0x20), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC203_MASK, 0x5), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC231_MASK, 0x13), + + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC239_MASK, 0x13), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC247_MASK, 0x26), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC251_MASK, 0x30), + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_AJ_MASK, 0) | + CFIELD_PREP(ST7701_CMD2_BK0_GAMCTRL_VC255_MASK, 0x1f) + }, + .nlinv = 7, + .vop_uv = 4800000, + .vcom_uv = 1512500, + .vgh_mv = 15000, + .vgl_mv = -11730, + .avdd_mv = 6600, + .avcl_mv = -4400, + .gamma_op_bias = OP_BIAS_MIDDLE, + .input_op_bias = OP_BIAS_MIN, + .output_op_bias = OP_BIAS_MIN, + .t2d_ns = 1600, + .t3d_ns = 10400, + .eot_en = true, + .gip_sequence = rg28xx_gip_sequence, +}; + +static void st7701_cleanup(void *data) +{ + struct st7701 *st7701 = (struct st7701 *)data; + + drm_panel_remove(&st7701->panel); + drm_panel_disable(&st7701->panel); + drm_panel_unprepare(&st7701->panel); +} + +static int st7701_probe(struct device *dev, int connector_type) { const struct st7701_panel_desc *desc; struct st7701 *st7701; int ret; - st7701 = devm_kzalloc(&dsi->dev, sizeof(*st7701), GFP_KERNEL); + st7701 = devm_kzalloc(dev, sizeof(*st7701), GFP_KERNEL); if (!st7701) return -ENOMEM; - desc = of_device_get_match_data(&dsi->dev); - dsi->mode_flags = MIPI_DSI_MODE_VIDEO | MIPI_DSI_MODE_VIDEO_BURST | - MIPI_DSI_MODE_LPM | MIPI_DSI_CLOCK_NON_CONTINUOUS; - dsi->format = desc->format; - dsi->lanes = desc->lanes; + desc = of_device_get_match_data(dev); + if (!desc) + return -ENODEV; st7701->supplies[0].supply = "VCC"; st7701->supplies[1].supply = "IOVCC"; - ret = devm_regulator_bulk_get(&dsi->dev, ARRAY_SIZE(st7701->supplies), + ret = devm_regulator_bulk_get(dev, ARRAY_SIZE(st7701->supplies), st7701->supplies); if (ret < 0) return ret; - st7701->reset = devm_gpiod_get(&dsi->dev, "reset", GPIOD_OUT_LOW); + st7701->reset = devm_gpiod_get(dev, "reset", GPIOD_OUT_LOW); if (IS_ERR(st7701->reset)) { - dev_err(&dsi->dev, "Couldn't get our reset GPIO\n"); + dev_err(dev, "Couldn't get our reset GPIO\n"); return PTR_ERR(st7701->reset); } - ret = of_drm_get_panel_orientation(dsi->dev.of_node, &st7701->orientation); + ret = of_drm_get_panel_orientation(dev->of_node, &st7701->orientation); if (ret < 0) - return dev_err_probe(&dsi->dev, ret, "Failed to get orientation\n"); + return dev_err_probe(dev, ret, "Failed to get orientation\n"); - drm_panel_init(&st7701->panel, &dsi->dev, &st7701_funcs, - DRM_MODE_CONNECTOR_DSI); + drm_panel_init(&st7701->panel, dev, &st7701_funcs, connector_type); /** * Once sleep out has been issued, ST7701 IC required to wait 120ms @@ -1028,48 +1195,143 @@ static int st7701_dsi_probe(struct mipi_dsi_device *dsi) drm_panel_add(&st7701->panel); - mipi_dsi_set_drvdata(dsi, st7701); - st7701->dsi = dsi; + dev_set_drvdata(dev, st7701); st7701->desc = desc; - ret = mipi_dsi_attach(dsi); - if (ret) - goto err_attach; + return devm_add_action_or_reset(dev, st7701_cleanup, st7701); +} + +static int st7701_dsi_probe(struct mipi_dsi_device *dsi) +{ + struct st7701 *st7701; + int err; + + err = st7701_probe(&dsi->dev, DRM_MODE_CONNECTOR_DSI); + if (err) + return err; + + st7701 = dev_get_drvdata(&dsi->dev); + st7701->dsi = dsi; + st7701->write_command = st7701_dsi_write; + + if (!st7701->desc->lanes) + return dev_err_probe(&dsi->dev, -EINVAL, "This panel is not for MIPI DSI\n"); + + dsi->mode_flags = MIPI_DSI_MODE_VIDEO | MIPI_DSI_MODE_VIDEO_BURST | + MIPI_DSI_MODE_LPM | MIPI_DSI_CLOCK_NON_CONTINUOUS; + dsi->format = st7701->desc->format; + dsi->lanes = st7701->desc->lanes; + + err = mipi_dsi_attach(dsi); + if (err) + return dev_err_probe(&dsi->dev, err, "Failed to init MIPI DSI\n"); return 0; +} -err_attach: - drm_panel_remove(&st7701->panel); - return ret; +static int st7701_spi_probe(struct spi_device *spi) +{ + struct st7701 *st7701; + struct gpio_desc *dc; + int err; + + err = st7701_probe(&spi->dev, DRM_MODE_CONNECTOR_DPI); + if (err) + return err; + + st7701 = dev_get_drvdata(&spi->dev); + st7701->write_command = st7701_dbi_write; + + dc = devm_gpiod_get_optional(&spi->dev, "dc", GPIOD_OUT_LOW); + if (IS_ERR(dc)) + return dev_err_probe(&spi->dev, PTR_ERR(dc), "Failed to get GPIO for D/CX\n"); + + err = mipi_dbi_spi_init(spi, &st7701->dbi, dc); + if (err) + return dev_err_probe(&spi->dev, err, "Failed to init MIPI DBI\n"); + st7701->dbi.read_commands = NULL; + + return 0; } static void st7701_dsi_remove(struct mipi_dsi_device *dsi) { - struct st7701 *st7701 = mipi_dsi_get_drvdata(dsi); - mipi_dsi_detach(dsi); - drm_panel_remove(&st7701->panel); } -static const struct of_device_id st7701_of_match[] = { +static const struct of_device_id st7701_dsi_of_match[] = { { .compatible = "anbernic,rg-arc-panel", .data = &rg_arc_desc }, { .compatible = "densitron,dmt028vghmcmi-1a", .data = &dmt028vghmcmi_1a_desc }, { .compatible = "elida,kd50t048a", .data = &kd50t048a_desc }, { .compatible = "techstar,ts8550b", .data = &ts8550b_desc }, { } }; -MODULE_DEVICE_TABLE(of, st7701_of_match); +MODULE_DEVICE_TABLE(of, st7701_dsi_of_match); + +static const struct of_device_id st7701_spi_of_match[] = { + { .compatible = "anbernic,rg28xx-panel", .data = &rg28xx_desc }, + { /* sentinel */ } +}; +MODULE_DEVICE_TABLE(of, st7701_spi_of_match); + +static const struct spi_device_id st7701_spi_ids[] = { + { "rg28xx-panel" }, + { /* sentinel */ } +}; +MODULE_DEVICE_TABLE(spi, st7701_spi_ids); static struct mipi_dsi_driver st7701_dsi_driver = { .probe = st7701_dsi_probe, .remove = st7701_dsi_remove, .driver = { .name = "st7701", - .of_match_table = st7701_of_match, + .of_match_table = st7701_dsi_of_match, }, }; -module_mipi_dsi_driver(st7701_dsi_driver); + +static struct spi_driver st7701_spi_driver = { + .probe = st7701_spi_probe, + .id_table = st7701_spi_ids, + .driver = { + .name = "st7701", + .of_match_table = st7701_spi_of_match, + }, +}; + +static int __init st7701_driver_init(void) +{ + int err; + + if (IS_ENABLED(CONFIG_SPI)) { + err = spi_register_driver(&st7701_spi_driver); + if (err) + return err; + } + + if (IS_ENABLED(CONFIG_DRM_MIPI_DSI)) { + err = mipi_dsi_driver_register(&st7701_dsi_driver); + if (err) { + if (IS_ENABLED(CONFIG_SPI)) + spi_unregister_driver(&st7701_spi_driver); + return err; + } + } + + return 0; +} +module_init(st7701_driver_init); + +static void __exit st7701_driver_exit(void) +{ + if (IS_ENABLED(CONFIG_DRM_MIPI_DSI)) + mipi_dsi_driver_unregister(&st7701_dsi_driver); + + if (IS_ENABLED(CONFIG_SPI)) + spi_unregister_driver(&st7701_spi_driver); +} +module_exit(st7701_driver_exit); MODULE_AUTHOR("Jagan Teki <jagan@amarulasolutions.com>"); +MODULE_AUTHOR("Hironori KIKUCHI <kikuchan98@gmail.com>"); MODULE_DESCRIPTION("Sitronix ST7701 LCD Panel Driver"); MODULE_LICENSE("GPL"); |