1 /* 2 * Copyright (C) 2011 Samsung Electronics Co.Ltd 3 * Authors: 4 * Seung-Woo Kim <sw0312.kim@samsung.com> 5 * Inki Dae <inki.dae@samsung.com> 6 * Joonyoung Shim <jy0922.shim@samsung.com> 7 * 8 * Based on drivers/media/video/s5p-tv/mixer_reg.c 9 * 10 * This program is free software; you can redistribute it and/or modify it 11 * under the terms of the GNU General Public License as published by the 12 * Free Software Foundation; either version 2 of the License, or (at your 13 * option) any later version. 14 * 15 */ 16 17 #include <drm/drmP.h> 18 19 #include "regs-mixer.h" 20 #include "regs-vp.h" 21 22 #include <linux/kernel.h> 23 #include <linux/spinlock.h> 24 #include <linux/wait.h> 25 #include <linux/i2c.h> 26 #include <linux/platform_device.h> 27 #include <linux/interrupt.h> 28 #include <linux/irq.h> 29 #include <linux/delay.h> 30 #include <linux/pm_runtime.h> 31 #include <linux/clk.h> 32 #include <linux/regulator/consumer.h> 33 #include <linux/of.h> 34 #include <linux/of_device.h> 35 #include <linux/component.h> 36 37 #include <drm/exynos_drm.h> 38 39 #include "exynos_drm_drv.h" 40 #include "exynos_drm_crtc.h" 41 #include "exynos_drm_fb.h" 42 #include "exynos_drm_plane.h" 43 #include "exynos_drm_iommu.h" 44 45 #define MIXER_WIN_NR 3 46 #define VP_DEFAULT_WIN 2 47 48 /* 49 * Mixer color space conversion coefficient triplet. 50 * Used for CSC from RGB to YCbCr. 51 * Each coefficient is a 10-bit fixed point number with 52 * sign and no integer part, i.e. 53 * [0:8] = fractional part (representing a value y = x / 2^9) 54 * [9] = sign 55 * Negative values are encoded with two's complement. 56 */ 57 #define MXR_CSC_C(x) ((int)((x) * 512.0) & 0x3ff) 58 #define MXR_CSC_CT(a0, a1, a2) \ 59 ((MXR_CSC_C(a0) << 20) | (MXR_CSC_C(a1) << 10) | (MXR_CSC_C(a2) << 0)) 60 61 /* YCbCr value, used for mixer background color configuration. */ 62 #define MXR_YCBCR_VAL(y, cb, cr) (((y) << 16) | ((cb) << 8) | ((cr) << 0)) 63 64 /* The pixelformats that are natively supported by the mixer. */ 65 #define MXR_FORMAT_RGB565 4 66 #define MXR_FORMAT_ARGB1555 5 67 #define MXR_FORMAT_ARGB4444 6 68 #define MXR_FORMAT_ARGB8888 7 69 70 struct mixer_resources { 71 int irq; 72 void __iomem *mixer_regs; 73 void __iomem *vp_regs; 74 spinlock_t reg_slock; 75 struct clk *mixer; 76 struct clk *vp; 77 struct clk *hdmi; 78 struct clk *sclk_mixer; 79 struct clk *sclk_hdmi; 80 struct clk *mout_mixer; 81 }; 82 83 enum mixer_version_id { 84 MXR_VER_0_0_0_16, 85 MXR_VER_16_0_33_0, 86 MXR_VER_128_0_0_184, 87 }; 88 89 enum mixer_flag_bits { 90 MXR_BIT_POWERED, 91 MXR_BIT_VSYNC, 92 MXR_BIT_INTERLACE, 93 MXR_BIT_VP_ENABLED, 94 MXR_BIT_HAS_SCLK, 95 }; 96 97 static const uint32_t mixer_formats[] = { 98 DRM_FORMAT_XRGB4444, 99 DRM_FORMAT_ARGB4444, 100 DRM_FORMAT_XRGB1555, 101 DRM_FORMAT_ARGB1555, 102 DRM_FORMAT_RGB565, 103 DRM_FORMAT_XRGB8888, 104 DRM_FORMAT_ARGB8888, 105 }; 106 107 static const uint32_t vp_formats[] = { 108 DRM_FORMAT_NV12, 109 DRM_FORMAT_NV21, 110 }; 111 112 struct mixer_context { 113 struct platform_device *pdev; 114 struct device *dev; 115 struct drm_device *drm_dev; 116 struct exynos_drm_crtc *crtc; 117 struct exynos_drm_plane planes[MIXER_WIN_NR]; 118 unsigned long flags; 119 120 struct mixer_resources mixer_res; 121 enum mixer_version_id mxr_ver; 122 }; 123 124 struct mixer_drv_data { 125 enum mixer_version_id version; 126 bool is_vp_enabled; 127 bool has_sclk; 128 }; 129 130 static const struct exynos_drm_plane_config plane_configs[MIXER_WIN_NR] = { 131 { 132 .zpos = 0, 133 .type = DRM_PLANE_TYPE_PRIMARY, 134 .pixel_formats = mixer_formats, 135 .num_pixel_formats = ARRAY_SIZE(mixer_formats), 136 .capabilities = EXYNOS_DRM_PLANE_CAP_DOUBLE | 137 EXYNOS_DRM_PLANE_CAP_ZPOS, 138 }, { 139 .zpos = 1, 140 .type = DRM_PLANE_TYPE_CURSOR, 141 .pixel_formats = mixer_formats, 142 .num_pixel_formats = ARRAY_SIZE(mixer_formats), 143 .capabilities = EXYNOS_DRM_PLANE_CAP_DOUBLE | 144 EXYNOS_DRM_PLANE_CAP_ZPOS, 145 }, { 146 .zpos = 2, 147 .type = DRM_PLANE_TYPE_OVERLAY, 148 .pixel_formats = vp_formats, 149 .num_pixel_formats = ARRAY_SIZE(vp_formats), 150 .capabilities = EXYNOS_DRM_PLANE_CAP_SCALE | 151 EXYNOS_DRM_PLANE_CAP_ZPOS | 152 EXYNOS_DRM_PLANE_CAP_TILE, 153 }, 154 }; 155 156 static const u8 filter_y_horiz_tap8[] = { 157 0, -1, -1, -1, -1, -1, -1, -1, 158 -1, -1, -1, -1, -1, 0, 0, 0, 159 0, 2, 4, 5, 6, 6, 6, 6, 160 6, 5, 5, 4, 3, 2, 1, 1, 161 0, -6, -12, -16, -18, -20, -21, -20, 162 -20, -18, -16, -13, -10, -8, -5, -2, 163 127, 126, 125, 121, 114, 107, 99, 89, 164 79, 68, 57, 46, 35, 25, 16, 8, 165 }; 166 167 static const u8 filter_y_vert_tap4[] = { 168 0, -3, -6, -8, -8, -8, -8, -7, 169 -6, -5, -4, -3, -2, -1, -1, 0, 170 127, 126, 124, 118, 111, 102, 92, 81, 171 70, 59, 48, 37, 27, 19, 11, 5, 172 0, 5, 11, 19, 27, 37, 48, 59, 173 70, 81, 92, 102, 111, 118, 124, 126, 174 0, 0, -1, -1, -2, -3, -4, -5, 175 -6, -7, -8, -8, -8, -8, -6, -3, 176 }; 177 178 static const u8 filter_cr_horiz_tap4[] = { 179 0, -3, -6, -8, -8, -8, -8, -7, 180 -6, -5, -4, -3, -2, -1, -1, 0, 181 127, 126, 124, 118, 111, 102, 92, 81, 182 70, 59, 48, 37, 27, 19, 11, 5, 183 }; 184 185 static inline bool is_alpha_format(unsigned int pixel_format) 186 { 187 switch (pixel_format) { 188 case DRM_FORMAT_ARGB8888: 189 case DRM_FORMAT_ARGB1555: 190 case DRM_FORMAT_ARGB4444: 191 return true; 192 default: 193 return false; 194 } 195 } 196 197 static inline u32 vp_reg_read(struct mixer_resources *res, u32 reg_id) 198 { 199 return readl(res->vp_regs + reg_id); 200 } 201 202 static inline void vp_reg_write(struct mixer_resources *res, u32 reg_id, 203 u32 val) 204 { 205 writel(val, res->vp_regs + reg_id); 206 } 207 208 static inline void vp_reg_writemask(struct mixer_resources *res, u32 reg_id, 209 u32 val, u32 mask) 210 { 211 u32 old = vp_reg_read(res, reg_id); 212 213 val = (val & mask) | (old & ~mask); 214 writel(val, res->vp_regs + reg_id); 215 } 216 217 static inline u32 mixer_reg_read(struct mixer_resources *res, u32 reg_id) 218 { 219 return readl(res->mixer_regs + reg_id); 220 } 221 222 static inline void mixer_reg_write(struct mixer_resources *res, u32 reg_id, 223 u32 val) 224 { 225 writel(val, res->mixer_regs + reg_id); 226 } 227 228 static inline void mixer_reg_writemask(struct mixer_resources *res, 229 u32 reg_id, u32 val, u32 mask) 230 { 231 u32 old = mixer_reg_read(res, reg_id); 232 233 val = (val & mask) | (old & ~mask); 234 writel(val, res->mixer_regs + reg_id); 235 } 236 237 static void mixer_regs_dump(struct mixer_context *ctx) 238 { 239 #define DUMPREG(reg_id) \ 240 do { \ 241 DRM_DEBUG_KMS(#reg_id " = %08x\n", \ 242 (u32)readl(ctx->mixer_res.mixer_regs + reg_id)); \ 243 } while (0) 244 245 DUMPREG(MXR_STATUS); 246 DUMPREG(MXR_CFG); 247 DUMPREG(MXR_INT_EN); 248 DUMPREG(MXR_INT_STATUS); 249 250 DUMPREG(MXR_LAYER_CFG); 251 DUMPREG(MXR_VIDEO_CFG); 252 253 DUMPREG(MXR_GRAPHIC0_CFG); 254 DUMPREG(MXR_GRAPHIC0_BASE); 255 DUMPREG(MXR_GRAPHIC0_SPAN); 256 DUMPREG(MXR_GRAPHIC0_WH); 257 DUMPREG(MXR_GRAPHIC0_SXY); 258 DUMPREG(MXR_GRAPHIC0_DXY); 259 260 DUMPREG(MXR_GRAPHIC1_CFG); 261 DUMPREG(MXR_GRAPHIC1_BASE); 262 DUMPREG(MXR_GRAPHIC1_SPAN); 263 DUMPREG(MXR_GRAPHIC1_WH); 264 DUMPREG(MXR_GRAPHIC1_SXY); 265 DUMPREG(MXR_GRAPHIC1_DXY); 266 #undef DUMPREG 267 } 268 269 static void vp_regs_dump(struct mixer_context *ctx) 270 { 271 #define DUMPREG(reg_id) \ 272 do { \ 273 DRM_DEBUG_KMS(#reg_id " = %08x\n", \ 274 (u32) readl(ctx->mixer_res.vp_regs + reg_id)); \ 275 } while (0) 276 277 DUMPREG(VP_ENABLE); 278 DUMPREG(VP_SRESET); 279 DUMPREG(VP_SHADOW_UPDATE); 280 DUMPREG(VP_FIELD_ID); 281 DUMPREG(VP_MODE); 282 DUMPREG(VP_IMG_SIZE_Y); 283 DUMPREG(VP_IMG_SIZE_C); 284 DUMPREG(VP_PER_RATE_CTRL); 285 DUMPREG(VP_TOP_Y_PTR); 286 DUMPREG(VP_BOT_Y_PTR); 287 DUMPREG(VP_TOP_C_PTR); 288 DUMPREG(VP_BOT_C_PTR); 289 DUMPREG(VP_ENDIAN_MODE); 290 DUMPREG(VP_SRC_H_POSITION); 291 DUMPREG(VP_SRC_V_POSITION); 292 DUMPREG(VP_SRC_WIDTH); 293 DUMPREG(VP_SRC_HEIGHT); 294 DUMPREG(VP_DST_H_POSITION); 295 DUMPREG(VP_DST_V_POSITION); 296 DUMPREG(VP_DST_WIDTH); 297 DUMPREG(VP_DST_HEIGHT); 298 DUMPREG(VP_H_RATIO); 299 DUMPREG(VP_V_RATIO); 300 301 #undef DUMPREG 302 } 303 304 static inline void vp_filter_set(struct mixer_resources *res, 305 int reg_id, const u8 *data, unsigned int size) 306 { 307 /* assure 4-byte align */ 308 BUG_ON(size & 3); 309 for (; size; size -= 4, reg_id += 4, data += 4) { 310 u32 val = (data[0] << 24) | (data[1] << 16) | 311 (data[2] << 8) | data[3]; 312 vp_reg_write(res, reg_id, val); 313 } 314 } 315 316 static void vp_default_filter(struct mixer_resources *res) 317 { 318 vp_filter_set(res, VP_POLY8_Y0_LL, 319 filter_y_horiz_tap8, sizeof(filter_y_horiz_tap8)); 320 vp_filter_set(res, VP_POLY4_Y0_LL, 321 filter_y_vert_tap4, sizeof(filter_y_vert_tap4)); 322 vp_filter_set(res, VP_POLY4_C0_LL, 323 filter_cr_horiz_tap4, sizeof(filter_cr_horiz_tap4)); 324 } 325 326 static void mixer_cfg_gfx_blend(struct mixer_context *ctx, unsigned int win, 327 bool alpha) 328 { 329 struct mixer_resources *res = &ctx->mixer_res; 330 u32 val; 331 332 val = MXR_GRP_CFG_COLOR_KEY_DISABLE; /* no blank key */ 333 if (alpha) { 334 /* blending based on pixel alpha */ 335 val |= MXR_GRP_CFG_BLEND_PRE_MUL; 336 val |= MXR_GRP_CFG_PIXEL_BLEND_EN; 337 } 338 mixer_reg_writemask(res, MXR_GRAPHIC_CFG(win), 339 val, MXR_GRP_CFG_MISC_MASK); 340 } 341 342 static void mixer_cfg_vp_blend(struct mixer_context *ctx) 343 { 344 struct mixer_resources *res = &ctx->mixer_res; 345 u32 val; 346 347 /* 348 * No blending at the moment since the NV12/NV21 pixelformats don't 349 * have an alpha channel. However the mixer supports a global alpha 350 * value for a layer. Once this functionality is exposed, we can 351 * support blending of the video layer through this. 352 */ 353 val = 0; 354 mixer_reg_write(res, MXR_VIDEO_CFG, val); 355 } 356 357 static void mixer_vsync_set_update(struct mixer_context *ctx, bool enable) 358 { 359 struct mixer_resources *res = &ctx->mixer_res; 360 361 /* block update on vsync */ 362 mixer_reg_writemask(res, MXR_STATUS, enable ? 363 MXR_STATUS_SYNC_ENABLE : 0, MXR_STATUS_SYNC_ENABLE); 364 365 if (test_bit(MXR_BIT_VP_ENABLED, &ctx->flags)) 366 vp_reg_write(res, VP_SHADOW_UPDATE, enable ? 367 VP_SHADOW_UPDATE_ENABLE : 0); 368 } 369 370 static void mixer_cfg_scan(struct mixer_context *ctx, unsigned int height) 371 { 372 struct mixer_resources *res = &ctx->mixer_res; 373 u32 val; 374 375 /* choosing between interlace and progressive mode */ 376 val = test_bit(MXR_BIT_INTERLACE, &ctx->flags) ? 377 MXR_CFG_SCAN_INTERLACE : MXR_CFG_SCAN_PROGRESSIVE; 378 379 if (ctx->mxr_ver != MXR_VER_128_0_0_184) { 380 /* choosing between proper HD and SD mode */ 381 if (height <= 480) 382 val |= MXR_CFG_SCAN_NTSC | MXR_CFG_SCAN_SD; 383 else if (height <= 576) 384 val |= MXR_CFG_SCAN_PAL | MXR_CFG_SCAN_SD; 385 else if (height <= 720) 386 val |= MXR_CFG_SCAN_HD_720 | MXR_CFG_SCAN_HD; 387 else if (height <= 1080) 388 val |= MXR_CFG_SCAN_HD_1080 | MXR_CFG_SCAN_HD; 389 else 390 val |= MXR_CFG_SCAN_HD_720 | MXR_CFG_SCAN_HD; 391 } 392 393 mixer_reg_writemask(res, MXR_CFG, val, MXR_CFG_SCAN_MASK); 394 } 395 396 static void mixer_cfg_rgb_fmt(struct mixer_context *ctx, unsigned int height) 397 { 398 struct mixer_resources *res = &ctx->mixer_res; 399 u32 val; 400 401 switch (height) { 402 case 480: 403 case 576: 404 val = MXR_CFG_RGB601_0_255; 405 break; 406 case 720: 407 case 1080: 408 default: 409 val = MXR_CFG_RGB709_16_235; 410 /* Configure the BT.709 CSC matrix for full range RGB. */ 411 mixer_reg_write(res, MXR_CM_COEFF_Y, 412 MXR_CSC_CT( 0.184, 0.614, 0.063) | 413 MXR_CM_COEFF_RGB_FULL); 414 mixer_reg_write(res, MXR_CM_COEFF_CB, 415 MXR_CSC_CT(-0.102, -0.338, 0.440)); 416 mixer_reg_write(res, MXR_CM_COEFF_CR, 417 MXR_CSC_CT( 0.440, -0.399, -0.040)); 418 break; 419 } 420 421 mixer_reg_writemask(res, MXR_CFG, val, MXR_CFG_RGB_FMT_MASK); 422 } 423 424 static void mixer_cfg_layer(struct mixer_context *ctx, unsigned int win, 425 unsigned int priority, bool enable) 426 { 427 struct mixer_resources *res = &ctx->mixer_res; 428 u32 val = enable ? ~0 : 0; 429 430 switch (win) { 431 case 0: 432 mixer_reg_writemask(res, MXR_CFG, val, MXR_CFG_GRP0_ENABLE); 433 mixer_reg_writemask(res, MXR_LAYER_CFG, 434 MXR_LAYER_CFG_GRP0_VAL(priority), 435 MXR_LAYER_CFG_GRP0_MASK); 436 break; 437 case 1: 438 mixer_reg_writemask(res, MXR_CFG, val, MXR_CFG_GRP1_ENABLE); 439 mixer_reg_writemask(res, MXR_LAYER_CFG, 440 MXR_LAYER_CFG_GRP1_VAL(priority), 441 MXR_LAYER_CFG_GRP1_MASK); 442 443 break; 444 case VP_DEFAULT_WIN: 445 if (test_bit(MXR_BIT_VP_ENABLED, &ctx->flags)) { 446 vp_reg_writemask(res, VP_ENABLE, val, VP_ENABLE_ON); 447 mixer_reg_writemask(res, MXR_CFG, val, 448 MXR_CFG_VP_ENABLE); 449 mixer_reg_writemask(res, MXR_LAYER_CFG, 450 MXR_LAYER_CFG_VP_VAL(priority), 451 MXR_LAYER_CFG_VP_MASK); 452 } 453 break; 454 } 455 } 456 457 static void mixer_run(struct mixer_context *ctx) 458 { 459 struct mixer_resources *res = &ctx->mixer_res; 460 461 mixer_reg_writemask(res, MXR_STATUS, ~0, MXR_STATUS_REG_RUN); 462 } 463 464 static void mixer_stop(struct mixer_context *ctx) 465 { 466 struct mixer_resources *res = &ctx->mixer_res; 467 int timeout = 20; 468 469 mixer_reg_writemask(res, MXR_STATUS, 0, MXR_STATUS_REG_RUN); 470 471 while (!(mixer_reg_read(res, MXR_STATUS) & MXR_STATUS_REG_IDLE) && 472 --timeout) 473 usleep_range(10000, 12000); 474 } 475 476 static void vp_video_buffer(struct mixer_context *ctx, 477 struct exynos_drm_plane *plane) 478 { 479 struct exynos_drm_plane_state *state = 480 to_exynos_plane_state(plane->base.state); 481 struct drm_display_mode *mode = &state->base.crtc->state->adjusted_mode; 482 struct mixer_resources *res = &ctx->mixer_res; 483 struct drm_framebuffer *fb = state->base.fb; 484 unsigned int priority = state->base.normalized_zpos + 1; 485 unsigned long flags; 486 dma_addr_t luma_addr[2], chroma_addr[2]; 487 bool is_tiled, is_nv21; 488 u32 val; 489 490 is_nv21 = (fb->format->format == DRM_FORMAT_NV21); 491 is_tiled = (fb->modifier == DRM_FORMAT_MOD_SAMSUNG_64_32_TILE); 492 493 luma_addr[0] = exynos_drm_fb_dma_addr(fb, 0); 494 chroma_addr[0] = exynos_drm_fb_dma_addr(fb, 1); 495 496 if (mode->flags & DRM_MODE_FLAG_INTERLACE) { 497 __set_bit(MXR_BIT_INTERLACE, &ctx->flags); 498 if (is_tiled) { 499 luma_addr[1] = luma_addr[0] + 0x40; 500 chroma_addr[1] = chroma_addr[0] + 0x40; 501 } else { 502 luma_addr[1] = luma_addr[0] + fb->pitches[0]; 503 chroma_addr[1] = chroma_addr[0] + fb->pitches[0]; 504 } 505 } else { 506 __clear_bit(MXR_BIT_INTERLACE, &ctx->flags); 507 luma_addr[1] = 0; 508 chroma_addr[1] = 0; 509 } 510 511 spin_lock_irqsave(&res->reg_slock, flags); 512 513 /* interlace or progressive scan mode */ 514 val = (test_bit(MXR_BIT_INTERLACE, &ctx->flags) ? ~0 : 0); 515 vp_reg_writemask(res, VP_MODE, val, VP_MODE_LINE_SKIP); 516 517 /* setup format */ 518 val = (is_nv21 ? VP_MODE_NV21 : VP_MODE_NV12); 519 val |= (is_tiled ? VP_MODE_MEM_TILED : VP_MODE_MEM_LINEAR); 520 vp_reg_writemask(res, VP_MODE, val, VP_MODE_FMT_MASK); 521 522 /* setting size of input image */ 523 vp_reg_write(res, VP_IMG_SIZE_Y, VP_IMG_HSIZE(fb->pitches[0]) | 524 VP_IMG_VSIZE(fb->height)); 525 /* chroma plane for NV12/NV21 is half the height of the luma plane */ 526 vp_reg_write(res, VP_IMG_SIZE_C, VP_IMG_HSIZE(fb->pitches[0]) | 527 VP_IMG_VSIZE(fb->height / 2)); 528 529 vp_reg_write(res, VP_SRC_WIDTH, state->src.w); 530 vp_reg_write(res, VP_SRC_HEIGHT, state->src.h); 531 vp_reg_write(res, VP_SRC_H_POSITION, 532 VP_SRC_H_POSITION_VAL(state->src.x)); 533 vp_reg_write(res, VP_SRC_V_POSITION, state->src.y); 534 535 vp_reg_write(res, VP_DST_WIDTH, state->crtc.w); 536 vp_reg_write(res, VP_DST_H_POSITION, state->crtc.x); 537 if (test_bit(MXR_BIT_INTERLACE, &ctx->flags)) { 538 vp_reg_write(res, VP_DST_HEIGHT, state->crtc.h / 2); 539 vp_reg_write(res, VP_DST_V_POSITION, state->crtc.y / 2); 540 } else { 541 vp_reg_write(res, VP_DST_HEIGHT, state->crtc.h); 542 vp_reg_write(res, VP_DST_V_POSITION, state->crtc.y); 543 } 544 545 vp_reg_write(res, VP_H_RATIO, state->h_ratio); 546 vp_reg_write(res, VP_V_RATIO, state->v_ratio); 547 548 vp_reg_write(res, VP_ENDIAN_MODE, VP_ENDIAN_MODE_LITTLE); 549 550 /* set buffer address to vp */ 551 vp_reg_write(res, VP_TOP_Y_PTR, luma_addr[0]); 552 vp_reg_write(res, VP_BOT_Y_PTR, luma_addr[1]); 553 vp_reg_write(res, VP_TOP_C_PTR, chroma_addr[0]); 554 vp_reg_write(res, VP_BOT_C_PTR, chroma_addr[1]); 555 556 mixer_cfg_scan(ctx, mode->vdisplay); 557 mixer_cfg_rgb_fmt(ctx, mode->vdisplay); 558 mixer_cfg_layer(ctx, plane->index, priority, true); 559 mixer_cfg_vp_blend(ctx); 560 mixer_run(ctx); 561 562 spin_unlock_irqrestore(&res->reg_slock, flags); 563 564 mixer_regs_dump(ctx); 565 vp_regs_dump(ctx); 566 } 567 568 static void mixer_layer_update(struct mixer_context *ctx) 569 { 570 struct mixer_resources *res = &ctx->mixer_res; 571 572 mixer_reg_writemask(res, MXR_CFG, ~0, MXR_CFG_LAYER_UPDATE); 573 } 574 575 static void mixer_graph_buffer(struct mixer_context *ctx, 576 struct exynos_drm_plane *plane) 577 { 578 struct exynos_drm_plane_state *state = 579 to_exynos_plane_state(plane->base.state); 580 struct drm_display_mode *mode = &state->base.crtc->state->adjusted_mode; 581 struct mixer_resources *res = &ctx->mixer_res; 582 struct drm_framebuffer *fb = state->base.fb; 583 unsigned int priority = state->base.normalized_zpos + 1; 584 unsigned long flags; 585 unsigned int win = plane->index; 586 unsigned int x_ratio = 0, y_ratio = 0; 587 unsigned int dst_x_offset, dst_y_offset; 588 dma_addr_t dma_addr; 589 unsigned int fmt; 590 u32 val; 591 592 switch (fb->format->format) { 593 case DRM_FORMAT_XRGB4444: 594 case DRM_FORMAT_ARGB4444: 595 fmt = MXR_FORMAT_ARGB4444; 596 break; 597 598 case DRM_FORMAT_XRGB1555: 599 case DRM_FORMAT_ARGB1555: 600 fmt = MXR_FORMAT_ARGB1555; 601 break; 602 603 case DRM_FORMAT_RGB565: 604 fmt = MXR_FORMAT_RGB565; 605 break; 606 607 case DRM_FORMAT_XRGB8888: 608 case DRM_FORMAT_ARGB8888: 609 default: 610 fmt = MXR_FORMAT_ARGB8888; 611 break; 612 } 613 614 /* ratio is already checked by common plane code */ 615 x_ratio = state->h_ratio == (1 << 15); 616 y_ratio = state->v_ratio == (1 << 15); 617 618 dst_x_offset = state->crtc.x; 619 dst_y_offset = state->crtc.y; 620 621 /* translate dma address base s.t. the source image offset is zero */ 622 dma_addr = exynos_drm_fb_dma_addr(fb, 0) 623 + (state->src.x * fb->format->cpp[0]) 624 + (state->src.y * fb->pitches[0]); 625 626 if (mode->flags & DRM_MODE_FLAG_INTERLACE) 627 __set_bit(MXR_BIT_INTERLACE, &ctx->flags); 628 else 629 __clear_bit(MXR_BIT_INTERLACE, &ctx->flags); 630 631 spin_lock_irqsave(&res->reg_slock, flags); 632 633 /* setup format */ 634 mixer_reg_writemask(res, MXR_GRAPHIC_CFG(win), 635 MXR_GRP_CFG_FORMAT_VAL(fmt), MXR_GRP_CFG_FORMAT_MASK); 636 637 /* setup geometry */ 638 mixer_reg_write(res, MXR_GRAPHIC_SPAN(win), 639 fb->pitches[0] / fb->format->cpp[0]); 640 641 /* setup display size */ 642 if (ctx->mxr_ver == MXR_VER_128_0_0_184 && 643 win == DEFAULT_WIN) { 644 val = MXR_MXR_RES_HEIGHT(mode->vdisplay); 645 val |= MXR_MXR_RES_WIDTH(mode->hdisplay); 646 mixer_reg_write(res, MXR_RESOLUTION, val); 647 } 648 649 val = MXR_GRP_WH_WIDTH(state->src.w); 650 val |= MXR_GRP_WH_HEIGHT(state->src.h); 651 val |= MXR_GRP_WH_H_SCALE(x_ratio); 652 val |= MXR_GRP_WH_V_SCALE(y_ratio); 653 mixer_reg_write(res, MXR_GRAPHIC_WH(win), val); 654 655 /* setup offsets in display image */ 656 val = MXR_GRP_DXY_DX(dst_x_offset); 657 val |= MXR_GRP_DXY_DY(dst_y_offset); 658 mixer_reg_write(res, MXR_GRAPHIC_DXY(win), val); 659 660 /* set buffer address to mixer */ 661 mixer_reg_write(res, MXR_GRAPHIC_BASE(win), dma_addr); 662 663 mixer_cfg_scan(ctx, mode->vdisplay); 664 mixer_cfg_rgb_fmt(ctx, mode->vdisplay); 665 mixer_cfg_layer(ctx, win, priority, true); 666 mixer_cfg_gfx_blend(ctx, win, is_alpha_format(fb->format->format)); 667 668 /* layer update mandatory for mixer 16.0.33.0 */ 669 if (ctx->mxr_ver == MXR_VER_16_0_33_0 || 670 ctx->mxr_ver == MXR_VER_128_0_0_184) 671 mixer_layer_update(ctx); 672 673 mixer_run(ctx); 674 675 spin_unlock_irqrestore(&res->reg_slock, flags); 676 677 mixer_regs_dump(ctx); 678 } 679 680 static void vp_win_reset(struct mixer_context *ctx) 681 { 682 struct mixer_resources *res = &ctx->mixer_res; 683 unsigned int tries = 100; 684 685 vp_reg_write(res, VP_SRESET, VP_SRESET_PROCESSING); 686 while (--tries) { 687 /* waiting until VP_SRESET_PROCESSING is 0 */ 688 if (~vp_reg_read(res, VP_SRESET) & VP_SRESET_PROCESSING) 689 break; 690 mdelay(10); 691 } 692 WARN(tries == 0, "failed to reset Video Processor\n"); 693 } 694 695 static void mixer_win_reset(struct mixer_context *ctx) 696 { 697 struct mixer_resources *res = &ctx->mixer_res; 698 unsigned long flags; 699 700 spin_lock_irqsave(&res->reg_slock, flags); 701 702 mixer_reg_writemask(res, MXR_CFG, MXR_CFG_DST_HDMI, MXR_CFG_DST_MASK); 703 704 /* set output in RGB888 mode */ 705 mixer_reg_writemask(res, MXR_CFG, MXR_CFG_OUT_RGB888, MXR_CFG_OUT_MASK); 706 707 /* 16 beat burst in DMA */ 708 mixer_reg_writemask(res, MXR_STATUS, MXR_STATUS_16_BURST, 709 MXR_STATUS_BURST_MASK); 710 711 /* reset default layer priority */ 712 mixer_reg_write(res, MXR_LAYER_CFG, 0); 713 714 /* set all background colors to RGB (0,0,0) */ 715 mixer_reg_write(res, MXR_BG_COLOR0, MXR_YCBCR_VAL(0, 128, 128)); 716 mixer_reg_write(res, MXR_BG_COLOR1, MXR_YCBCR_VAL(0, 128, 128)); 717 mixer_reg_write(res, MXR_BG_COLOR2, MXR_YCBCR_VAL(0, 128, 128)); 718 719 if (test_bit(MXR_BIT_VP_ENABLED, &ctx->flags)) { 720 /* configuration of Video Processor Registers */ 721 vp_win_reset(ctx); 722 vp_default_filter(res); 723 } 724 725 /* disable all layers */ 726 mixer_reg_writemask(res, MXR_CFG, 0, MXR_CFG_GRP0_ENABLE); 727 mixer_reg_writemask(res, MXR_CFG, 0, MXR_CFG_GRP1_ENABLE); 728 if (test_bit(MXR_BIT_VP_ENABLED, &ctx->flags)) 729 mixer_reg_writemask(res, MXR_CFG, 0, MXR_CFG_VP_ENABLE); 730 731 /* set all source image offsets to zero */ 732 mixer_reg_write(res, MXR_GRAPHIC_SXY(0), 0); 733 mixer_reg_write(res, MXR_GRAPHIC_SXY(1), 0); 734 735 spin_unlock_irqrestore(&res->reg_slock, flags); 736 } 737 738 static irqreturn_t mixer_irq_handler(int irq, void *arg) 739 { 740 struct mixer_context *ctx = arg; 741 struct mixer_resources *res = &ctx->mixer_res; 742 u32 val, base, shadow; 743 744 spin_lock(&res->reg_slock); 745 746 /* read interrupt status for handling and clearing flags for VSYNC */ 747 val = mixer_reg_read(res, MXR_INT_STATUS); 748 749 /* handling VSYNC */ 750 if (val & MXR_INT_STATUS_VSYNC) { 751 /* vsync interrupt use different bit for read and clear */ 752 val |= MXR_INT_CLEAR_VSYNC; 753 val &= ~MXR_INT_STATUS_VSYNC; 754 755 /* interlace scan need to check shadow register */ 756 if (test_bit(MXR_BIT_INTERLACE, &ctx->flags)) { 757 base = mixer_reg_read(res, MXR_GRAPHIC_BASE(0)); 758 shadow = mixer_reg_read(res, MXR_GRAPHIC_BASE_S(0)); 759 if (base != shadow) 760 goto out; 761 762 base = mixer_reg_read(res, MXR_GRAPHIC_BASE(1)); 763 shadow = mixer_reg_read(res, MXR_GRAPHIC_BASE_S(1)); 764 if (base != shadow) 765 goto out; 766 } 767 768 drm_crtc_handle_vblank(&ctx->crtc->base); 769 } 770 771 out: 772 /* clear interrupts */ 773 mixer_reg_write(res, MXR_INT_STATUS, val); 774 775 spin_unlock(&res->reg_slock); 776 777 return IRQ_HANDLED; 778 } 779 780 static int mixer_resources_init(struct mixer_context *mixer_ctx) 781 { 782 struct device *dev = &mixer_ctx->pdev->dev; 783 struct mixer_resources *mixer_res = &mixer_ctx->mixer_res; 784 struct resource *res; 785 int ret; 786 787 spin_lock_init(&mixer_res->reg_slock); 788 789 mixer_res->mixer = devm_clk_get(dev, "mixer"); 790 if (IS_ERR(mixer_res->mixer)) { 791 dev_err(dev, "failed to get clock 'mixer'\n"); 792 return -ENODEV; 793 } 794 795 mixer_res->hdmi = devm_clk_get(dev, "hdmi"); 796 if (IS_ERR(mixer_res->hdmi)) { 797 dev_err(dev, "failed to get clock 'hdmi'\n"); 798 return PTR_ERR(mixer_res->hdmi); 799 } 800 801 mixer_res->sclk_hdmi = devm_clk_get(dev, "sclk_hdmi"); 802 if (IS_ERR(mixer_res->sclk_hdmi)) { 803 dev_err(dev, "failed to get clock 'sclk_hdmi'\n"); 804 return -ENODEV; 805 } 806 res = platform_get_resource(mixer_ctx->pdev, IORESOURCE_MEM, 0); 807 if (res == NULL) { 808 dev_err(dev, "get memory resource failed.\n"); 809 return -ENXIO; 810 } 811 812 mixer_res->mixer_regs = devm_ioremap(dev, res->start, 813 resource_size(res)); 814 if (mixer_res->mixer_regs == NULL) { 815 dev_err(dev, "register mapping failed.\n"); 816 return -ENXIO; 817 } 818 819 res = platform_get_resource(mixer_ctx->pdev, IORESOURCE_IRQ, 0); 820 if (res == NULL) { 821 dev_err(dev, "get interrupt resource failed.\n"); 822 return -ENXIO; 823 } 824 825 ret = devm_request_irq(dev, res->start, mixer_irq_handler, 826 0, "drm_mixer", mixer_ctx); 827 if (ret) { 828 dev_err(dev, "request interrupt failed.\n"); 829 return ret; 830 } 831 mixer_res->irq = res->start; 832 833 return 0; 834 } 835 836 static int vp_resources_init(struct mixer_context *mixer_ctx) 837 { 838 struct device *dev = &mixer_ctx->pdev->dev; 839 struct mixer_resources *mixer_res = &mixer_ctx->mixer_res; 840 struct resource *res; 841 842 mixer_res->vp = devm_clk_get(dev, "vp"); 843 if (IS_ERR(mixer_res->vp)) { 844 dev_err(dev, "failed to get clock 'vp'\n"); 845 return -ENODEV; 846 } 847 848 if (test_bit(MXR_BIT_HAS_SCLK, &mixer_ctx->flags)) { 849 mixer_res->sclk_mixer = devm_clk_get(dev, "sclk_mixer"); 850 if (IS_ERR(mixer_res->sclk_mixer)) { 851 dev_err(dev, "failed to get clock 'sclk_mixer'\n"); 852 return -ENODEV; 853 } 854 mixer_res->mout_mixer = devm_clk_get(dev, "mout_mixer"); 855 if (IS_ERR(mixer_res->mout_mixer)) { 856 dev_err(dev, "failed to get clock 'mout_mixer'\n"); 857 return -ENODEV; 858 } 859 860 if (mixer_res->sclk_hdmi && mixer_res->mout_mixer) 861 clk_set_parent(mixer_res->mout_mixer, 862 mixer_res->sclk_hdmi); 863 } 864 865 res = platform_get_resource(mixer_ctx->pdev, IORESOURCE_MEM, 1); 866 if (res == NULL) { 867 dev_err(dev, "get memory resource failed.\n"); 868 return -ENXIO; 869 } 870 871 mixer_res->vp_regs = devm_ioremap(dev, res->start, 872 resource_size(res)); 873 if (mixer_res->vp_regs == NULL) { 874 dev_err(dev, "register mapping failed.\n"); 875 return -ENXIO; 876 } 877 878 return 0; 879 } 880 881 static int mixer_initialize(struct mixer_context *mixer_ctx, 882 struct drm_device *drm_dev) 883 { 884 int ret; 885 struct exynos_drm_private *priv; 886 priv = drm_dev->dev_private; 887 888 mixer_ctx->drm_dev = drm_dev; 889 890 /* acquire resources: regs, irqs, clocks */ 891 ret = mixer_resources_init(mixer_ctx); 892 if (ret) { 893 DRM_ERROR("mixer_resources_init failed ret=%d\n", ret); 894 return ret; 895 } 896 897 if (test_bit(MXR_BIT_VP_ENABLED, &mixer_ctx->flags)) { 898 /* acquire vp resources: regs, irqs, clocks */ 899 ret = vp_resources_init(mixer_ctx); 900 if (ret) { 901 DRM_ERROR("vp_resources_init failed ret=%d\n", ret); 902 return ret; 903 } 904 } 905 906 return drm_iommu_attach_device(drm_dev, mixer_ctx->dev); 907 } 908 909 static void mixer_ctx_remove(struct mixer_context *mixer_ctx) 910 { 911 drm_iommu_detach_device(mixer_ctx->drm_dev, mixer_ctx->dev); 912 } 913 914 static int mixer_enable_vblank(struct exynos_drm_crtc *crtc) 915 { 916 struct mixer_context *mixer_ctx = crtc->ctx; 917 struct mixer_resources *res = &mixer_ctx->mixer_res; 918 919 __set_bit(MXR_BIT_VSYNC, &mixer_ctx->flags); 920 if (!test_bit(MXR_BIT_POWERED, &mixer_ctx->flags)) 921 return 0; 922 923 /* enable vsync interrupt */ 924 mixer_reg_writemask(res, MXR_INT_STATUS, ~0, MXR_INT_CLEAR_VSYNC); 925 mixer_reg_writemask(res, MXR_INT_EN, ~0, MXR_INT_EN_VSYNC); 926 927 return 0; 928 } 929 930 static void mixer_disable_vblank(struct exynos_drm_crtc *crtc) 931 { 932 struct mixer_context *mixer_ctx = crtc->ctx; 933 struct mixer_resources *res = &mixer_ctx->mixer_res; 934 935 __clear_bit(MXR_BIT_VSYNC, &mixer_ctx->flags); 936 937 if (!test_bit(MXR_BIT_POWERED, &mixer_ctx->flags)) 938 return; 939 940 /* disable vsync interrupt */ 941 mixer_reg_writemask(res, MXR_INT_STATUS, ~0, MXR_INT_CLEAR_VSYNC); 942 mixer_reg_writemask(res, MXR_INT_EN, 0, MXR_INT_EN_VSYNC); 943 } 944 945 static void mixer_atomic_begin(struct exynos_drm_crtc *crtc) 946 { 947 struct mixer_context *mixer_ctx = crtc->ctx; 948 949 if (!test_bit(MXR_BIT_POWERED, &mixer_ctx->flags)) 950 return; 951 952 mixer_vsync_set_update(mixer_ctx, false); 953 } 954 955 static void mixer_update_plane(struct exynos_drm_crtc *crtc, 956 struct exynos_drm_plane *plane) 957 { 958 struct mixer_context *mixer_ctx = crtc->ctx; 959 960 DRM_DEBUG_KMS("win: %d\n", plane->index); 961 962 if (!test_bit(MXR_BIT_POWERED, &mixer_ctx->flags)) 963 return; 964 965 if (plane->index == VP_DEFAULT_WIN) 966 vp_video_buffer(mixer_ctx, plane); 967 else 968 mixer_graph_buffer(mixer_ctx, plane); 969 } 970 971 static void mixer_disable_plane(struct exynos_drm_crtc *crtc, 972 struct exynos_drm_plane *plane) 973 { 974 struct mixer_context *mixer_ctx = crtc->ctx; 975 struct mixer_resources *res = &mixer_ctx->mixer_res; 976 unsigned long flags; 977 978 DRM_DEBUG_KMS("win: %d\n", plane->index); 979 980 if (!test_bit(MXR_BIT_POWERED, &mixer_ctx->flags)) 981 return; 982 983 spin_lock_irqsave(&res->reg_slock, flags); 984 mixer_cfg_layer(mixer_ctx, plane->index, 0, false); 985 spin_unlock_irqrestore(&res->reg_slock, flags); 986 } 987 988 static void mixer_atomic_flush(struct exynos_drm_crtc *crtc) 989 { 990 struct mixer_context *mixer_ctx = crtc->ctx; 991 992 if (!test_bit(MXR_BIT_POWERED, &mixer_ctx->flags)) 993 return; 994 995 mixer_vsync_set_update(mixer_ctx, true); 996 exynos_crtc_handle_event(crtc); 997 } 998 999 static void mixer_enable(struct exynos_drm_crtc *crtc) 1000 { 1001 struct mixer_context *ctx = crtc->ctx; 1002 struct mixer_resources *res = &ctx->mixer_res; 1003 1004 if (test_bit(MXR_BIT_POWERED, &ctx->flags)) 1005 return; 1006 1007 pm_runtime_get_sync(ctx->dev); 1008 1009 exynos_drm_pipe_clk_enable(crtc, true); 1010 1011 mixer_vsync_set_update(ctx, false); 1012 1013 mixer_reg_writemask(res, MXR_STATUS, ~0, MXR_STATUS_SOFT_RESET); 1014 1015 if (test_bit(MXR_BIT_VSYNC, &ctx->flags)) { 1016 mixer_reg_writemask(res, MXR_INT_STATUS, ~0, MXR_INT_CLEAR_VSYNC); 1017 mixer_reg_writemask(res, MXR_INT_EN, ~0, MXR_INT_EN_VSYNC); 1018 } 1019 mixer_win_reset(ctx); 1020 1021 mixer_vsync_set_update(ctx, true); 1022 1023 set_bit(MXR_BIT_POWERED, &ctx->flags); 1024 } 1025 1026 static void mixer_disable(struct exynos_drm_crtc *crtc) 1027 { 1028 struct mixer_context *ctx = crtc->ctx; 1029 int i; 1030 1031 if (!test_bit(MXR_BIT_POWERED, &ctx->flags)) 1032 return; 1033 1034 mixer_stop(ctx); 1035 mixer_regs_dump(ctx); 1036 1037 for (i = 0; i < MIXER_WIN_NR; i++) 1038 mixer_disable_plane(crtc, &ctx->planes[i]); 1039 1040 exynos_drm_pipe_clk_enable(crtc, false); 1041 1042 pm_runtime_put(ctx->dev); 1043 1044 clear_bit(MXR_BIT_POWERED, &ctx->flags); 1045 } 1046 1047 /* Only valid for Mixer version 16.0.33.0 */ 1048 static int mixer_atomic_check(struct exynos_drm_crtc *crtc, 1049 struct drm_crtc_state *state) 1050 { 1051 struct drm_display_mode *mode = &state->adjusted_mode; 1052 u32 w, h; 1053 1054 w = mode->hdisplay; 1055 h = mode->vdisplay; 1056 1057 DRM_DEBUG_KMS("xres=%d, yres=%d, refresh=%d, intl=%d\n", 1058 mode->hdisplay, mode->vdisplay, mode->vrefresh, 1059 (mode->flags & DRM_MODE_FLAG_INTERLACE) ? 1 : 0); 1060 1061 if ((w >= 464 && w <= 720 && h >= 261 && h <= 576) || 1062 (w >= 1024 && w <= 1280 && h >= 576 && h <= 720) || 1063 (w >= 1664 && w <= 1920 && h >= 936 && h <= 1080)) 1064 return 0; 1065 1066 return -EINVAL; 1067 } 1068 1069 static const struct exynos_drm_crtc_ops mixer_crtc_ops = { 1070 .enable = mixer_enable, 1071 .disable = mixer_disable, 1072 .enable_vblank = mixer_enable_vblank, 1073 .disable_vblank = mixer_disable_vblank, 1074 .atomic_begin = mixer_atomic_begin, 1075 .update_plane = mixer_update_plane, 1076 .disable_plane = mixer_disable_plane, 1077 .atomic_flush = mixer_atomic_flush, 1078 .atomic_check = mixer_atomic_check, 1079 }; 1080 1081 static const struct mixer_drv_data exynos5420_mxr_drv_data = { 1082 .version = MXR_VER_128_0_0_184, 1083 .is_vp_enabled = 0, 1084 }; 1085 1086 static const struct mixer_drv_data exynos5250_mxr_drv_data = { 1087 .version = MXR_VER_16_0_33_0, 1088 .is_vp_enabled = 0, 1089 }; 1090 1091 static const struct mixer_drv_data exynos4212_mxr_drv_data = { 1092 .version = MXR_VER_0_0_0_16, 1093 .is_vp_enabled = 1, 1094 }; 1095 1096 static const struct mixer_drv_data exynos4210_mxr_drv_data = { 1097 .version = MXR_VER_0_0_0_16, 1098 .is_vp_enabled = 1, 1099 .has_sclk = 1, 1100 }; 1101 1102 static const struct of_device_id mixer_match_types[] = { 1103 { 1104 .compatible = "samsung,exynos4210-mixer", 1105 .data = &exynos4210_mxr_drv_data, 1106 }, { 1107 .compatible = "samsung,exynos4212-mixer", 1108 .data = &exynos4212_mxr_drv_data, 1109 }, { 1110 .compatible = "samsung,exynos5-mixer", 1111 .data = &exynos5250_mxr_drv_data, 1112 }, { 1113 .compatible = "samsung,exynos5250-mixer", 1114 .data = &exynos5250_mxr_drv_data, 1115 }, { 1116 .compatible = "samsung,exynos5420-mixer", 1117 .data = &exynos5420_mxr_drv_data, 1118 }, { 1119 /* end node */ 1120 } 1121 }; 1122 MODULE_DEVICE_TABLE(of, mixer_match_types); 1123 1124 static int mixer_bind(struct device *dev, struct device *manager, void *data) 1125 { 1126 struct mixer_context *ctx = dev_get_drvdata(dev); 1127 struct drm_device *drm_dev = data; 1128 struct exynos_drm_plane *exynos_plane; 1129 unsigned int i; 1130 int ret; 1131 1132 ret = mixer_initialize(ctx, drm_dev); 1133 if (ret) 1134 return ret; 1135 1136 for (i = 0; i < MIXER_WIN_NR; i++) { 1137 if (i == VP_DEFAULT_WIN && !test_bit(MXR_BIT_VP_ENABLED, 1138 &ctx->flags)) 1139 continue; 1140 1141 ret = exynos_plane_init(drm_dev, &ctx->planes[i], i, 1142 &plane_configs[i]); 1143 if (ret) 1144 return ret; 1145 } 1146 1147 exynos_plane = &ctx->planes[DEFAULT_WIN]; 1148 ctx->crtc = exynos_drm_crtc_create(drm_dev, &exynos_plane->base, 1149 EXYNOS_DISPLAY_TYPE_HDMI, &mixer_crtc_ops, ctx); 1150 if (IS_ERR(ctx->crtc)) { 1151 mixer_ctx_remove(ctx); 1152 ret = PTR_ERR(ctx->crtc); 1153 goto free_ctx; 1154 } 1155 1156 return 0; 1157 1158 free_ctx: 1159 devm_kfree(dev, ctx); 1160 return ret; 1161 } 1162 1163 static void mixer_unbind(struct device *dev, struct device *master, void *data) 1164 { 1165 struct mixer_context *ctx = dev_get_drvdata(dev); 1166 1167 mixer_ctx_remove(ctx); 1168 } 1169 1170 static const struct component_ops mixer_component_ops = { 1171 .bind = mixer_bind, 1172 .unbind = mixer_unbind, 1173 }; 1174 1175 static int mixer_probe(struct platform_device *pdev) 1176 { 1177 struct device *dev = &pdev->dev; 1178 const struct mixer_drv_data *drv; 1179 struct mixer_context *ctx; 1180 int ret; 1181 1182 ctx = devm_kzalloc(&pdev->dev, sizeof(*ctx), GFP_KERNEL); 1183 if (!ctx) { 1184 DRM_ERROR("failed to alloc mixer context.\n"); 1185 return -ENOMEM; 1186 } 1187 1188 drv = of_device_get_match_data(dev); 1189 1190 ctx->pdev = pdev; 1191 ctx->dev = dev; 1192 ctx->mxr_ver = drv->version; 1193 1194 if (drv->is_vp_enabled) 1195 __set_bit(MXR_BIT_VP_ENABLED, &ctx->flags); 1196 if (drv->has_sclk) 1197 __set_bit(MXR_BIT_HAS_SCLK, &ctx->flags); 1198 1199 platform_set_drvdata(pdev, ctx); 1200 1201 ret = component_add(&pdev->dev, &mixer_component_ops); 1202 if (!ret) 1203 pm_runtime_enable(dev); 1204 1205 return ret; 1206 } 1207 1208 static int mixer_remove(struct platform_device *pdev) 1209 { 1210 pm_runtime_disable(&pdev->dev); 1211 1212 component_del(&pdev->dev, &mixer_component_ops); 1213 1214 return 0; 1215 } 1216 1217 static int __maybe_unused exynos_mixer_suspend(struct device *dev) 1218 { 1219 struct mixer_context *ctx = dev_get_drvdata(dev); 1220 struct mixer_resources *res = &ctx->mixer_res; 1221 1222 clk_disable_unprepare(res->hdmi); 1223 clk_disable_unprepare(res->mixer); 1224 if (test_bit(MXR_BIT_VP_ENABLED, &ctx->flags)) { 1225 clk_disable_unprepare(res->vp); 1226 if (test_bit(MXR_BIT_HAS_SCLK, &ctx->flags)) 1227 clk_disable_unprepare(res->sclk_mixer); 1228 } 1229 1230 return 0; 1231 } 1232 1233 static int __maybe_unused exynos_mixer_resume(struct device *dev) 1234 { 1235 struct mixer_context *ctx = dev_get_drvdata(dev); 1236 struct mixer_resources *res = &ctx->mixer_res; 1237 int ret; 1238 1239 ret = clk_prepare_enable(res->mixer); 1240 if (ret < 0) { 1241 DRM_ERROR("Failed to prepare_enable the mixer clk [%d]\n", ret); 1242 return ret; 1243 } 1244 ret = clk_prepare_enable(res->hdmi); 1245 if (ret < 0) { 1246 DRM_ERROR("Failed to prepare_enable the hdmi clk [%d]\n", ret); 1247 return ret; 1248 } 1249 if (test_bit(MXR_BIT_VP_ENABLED, &ctx->flags)) { 1250 ret = clk_prepare_enable(res->vp); 1251 if (ret < 0) { 1252 DRM_ERROR("Failed to prepare_enable the vp clk [%d]\n", 1253 ret); 1254 return ret; 1255 } 1256 if (test_bit(MXR_BIT_HAS_SCLK, &ctx->flags)) { 1257 ret = clk_prepare_enable(res->sclk_mixer); 1258 if (ret < 0) { 1259 DRM_ERROR("Failed to prepare_enable the " \ 1260 "sclk_mixer clk [%d]\n", 1261 ret); 1262 return ret; 1263 } 1264 } 1265 } 1266 1267 return 0; 1268 } 1269 1270 static const struct dev_pm_ops exynos_mixer_pm_ops = { 1271 SET_RUNTIME_PM_OPS(exynos_mixer_suspend, exynos_mixer_resume, NULL) 1272 }; 1273 1274 struct platform_driver mixer_driver = { 1275 .driver = { 1276 .name = "exynos-mixer", 1277 .owner = THIS_MODULE, 1278 .pm = &exynos_mixer_pm_ops, 1279 .of_match_table = mixer_match_types, 1280 }, 1281 .probe = mixer_probe, 1282 .remove = mixer_remove, 1283 }; 1284