1 // SPDX-License-Identifier: GPL-2.0 2 // 3 // Ingenic JZ47xx KMS driver 4 // 5 // Copyright (C) 2019, Paul Cercueil <paul@crapouillou.net> 6 7 #include "ingenic-drm.h" 8 9 #include <linux/component.h> 10 #include <linux/clk.h> 11 #include <linux/dma-mapping.h> 12 #include <linux/module.h> 13 #include <linux/of_device.h> 14 #include <linux/platform_device.h> 15 #include <linux/regmap.h> 16 17 #include <drm/drm_atomic.h> 18 #include <drm/drm_atomic_helper.h> 19 #include <drm/drm_bridge.h> 20 #include <drm/drm_crtc.h> 21 #include <drm/drm_crtc_helper.h> 22 #include <drm/drm_drv.h> 23 #include <drm/drm_gem_cma_helper.h> 24 #include <drm/drm_fb_cma_helper.h> 25 #include <drm/drm_fb_helper.h> 26 #include <drm/drm_fourcc.h> 27 #include <drm/drm_gem_framebuffer_helper.h> 28 #include <drm/drm_irq.h> 29 #include <drm/drm_managed.h> 30 #include <drm/drm_of.h> 31 #include <drm/drm_panel.h> 32 #include <drm/drm_plane.h> 33 #include <drm/drm_plane_helper.h> 34 #include <drm/drm_probe_helper.h> 35 #include <drm/drm_simple_kms_helper.h> 36 #include <drm/drm_vblank.h> 37 38 struct ingenic_dma_hwdesc { 39 u32 next; 40 u32 addr; 41 u32 id; 42 u32 cmd; 43 } __packed; 44 45 struct jz_soc_info { 46 bool needs_dev_clk; 47 bool has_osd; 48 unsigned int max_width, max_height; 49 }; 50 51 struct ingenic_drm { 52 struct drm_device drm; 53 /* 54 * f1 (aka. foreground1) is our primary plane, on top of which 55 * f0 (aka. foreground0) can be overlayed. Z-order is fixed in 56 * hardware and cannot be changed. 57 */ 58 struct drm_plane f0, f1, *ipu_plane; 59 struct drm_crtc crtc; 60 61 struct device *dev; 62 struct regmap *map; 63 struct clk *lcd_clk, *pix_clk; 64 const struct jz_soc_info *soc_info; 65 66 struct ingenic_dma_hwdesc *dma_hwdesc_f0, *dma_hwdesc_f1; 67 dma_addr_t dma_hwdesc_phys_f0, dma_hwdesc_phys_f1; 68 69 bool panel_is_sharp; 70 bool no_vblank; 71 }; 72 73 static const u32 ingenic_drm_primary_formats[] = { 74 DRM_FORMAT_XRGB1555, 75 DRM_FORMAT_RGB565, 76 DRM_FORMAT_XRGB8888, 77 }; 78 79 static bool ingenic_drm_writeable_reg(struct device *dev, unsigned int reg) 80 { 81 switch (reg) { 82 case JZ_REG_LCD_IID: 83 case JZ_REG_LCD_SA0: 84 case JZ_REG_LCD_FID0: 85 case JZ_REG_LCD_CMD0: 86 case JZ_REG_LCD_SA1: 87 case JZ_REG_LCD_FID1: 88 case JZ_REG_LCD_CMD1: 89 return false; 90 default: 91 return true; 92 } 93 } 94 95 static const struct regmap_config ingenic_drm_regmap_config = { 96 .reg_bits = 32, 97 .val_bits = 32, 98 .reg_stride = 4, 99 100 .max_register = JZ_REG_LCD_SIZE1, 101 .writeable_reg = ingenic_drm_writeable_reg, 102 }; 103 104 static inline struct ingenic_drm *drm_device_get_priv(struct drm_device *drm) 105 { 106 return container_of(drm, struct ingenic_drm, drm); 107 } 108 109 static inline struct ingenic_drm *drm_crtc_get_priv(struct drm_crtc *crtc) 110 { 111 return container_of(crtc, struct ingenic_drm, crtc); 112 } 113 114 static void ingenic_drm_crtc_atomic_enable(struct drm_crtc *crtc, 115 struct drm_crtc_state *state) 116 { 117 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 118 119 regmap_write(priv->map, JZ_REG_LCD_STATE, 0); 120 121 regmap_update_bits(priv->map, JZ_REG_LCD_CTRL, 122 JZ_LCD_CTRL_ENABLE | JZ_LCD_CTRL_DISABLE, 123 JZ_LCD_CTRL_ENABLE); 124 125 drm_crtc_vblank_on(crtc); 126 } 127 128 static void ingenic_drm_crtc_atomic_disable(struct drm_crtc *crtc, 129 struct drm_crtc_state *state) 130 { 131 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 132 unsigned int var; 133 134 drm_crtc_vblank_off(crtc); 135 136 regmap_update_bits(priv->map, JZ_REG_LCD_CTRL, 137 JZ_LCD_CTRL_DISABLE, JZ_LCD_CTRL_DISABLE); 138 139 regmap_read_poll_timeout(priv->map, JZ_REG_LCD_STATE, var, 140 var & JZ_LCD_STATE_DISABLED, 141 1000, 0); 142 } 143 144 static void ingenic_drm_crtc_update_timings(struct ingenic_drm *priv, 145 struct drm_display_mode *mode) 146 { 147 unsigned int vpe, vds, vde, vt, hpe, hds, hde, ht; 148 149 vpe = mode->vsync_end - mode->vsync_start; 150 vds = mode->vtotal - mode->vsync_start; 151 vde = vds + mode->vdisplay; 152 vt = vde + mode->vsync_start - mode->vdisplay; 153 154 hpe = mode->hsync_end - mode->hsync_start; 155 hds = mode->htotal - mode->hsync_start; 156 hde = hds + mode->hdisplay; 157 ht = hde + mode->hsync_start - mode->hdisplay; 158 159 regmap_write(priv->map, JZ_REG_LCD_VSYNC, 160 0 << JZ_LCD_VSYNC_VPS_OFFSET | 161 vpe << JZ_LCD_VSYNC_VPE_OFFSET); 162 163 regmap_write(priv->map, JZ_REG_LCD_HSYNC, 164 0 << JZ_LCD_HSYNC_HPS_OFFSET | 165 hpe << JZ_LCD_HSYNC_HPE_OFFSET); 166 167 regmap_write(priv->map, JZ_REG_LCD_VAT, 168 ht << JZ_LCD_VAT_HT_OFFSET | 169 vt << JZ_LCD_VAT_VT_OFFSET); 170 171 regmap_write(priv->map, JZ_REG_LCD_DAH, 172 hds << JZ_LCD_DAH_HDS_OFFSET | 173 hde << JZ_LCD_DAH_HDE_OFFSET); 174 regmap_write(priv->map, JZ_REG_LCD_DAV, 175 vds << JZ_LCD_DAV_VDS_OFFSET | 176 vde << JZ_LCD_DAV_VDE_OFFSET); 177 178 if (priv->panel_is_sharp) { 179 regmap_write(priv->map, JZ_REG_LCD_PS, hde << 16 | (hde + 1)); 180 regmap_write(priv->map, JZ_REG_LCD_CLS, hde << 16 | (hde + 1)); 181 regmap_write(priv->map, JZ_REG_LCD_SPL, hpe << 16 | (hpe + 1)); 182 regmap_write(priv->map, JZ_REG_LCD_REV, mode->htotal << 16); 183 } 184 185 regmap_set_bits(priv->map, JZ_REG_LCD_CTRL, 186 JZ_LCD_CTRL_OFUP | JZ_LCD_CTRL_BURST_16); 187 188 /* 189 * IPU restart - specify how much time the LCDC will wait before 190 * transferring a new frame from the IPU. The value is the one 191 * suggested in the programming manual. 192 */ 193 regmap_write(priv->map, JZ_REG_LCD_IPUR, JZ_LCD_IPUR_IPUREN | 194 (ht * vpe / 3) << JZ_LCD_IPUR_IPUR_LSB); 195 } 196 197 static int ingenic_drm_crtc_atomic_check(struct drm_crtc *crtc, 198 struct drm_crtc_state *state) 199 { 200 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 201 struct drm_plane_state *f1_state, *f0_state, *ipu_state = NULL; 202 203 if (drm_atomic_crtc_needs_modeset(state) && priv->soc_info->has_osd) { 204 f1_state = drm_atomic_get_plane_state(state->state, &priv->f1); 205 if (IS_ERR(f1_state)) 206 return PTR_ERR(f1_state); 207 208 f0_state = drm_atomic_get_plane_state(state->state, &priv->f0); 209 if (IS_ERR(f0_state)) 210 return PTR_ERR(f0_state); 211 212 if (IS_ENABLED(CONFIG_DRM_INGENIC_IPU) && priv->ipu_plane) { 213 ipu_state = drm_atomic_get_plane_state(state->state, priv->ipu_plane); 214 if (IS_ERR(ipu_state)) 215 return PTR_ERR(ipu_state); 216 217 /* IPU and F1 planes cannot be enabled at the same time. */ 218 if (f1_state->fb && ipu_state->fb) { 219 dev_dbg(priv->dev, "Cannot enable both F1 and IPU\n"); 220 return -EINVAL; 221 } 222 } 223 224 /* If all the planes are disabled, we won't get a VBLANK IRQ */ 225 priv->no_vblank = !f1_state->fb && !f0_state->fb && 226 !(ipu_state && ipu_state->fb); 227 } 228 229 return 0; 230 } 231 232 static enum drm_mode_status 233 ingenic_drm_crtc_mode_valid(struct drm_crtc *crtc, const struct drm_display_mode *mode) 234 { 235 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 236 long rate; 237 238 if (mode->hdisplay > priv->soc_info->max_width) 239 return MODE_BAD_HVALUE; 240 if (mode->vdisplay > priv->soc_info->max_height) 241 return MODE_BAD_VVALUE; 242 243 rate = clk_round_rate(priv->pix_clk, mode->clock * 1000); 244 if (rate < 0) 245 return MODE_CLOCK_RANGE; 246 247 return MODE_OK; 248 } 249 250 static void ingenic_drm_crtc_atomic_begin(struct drm_crtc *crtc, 251 struct drm_crtc_state *oldstate) 252 { 253 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 254 u32 ctrl = 0; 255 256 if (priv->soc_info->has_osd && 257 drm_atomic_crtc_needs_modeset(crtc->state)) { 258 /* 259 * If IPU plane is enabled, enable IPU as source for the F1 260 * plane; otherwise use regular DMA. 261 */ 262 if (priv->ipu_plane && priv->ipu_plane->state->fb) 263 ctrl |= JZ_LCD_OSDCTRL_IPU; 264 265 regmap_update_bits(priv->map, JZ_REG_LCD_OSDCTRL, 266 JZ_LCD_OSDCTRL_IPU, ctrl); 267 } 268 } 269 270 static void ingenic_drm_crtc_atomic_flush(struct drm_crtc *crtc, 271 struct drm_crtc_state *oldstate) 272 { 273 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 274 struct drm_crtc_state *state = crtc->state; 275 struct drm_pending_vblank_event *event = state->event; 276 277 if (drm_atomic_crtc_needs_modeset(state)) { 278 ingenic_drm_crtc_update_timings(priv, &state->mode); 279 280 clk_set_rate(priv->pix_clk, state->adjusted_mode.clock * 1000); 281 } 282 283 if (event) { 284 state->event = NULL; 285 286 spin_lock_irq(&crtc->dev->event_lock); 287 if (drm_crtc_vblank_get(crtc) == 0) 288 drm_crtc_arm_vblank_event(crtc, event); 289 else 290 drm_crtc_send_vblank_event(crtc, event); 291 spin_unlock_irq(&crtc->dev->event_lock); 292 } 293 } 294 295 static int ingenic_drm_plane_atomic_check(struct drm_plane *plane, 296 struct drm_plane_state *state) 297 { 298 struct ingenic_drm *priv = drm_device_get_priv(plane->dev); 299 struct drm_crtc_state *crtc_state; 300 struct drm_crtc *crtc = state->crtc ?: plane->state->crtc; 301 int ret; 302 303 if (!crtc) 304 return 0; 305 306 crtc_state = drm_atomic_get_existing_crtc_state(state->state, crtc); 307 if (WARN_ON(!crtc_state)) 308 return -EINVAL; 309 310 ret = drm_atomic_helper_check_plane_state(state, crtc_state, 311 DRM_PLANE_HELPER_NO_SCALING, 312 DRM_PLANE_HELPER_NO_SCALING, 313 priv->soc_info->has_osd, 314 true); 315 if (ret) 316 return ret; 317 318 /* 319 * If OSD is not available, check that the width/height match. 320 * Note that state->src_* are in 16.16 fixed-point format. 321 */ 322 if (!priv->soc_info->has_osd && 323 (state->src_x != 0 || 324 (state->src_w >> 16) != state->crtc_w || 325 (state->src_h >> 16) != state->crtc_h)) 326 return -EINVAL; 327 328 /* 329 * Require full modeset if enabling or disabling a plane, or changing 330 * its position, size or depth. 331 */ 332 if (priv->soc_info->has_osd && 333 (!plane->state->fb || !state->fb || 334 plane->state->crtc_x != state->crtc_x || 335 plane->state->crtc_y != state->crtc_y || 336 plane->state->crtc_w != state->crtc_w || 337 plane->state->crtc_h != state->crtc_h || 338 plane->state->fb->format->format != state->fb->format->format)) 339 crtc_state->mode_changed = true; 340 341 return 0; 342 } 343 344 static void ingenic_drm_plane_enable(struct ingenic_drm *priv, 345 struct drm_plane *plane) 346 { 347 unsigned int en_bit; 348 349 if (priv->soc_info->has_osd) { 350 if (plane->type == DRM_PLANE_TYPE_PRIMARY) 351 en_bit = JZ_LCD_OSDC_F1EN; 352 else 353 en_bit = JZ_LCD_OSDC_F0EN; 354 355 regmap_set_bits(priv->map, JZ_REG_LCD_OSDC, en_bit); 356 } 357 } 358 359 void ingenic_drm_plane_disable(struct device *dev, struct drm_plane *plane) 360 { 361 struct ingenic_drm *priv = dev_get_drvdata(dev); 362 unsigned int en_bit; 363 364 if (priv->soc_info->has_osd) { 365 if (plane->type == DRM_PLANE_TYPE_PRIMARY) 366 en_bit = JZ_LCD_OSDC_F1EN; 367 else 368 en_bit = JZ_LCD_OSDC_F0EN; 369 370 regmap_clear_bits(priv->map, JZ_REG_LCD_OSDC, en_bit); 371 } 372 } 373 374 static void ingenic_drm_plane_atomic_disable(struct drm_plane *plane, 375 struct drm_plane_state *old_state) 376 { 377 struct ingenic_drm *priv = drm_device_get_priv(plane->dev); 378 379 ingenic_drm_plane_disable(priv->dev, plane); 380 } 381 382 void ingenic_drm_plane_config(struct device *dev, 383 struct drm_plane *plane, u32 fourcc) 384 { 385 struct ingenic_drm *priv = dev_get_drvdata(dev); 386 struct drm_plane_state *state = plane->state; 387 unsigned int xy_reg, size_reg; 388 unsigned int ctrl = 0; 389 390 ingenic_drm_plane_enable(priv, plane); 391 392 if (priv->soc_info->has_osd && 393 plane->type == DRM_PLANE_TYPE_PRIMARY) { 394 switch (fourcc) { 395 case DRM_FORMAT_XRGB1555: 396 ctrl |= JZ_LCD_OSDCTRL_RGB555; 397 fallthrough; 398 case DRM_FORMAT_RGB565: 399 ctrl |= JZ_LCD_OSDCTRL_BPP_15_16; 400 break; 401 case DRM_FORMAT_XRGB8888: 402 ctrl |= JZ_LCD_OSDCTRL_BPP_18_24; 403 break; 404 } 405 406 regmap_update_bits(priv->map, JZ_REG_LCD_OSDCTRL, 407 JZ_LCD_OSDCTRL_BPP_MASK, ctrl); 408 } else { 409 switch (fourcc) { 410 case DRM_FORMAT_XRGB1555: 411 ctrl |= JZ_LCD_CTRL_RGB555; 412 fallthrough; 413 case DRM_FORMAT_RGB565: 414 ctrl |= JZ_LCD_CTRL_BPP_15_16; 415 break; 416 case DRM_FORMAT_XRGB8888: 417 ctrl |= JZ_LCD_CTRL_BPP_18_24; 418 break; 419 } 420 421 regmap_update_bits(priv->map, JZ_REG_LCD_CTRL, 422 JZ_LCD_CTRL_BPP_MASK, ctrl); 423 } 424 425 if (priv->soc_info->has_osd) { 426 if (plane->type == DRM_PLANE_TYPE_PRIMARY) { 427 xy_reg = JZ_REG_LCD_XYP1; 428 size_reg = JZ_REG_LCD_SIZE1; 429 } else { 430 xy_reg = JZ_REG_LCD_XYP0; 431 size_reg = JZ_REG_LCD_SIZE0; 432 } 433 434 regmap_write(priv->map, xy_reg, 435 state->crtc_x << JZ_LCD_XYP01_XPOS_LSB | 436 state->crtc_y << JZ_LCD_XYP01_YPOS_LSB); 437 regmap_write(priv->map, size_reg, 438 state->crtc_w << JZ_LCD_SIZE01_WIDTH_LSB | 439 state->crtc_h << JZ_LCD_SIZE01_HEIGHT_LSB); 440 } 441 } 442 443 static void ingenic_drm_plane_atomic_update(struct drm_plane *plane, 444 struct drm_plane_state *oldstate) 445 { 446 struct ingenic_drm *priv = drm_device_get_priv(plane->dev); 447 struct drm_plane_state *state = plane->state; 448 struct ingenic_dma_hwdesc *hwdesc; 449 unsigned int width, height, cpp; 450 dma_addr_t addr; 451 452 if (state && state->fb) { 453 addr = drm_fb_cma_get_gem_addr(state->fb, state, 0); 454 width = state->src_w >> 16; 455 height = state->src_h >> 16; 456 cpp = state->fb->format->cpp[0]; 457 458 if (priv->soc_info->has_osd && plane->type == DRM_PLANE_TYPE_OVERLAY) 459 hwdesc = priv->dma_hwdesc_f0; 460 else 461 hwdesc = priv->dma_hwdesc_f1; 462 463 hwdesc->addr = addr; 464 hwdesc->cmd = JZ_LCD_CMD_EOF_IRQ | (width * height * cpp / 4); 465 466 if (drm_atomic_crtc_needs_modeset(state->crtc->state)) 467 ingenic_drm_plane_config(priv->dev, plane, 468 state->fb->format->format); 469 } 470 } 471 472 static void ingenic_drm_encoder_atomic_mode_set(struct drm_encoder *encoder, 473 struct drm_crtc_state *crtc_state, 474 struct drm_connector_state *conn_state) 475 { 476 struct ingenic_drm *priv = drm_device_get_priv(encoder->dev); 477 struct drm_display_mode *mode = &crtc_state->adjusted_mode; 478 struct drm_connector *conn = conn_state->connector; 479 struct drm_display_info *info = &conn->display_info; 480 unsigned int cfg; 481 482 priv->panel_is_sharp = info->bus_flags & DRM_BUS_FLAG_SHARP_SIGNALS; 483 484 if (priv->panel_is_sharp) { 485 cfg = JZ_LCD_CFG_MODE_SPECIAL_TFT_1 | JZ_LCD_CFG_REV_POLARITY; 486 } else { 487 cfg = JZ_LCD_CFG_PS_DISABLE | JZ_LCD_CFG_CLS_DISABLE 488 | JZ_LCD_CFG_SPL_DISABLE | JZ_LCD_CFG_REV_DISABLE; 489 } 490 491 if (mode->flags & DRM_MODE_FLAG_NHSYNC) 492 cfg |= JZ_LCD_CFG_HSYNC_ACTIVE_LOW; 493 if (mode->flags & DRM_MODE_FLAG_NVSYNC) 494 cfg |= JZ_LCD_CFG_VSYNC_ACTIVE_LOW; 495 if (info->bus_flags & DRM_BUS_FLAG_DE_LOW) 496 cfg |= JZ_LCD_CFG_DE_ACTIVE_LOW; 497 if (info->bus_flags & DRM_BUS_FLAG_PIXDATA_DRIVE_NEGEDGE) 498 cfg |= JZ_LCD_CFG_PCLK_FALLING_EDGE; 499 500 if (!priv->panel_is_sharp) { 501 if (conn->connector_type == DRM_MODE_CONNECTOR_TV) { 502 if (mode->flags & DRM_MODE_FLAG_INTERLACE) 503 cfg |= JZ_LCD_CFG_MODE_TV_OUT_I; 504 else 505 cfg |= JZ_LCD_CFG_MODE_TV_OUT_P; 506 } else { 507 switch (*info->bus_formats) { 508 case MEDIA_BUS_FMT_RGB565_1X16: 509 cfg |= JZ_LCD_CFG_MODE_GENERIC_16BIT; 510 break; 511 case MEDIA_BUS_FMT_RGB666_1X18: 512 cfg |= JZ_LCD_CFG_MODE_GENERIC_18BIT; 513 break; 514 case MEDIA_BUS_FMT_RGB888_1X24: 515 cfg |= JZ_LCD_CFG_MODE_GENERIC_24BIT; 516 break; 517 case MEDIA_BUS_FMT_RGB888_3X8: 518 cfg |= JZ_LCD_CFG_MODE_8BIT_SERIAL; 519 break; 520 default: 521 break; 522 } 523 } 524 } 525 526 regmap_write(priv->map, JZ_REG_LCD_CFG, cfg); 527 } 528 529 static int ingenic_drm_encoder_atomic_check(struct drm_encoder *encoder, 530 struct drm_crtc_state *crtc_state, 531 struct drm_connector_state *conn_state) 532 { 533 struct drm_display_info *info = &conn_state->connector->display_info; 534 535 if (info->num_bus_formats != 1) 536 return -EINVAL; 537 538 if (conn_state->connector->connector_type == DRM_MODE_CONNECTOR_TV) 539 return 0; 540 541 switch (*info->bus_formats) { 542 case MEDIA_BUS_FMT_RGB565_1X16: 543 case MEDIA_BUS_FMT_RGB666_1X18: 544 case MEDIA_BUS_FMT_RGB888_1X24: 545 case MEDIA_BUS_FMT_RGB888_3X8: 546 return 0; 547 default: 548 return -EINVAL; 549 } 550 } 551 552 static void ingenic_drm_atomic_helper_commit_tail(struct drm_atomic_state *old_state) 553 { 554 /* 555 * Just your regular drm_atomic_helper_commit_tail(), but only calls 556 * drm_atomic_helper_wait_for_vblanks() if priv->no_vblank. 557 */ 558 struct drm_device *dev = old_state->dev; 559 struct ingenic_drm *priv = drm_device_get_priv(dev); 560 561 drm_atomic_helper_commit_modeset_disables(dev, old_state); 562 563 drm_atomic_helper_commit_planes(dev, old_state, 0); 564 565 drm_atomic_helper_commit_modeset_enables(dev, old_state); 566 567 drm_atomic_helper_commit_hw_done(old_state); 568 569 if (!priv->no_vblank) 570 drm_atomic_helper_wait_for_vblanks(dev, old_state); 571 572 drm_atomic_helper_cleanup_planes(dev, old_state); 573 } 574 575 static irqreturn_t ingenic_drm_irq_handler(int irq, void *arg) 576 { 577 struct ingenic_drm *priv = drm_device_get_priv(arg); 578 unsigned int state; 579 580 regmap_read(priv->map, JZ_REG_LCD_STATE, &state); 581 582 regmap_update_bits(priv->map, JZ_REG_LCD_STATE, 583 JZ_LCD_STATE_EOF_IRQ, 0); 584 585 if (state & JZ_LCD_STATE_EOF_IRQ) 586 drm_crtc_handle_vblank(&priv->crtc); 587 588 return IRQ_HANDLED; 589 } 590 591 static int ingenic_drm_enable_vblank(struct drm_crtc *crtc) 592 { 593 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 594 595 regmap_update_bits(priv->map, JZ_REG_LCD_CTRL, 596 JZ_LCD_CTRL_EOF_IRQ, JZ_LCD_CTRL_EOF_IRQ); 597 598 return 0; 599 } 600 601 static void ingenic_drm_disable_vblank(struct drm_crtc *crtc) 602 { 603 struct ingenic_drm *priv = drm_crtc_get_priv(crtc); 604 605 regmap_update_bits(priv->map, JZ_REG_LCD_CTRL, JZ_LCD_CTRL_EOF_IRQ, 0); 606 } 607 608 DEFINE_DRM_GEM_CMA_FOPS(ingenic_drm_fops); 609 610 static struct drm_driver ingenic_drm_driver_data = { 611 .driver_features = DRIVER_MODESET | DRIVER_GEM | DRIVER_ATOMIC, 612 .name = "ingenic-drm", 613 .desc = "DRM module for Ingenic SoCs", 614 .date = "20200716", 615 .major = 1, 616 .minor = 1, 617 .patchlevel = 0, 618 619 .fops = &ingenic_drm_fops, 620 DRM_GEM_CMA_DRIVER_OPS, 621 622 .irq_handler = ingenic_drm_irq_handler, 623 }; 624 625 static const struct drm_plane_funcs ingenic_drm_primary_plane_funcs = { 626 .update_plane = drm_atomic_helper_update_plane, 627 .disable_plane = drm_atomic_helper_disable_plane, 628 .reset = drm_atomic_helper_plane_reset, 629 .destroy = drm_plane_cleanup, 630 631 .atomic_duplicate_state = drm_atomic_helper_plane_duplicate_state, 632 .atomic_destroy_state = drm_atomic_helper_plane_destroy_state, 633 }; 634 635 static const struct drm_crtc_funcs ingenic_drm_crtc_funcs = { 636 .set_config = drm_atomic_helper_set_config, 637 .page_flip = drm_atomic_helper_page_flip, 638 .reset = drm_atomic_helper_crtc_reset, 639 .destroy = drm_crtc_cleanup, 640 641 .atomic_duplicate_state = drm_atomic_helper_crtc_duplicate_state, 642 .atomic_destroy_state = drm_atomic_helper_crtc_destroy_state, 643 644 .enable_vblank = ingenic_drm_enable_vblank, 645 .disable_vblank = ingenic_drm_disable_vblank, 646 647 .gamma_set = drm_atomic_helper_legacy_gamma_set, 648 }; 649 650 static const struct drm_plane_helper_funcs ingenic_drm_plane_helper_funcs = { 651 .atomic_update = ingenic_drm_plane_atomic_update, 652 .atomic_check = ingenic_drm_plane_atomic_check, 653 .atomic_disable = ingenic_drm_plane_atomic_disable, 654 .prepare_fb = drm_gem_fb_prepare_fb, 655 }; 656 657 static const struct drm_crtc_helper_funcs ingenic_drm_crtc_helper_funcs = { 658 .atomic_enable = ingenic_drm_crtc_atomic_enable, 659 .atomic_disable = ingenic_drm_crtc_atomic_disable, 660 .atomic_begin = ingenic_drm_crtc_atomic_begin, 661 .atomic_flush = ingenic_drm_crtc_atomic_flush, 662 .atomic_check = ingenic_drm_crtc_atomic_check, 663 .mode_valid = ingenic_drm_crtc_mode_valid, 664 }; 665 666 static const struct drm_encoder_helper_funcs ingenic_drm_encoder_helper_funcs = { 667 .atomic_mode_set = ingenic_drm_encoder_atomic_mode_set, 668 .atomic_check = ingenic_drm_encoder_atomic_check, 669 }; 670 671 static const struct drm_mode_config_funcs ingenic_drm_mode_config_funcs = { 672 .fb_create = drm_gem_fb_create, 673 .output_poll_changed = drm_fb_helper_output_poll_changed, 674 .atomic_check = drm_atomic_helper_check, 675 .atomic_commit = drm_atomic_helper_commit, 676 }; 677 678 static struct drm_mode_config_helper_funcs ingenic_drm_mode_config_helpers = { 679 .atomic_commit_tail = ingenic_drm_atomic_helper_commit_tail, 680 }; 681 682 static void ingenic_drm_unbind_all(void *d) 683 { 684 struct ingenic_drm *priv = d; 685 686 component_unbind_all(priv->dev, &priv->drm); 687 } 688 689 static int ingenic_drm_bind(struct device *dev, bool has_components) 690 { 691 struct platform_device *pdev = to_platform_device(dev); 692 const struct jz_soc_info *soc_info; 693 struct ingenic_drm *priv; 694 struct clk *parent_clk; 695 struct drm_bridge *bridge; 696 struct drm_panel *panel; 697 struct drm_encoder *encoder; 698 struct drm_device *drm; 699 void __iomem *base; 700 long parent_rate; 701 unsigned int i, clone_mask = 0; 702 int ret, irq; 703 704 soc_info = of_device_get_match_data(dev); 705 if (!soc_info) { 706 dev_err(dev, "Missing platform data\n"); 707 return -EINVAL; 708 } 709 710 priv = devm_drm_dev_alloc(dev, &ingenic_drm_driver_data, 711 struct ingenic_drm, drm); 712 if (IS_ERR(priv)) 713 return PTR_ERR(priv); 714 715 priv->soc_info = soc_info; 716 priv->dev = dev; 717 drm = &priv->drm; 718 719 platform_set_drvdata(pdev, priv); 720 721 ret = drmm_mode_config_init(drm); 722 if (ret) 723 return ret; 724 725 drm->mode_config.min_width = 0; 726 drm->mode_config.min_height = 0; 727 drm->mode_config.max_width = soc_info->max_width; 728 drm->mode_config.max_height = 4095; 729 drm->mode_config.funcs = &ingenic_drm_mode_config_funcs; 730 drm->mode_config.helper_private = &ingenic_drm_mode_config_helpers; 731 732 base = devm_platform_ioremap_resource(pdev, 0); 733 if (IS_ERR(base)) { 734 dev_err(dev, "Failed to get memory resource\n"); 735 return PTR_ERR(base); 736 } 737 738 priv->map = devm_regmap_init_mmio(dev, base, 739 &ingenic_drm_regmap_config); 740 if (IS_ERR(priv->map)) { 741 dev_err(dev, "Failed to create regmap\n"); 742 return PTR_ERR(priv->map); 743 } 744 745 irq = platform_get_irq(pdev, 0); 746 if (irq < 0) 747 return irq; 748 749 if (soc_info->needs_dev_clk) { 750 priv->lcd_clk = devm_clk_get(dev, "lcd"); 751 if (IS_ERR(priv->lcd_clk)) { 752 dev_err(dev, "Failed to get lcd clock\n"); 753 return PTR_ERR(priv->lcd_clk); 754 } 755 } 756 757 priv->pix_clk = devm_clk_get(dev, "lcd_pclk"); 758 if (IS_ERR(priv->pix_clk)) { 759 dev_err(dev, "Failed to get pixel clock\n"); 760 return PTR_ERR(priv->pix_clk); 761 } 762 763 priv->dma_hwdesc_f1 = dmam_alloc_coherent(dev, sizeof(*priv->dma_hwdesc_f1), 764 &priv->dma_hwdesc_phys_f1, 765 GFP_KERNEL); 766 if (!priv->dma_hwdesc_f1) 767 return -ENOMEM; 768 769 priv->dma_hwdesc_f1->next = priv->dma_hwdesc_phys_f1; 770 priv->dma_hwdesc_f1->id = 0xf1; 771 772 if (priv->soc_info->has_osd) { 773 priv->dma_hwdesc_f0 = dmam_alloc_coherent(dev, 774 sizeof(*priv->dma_hwdesc_f0), 775 &priv->dma_hwdesc_phys_f0, 776 GFP_KERNEL); 777 if (!priv->dma_hwdesc_f0) 778 return -ENOMEM; 779 780 priv->dma_hwdesc_f0->next = priv->dma_hwdesc_phys_f0; 781 priv->dma_hwdesc_f0->id = 0xf0; 782 } 783 784 if (soc_info->has_osd) 785 priv->ipu_plane = drm_plane_from_index(drm, 0); 786 787 drm_plane_helper_add(&priv->f1, &ingenic_drm_plane_helper_funcs); 788 789 ret = drm_universal_plane_init(drm, &priv->f1, 1, 790 &ingenic_drm_primary_plane_funcs, 791 ingenic_drm_primary_formats, 792 ARRAY_SIZE(ingenic_drm_primary_formats), 793 NULL, DRM_PLANE_TYPE_PRIMARY, NULL); 794 if (ret) { 795 dev_err(dev, "Failed to register plane: %i\n", ret); 796 return ret; 797 } 798 799 drm_crtc_helper_add(&priv->crtc, &ingenic_drm_crtc_helper_funcs); 800 801 ret = drm_crtc_init_with_planes(drm, &priv->crtc, &priv->f1, 802 NULL, &ingenic_drm_crtc_funcs, NULL); 803 if (ret) { 804 dev_err(dev, "Failed to init CRTC: %i\n", ret); 805 return ret; 806 } 807 808 if (soc_info->has_osd) { 809 drm_plane_helper_add(&priv->f0, 810 &ingenic_drm_plane_helper_funcs); 811 812 ret = drm_universal_plane_init(drm, &priv->f0, 1, 813 &ingenic_drm_primary_plane_funcs, 814 ingenic_drm_primary_formats, 815 ARRAY_SIZE(ingenic_drm_primary_formats), 816 NULL, DRM_PLANE_TYPE_OVERLAY, 817 NULL); 818 if (ret) { 819 dev_err(dev, "Failed to register overlay plane: %i\n", 820 ret); 821 return ret; 822 } 823 824 if (IS_ENABLED(CONFIG_DRM_INGENIC_IPU) && has_components) { 825 ret = component_bind_all(dev, drm); 826 if (ret) { 827 if (ret != -EPROBE_DEFER) 828 dev_err(dev, "Failed to bind components: %i\n", ret); 829 return ret; 830 } 831 832 ret = devm_add_action_or_reset(dev, ingenic_drm_unbind_all, priv); 833 if (ret) 834 return ret; 835 836 priv->ipu_plane = drm_plane_from_index(drm, 2); 837 if (!priv->ipu_plane) { 838 dev_err(dev, "Failed to retrieve IPU plane\n"); 839 return -EINVAL; 840 } 841 } 842 } 843 844 for (i = 0; ; i++) { 845 ret = drm_of_find_panel_or_bridge(dev->of_node, 0, i, &panel, &bridge); 846 if (ret) { 847 if (ret == -ENODEV) 848 break; /* we're done */ 849 if (ret != -EPROBE_DEFER) 850 dev_err(dev, "Failed to get bridge handle\n"); 851 return ret; 852 } 853 854 if (panel) 855 bridge = devm_drm_panel_bridge_add_typed(dev, panel, 856 DRM_MODE_CONNECTOR_DPI); 857 858 encoder = devm_kzalloc(dev, sizeof(*encoder), GFP_KERNEL); 859 if (!encoder) 860 return -ENOMEM; 861 862 encoder->possible_crtcs = 1; 863 864 drm_encoder_helper_add(encoder, &ingenic_drm_encoder_helper_funcs); 865 866 ret = drm_simple_encoder_init(drm, encoder, DRM_MODE_ENCODER_DPI); 867 if (ret) { 868 dev_err(dev, "Failed to init encoder: %d\n", ret); 869 return ret; 870 } 871 872 ret = drm_bridge_attach(encoder, bridge, NULL, 0); 873 if (ret) { 874 dev_err(dev, "Unable to attach bridge\n"); 875 return ret; 876 } 877 } 878 879 drm_for_each_encoder(encoder, drm) { 880 clone_mask |= BIT(drm_encoder_index(encoder)); 881 } 882 883 drm_for_each_encoder(encoder, drm) { 884 encoder->possible_clones = clone_mask; 885 } 886 887 ret = drm_irq_install(drm, irq); 888 if (ret) { 889 dev_err(dev, "Unable to install IRQ handler\n"); 890 return ret; 891 } 892 893 ret = drm_vblank_init(drm, 1); 894 if (ret) { 895 dev_err(dev, "Failed calling drm_vblank_init()\n"); 896 return ret; 897 } 898 899 drm_mode_config_reset(drm); 900 901 ret = clk_prepare_enable(priv->pix_clk); 902 if (ret) { 903 dev_err(dev, "Unable to start pixel clock\n"); 904 return ret; 905 } 906 907 if (priv->lcd_clk) { 908 parent_clk = clk_get_parent(priv->lcd_clk); 909 parent_rate = clk_get_rate(parent_clk); 910 911 /* LCD Device clock must be 3x the pixel clock for STN panels, 912 * or 1.5x the pixel clock for TFT panels. To avoid having to 913 * check for the LCD device clock everytime we do a mode change, 914 * we set the LCD device clock to the highest rate possible. 915 */ 916 ret = clk_set_rate(priv->lcd_clk, parent_rate); 917 if (ret) { 918 dev_err(dev, "Unable to set LCD clock rate\n"); 919 goto err_pixclk_disable; 920 } 921 922 ret = clk_prepare_enable(priv->lcd_clk); 923 if (ret) { 924 dev_err(dev, "Unable to start lcd clock\n"); 925 goto err_pixclk_disable; 926 } 927 } 928 929 /* Set address of our DMA descriptor chain */ 930 regmap_write(priv->map, JZ_REG_LCD_DA0, priv->dma_hwdesc_phys_f0); 931 regmap_write(priv->map, JZ_REG_LCD_DA1, priv->dma_hwdesc_phys_f1); 932 933 /* Enable OSD if available */ 934 if (soc_info->has_osd) 935 regmap_write(priv->map, JZ_REG_LCD_OSDC, JZ_LCD_OSDC_OSDEN); 936 937 ret = drm_dev_register(drm, 0); 938 if (ret) { 939 dev_err(dev, "Failed to register DRM driver\n"); 940 goto err_devclk_disable; 941 } 942 943 drm_fbdev_generic_setup(drm, 32); 944 945 return 0; 946 947 err_devclk_disable: 948 if (priv->lcd_clk) 949 clk_disable_unprepare(priv->lcd_clk); 950 err_pixclk_disable: 951 clk_disable_unprepare(priv->pix_clk); 952 return ret; 953 } 954 955 static int ingenic_drm_bind_with_components(struct device *dev) 956 { 957 return ingenic_drm_bind(dev, true); 958 } 959 960 static int compare_of(struct device *dev, void *data) 961 { 962 return dev->of_node == data; 963 } 964 965 static void ingenic_drm_unbind(struct device *dev) 966 { 967 struct ingenic_drm *priv = dev_get_drvdata(dev); 968 969 if (priv->lcd_clk) 970 clk_disable_unprepare(priv->lcd_clk); 971 clk_disable_unprepare(priv->pix_clk); 972 973 drm_dev_unregister(&priv->drm); 974 drm_atomic_helper_shutdown(&priv->drm); 975 } 976 977 static const struct component_master_ops ingenic_master_ops = { 978 .bind = ingenic_drm_bind_with_components, 979 .unbind = ingenic_drm_unbind, 980 }; 981 982 static int ingenic_drm_probe(struct platform_device *pdev) 983 { 984 struct device *dev = &pdev->dev; 985 struct component_match *match = NULL; 986 struct device_node *np; 987 988 if (!IS_ENABLED(CONFIG_DRM_INGENIC_IPU)) 989 return ingenic_drm_bind(dev, false); 990 991 /* IPU is at port address 8 */ 992 np = of_graph_get_remote_node(dev->of_node, 8, 0); 993 if (!np) 994 return ingenic_drm_bind(dev, false); 995 996 drm_of_component_match_add(dev, &match, compare_of, np); 997 of_node_put(np); 998 999 return component_master_add_with_match(dev, &ingenic_master_ops, match); 1000 } 1001 1002 static int ingenic_drm_remove(struct platform_device *pdev) 1003 { 1004 struct device *dev = &pdev->dev; 1005 1006 if (!IS_ENABLED(CONFIG_DRM_INGENIC_IPU)) 1007 ingenic_drm_unbind(dev); 1008 else 1009 component_master_del(dev, &ingenic_master_ops); 1010 1011 return 0; 1012 } 1013 1014 static const struct jz_soc_info jz4740_soc_info = { 1015 .needs_dev_clk = true, 1016 .has_osd = false, 1017 .max_width = 800, 1018 .max_height = 600, 1019 }; 1020 1021 static const struct jz_soc_info jz4725b_soc_info = { 1022 .needs_dev_clk = false, 1023 .has_osd = true, 1024 .max_width = 800, 1025 .max_height = 600, 1026 }; 1027 1028 static const struct jz_soc_info jz4770_soc_info = { 1029 .needs_dev_clk = false, 1030 .has_osd = true, 1031 .max_width = 1280, 1032 .max_height = 720, 1033 }; 1034 1035 static const struct of_device_id ingenic_drm_of_match[] = { 1036 { .compatible = "ingenic,jz4740-lcd", .data = &jz4740_soc_info }, 1037 { .compatible = "ingenic,jz4725b-lcd", .data = &jz4725b_soc_info }, 1038 { .compatible = "ingenic,jz4770-lcd", .data = &jz4770_soc_info }, 1039 { /* sentinel */ }, 1040 }; 1041 MODULE_DEVICE_TABLE(of, ingenic_drm_of_match); 1042 1043 static struct platform_driver ingenic_drm_driver = { 1044 .driver = { 1045 .name = "ingenic-drm", 1046 .of_match_table = of_match_ptr(ingenic_drm_of_match), 1047 }, 1048 .probe = ingenic_drm_probe, 1049 .remove = ingenic_drm_remove, 1050 }; 1051 1052 static int ingenic_drm_init(void) 1053 { 1054 int err; 1055 1056 if (IS_ENABLED(CONFIG_DRM_INGENIC_IPU)) { 1057 err = platform_driver_register(ingenic_ipu_driver_ptr); 1058 if (err) 1059 return err; 1060 } 1061 1062 return platform_driver_register(&ingenic_drm_driver); 1063 } 1064 module_init(ingenic_drm_init); 1065 1066 static void ingenic_drm_exit(void) 1067 { 1068 platform_driver_unregister(&ingenic_drm_driver); 1069 1070 if (IS_ENABLED(CONFIG_DRM_INGENIC_IPU)) 1071 platform_driver_unregister(ingenic_ipu_driver_ptr); 1072 } 1073 module_exit(ingenic_drm_exit); 1074 1075 MODULE_AUTHOR("Paul Cercueil <paul@crapouillou.net>"); 1076 MODULE_DESCRIPTION("DRM driver for the Ingenic SoCs\n"); 1077 MODULE_LICENSE("GPL v2"); 1078