1 /* 2 * Copyright (C) 2017 Free Electrons 3 * 4 * This program is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU General Public License version 6 * 2 as published by the Free Software Foundation. 7 */ 8 9 #include <linux/backlight.h> 10 #include <linux/delay.h> 11 #include <linux/gpio/consumer.h> 12 #include <linux/module.h> 13 #include <linux/regulator/consumer.h> 14 #include <linux/spi/spi.h> 15 16 #include <video/mipi_display.h> 17 18 #include <drm/drm_device.h> 19 #include <drm/drm_modes.h> 20 #include <drm/drm_panel.h> 21 22 #define ST7789V_COLMOD_RGB_FMT_18BITS (6 << 4) 23 #define ST7789V_COLMOD_CTRL_FMT_18BITS (6 << 0) 24 25 #define ST7789V_RAMCTRL_CMD 0xb0 26 #define ST7789V_RAMCTRL_RM_RGB BIT(4) 27 #define ST7789V_RAMCTRL_DM_RGB BIT(0) 28 #define ST7789V_RAMCTRL_MAGIC (3 << 6) 29 #define ST7789V_RAMCTRL_EPF(n) (((n) & 3) << 4) 30 31 #define ST7789V_RGBCTRL_CMD 0xb1 32 #define ST7789V_RGBCTRL_WO BIT(7) 33 #define ST7789V_RGBCTRL_RCM(n) (((n) & 3) << 5) 34 #define ST7789V_RGBCTRL_VSYNC_HIGH BIT(3) 35 #define ST7789V_RGBCTRL_HSYNC_HIGH BIT(2) 36 #define ST7789V_RGBCTRL_PCLK_HIGH BIT(1) 37 #define ST7789V_RGBCTRL_VBP(n) ((n) & 0x7f) 38 #define ST7789V_RGBCTRL_HBP(n) ((n) & 0x1f) 39 40 #define ST7789V_PORCTRL_CMD 0xb2 41 #define ST7789V_PORCTRL_IDLE_BP(n) (((n) & 0xf) << 4) 42 #define ST7789V_PORCTRL_IDLE_FP(n) ((n) & 0xf) 43 #define ST7789V_PORCTRL_PARTIAL_BP(n) (((n) & 0xf) << 4) 44 #define ST7789V_PORCTRL_PARTIAL_FP(n) ((n) & 0xf) 45 46 #define ST7789V_GCTRL_CMD 0xb7 47 #define ST7789V_GCTRL_VGHS(n) (((n) & 7) << 4) 48 #define ST7789V_GCTRL_VGLS(n) ((n) & 7) 49 50 #define ST7789V_VCOMS_CMD 0xbb 51 52 #define ST7789V_LCMCTRL_CMD 0xc0 53 #define ST7789V_LCMCTRL_XBGR BIT(5) 54 #define ST7789V_LCMCTRL_XMX BIT(3) 55 #define ST7789V_LCMCTRL_XMH BIT(2) 56 57 #define ST7789V_VDVVRHEN_CMD 0xc2 58 #define ST7789V_VDVVRHEN_CMDEN BIT(0) 59 60 #define ST7789V_VRHS_CMD 0xc3 61 62 #define ST7789V_VDVS_CMD 0xc4 63 64 #define ST7789V_FRCTRL2_CMD 0xc6 65 66 #define ST7789V_PWCTRL1_CMD 0xd0 67 #define ST7789V_PWCTRL1_MAGIC 0xa4 68 #define ST7789V_PWCTRL1_AVDD(n) (((n) & 3) << 6) 69 #define ST7789V_PWCTRL1_AVCL(n) (((n) & 3) << 4) 70 #define ST7789V_PWCTRL1_VDS(n) ((n) & 3) 71 72 #define ST7789V_PVGAMCTRL_CMD 0xe0 73 #define ST7789V_PVGAMCTRL_JP0(n) (((n) & 3) << 4) 74 #define ST7789V_PVGAMCTRL_JP1(n) (((n) & 3) << 4) 75 #define ST7789V_PVGAMCTRL_VP0(n) ((n) & 0xf) 76 #define ST7789V_PVGAMCTRL_VP1(n) ((n) & 0x3f) 77 #define ST7789V_PVGAMCTRL_VP2(n) ((n) & 0x3f) 78 #define ST7789V_PVGAMCTRL_VP4(n) ((n) & 0x1f) 79 #define ST7789V_PVGAMCTRL_VP6(n) ((n) & 0x1f) 80 #define ST7789V_PVGAMCTRL_VP13(n) ((n) & 0xf) 81 #define ST7789V_PVGAMCTRL_VP20(n) ((n) & 0x7f) 82 #define ST7789V_PVGAMCTRL_VP27(n) ((n) & 7) 83 #define ST7789V_PVGAMCTRL_VP36(n) (((n) & 7) << 4) 84 #define ST7789V_PVGAMCTRL_VP43(n) ((n) & 0x7f) 85 #define ST7789V_PVGAMCTRL_VP50(n) ((n) & 0xf) 86 #define ST7789V_PVGAMCTRL_VP57(n) ((n) & 0x1f) 87 #define ST7789V_PVGAMCTRL_VP59(n) ((n) & 0x1f) 88 #define ST7789V_PVGAMCTRL_VP61(n) ((n) & 0x3f) 89 #define ST7789V_PVGAMCTRL_VP62(n) ((n) & 0x3f) 90 #define ST7789V_PVGAMCTRL_VP63(n) (((n) & 0xf) << 4) 91 92 #define ST7789V_NVGAMCTRL_CMD 0xe1 93 #define ST7789V_NVGAMCTRL_JN0(n) (((n) & 3) << 4) 94 #define ST7789V_NVGAMCTRL_JN1(n) (((n) & 3) << 4) 95 #define ST7789V_NVGAMCTRL_VN0(n) ((n) & 0xf) 96 #define ST7789V_NVGAMCTRL_VN1(n) ((n) & 0x3f) 97 #define ST7789V_NVGAMCTRL_VN2(n) ((n) & 0x3f) 98 #define ST7789V_NVGAMCTRL_VN4(n) ((n) & 0x1f) 99 #define ST7789V_NVGAMCTRL_VN6(n) ((n) & 0x1f) 100 #define ST7789V_NVGAMCTRL_VN13(n) ((n) & 0xf) 101 #define ST7789V_NVGAMCTRL_VN20(n) ((n) & 0x7f) 102 #define ST7789V_NVGAMCTRL_VN27(n) ((n) & 7) 103 #define ST7789V_NVGAMCTRL_VN36(n) (((n) & 7) << 4) 104 #define ST7789V_NVGAMCTRL_VN43(n) ((n) & 0x7f) 105 #define ST7789V_NVGAMCTRL_VN50(n) ((n) & 0xf) 106 #define ST7789V_NVGAMCTRL_VN57(n) ((n) & 0x1f) 107 #define ST7789V_NVGAMCTRL_VN59(n) ((n) & 0x1f) 108 #define ST7789V_NVGAMCTRL_VN61(n) ((n) & 0x3f) 109 #define ST7789V_NVGAMCTRL_VN62(n) ((n) & 0x3f) 110 #define ST7789V_NVGAMCTRL_VN63(n) (((n) & 0xf) << 4) 111 112 #define ST7789V_TEST(val, func) \ 113 do { \ 114 if ((val = (func))) \ 115 return val; \ 116 } while (0) 117 118 struct st7789v { 119 struct drm_panel panel; 120 struct spi_device *spi; 121 struct gpio_desc *reset; 122 struct backlight_device *backlight; 123 struct regulator *power; 124 }; 125 126 enum st7789v_prefix { 127 ST7789V_COMMAND = 0, 128 ST7789V_DATA = 1, 129 }; 130 131 static inline struct st7789v *panel_to_st7789v(struct drm_panel *panel) 132 { 133 return container_of(panel, struct st7789v, panel); 134 } 135 136 static int st7789v_spi_write(struct st7789v *ctx, enum st7789v_prefix prefix, 137 u8 data) 138 { 139 struct spi_transfer xfer = { }; 140 struct spi_message msg; 141 u16 txbuf = ((prefix & 1) << 8) | data; 142 143 spi_message_init(&msg); 144 145 xfer.tx_buf = &txbuf; 146 xfer.bits_per_word = 9; 147 xfer.len = sizeof(txbuf); 148 149 spi_message_add_tail(&xfer, &msg); 150 return spi_sync(ctx->spi, &msg); 151 } 152 153 static int st7789v_write_command(struct st7789v *ctx, u8 cmd) 154 { 155 return st7789v_spi_write(ctx, ST7789V_COMMAND, cmd); 156 } 157 158 static int st7789v_write_data(struct st7789v *ctx, u8 cmd) 159 { 160 return st7789v_spi_write(ctx, ST7789V_DATA, cmd); 161 } 162 163 static const struct drm_display_mode default_mode = { 164 .clock = 7000, 165 .hdisplay = 240, 166 .hsync_start = 240 + 38, 167 .hsync_end = 240 + 38 + 10, 168 .htotal = 240 + 38 + 10 + 10, 169 .vdisplay = 320, 170 .vsync_start = 320 + 8, 171 .vsync_end = 320 + 8 + 4, 172 .vtotal = 320 + 8 + 4 + 4, 173 .vrefresh = 60, 174 }; 175 176 static int st7789v_get_modes(struct drm_panel *panel) 177 { 178 struct drm_connector *connector = panel->connector; 179 struct drm_display_mode *mode; 180 181 mode = drm_mode_duplicate(panel->drm, &default_mode); 182 if (!mode) { 183 dev_err(panel->drm->dev, "failed to add mode %ux%ux@%u\n", 184 default_mode.hdisplay, default_mode.vdisplay, 185 default_mode.vrefresh); 186 return -ENOMEM; 187 } 188 189 drm_mode_set_name(mode); 190 191 mode->type = DRM_MODE_TYPE_DRIVER | DRM_MODE_TYPE_PREFERRED; 192 drm_mode_probed_add(connector, mode); 193 194 panel->connector->display_info.width_mm = 61; 195 panel->connector->display_info.height_mm = 103; 196 197 return 1; 198 } 199 200 static int st7789v_prepare(struct drm_panel *panel) 201 { 202 struct st7789v *ctx = panel_to_st7789v(panel); 203 int ret; 204 205 ret = regulator_enable(ctx->power); 206 if (ret) 207 return ret; 208 209 gpiod_set_value(ctx->reset, 1); 210 msleep(30); 211 gpiod_set_value(ctx->reset, 0); 212 msleep(120); 213 214 ST7789V_TEST(ret, st7789v_write_command(ctx, MIPI_DCS_EXIT_SLEEP_MODE)); 215 216 /* We need to wait 120ms after a sleep out command */ 217 msleep(120); 218 219 ST7789V_TEST(ret, st7789v_write_command(ctx, 220 MIPI_DCS_SET_ADDRESS_MODE)); 221 ST7789V_TEST(ret, st7789v_write_data(ctx, 0)); 222 223 ST7789V_TEST(ret, st7789v_write_command(ctx, 224 MIPI_DCS_SET_PIXEL_FORMAT)); 225 ST7789V_TEST(ret, st7789v_write_data(ctx, 226 (MIPI_DCS_PIXEL_FMT_18BIT << 4) | 227 (MIPI_DCS_PIXEL_FMT_18BIT))); 228 229 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_PORCTRL_CMD)); 230 ST7789V_TEST(ret, st7789v_write_data(ctx, 0xc)); 231 ST7789V_TEST(ret, st7789v_write_data(ctx, 0xc)); 232 ST7789V_TEST(ret, st7789v_write_data(ctx, 0)); 233 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PORCTRL_IDLE_BP(3) | 234 ST7789V_PORCTRL_IDLE_FP(3))); 235 ST7789V_TEST(ret, st7789v_write_data(ctx, 236 ST7789V_PORCTRL_PARTIAL_BP(3) | 237 ST7789V_PORCTRL_PARTIAL_FP(3))); 238 239 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_GCTRL_CMD)); 240 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_GCTRL_VGLS(5) | 241 ST7789V_GCTRL_VGHS(3))); 242 243 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_VCOMS_CMD)); 244 ST7789V_TEST(ret, st7789v_write_data(ctx, 0x2b)); 245 246 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_LCMCTRL_CMD)); 247 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_LCMCTRL_XMH | 248 ST7789V_LCMCTRL_XMX | 249 ST7789V_LCMCTRL_XBGR)); 250 251 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_VDVVRHEN_CMD)); 252 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_VDVVRHEN_CMDEN)); 253 254 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_VRHS_CMD)); 255 ST7789V_TEST(ret, st7789v_write_data(ctx, 0xf)); 256 257 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_VDVS_CMD)); 258 ST7789V_TEST(ret, st7789v_write_data(ctx, 0x20)); 259 260 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_FRCTRL2_CMD)); 261 ST7789V_TEST(ret, st7789v_write_data(ctx, 0xf)); 262 263 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_PWCTRL1_CMD)); 264 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PWCTRL1_MAGIC)); 265 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PWCTRL1_AVDD(2) | 266 ST7789V_PWCTRL1_AVCL(2) | 267 ST7789V_PWCTRL1_VDS(1))); 268 269 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_PVGAMCTRL_CMD)); 270 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP63(0xd))); 271 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP1(0xca))); 272 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP2(0xe))); 273 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP4(8))); 274 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP6(9))); 275 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP13(7))); 276 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP20(0x2d))); 277 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP27(0xb) | 278 ST7789V_PVGAMCTRL_VP36(3))); 279 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP43(0x3d))); 280 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_JP1(3) | 281 ST7789V_PVGAMCTRL_VP50(4))); 282 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP57(0xa))); 283 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP59(0xa))); 284 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP61(0x1b))); 285 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_PVGAMCTRL_VP62(0x28))); 286 287 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_NVGAMCTRL_CMD)); 288 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN63(0xd))); 289 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN1(0xca))); 290 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN2(0xf))); 291 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN4(8))); 292 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN6(8))); 293 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN13(7))); 294 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN20(0x2e))); 295 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN27(0xc) | 296 ST7789V_NVGAMCTRL_VN36(5))); 297 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN43(0x40))); 298 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_JN1(3) | 299 ST7789V_NVGAMCTRL_VN50(4))); 300 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN57(9))); 301 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN59(0xb))); 302 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN61(0x1b))); 303 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_NVGAMCTRL_VN62(0x28))); 304 305 ST7789V_TEST(ret, st7789v_write_command(ctx, MIPI_DCS_ENTER_INVERT_MODE)); 306 307 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_RAMCTRL_CMD)); 308 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_RAMCTRL_DM_RGB | 309 ST7789V_RAMCTRL_RM_RGB)); 310 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_RAMCTRL_EPF(3) | 311 ST7789V_RAMCTRL_MAGIC)); 312 313 ST7789V_TEST(ret, st7789v_write_command(ctx, ST7789V_RGBCTRL_CMD)); 314 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_RGBCTRL_WO | 315 ST7789V_RGBCTRL_RCM(2) | 316 ST7789V_RGBCTRL_VSYNC_HIGH | 317 ST7789V_RGBCTRL_HSYNC_HIGH | 318 ST7789V_RGBCTRL_PCLK_HIGH)); 319 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_RGBCTRL_VBP(8))); 320 ST7789V_TEST(ret, st7789v_write_data(ctx, ST7789V_RGBCTRL_HBP(20))); 321 322 return 0; 323 } 324 325 static int st7789v_enable(struct drm_panel *panel) 326 { 327 struct st7789v *ctx = panel_to_st7789v(panel); 328 329 if (ctx->backlight) { 330 ctx->backlight->props.state &= ~BL_CORE_FBBLANK; 331 ctx->backlight->props.power = FB_BLANK_UNBLANK; 332 backlight_update_status(ctx->backlight); 333 } 334 335 return st7789v_write_command(ctx, MIPI_DCS_SET_DISPLAY_ON); 336 } 337 338 static int st7789v_disable(struct drm_panel *panel) 339 { 340 struct st7789v *ctx = panel_to_st7789v(panel); 341 int ret; 342 343 ST7789V_TEST(ret, st7789v_write_command(ctx, MIPI_DCS_SET_DISPLAY_OFF)); 344 345 if (ctx->backlight) { 346 ctx->backlight->props.power = FB_BLANK_POWERDOWN; 347 ctx->backlight->props.state |= BL_CORE_FBBLANK; 348 backlight_update_status(ctx->backlight); 349 } 350 351 return 0; 352 } 353 354 static int st7789v_unprepare(struct drm_panel *panel) 355 { 356 struct st7789v *ctx = panel_to_st7789v(panel); 357 int ret; 358 359 ST7789V_TEST(ret, st7789v_write_command(ctx, MIPI_DCS_ENTER_SLEEP_MODE)); 360 361 regulator_disable(ctx->power); 362 363 return 0; 364 } 365 366 static const struct drm_panel_funcs st7789v_drm_funcs = { 367 .disable = st7789v_disable, 368 .enable = st7789v_enable, 369 .get_modes = st7789v_get_modes, 370 .prepare = st7789v_prepare, 371 .unprepare = st7789v_unprepare, 372 }; 373 374 static int st7789v_probe(struct spi_device *spi) 375 { 376 struct device_node *backlight; 377 struct st7789v *ctx; 378 int ret; 379 380 ctx = devm_kzalloc(&spi->dev, sizeof(*ctx), GFP_KERNEL); 381 if (!ctx) 382 return -ENOMEM; 383 384 spi_set_drvdata(spi, ctx); 385 ctx->spi = spi; 386 387 ctx->panel.dev = &spi->dev; 388 ctx->panel.funcs = &st7789v_drm_funcs; 389 390 ctx->power = devm_regulator_get(&spi->dev, "power"); 391 if (IS_ERR(ctx->power)) 392 return PTR_ERR(ctx->power); 393 394 ctx->reset = devm_gpiod_get(&spi->dev, "reset", GPIOD_OUT_LOW); 395 if (IS_ERR(ctx->reset)) { 396 dev_err(&spi->dev, "Couldn't get our reset line\n"); 397 return PTR_ERR(ctx->reset); 398 } 399 400 backlight = of_parse_phandle(spi->dev.of_node, "backlight", 0); 401 if (backlight) { 402 ctx->backlight = of_find_backlight_by_node(backlight); 403 of_node_put(backlight); 404 405 if (!ctx->backlight) 406 return -EPROBE_DEFER; 407 } 408 409 ret = drm_panel_add(&ctx->panel); 410 if (ret < 0) 411 goto err_free_backlight; 412 413 return 0; 414 415 err_free_backlight: 416 if (ctx->backlight) 417 put_device(&ctx->backlight->dev); 418 419 return ret; 420 } 421 422 static int st7789v_remove(struct spi_device *spi) 423 { 424 struct st7789v *ctx = spi_get_drvdata(spi); 425 426 drm_panel_remove(&ctx->panel); 427 428 if (ctx->backlight) 429 put_device(&ctx->backlight->dev); 430 431 return 0; 432 } 433 434 static const struct of_device_id st7789v_of_match[] = { 435 { .compatible = "sitronix,st7789v" }, 436 { } 437 }; 438 MODULE_DEVICE_TABLE(of, st7789v_of_match); 439 440 static struct spi_driver st7789v_driver = { 441 .probe = st7789v_probe, 442 .remove = st7789v_remove, 443 .driver = { 444 .name = "st7789v", 445 .of_match_table = st7789v_of_match, 446 }, 447 }; 448 module_spi_driver(st7789v_driver); 449 450 MODULE_AUTHOR("Maxime Ripard <maxime.ripard@free-electrons.com>"); 451 MODULE_DESCRIPTION("Sitronix st7789v LCD Driver"); 452 MODULE_LICENSE("GPL v2"); 453