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