1 // SPDX-License-Identifier: GPL-2.0
3 * Elida kd35t133 5.5" MIPI-DSI panel driver
4 * Copyright (C) 2020 Theobroma Systems Design und Consulting GmbH
8 * Rockteck jh057n00900 5.5" MIPI-DSI panel driver
9 * Copyright (C) Purism SPC 2019
12 #include <linux/delay.h>
13 #include <linux/gpio/consumer.h>
14 #include <linux/media-bus-format.h>
15 #include <linux/module.h>
17 #include <linux/regulator/consumer.h>
19 #include <video/display_timing.h>
20 #include <video/mipi_display.h>
22 #include <drm/drm_mipi_dsi.h>
23 #include <drm/drm_modes.h>
24 #include <drm/drm_panel.h>
26 /* Manufacturer specific Commands send via DSI */
27 #define KD35T133_CMD_INTERFACEMODECTRL 0xb0
28 #define KD35T133_CMD_FRAMERATECTRL 0xb1
29 #define KD35T133_CMD_DISPLAYINVERSIONCTRL 0xb4
30 #define KD35T133_CMD_DISPLAYFUNCTIONCTRL 0xb6
31 #define KD35T133_CMD_POWERCONTROL1 0xc0
32 #define KD35T133_CMD_POWERCONTROL2 0xc1
33 #define KD35T133_CMD_VCOMCONTROL 0xc5
34 #define KD35T133_CMD_POSITIVEGAMMA 0xe0
35 #define KD35T133_CMD_NEGATIVEGAMMA 0xe1
36 #define KD35T133_CMD_SETIMAGEFUNCTION 0xe9
37 #define KD35T133_CMD_ADJUSTCONTROL3 0xf7
41 struct drm_panel panel
;
42 struct gpio_desc
*reset_gpio
;
43 struct regulator
*vdd
;
44 struct regulator
*iovcc
;
48 static inline struct kd35t133
*panel_to_kd35t133(struct drm_panel
*panel
)
50 return container_of(panel
, struct kd35t133
, panel
);
53 #define dsi_dcs_write_seq(dsi, cmd, seq...) do { \
54 static const u8 b[] = { cmd, seq }; \
56 ret = mipi_dsi_dcs_write_buffer(dsi, b, ARRAY_SIZE(b)); \
61 static int kd35t133_init_sequence(struct kd35t133
*ctx
)
63 struct mipi_dsi_device
*dsi
= to_mipi_dsi_device(ctx
->dev
);
64 struct device
*dev
= ctx
->dev
;
67 * Init sequence was supplied by the panel vendor with minimal
70 dsi_dcs_write_seq(dsi
, KD35T133_CMD_POSITIVEGAMMA
,
71 0x00, 0x13, 0x18, 0x04, 0x0f, 0x06, 0x3a, 0x56,
72 0x4d, 0x03, 0x0a, 0x06, 0x30, 0x3e, 0x0f);
73 dsi_dcs_write_seq(dsi
, KD35T133_CMD_NEGATIVEGAMMA
,
74 0x00, 0x13, 0x18, 0x01, 0x11, 0x06, 0x38, 0x34,
75 0x4d, 0x06, 0x0d, 0x0b, 0x31, 0x37, 0x0f);
76 dsi_dcs_write_seq(dsi
, KD35T133_CMD_POWERCONTROL1
, 0x18, 0x17);
77 dsi_dcs_write_seq(dsi
, KD35T133_CMD_POWERCONTROL2
, 0x41);
78 dsi_dcs_write_seq(dsi
, KD35T133_CMD_VCOMCONTROL
, 0x00, 0x1a, 0x80);
79 dsi_dcs_write_seq(dsi
, MIPI_DCS_SET_ADDRESS_MODE
, 0x48);
80 dsi_dcs_write_seq(dsi
, MIPI_DCS_SET_PIXEL_FORMAT
, 0x55);
81 dsi_dcs_write_seq(dsi
, KD35T133_CMD_INTERFACEMODECTRL
, 0x00);
82 dsi_dcs_write_seq(dsi
, KD35T133_CMD_FRAMERATECTRL
, 0xa0);
83 dsi_dcs_write_seq(dsi
, KD35T133_CMD_DISPLAYINVERSIONCTRL
, 0x02);
84 dsi_dcs_write_seq(dsi
, KD35T133_CMD_DISPLAYFUNCTIONCTRL
,
86 dsi_dcs_write_seq(dsi
, KD35T133_CMD_SETIMAGEFUNCTION
, 0x00);
87 dsi_dcs_write_seq(dsi
, KD35T133_CMD_ADJUSTCONTROL3
,
88 0xa9, 0x51, 0x2c, 0x82);
89 mipi_dsi_dcs_write(dsi
, MIPI_DCS_ENTER_INVERT_MODE
, NULL
, 0);
91 dev_dbg(dev
, "Panel init sequence done\n");
95 static int kd35t133_unprepare(struct drm_panel
*panel
)
97 struct kd35t133
*ctx
= panel_to_kd35t133(panel
);
98 struct mipi_dsi_device
*dsi
= to_mipi_dsi_device(ctx
->dev
);
104 ret
= mipi_dsi_dcs_set_display_off(dsi
);
106 dev_err(ctx
->dev
, "failed to set display off: %d\n", ret
);
108 ret
= mipi_dsi_dcs_enter_sleep_mode(dsi
);
110 dev_err(ctx
->dev
, "failed to enter sleep mode: %d\n", ret
);
114 regulator_disable(ctx
->iovcc
);
115 regulator_disable(ctx
->vdd
);
117 ctx
->prepared
= false;
122 static int kd35t133_prepare(struct drm_panel
*panel
)
124 struct kd35t133
*ctx
= panel_to_kd35t133(panel
);
125 struct mipi_dsi_device
*dsi
= to_mipi_dsi_device(ctx
->dev
);
131 dev_dbg(ctx
->dev
, "Resetting the panel\n");
132 ret
= regulator_enable(ctx
->vdd
);
134 dev_err(ctx
->dev
, "Failed to enable vdd supply: %d\n", ret
);
138 ret
= regulator_enable(ctx
->iovcc
);
140 dev_err(ctx
->dev
, "Failed to enable iovcc supply: %d\n", ret
);
146 gpiod_set_value_cansleep(ctx
->reset_gpio
, 1);
147 usleep_range(10, 20);
148 gpiod_set_value_cansleep(ctx
->reset_gpio
, 0);
152 ret
= mipi_dsi_dcs_exit_sleep_mode(dsi
);
154 dev_err(ctx
->dev
, "Failed to exit sleep mode: %d\n", ret
);
160 ret
= kd35t133_init_sequence(ctx
);
162 dev_err(ctx
->dev
, "Panel init sequence failed: %d\n", ret
);
166 ret
= mipi_dsi_dcs_set_display_on(dsi
);
168 dev_err(ctx
->dev
, "Failed to set display on: %d\n", ret
);
174 ctx
->prepared
= true;
179 regulator_disable(ctx
->iovcc
);
181 regulator_disable(ctx
->vdd
);
185 static const struct drm_display_mode default_mode
= {
187 .hsync_start
= 320 + 130,
188 .hsync_end
= 320 + 130 + 4,
189 .htotal
= 320 + 130 + 4 + 130,
191 .vsync_start
= 480 + 2,
192 .vsync_end
= 480 + 2 + 1,
193 .vtotal
= 480 + 2 + 1 + 2,
199 static int kd35t133_get_modes(struct drm_panel
*panel
,
200 struct drm_connector
*connector
)
202 struct kd35t133
*ctx
= panel_to_kd35t133(panel
);
203 struct drm_display_mode
*mode
;
205 mode
= drm_mode_duplicate(connector
->dev
, &default_mode
);
207 dev_err(ctx
->dev
, "Failed to add mode %ux%u@%u\n",
208 default_mode
.hdisplay
, default_mode
.vdisplay
,
209 drm_mode_vrefresh(&default_mode
));
213 drm_mode_set_name(mode
);
215 mode
->type
= DRM_MODE_TYPE_DRIVER
| DRM_MODE_TYPE_PREFERRED
;
216 connector
->display_info
.width_mm
= mode
->width_mm
;
217 connector
->display_info
.height_mm
= mode
->height_mm
;
218 drm_mode_probed_add(connector
, mode
);
223 static const struct drm_panel_funcs kd35t133_funcs
= {
224 .unprepare
= kd35t133_unprepare
,
225 .prepare
= kd35t133_prepare
,
226 .get_modes
= kd35t133_get_modes
,
229 static int kd35t133_probe(struct mipi_dsi_device
*dsi
)
231 struct device
*dev
= &dsi
->dev
;
232 struct kd35t133
*ctx
;
235 ctx
= devm_kzalloc(dev
, sizeof(*ctx
), GFP_KERNEL
);
239 ctx
->reset_gpio
= devm_gpiod_get_optional(dev
, "reset", GPIOD_OUT_LOW
);
240 if (IS_ERR(ctx
->reset_gpio
)) {
241 dev_err(dev
, "cannot get reset gpio\n");
242 return PTR_ERR(ctx
->reset_gpio
);
245 ctx
->vdd
= devm_regulator_get(dev
, "vdd");
246 if (IS_ERR(ctx
->vdd
)) {
247 ret
= PTR_ERR(ctx
->vdd
);
248 if (ret
!= -EPROBE_DEFER
)
249 dev_err(dev
, "Failed to request vdd regulator: %d\n", ret
);
253 ctx
->iovcc
= devm_regulator_get(dev
, "iovcc");
254 if (IS_ERR(ctx
->iovcc
)) {
255 ret
= PTR_ERR(ctx
->iovcc
);
256 if (ret
!= -EPROBE_DEFER
)
257 dev_err(dev
, "Failed to request iovcc regulator: %d\n", ret
);
261 mipi_dsi_set_drvdata(dsi
, ctx
);
266 dsi
->format
= MIPI_DSI_FMT_RGB888
;
267 dsi
->mode_flags
= MIPI_DSI_MODE_VIDEO
| MIPI_DSI_MODE_VIDEO_BURST
|
268 MIPI_DSI_MODE_LPM
| MIPI_DSI_MODE_EOT_PACKET
;
270 drm_panel_init(&ctx
->panel
, &dsi
->dev
, &kd35t133_funcs
,
271 DRM_MODE_CONNECTOR_DSI
);
273 ret
= drm_panel_of_backlight(&ctx
->panel
);
277 drm_panel_add(&ctx
->panel
);
279 ret
= mipi_dsi_attach(dsi
);
281 dev_err(dev
, "mipi_dsi_attach failed: %d\n", ret
);
282 drm_panel_remove(&ctx
->panel
);
289 static void kd35t133_shutdown(struct mipi_dsi_device
*dsi
)
291 struct kd35t133
*ctx
= mipi_dsi_get_drvdata(dsi
);
294 ret
= drm_panel_unprepare(&ctx
->panel
);
296 dev_err(&dsi
->dev
, "Failed to unprepare panel: %d\n", ret
);
298 ret
= drm_panel_disable(&ctx
->panel
);
300 dev_err(&dsi
->dev
, "Failed to disable panel: %d\n", ret
);
303 static int kd35t133_remove(struct mipi_dsi_device
*dsi
)
305 struct kd35t133
*ctx
= mipi_dsi_get_drvdata(dsi
);
308 kd35t133_shutdown(dsi
);
310 ret
= mipi_dsi_detach(dsi
);
312 dev_err(&dsi
->dev
, "Failed to detach from DSI host: %d\n", ret
);
314 drm_panel_remove(&ctx
->panel
);
319 static const struct of_device_id kd35t133_of_match
[] = {
320 { .compatible
= "elida,kd35t133" },
323 MODULE_DEVICE_TABLE(of
, kd35t133_of_match
);
325 static struct mipi_dsi_driver kd35t133_driver
= {
327 .name
= "panel-elida-kd35t133",
328 .of_match_table
= kd35t133_of_match
,
330 .probe
= kd35t133_probe
,
331 .remove
= kd35t133_remove
,
332 .shutdown
= kd35t133_shutdown
,
334 module_mipi_dsi_driver(kd35t133_driver
);
336 MODULE_AUTHOR("Heiko Stuebner <heiko.stuebner@theobroma-systems.com>");
337 MODULE_DESCRIPTION("DRM driver for Elida kd35t133 MIPI DSI panel");
338 MODULE_LICENSE("GPL v2");