2 * Copyright (C) 2011 Samsung Electronics Co.Ltd
4 * Seung-Woo Kim <sw0312.kim@samsung.com>
5 * Inki Dae <inki.dae@samsung.com>
6 * Joonyoung Shim <jy0922.shim@samsung.com>
8 * Based on drivers/media/video/s5p-tv/hdmi_drv.c
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.
18 #include <drm/drm_edid.h>
19 #include <drm/drm_crtc_helper.h>
21 #include "regs-hdmi.h"
23 #include <linux/kernel.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>
36 #include <linux/of_address.h>
37 #include <linux/of_gpio.h>
38 #include <linux/hdmi.h>
39 #include <linux/component.h>
40 #include <linux/mfd/syscon.h>
41 #include <linux/regmap.h>
43 #include <drm/exynos_drm.h>
45 #include "exynos_drm_drv.h"
46 #include "exynos_drm_crtc.h"
47 #include "exynos_mixer.h"
49 #include <linux/gpio.h>
50 #include <media/s5p_hdmi.h>
52 #define get_hdmi_display(dev) platform_get_drvdata(to_platform_device(dev))
53 #define ctx_from_connector(c) container_of(c, struct hdmi_context, connector)
55 #define HOTPLUG_DEBOUNCE_MS 1100
57 /* AVI header and aspect ratio */
58 #define HDMI_AVI_VERSION 0x02
59 #define HDMI_AVI_LENGTH 0x0D
62 #define HDMI_AUI_VERSION 0x01
63 #define HDMI_AUI_LENGTH 0x0A
64 #define AVI_SAME_AS_PIC_ASPECT_RATIO 0x8
65 #define AVI_4_3_CENTER_RATIO 0x9
66 #define AVI_16_9_CENTER_RATIO 0xa
73 struct hdmi_driver_data {
75 const struct hdmiphy_config *phy_confs;
76 unsigned int phy_conf_count;
77 unsigned int is_apb_phy:1;
80 struct hdmi_resources {
82 struct clk *sclk_hdmi;
83 struct clk *sclk_pixel;
84 struct clk *sclk_hdmiphy;
85 struct clk *mout_hdmi;
86 struct regulator_bulk_data *regul_bulk;
87 struct regulator *reg_hdmi_en;
105 u8 vsync_top_hdmi[2];
106 u8 vsync_bot_hdmi[2];
107 u8 field_top_hdmi[2];
108 u8 field_bot_hdmi[2];
112 struct hdmi_v13_core_regs {
125 struct hdmi_v14_core_regs {
138 u8 v_sync_line_bef_2[2];
139 u8 v_sync_line_bef_1[2];
140 u8 v_sync_line_aft_2[2];
141 u8 v_sync_line_aft_1[2];
142 u8 v_sync_line_aft_pxl_2[2];
143 u8 v_sync_line_aft_pxl_1[2];
144 u8 v_blank_f2[2]; /* for 3D mode */
145 u8 v_blank_f3[2]; /* for 3D mode */
146 u8 v_blank_f4[2]; /* for 3D mode */
147 u8 v_blank_f5[2]; /* for 3D mode */
148 u8 v_sync_line_aft_3[2];
149 u8 v_sync_line_aft_4[2];
150 u8 v_sync_line_aft_5[2];
151 u8 v_sync_line_aft_6[2];
152 u8 v_sync_line_aft_pxl_3[2];
153 u8 v_sync_line_aft_pxl_4[2];
154 u8 v_sync_line_aft_pxl_5[2];
155 u8 v_sync_line_aft_pxl_6[2];
164 struct hdmi_v13_conf {
165 struct hdmi_v13_core_regs core;
166 struct hdmi_tg_regs tg;
169 struct hdmi_v14_conf {
170 struct hdmi_v14_core_regs core;
171 struct hdmi_tg_regs tg;
174 struct hdmi_conf_regs {
177 enum hdmi_picture_aspect aspect_ratio;
179 struct hdmi_v13_conf v13_conf;
180 struct hdmi_v14_conf v14_conf;
184 struct hdmi_context {
186 struct drm_device *drm_dev;
187 struct drm_connector connector;
188 struct drm_encoder *encoder;
192 struct mutex hdmi_mutex;
196 struct delayed_work hotplug_work;
198 struct i2c_adapter *ddc_adpt;
199 struct i2c_client *hdmiphy_port;
201 /* current hdmiphy conf regs */
202 struct drm_display_mode current_mode;
203 struct hdmi_conf_regs mode_conf;
205 struct hdmi_resources res;
208 void __iomem *regs_hdmiphy;
209 const struct hdmiphy_config *phy_confs;
210 unsigned int phy_conf_count;
212 struct regmap *pmureg;
216 struct hdmiphy_config {
221 /* list of phy config settings */
222 static const struct hdmiphy_config hdmiphy_v13_configs[] = {
224 .pixel_clock = 27000000,
226 0x01, 0x05, 0x00, 0xD8, 0x10, 0x1C, 0x30, 0x40,
227 0x6B, 0x10, 0x02, 0x51, 0xDF, 0xF2, 0x54, 0x87,
228 0x84, 0x00, 0x30, 0x38, 0x00, 0x08, 0x10, 0xE0,
229 0x22, 0x40, 0xE3, 0x26, 0x00, 0x00, 0x00, 0x00,
233 .pixel_clock = 27027000,
235 0x01, 0x05, 0x00, 0xD4, 0x10, 0x9C, 0x09, 0x64,
236 0x6B, 0x10, 0x02, 0x51, 0xDF, 0xF2, 0x54, 0x87,
237 0x84, 0x00, 0x30, 0x38, 0x00, 0x08, 0x10, 0xE0,
238 0x22, 0x40, 0xE3, 0x26, 0x00, 0x00, 0x00, 0x00,
242 .pixel_clock = 74176000,
244 0x01, 0x05, 0x00, 0xD8, 0x10, 0x9C, 0xef, 0x5B,
245 0x6D, 0x10, 0x01, 0x51, 0xef, 0xF3, 0x54, 0xb9,
246 0x84, 0x00, 0x30, 0x38, 0x00, 0x08, 0x10, 0xE0,
247 0x22, 0x40, 0xa5, 0x26, 0x01, 0x00, 0x00, 0x00,
251 .pixel_clock = 74250000,
253 0x01, 0x05, 0x00, 0xd8, 0x10, 0x9c, 0xf8, 0x40,
254 0x6a, 0x10, 0x01, 0x51, 0xff, 0xf1, 0x54, 0xba,
255 0x84, 0x00, 0x10, 0x38, 0x00, 0x08, 0x10, 0xe0,
256 0x22, 0x40, 0xa4, 0x26, 0x01, 0x00, 0x00, 0x00,
260 .pixel_clock = 148500000,
262 0x01, 0x05, 0x00, 0xD8, 0x10, 0x9C, 0xf8, 0x40,
263 0x6A, 0x18, 0x00, 0x51, 0xff, 0xF1, 0x54, 0xba,
264 0x84, 0x00, 0x10, 0x38, 0x00, 0x08, 0x10, 0xE0,
265 0x22, 0x40, 0xa4, 0x26, 0x02, 0x00, 0x00, 0x00,
270 static const struct hdmiphy_config hdmiphy_v14_configs[] = {
272 .pixel_clock = 25200000,
274 0x01, 0x51, 0x2A, 0x75, 0x40, 0x01, 0x00, 0x08,
275 0x82, 0x80, 0xfc, 0xd8, 0x45, 0xa0, 0xac, 0x80,
276 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
277 0x54, 0xf4, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
281 .pixel_clock = 27000000,
283 0x01, 0xd1, 0x22, 0x51, 0x40, 0x08, 0xfc, 0x20,
284 0x98, 0xa0, 0xcb, 0xd8, 0x45, 0xa0, 0xac, 0x80,
285 0x06, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
286 0x54, 0xe4, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
290 .pixel_clock = 27027000,
292 0x01, 0xd1, 0x2d, 0x72, 0x40, 0x64, 0x12, 0x08,
293 0x43, 0xa0, 0x0e, 0xd9, 0x45, 0xa0, 0xac, 0x80,
294 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
295 0x54, 0xe3, 0x24, 0x00, 0x00, 0x00, 0x01, 0x00,
299 .pixel_clock = 36000000,
301 0x01, 0x51, 0x2d, 0x55, 0x40, 0x01, 0x00, 0x08,
302 0x82, 0x80, 0x0e, 0xd9, 0x45, 0xa0, 0xac, 0x80,
303 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
304 0x54, 0xab, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
308 .pixel_clock = 40000000,
310 0x01, 0x51, 0x32, 0x55, 0x40, 0x01, 0x00, 0x08,
311 0x82, 0x80, 0x2c, 0xd9, 0x45, 0xa0, 0xac, 0x80,
312 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
313 0x54, 0x9a, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
317 .pixel_clock = 65000000,
319 0x01, 0xd1, 0x36, 0x34, 0x40, 0x1e, 0x0a, 0x08,
320 0x82, 0xa0, 0x45, 0xd9, 0x45, 0xa0, 0xac, 0x80,
321 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
322 0x54, 0xbd, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
326 .pixel_clock = 71000000,
328 0x01, 0xd1, 0x3b, 0x35, 0x40, 0x0c, 0x04, 0x08,
329 0x85, 0xa0, 0x63, 0xd9, 0x45, 0xa0, 0xac, 0x80,
330 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
331 0x54, 0xad, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
335 .pixel_clock = 73250000,
337 0x01, 0xd1, 0x3d, 0x35, 0x40, 0x18, 0x02, 0x08,
338 0x83, 0xa0, 0x6e, 0xd9, 0x45, 0xa0, 0xac, 0x80,
339 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
340 0x54, 0xa8, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
344 .pixel_clock = 74176000,
346 0x01, 0xd1, 0x3e, 0x35, 0x40, 0x5b, 0xde, 0x08,
347 0x82, 0xa0, 0x73, 0xd9, 0x45, 0xa0, 0xac, 0x80,
348 0x56, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
349 0x54, 0xa6, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
353 .pixel_clock = 74250000,
355 0x01, 0xd1, 0x1f, 0x10, 0x40, 0x40, 0xf8, 0x08,
356 0x81, 0xa0, 0xba, 0xd8, 0x45, 0xa0, 0xac, 0x80,
357 0x3c, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
358 0x54, 0xa5, 0x24, 0x01, 0x00, 0x00, 0x01, 0x00,
362 .pixel_clock = 83500000,
364 0x01, 0xd1, 0x23, 0x11, 0x40, 0x0c, 0xfb, 0x08,
365 0x85, 0xa0, 0xd1, 0xd8, 0x45, 0xa0, 0xac, 0x80,
366 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
367 0x54, 0x93, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
371 .pixel_clock = 106500000,
373 0x01, 0xd1, 0x2c, 0x12, 0x40, 0x0c, 0x09, 0x08,
374 0x84, 0xa0, 0x0a, 0xd9, 0x45, 0xa0, 0xac, 0x80,
375 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
376 0x54, 0x73, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
380 .pixel_clock = 108000000,
382 0x01, 0x51, 0x2d, 0x15, 0x40, 0x01, 0x00, 0x08,
383 0x82, 0x80, 0x0e, 0xd9, 0x45, 0xa0, 0xac, 0x80,
384 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
385 0x54, 0xc7, 0x25, 0x03, 0x00, 0x00, 0x01, 0x80,
389 .pixel_clock = 115500000,
391 0x01, 0xd1, 0x30, 0x12, 0x40, 0x40, 0x10, 0x08,
392 0x80, 0x80, 0x21, 0xd9, 0x45, 0xa0, 0xac, 0x80,
393 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
394 0x54, 0xaa, 0x25, 0x03, 0x00, 0x00, 0x01, 0x80,
398 .pixel_clock = 119000000,
400 0x01, 0xd1, 0x32, 0x1a, 0x40, 0x30, 0xd8, 0x08,
401 0x04, 0xa0, 0x2a, 0xd9, 0x45, 0xa0, 0xac, 0x80,
402 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
403 0x54, 0x9d, 0x25, 0x03, 0x00, 0x00, 0x01, 0x80,
407 .pixel_clock = 146250000,
409 0x01, 0xd1, 0x3d, 0x15, 0x40, 0x18, 0xfd, 0x08,
410 0x83, 0xa0, 0x6e, 0xd9, 0x45, 0xa0, 0xac, 0x80,
411 0x08, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
412 0x54, 0x50, 0x25, 0x03, 0x00, 0x00, 0x01, 0x80,
416 .pixel_clock = 148500000,
418 0x01, 0xd1, 0x1f, 0x00, 0x40, 0x40, 0xf8, 0x08,
419 0x81, 0xa0, 0xba, 0xd8, 0x45, 0xa0, 0xac, 0x80,
420 0x3c, 0x80, 0x11, 0x04, 0x02, 0x22, 0x44, 0x86,
421 0x54, 0x4b, 0x25, 0x03, 0x00, 0x00, 0x01, 0x00,
426 static const struct hdmiphy_config hdmiphy_5420_configs[] = {
428 .pixel_clock = 25200000,
430 0x01, 0x52, 0x3F, 0x55, 0x40, 0x01, 0x00, 0xC8,
431 0x82, 0xC8, 0xBD, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
432 0x06, 0x80, 0x01, 0x84, 0x05, 0x02, 0x24, 0x66,
433 0x54, 0xF4, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
437 .pixel_clock = 27000000,
439 0x01, 0xD1, 0x22, 0x51, 0x40, 0x08, 0xFC, 0xE0,
440 0x98, 0xE8, 0xCB, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
441 0x06, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
442 0x54, 0xE4, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
446 .pixel_clock = 27027000,
448 0x01, 0xD1, 0x2D, 0x72, 0x40, 0x64, 0x12, 0xC8,
449 0x43, 0xE8, 0x0E, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
450 0x26, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
451 0x54, 0xE3, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
455 .pixel_clock = 36000000,
457 0x01, 0x51, 0x2D, 0x55, 0x40, 0x40, 0x00, 0xC8,
458 0x02, 0xC8, 0x0E, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
459 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
460 0x54, 0xAB, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
464 .pixel_clock = 40000000,
466 0x01, 0xD1, 0x21, 0x31, 0x40, 0x3C, 0x28, 0xC8,
467 0x87, 0xE8, 0xC8, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
468 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
469 0x54, 0x9A, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
473 .pixel_clock = 65000000,
475 0x01, 0xD1, 0x36, 0x34, 0x40, 0x0C, 0x04, 0xC8,
476 0x82, 0xE8, 0x45, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
477 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
478 0x54, 0xBD, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
482 .pixel_clock = 71000000,
484 0x01, 0xD1, 0x3B, 0x35, 0x40, 0x0C, 0x04, 0xC8,
485 0x85, 0xE8, 0x63, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
486 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
487 0x54, 0x57, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
491 .pixel_clock = 73250000,
493 0x01, 0xD1, 0x1F, 0x10, 0x40, 0x78, 0x8D, 0xC8,
494 0x81, 0xE8, 0xB7, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
495 0x56, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
496 0x54, 0xA8, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
500 .pixel_clock = 74176000,
502 0x01, 0xD1, 0x1F, 0x10, 0x40, 0x5B, 0xEF, 0xC8,
503 0x81, 0xE8, 0xB9, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
504 0x56, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
505 0x54, 0xA6, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
509 .pixel_clock = 74250000,
511 0x01, 0xD1, 0x1F, 0x10, 0x40, 0x40, 0xF8, 0x08,
512 0x81, 0xE8, 0xBA, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
513 0x26, 0x80, 0x09, 0x84, 0x05, 0x22, 0x24, 0x66,
514 0x54, 0xA5, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
518 .pixel_clock = 83500000,
520 0x01, 0xD1, 0x23, 0x11, 0x40, 0x0C, 0xFB, 0xC8,
521 0x85, 0xE8, 0xD1, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
522 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
523 0x54, 0x4A, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
527 .pixel_clock = 88750000,
529 0x01, 0xD1, 0x25, 0x11, 0x40, 0x18, 0xFF, 0xC8,
530 0x83, 0xE8, 0xDE, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
531 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
532 0x54, 0x45, 0x24, 0x00, 0x00, 0x00, 0x01, 0x80,
536 .pixel_clock = 106500000,
538 0x01, 0xD1, 0x2C, 0x12, 0x40, 0x0C, 0x09, 0xC8,
539 0x84, 0xE8, 0x0A, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
540 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
541 0x54, 0x73, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
545 .pixel_clock = 108000000,
547 0x01, 0x51, 0x2D, 0x15, 0x40, 0x01, 0x00, 0xC8,
548 0x82, 0xC8, 0x0E, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
549 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
550 0x54, 0xC7, 0x25, 0x03, 0x00, 0x00, 0x01, 0x80,
554 .pixel_clock = 115500000,
556 0x01, 0xD1, 0x30, 0x14, 0x40, 0x0C, 0x03, 0xC8,
557 0x88, 0xE8, 0x21, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
558 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
559 0x54, 0x6A, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
563 .pixel_clock = 146250000,
565 0x01, 0xD1, 0x3D, 0x15, 0x40, 0x18, 0xFD, 0xC8,
566 0x83, 0xE8, 0x6E, 0xD9, 0x45, 0xA0, 0xAC, 0x80,
567 0x08, 0x80, 0x09, 0x84, 0x05, 0x02, 0x24, 0x66,
568 0x54, 0x54, 0x24, 0x01, 0x00, 0x00, 0x01, 0x80,
572 .pixel_clock = 148500000,
574 0x01, 0xD1, 0x1F, 0x00, 0x40, 0x40, 0xF8, 0x08,
575 0x81, 0xE8, 0xBA, 0xD8, 0x45, 0xA0, 0xAC, 0x80,
576 0x26, 0x80, 0x09, 0x84, 0x05, 0x22, 0x24, 0x66,
577 0x54, 0x4B, 0x25, 0x03, 0x00, 0x80, 0x01, 0x80,
582 static struct hdmi_driver_data exynos5420_hdmi_driver_data = {
584 .phy_confs = hdmiphy_5420_configs,
585 .phy_conf_count = ARRAY_SIZE(hdmiphy_5420_configs),
589 static struct hdmi_driver_data exynos4212_hdmi_driver_data = {
591 .phy_confs = hdmiphy_v14_configs,
592 .phy_conf_count = ARRAY_SIZE(hdmiphy_v14_configs),
596 static struct hdmi_driver_data exynos4210_hdmi_driver_data = {
598 .phy_confs = hdmiphy_v13_configs,
599 .phy_conf_count = ARRAY_SIZE(hdmiphy_v13_configs),
603 static struct hdmi_driver_data exynos5_hdmi_driver_data = {
605 .phy_confs = hdmiphy_v13_configs,
606 .phy_conf_count = ARRAY_SIZE(hdmiphy_v13_configs),
610 static inline u32 hdmi_reg_read(struct hdmi_context *hdata, u32 reg_id)
612 return readl(hdata->regs + reg_id);
615 static inline void hdmi_reg_writeb(struct hdmi_context *hdata,
616 u32 reg_id, u8 value)
618 writeb(value, hdata->regs + reg_id);
621 static inline void hdmi_reg_writemask(struct hdmi_context *hdata,
622 u32 reg_id, u32 value, u32 mask)
624 u32 old = readl(hdata->regs + reg_id);
625 value = (value & mask) | (old & ~mask);
626 writel(value, hdata->regs + reg_id);
629 static int hdmiphy_reg_writeb(struct hdmi_context *hdata,
630 u32 reg_offset, u8 value)
632 if (hdata->hdmiphy_port) {
636 buffer[0] = reg_offset;
639 ret = i2c_master_send(hdata->hdmiphy_port, buffer, 2);
644 writeb(value, hdata->regs_hdmiphy + (reg_offset<<2));
649 static int hdmiphy_reg_write_buf(struct hdmi_context *hdata,
650 u32 reg_offset, const u8 *buf, u32 len)
652 if ((reg_offset + len) > 32)
655 if (hdata->hdmiphy_port) {
658 ret = i2c_master_send(hdata->hdmiphy_port, buf, len);
664 for (i = 0; i < len; i++)
665 writeb(buf[i], hdata->regs_hdmiphy +
666 ((reg_offset + i)<<2));
671 static void hdmi_v13_regs_dump(struct hdmi_context *hdata, char *prefix)
673 #define DUMPREG(reg_id) \
674 DRM_DEBUG_KMS("%s:" #reg_id " = %08x\n", prefix, \
675 readl(hdata->regs + reg_id))
676 DRM_DEBUG_KMS("%s: ---- CONTROL REGISTERS ----\n", prefix);
677 DUMPREG(HDMI_INTC_FLAG);
678 DUMPREG(HDMI_INTC_CON);
679 DUMPREG(HDMI_HPD_STATUS);
680 DUMPREG(HDMI_V13_PHY_RSTOUT);
681 DUMPREG(HDMI_V13_PHY_VPLL);
682 DUMPREG(HDMI_V13_PHY_CMU);
683 DUMPREG(HDMI_V13_CORE_RSTOUT);
685 DRM_DEBUG_KMS("%s: ---- CORE REGISTERS ----\n", prefix);
689 DUMPREG(HDMI_SYS_STATUS);
690 DUMPREG(HDMI_V13_PHY_STATUS);
691 DUMPREG(HDMI_STATUS_EN);
693 DUMPREG(HDMI_MODE_SEL);
694 DUMPREG(HDMI_V13_HPD_GEN);
695 DUMPREG(HDMI_V13_DC_CONTROL);
696 DUMPREG(HDMI_V13_VIDEO_PATTERN_GEN);
698 DRM_DEBUG_KMS("%s: ---- CORE SYNC REGISTERS ----\n", prefix);
699 DUMPREG(HDMI_H_BLANK_0);
700 DUMPREG(HDMI_H_BLANK_1);
701 DUMPREG(HDMI_V13_V_BLANK_0);
702 DUMPREG(HDMI_V13_V_BLANK_1);
703 DUMPREG(HDMI_V13_V_BLANK_2);
704 DUMPREG(HDMI_V13_H_V_LINE_0);
705 DUMPREG(HDMI_V13_H_V_LINE_1);
706 DUMPREG(HDMI_V13_H_V_LINE_2);
707 DUMPREG(HDMI_VSYNC_POL);
708 DUMPREG(HDMI_INT_PRO_MODE);
709 DUMPREG(HDMI_V13_V_BLANK_F_0);
710 DUMPREG(HDMI_V13_V_BLANK_F_1);
711 DUMPREG(HDMI_V13_V_BLANK_F_2);
712 DUMPREG(HDMI_V13_H_SYNC_GEN_0);
713 DUMPREG(HDMI_V13_H_SYNC_GEN_1);
714 DUMPREG(HDMI_V13_H_SYNC_GEN_2);
715 DUMPREG(HDMI_V13_V_SYNC_GEN_1_0);
716 DUMPREG(HDMI_V13_V_SYNC_GEN_1_1);
717 DUMPREG(HDMI_V13_V_SYNC_GEN_1_2);
718 DUMPREG(HDMI_V13_V_SYNC_GEN_2_0);
719 DUMPREG(HDMI_V13_V_SYNC_GEN_2_1);
720 DUMPREG(HDMI_V13_V_SYNC_GEN_2_2);
721 DUMPREG(HDMI_V13_V_SYNC_GEN_3_0);
722 DUMPREG(HDMI_V13_V_SYNC_GEN_3_1);
723 DUMPREG(HDMI_V13_V_SYNC_GEN_3_2);
725 DRM_DEBUG_KMS("%s: ---- TG REGISTERS ----\n", prefix);
726 DUMPREG(HDMI_TG_CMD);
727 DUMPREG(HDMI_TG_H_FSZ_L);
728 DUMPREG(HDMI_TG_H_FSZ_H);
729 DUMPREG(HDMI_TG_HACT_ST_L);
730 DUMPREG(HDMI_TG_HACT_ST_H);
731 DUMPREG(HDMI_TG_HACT_SZ_L);
732 DUMPREG(HDMI_TG_HACT_SZ_H);
733 DUMPREG(HDMI_TG_V_FSZ_L);
734 DUMPREG(HDMI_TG_V_FSZ_H);
735 DUMPREG(HDMI_TG_VSYNC_L);
736 DUMPREG(HDMI_TG_VSYNC_H);
737 DUMPREG(HDMI_TG_VSYNC2_L);
738 DUMPREG(HDMI_TG_VSYNC2_H);
739 DUMPREG(HDMI_TG_VACT_ST_L);
740 DUMPREG(HDMI_TG_VACT_ST_H);
741 DUMPREG(HDMI_TG_VACT_SZ_L);
742 DUMPREG(HDMI_TG_VACT_SZ_H);
743 DUMPREG(HDMI_TG_FIELD_CHG_L);
744 DUMPREG(HDMI_TG_FIELD_CHG_H);
745 DUMPREG(HDMI_TG_VACT_ST2_L);
746 DUMPREG(HDMI_TG_VACT_ST2_H);
747 DUMPREG(HDMI_TG_VSYNC_TOP_HDMI_L);
748 DUMPREG(HDMI_TG_VSYNC_TOP_HDMI_H);
749 DUMPREG(HDMI_TG_VSYNC_BOT_HDMI_L);
750 DUMPREG(HDMI_TG_VSYNC_BOT_HDMI_H);
751 DUMPREG(HDMI_TG_FIELD_TOP_HDMI_L);
752 DUMPREG(HDMI_TG_FIELD_TOP_HDMI_H);
753 DUMPREG(HDMI_TG_FIELD_BOT_HDMI_L);
754 DUMPREG(HDMI_TG_FIELD_BOT_HDMI_H);
758 static void hdmi_v14_regs_dump(struct hdmi_context *hdata, char *prefix)
762 #define DUMPREG(reg_id) \
763 DRM_DEBUG_KMS("%s:" #reg_id " = %08x\n", prefix, \
764 readl(hdata->regs + reg_id))
766 DRM_DEBUG_KMS("%s: ---- CONTROL REGISTERS ----\n", prefix);
767 DUMPREG(HDMI_INTC_CON);
768 DUMPREG(HDMI_INTC_FLAG);
769 DUMPREG(HDMI_HPD_STATUS);
770 DUMPREG(HDMI_INTC_CON_1);
771 DUMPREG(HDMI_INTC_FLAG_1);
772 DUMPREG(HDMI_PHY_STATUS_0);
773 DUMPREG(HDMI_PHY_STATUS_PLL);
774 DUMPREG(HDMI_PHY_CON_0);
775 DUMPREG(HDMI_PHY_RSTOUT);
776 DUMPREG(HDMI_PHY_VPLL);
777 DUMPREG(HDMI_PHY_CMU);
778 DUMPREG(HDMI_CORE_RSTOUT);
780 DRM_DEBUG_KMS("%s: ---- CORE REGISTERS ----\n", prefix);
784 DUMPREG(HDMI_SYS_STATUS);
785 DUMPREG(HDMI_PHY_STATUS_0);
786 DUMPREG(HDMI_STATUS_EN);
788 DUMPREG(HDMI_MODE_SEL);
789 DUMPREG(HDMI_ENC_EN);
790 DUMPREG(HDMI_DC_CONTROL);
791 DUMPREG(HDMI_VIDEO_PATTERN_GEN);
793 DRM_DEBUG_KMS("%s: ---- CORE SYNC REGISTERS ----\n", prefix);
794 DUMPREG(HDMI_H_BLANK_0);
795 DUMPREG(HDMI_H_BLANK_1);
796 DUMPREG(HDMI_V2_BLANK_0);
797 DUMPREG(HDMI_V2_BLANK_1);
798 DUMPREG(HDMI_V1_BLANK_0);
799 DUMPREG(HDMI_V1_BLANK_1);
800 DUMPREG(HDMI_V_LINE_0);
801 DUMPREG(HDMI_V_LINE_1);
802 DUMPREG(HDMI_H_LINE_0);
803 DUMPREG(HDMI_H_LINE_1);
804 DUMPREG(HDMI_HSYNC_POL);
806 DUMPREG(HDMI_VSYNC_POL);
807 DUMPREG(HDMI_INT_PRO_MODE);
808 DUMPREG(HDMI_V_BLANK_F0_0);
809 DUMPREG(HDMI_V_BLANK_F0_1);
810 DUMPREG(HDMI_V_BLANK_F1_0);
811 DUMPREG(HDMI_V_BLANK_F1_1);
813 DUMPREG(HDMI_H_SYNC_START_0);
814 DUMPREG(HDMI_H_SYNC_START_1);
815 DUMPREG(HDMI_H_SYNC_END_0);
816 DUMPREG(HDMI_H_SYNC_END_1);
818 DUMPREG(HDMI_V_SYNC_LINE_BEF_2_0);
819 DUMPREG(HDMI_V_SYNC_LINE_BEF_2_1);
820 DUMPREG(HDMI_V_SYNC_LINE_BEF_1_0);
821 DUMPREG(HDMI_V_SYNC_LINE_BEF_1_1);
823 DUMPREG(HDMI_V_SYNC_LINE_AFT_2_0);
824 DUMPREG(HDMI_V_SYNC_LINE_AFT_2_1);
825 DUMPREG(HDMI_V_SYNC_LINE_AFT_1_0);
826 DUMPREG(HDMI_V_SYNC_LINE_AFT_1_1);
828 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_2_0);
829 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_2_1);
830 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_1_0);
831 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_1_1);
833 DUMPREG(HDMI_V_BLANK_F2_0);
834 DUMPREG(HDMI_V_BLANK_F2_1);
835 DUMPREG(HDMI_V_BLANK_F3_0);
836 DUMPREG(HDMI_V_BLANK_F3_1);
837 DUMPREG(HDMI_V_BLANK_F4_0);
838 DUMPREG(HDMI_V_BLANK_F4_1);
839 DUMPREG(HDMI_V_BLANK_F5_0);
840 DUMPREG(HDMI_V_BLANK_F5_1);
842 DUMPREG(HDMI_V_SYNC_LINE_AFT_3_0);
843 DUMPREG(HDMI_V_SYNC_LINE_AFT_3_1);
844 DUMPREG(HDMI_V_SYNC_LINE_AFT_4_0);
845 DUMPREG(HDMI_V_SYNC_LINE_AFT_4_1);
846 DUMPREG(HDMI_V_SYNC_LINE_AFT_5_0);
847 DUMPREG(HDMI_V_SYNC_LINE_AFT_5_1);
848 DUMPREG(HDMI_V_SYNC_LINE_AFT_6_0);
849 DUMPREG(HDMI_V_SYNC_LINE_AFT_6_1);
851 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_3_0);
852 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_3_1);
853 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_4_0);
854 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_4_1);
855 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_5_0);
856 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_5_1);
857 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_6_0);
858 DUMPREG(HDMI_V_SYNC_LINE_AFT_PXL_6_1);
860 DUMPREG(HDMI_VACT_SPACE_1_0);
861 DUMPREG(HDMI_VACT_SPACE_1_1);
862 DUMPREG(HDMI_VACT_SPACE_2_0);
863 DUMPREG(HDMI_VACT_SPACE_2_1);
864 DUMPREG(HDMI_VACT_SPACE_3_0);
865 DUMPREG(HDMI_VACT_SPACE_3_1);
866 DUMPREG(HDMI_VACT_SPACE_4_0);
867 DUMPREG(HDMI_VACT_SPACE_4_1);
868 DUMPREG(HDMI_VACT_SPACE_5_0);
869 DUMPREG(HDMI_VACT_SPACE_5_1);
870 DUMPREG(HDMI_VACT_SPACE_6_0);
871 DUMPREG(HDMI_VACT_SPACE_6_1);
873 DRM_DEBUG_KMS("%s: ---- TG REGISTERS ----\n", prefix);
874 DUMPREG(HDMI_TG_CMD);
875 DUMPREG(HDMI_TG_H_FSZ_L);
876 DUMPREG(HDMI_TG_H_FSZ_H);
877 DUMPREG(HDMI_TG_HACT_ST_L);
878 DUMPREG(HDMI_TG_HACT_ST_H);
879 DUMPREG(HDMI_TG_HACT_SZ_L);
880 DUMPREG(HDMI_TG_HACT_SZ_H);
881 DUMPREG(HDMI_TG_V_FSZ_L);
882 DUMPREG(HDMI_TG_V_FSZ_H);
883 DUMPREG(HDMI_TG_VSYNC_L);
884 DUMPREG(HDMI_TG_VSYNC_H);
885 DUMPREG(HDMI_TG_VSYNC2_L);
886 DUMPREG(HDMI_TG_VSYNC2_H);
887 DUMPREG(HDMI_TG_VACT_ST_L);
888 DUMPREG(HDMI_TG_VACT_ST_H);
889 DUMPREG(HDMI_TG_VACT_SZ_L);
890 DUMPREG(HDMI_TG_VACT_SZ_H);
891 DUMPREG(HDMI_TG_FIELD_CHG_L);
892 DUMPREG(HDMI_TG_FIELD_CHG_H);
893 DUMPREG(HDMI_TG_VACT_ST2_L);
894 DUMPREG(HDMI_TG_VACT_ST2_H);
895 DUMPREG(HDMI_TG_VACT_ST3_L);
896 DUMPREG(HDMI_TG_VACT_ST3_H);
897 DUMPREG(HDMI_TG_VACT_ST4_L);
898 DUMPREG(HDMI_TG_VACT_ST4_H);
899 DUMPREG(HDMI_TG_VSYNC_TOP_HDMI_L);
900 DUMPREG(HDMI_TG_VSYNC_TOP_HDMI_H);
901 DUMPREG(HDMI_TG_VSYNC_BOT_HDMI_L);
902 DUMPREG(HDMI_TG_VSYNC_BOT_HDMI_H);
903 DUMPREG(HDMI_TG_FIELD_TOP_HDMI_L);
904 DUMPREG(HDMI_TG_FIELD_TOP_HDMI_H);
905 DUMPREG(HDMI_TG_FIELD_BOT_HDMI_L);
906 DUMPREG(HDMI_TG_FIELD_BOT_HDMI_H);
909 DRM_DEBUG_KMS("%s: ---- PACKET REGISTERS ----\n", prefix);
910 DUMPREG(HDMI_AVI_CON);
911 DUMPREG(HDMI_AVI_HEADER0);
912 DUMPREG(HDMI_AVI_HEADER1);
913 DUMPREG(HDMI_AVI_HEADER2);
914 DUMPREG(HDMI_AVI_CHECK_SUM);
915 DUMPREG(HDMI_VSI_CON);
916 DUMPREG(HDMI_VSI_HEADER0);
917 DUMPREG(HDMI_VSI_HEADER1);
918 DUMPREG(HDMI_VSI_HEADER2);
919 for (i = 0; i < 7; ++i)
920 DUMPREG(HDMI_VSI_DATA(i));
925 static void hdmi_regs_dump(struct hdmi_context *hdata, char *prefix)
927 if (hdata->type == HDMI_TYPE13)
928 hdmi_v13_regs_dump(hdata, prefix);
930 hdmi_v14_regs_dump(hdata, prefix);
933 static u8 hdmi_chksum(struct hdmi_context *hdata,
934 u32 start, u8 len, u32 hdr_sum)
938 /* hdr_sum : header0 + header1 + header2
939 * start : start address of packet byte1
940 * len : packet bytes - 1 */
941 for (i = 0; i < len; ++i)
942 hdr_sum += 0xff & hdmi_reg_read(hdata, start + i * 4);
944 /* return 2's complement of 8 bit hdr_sum */
945 return (u8)(~(hdr_sum & 0xff) + 1);
948 static void hdmi_reg_infoframe(struct hdmi_context *hdata,
949 union hdmi_infoframe *infoframe)
956 mod = hdmi_reg_read(hdata, HDMI_MODE_SEL);
957 if (hdata->dvi_mode) {
958 hdmi_reg_writeb(hdata, HDMI_VSI_CON,
959 HDMI_VSI_CON_DO_NOT_TRANSMIT);
960 hdmi_reg_writeb(hdata, HDMI_AVI_CON,
961 HDMI_AVI_CON_DO_NOT_TRANSMIT);
962 hdmi_reg_writeb(hdata, HDMI_AUI_CON, HDMI_AUI_CON_NO_TRAN);
966 switch (infoframe->any.type) {
967 case HDMI_INFOFRAME_TYPE_AVI:
968 hdmi_reg_writeb(hdata, HDMI_AVI_CON, HDMI_AVI_CON_EVERY_VSYNC);
969 hdmi_reg_writeb(hdata, HDMI_AVI_HEADER0, infoframe->any.type);
970 hdmi_reg_writeb(hdata, HDMI_AVI_HEADER1,
971 infoframe->any.version);
972 hdmi_reg_writeb(hdata, HDMI_AVI_HEADER2, infoframe->any.length);
973 hdr_sum = infoframe->any.type + infoframe->any.version +
974 infoframe->any.length;
976 /* Output format zero hardcoded ,RGB YBCR selection */
977 hdmi_reg_writeb(hdata, HDMI_AVI_BYTE(1), 0 << 5 |
978 AVI_ACTIVE_FORMAT_VALID |
979 AVI_UNDERSCANNED_DISPLAY_VALID);
982 * Set the aspect ratio as per the mode, mentioned in
983 * Table 9 AVI InfoFrame Data Byte 2 of CEA-861-D Standard
985 switch (hdata->mode_conf.aspect_ratio) {
986 case HDMI_PICTURE_ASPECT_4_3:
987 hdmi_reg_writeb(hdata, HDMI_AVI_BYTE(2),
988 hdata->mode_conf.aspect_ratio |
989 AVI_4_3_CENTER_RATIO);
991 case HDMI_PICTURE_ASPECT_16_9:
992 hdmi_reg_writeb(hdata, HDMI_AVI_BYTE(2),
993 hdata->mode_conf.aspect_ratio |
994 AVI_16_9_CENTER_RATIO);
996 case HDMI_PICTURE_ASPECT_NONE:
998 hdmi_reg_writeb(hdata, HDMI_AVI_BYTE(2),
999 hdata->mode_conf.aspect_ratio |
1000 AVI_SAME_AS_PIC_ASPECT_RATIO);
1004 vic = hdata->mode_conf.cea_video_id;
1005 hdmi_reg_writeb(hdata, HDMI_AVI_BYTE(4), vic);
1007 chksum = hdmi_chksum(hdata, HDMI_AVI_BYTE(1),
1008 infoframe->any.length, hdr_sum);
1009 DRM_DEBUG_KMS("AVI checksum = 0x%x\n", chksum);
1010 hdmi_reg_writeb(hdata, HDMI_AVI_CHECK_SUM, chksum);
1012 case HDMI_INFOFRAME_TYPE_AUDIO:
1013 hdmi_reg_writeb(hdata, HDMI_AUI_CON, 0x02);
1014 hdmi_reg_writeb(hdata, HDMI_AUI_HEADER0, infoframe->any.type);
1015 hdmi_reg_writeb(hdata, HDMI_AUI_HEADER1,
1016 infoframe->any.version);
1017 hdmi_reg_writeb(hdata, HDMI_AUI_HEADER2, infoframe->any.length);
1018 hdr_sum = infoframe->any.type + infoframe->any.version +
1019 infoframe->any.length;
1020 chksum = hdmi_chksum(hdata, HDMI_AUI_BYTE(1),
1021 infoframe->any.length, hdr_sum);
1022 DRM_DEBUG_KMS("AUI checksum = 0x%x\n", chksum);
1023 hdmi_reg_writeb(hdata, HDMI_AUI_CHECK_SUM, chksum);
1030 static enum drm_connector_status hdmi_detect(struct drm_connector *connector,
1033 struct hdmi_context *hdata = ctx_from_connector(connector);
1035 hdata->hpd = gpio_get_value(hdata->hpd_gpio);
1037 return hdata->hpd ? connector_status_connected :
1038 connector_status_disconnected;
1041 static void hdmi_connector_destroy(struct drm_connector *connector)
1045 static struct drm_connector_funcs hdmi_connector_funcs = {
1046 .dpms = drm_helper_connector_dpms,
1047 .fill_modes = drm_helper_probe_single_connector_modes,
1048 .detect = hdmi_detect,
1049 .destroy = hdmi_connector_destroy,
1052 static int hdmi_get_modes(struct drm_connector *connector)
1054 struct hdmi_context *hdata = ctx_from_connector(connector);
1057 if (!hdata->ddc_adpt)
1060 edid = drm_get_edid(connector, hdata->ddc_adpt);
1064 hdata->dvi_mode = !drm_detect_hdmi_monitor(edid);
1065 DRM_DEBUG_KMS("%s : width[%d] x height[%d]\n",
1066 (hdata->dvi_mode ? "dvi monitor" : "hdmi monitor"),
1067 edid->width_cm, edid->height_cm);
1069 drm_mode_connector_update_edid_property(connector, edid);
1071 return drm_add_edid_modes(connector, edid);
1074 static int hdmi_find_phy_conf(struct hdmi_context *hdata, u32 pixel_clock)
1078 for (i = 0; i < hdata->phy_conf_count; i++)
1079 if (hdata->phy_confs[i].pixel_clock == pixel_clock)
1082 DRM_DEBUG_KMS("Could not find phy config for %d\n", pixel_clock);
1086 static int hdmi_mode_valid(struct drm_connector *connector,
1087 struct drm_display_mode *mode)
1089 struct hdmi_context *hdata = ctx_from_connector(connector);
1092 DRM_DEBUG_KMS("xres=%d, yres=%d, refresh=%d, intl=%d clock=%d\n",
1093 mode->hdisplay, mode->vdisplay, mode->vrefresh,
1094 (mode->flags & DRM_MODE_FLAG_INTERLACE) ? true :
1095 false, mode->clock * 1000);
1097 ret = mixer_check_mode(mode);
1101 ret = hdmi_find_phy_conf(hdata, mode->clock * 1000);
1108 static struct drm_encoder *hdmi_best_encoder(struct drm_connector *connector)
1110 struct hdmi_context *hdata = ctx_from_connector(connector);
1112 return hdata->encoder;
1115 static struct drm_connector_helper_funcs hdmi_connector_helper_funcs = {
1116 .get_modes = hdmi_get_modes,
1117 .mode_valid = hdmi_mode_valid,
1118 .best_encoder = hdmi_best_encoder,
1121 static int hdmi_create_connector(struct exynos_drm_display *display,
1122 struct drm_encoder *encoder)
1124 struct hdmi_context *hdata = display->ctx;
1125 struct drm_connector *connector = &hdata->connector;
1128 hdata->encoder = encoder;
1129 connector->interlace_allowed = true;
1130 connector->polled = DRM_CONNECTOR_POLL_HPD;
1132 ret = drm_connector_init(hdata->drm_dev, connector,
1133 &hdmi_connector_funcs, DRM_MODE_CONNECTOR_HDMIA);
1135 DRM_ERROR("Failed to initialize connector with drm\n");
1139 drm_connector_helper_add(connector, &hdmi_connector_helper_funcs);
1140 drm_connector_register(connector);
1141 drm_mode_connector_attach_encoder(connector, encoder);
1146 static void hdmi_mode_fixup(struct exynos_drm_display *display,
1147 struct drm_connector *connector,
1148 const struct drm_display_mode *mode,
1149 struct drm_display_mode *adjusted_mode)
1151 struct drm_display_mode *m;
1154 DRM_DEBUG_KMS("%s\n", __FILE__);
1156 drm_mode_set_crtcinfo(adjusted_mode, 0);
1158 mode_ok = hdmi_mode_valid(connector, adjusted_mode);
1160 /* just return if user desired mode exists. */
1161 if (mode_ok == MODE_OK)
1165 * otherwise, find the most suitable mode among modes and change it
1168 list_for_each_entry(m, &connector->modes, head) {
1169 mode_ok = hdmi_mode_valid(connector, m);
1171 if (mode_ok == MODE_OK) {
1172 DRM_INFO("desired mode doesn't exist so\n");
1173 DRM_INFO("use the most suitable mode among modes.\n");
1175 DRM_DEBUG_KMS("Adjusted Mode: [%d]x[%d] [%d]Hz\n",
1176 m->hdisplay, m->vdisplay, m->vrefresh);
1178 drm_mode_copy(adjusted_mode, m);
1184 static void hdmi_set_acr(u32 freq, u8 *acr)
1224 acr[2] = cts >> 8 & 0xff;
1225 acr[3] = cts & 0xff;
1228 acr[5] = n >> 8 & 0xff;
1232 static void hdmi_reg_acr(struct hdmi_context *hdata, u8 *acr)
1234 hdmi_reg_writeb(hdata, HDMI_ACR_N0, acr[6]);
1235 hdmi_reg_writeb(hdata, HDMI_ACR_N1, acr[5]);
1236 hdmi_reg_writeb(hdata, HDMI_ACR_N2, acr[4]);
1237 hdmi_reg_writeb(hdata, HDMI_ACR_MCTS0, acr[3]);
1238 hdmi_reg_writeb(hdata, HDMI_ACR_MCTS1, acr[2]);
1239 hdmi_reg_writeb(hdata, HDMI_ACR_MCTS2, acr[1]);
1240 hdmi_reg_writeb(hdata, HDMI_ACR_CTS0, acr[3]);
1241 hdmi_reg_writeb(hdata, HDMI_ACR_CTS1, acr[2]);
1242 hdmi_reg_writeb(hdata, HDMI_ACR_CTS2, acr[1]);
1244 if (hdata->type == HDMI_TYPE13)
1245 hdmi_reg_writeb(hdata, HDMI_V13_ACR_CON, 4);
1247 hdmi_reg_writeb(hdata, HDMI_ACR_CON, 4);
1250 static void hdmi_audio_init(struct hdmi_context *hdata)
1252 u32 sample_rate, bits_per_sample;
1253 u32 data_num, bit_ch, sample_frq;
1257 sample_rate = 44100;
1258 bits_per_sample = 16;
1260 switch (bits_per_sample) {
1275 hdmi_set_acr(sample_rate, acr);
1276 hdmi_reg_acr(hdata, acr);
1278 hdmi_reg_writeb(hdata, HDMI_I2S_MUX_CON, HDMI_I2S_IN_DISABLE
1279 | HDMI_I2S_AUD_I2S | HDMI_I2S_CUV_I2S_ENABLE
1280 | HDMI_I2S_MUX_ENABLE);
1282 hdmi_reg_writeb(hdata, HDMI_I2S_MUX_CH, HDMI_I2S_CH0_EN
1283 | HDMI_I2S_CH1_EN | HDMI_I2S_CH2_EN);
1285 hdmi_reg_writeb(hdata, HDMI_I2S_MUX_CUV, HDMI_I2S_CUV_RL_EN);
1287 sample_frq = (sample_rate == 44100) ? 0 :
1288 (sample_rate == 48000) ? 2 :
1289 (sample_rate == 32000) ? 3 :
1290 (sample_rate == 96000) ? 0xa : 0x0;
1292 hdmi_reg_writeb(hdata, HDMI_I2S_CLK_CON, HDMI_I2S_CLK_DIS);
1293 hdmi_reg_writeb(hdata, HDMI_I2S_CLK_CON, HDMI_I2S_CLK_EN);
1295 val = hdmi_reg_read(hdata, HDMI_I2S_DSD_CON) | 0x01;
1296 hdmi_reg_writeb(hdata, HDMI_I2S_DSD_CON, val);
1298 /* Configuration I2S input ports. Configure I2S_PIN_SEL_0~4 */
1299 hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_0, HDMI_I2S_SEL_SCLK(5)
1300 | HDMI_I2S_SEL_LRCK(6));
1301 hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_1, HDMI_I2S_SEL_SDATA1(1)
1302 | HDMI_I2S_SEL_SDATA2(4));
1303 hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_2, HDMI_I2S_SEL_SDATA3(1)
1304 | HDMI_I2S_SEL_SDATA2(2));
1305 hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_3, HDMI_I2S_SEL_DSD(0));
1308 hdmi_reg_writeb(hdata, HDMI_I2S_CON_1, HDMI_I2S_SCLK_FALLING_EDGE
1309 | HDMI_I2S_L_CH_LOW_POL);
1310 hdmi_reg_writeb(hdata, HDMI_I2S_CON_2, HDMI_I2S_MSB_FIRST_MODE
1311 | HDMI_I2S_SET_BIT_CH(bit_ch)
1312 | HDMI_I2S_SET_SDATA_BIT(data_num)
1313 | HDMI_I2S_BASIC_FORMAT);
1315 /* Configure register related to CUV information */
1316 hdmi_reg_writeb(hdata, HDMI_I2S_CH_ST_0, HDMI_I2S_CH_STATUS_MODE_0
1317 | HDMI_I2S_2AUD_CH_WITHOUT_PREEMPH
1318 | HDMI_I2S_COPYRIGHT
1319 | HDMI_I2S_LINEAR_PCM
1320 | HDMI_I2S_CONSUMER_FORMAT);
1321 hdmi_reg_writeb(hdata, HDMI_I2S_CH_ST_1, HDMI_I2S_CD_PLAYER);
1322 hdmi_reg_writeb(hdata, HDMI_I2S_CH_ST_2, HDMI_I2S_SET_SOURCE_NUM(0));
1323 hdmi_reg_writeb(hdata, HDMI_I2S_CH_ST_3, HDMI_I2S_CLK_ACCUR_LEVEL_2
1324 | HDMI_I2S_SET_SMP_FREQ(sample_frq));
1325 hdmi_reg_writeb(hdata, HDMI_I2S_CH_ST_4,
1326 HDMI_I2S_ORG_SMP_FREQ_44_1
1327 | HDMI_I2S_WORD_LEN_MAX24_24BITS
1328 | HDMI_I2S_WORD_LEN_MAX_24BITS);
1330 hdmi_reg_writeb(hdata, HDMI_I2S_CH_ST_CON, HDMI_I2S_CH_STATUS_RELOAD);
1333 static void hdmi_audio_control(struct hdmi_context *hdata, bool onoff)
1335 if (hdata->dvi_mode)
1338 hdmi_reg_writeb(hdata, HDMI_AUI_CON, onoff ? 2 : 0);
1339 hdmi_reg_writemask(hdata, HDMI_CON_0, onoff ?
1340 HDMI_ASP_EN : HDMI_ASP_DIS, HDMI_ASP_MASK);
1343 static void hdmi_start(struct hdmi_context *hdata, bool start)
1345 u32 val = start ? HDMI_TG_EN : 0;
1347 if (hdata->current_mode.flags & DRM_MODE_FLAG_INTERLACE)
1348 val |= HDMI_FIELD_EN;
1350 hdmi_reg_writemask(hdata, HDMI_CON_0, val, HDMI_EN);
1351 hdmi_reg_writemask(hdata, HDMI_TG_CMD, val, HDMI_TG_EN | HDMI_FIELD_EN);
1354 static void hdmi_conf_init(struct hdmi_context *hdata)
1356 union hdmi_infoframe infoframe;
1358 /* disable HPD interrupts from HDMI IP block, use GPIO instead */
1359 hdmi_reg_writemask(hdata, HDMI_INTC_CON, 0, HDMI_INTC_EN_GLOBAL |
1360 HDMI_INTC_EN_HPD_PLUG | HDMI_INTC_EN_HPD_UNPLUG);
1362 /* choose HDMI mode */
1363 hdmi_reg_writemask(hdata, HDMI_MODE_SEL,
1364 HDMI_MODE_HDMI_EN, HDMI_MODE_MASK);
1365 /* Apply Video preable and Guard band in HDMI mode only */
1366 hdmi_reg_writeb(hdata, HDMI_CON_2, 0);
1367 /* disable bluescreen */
1368 hdmi_reg_writemask(hdata, HDMI_CON_0, 0, HDMI_BLUE_SCR_EN);
1370 if (hdata->dvi_mode) {
1371 /* choose DVI mode */
1372 hdmi_reg_writemask(hdata, HDMI_MODE_SEL,
1373 HDMI_MODE_DVI_EN, HDMI_MODE_MASK);
1374 hdmi_reg_writeb(hdata, HDMI_CON_2,
1375 HDMI_VID_PREAMBLE_DIS | HDMI_GUARD_BAND_DIS);
1378 if (hdata->type == HDMI_TYPE13) {
1379 /* choose bluescreen (fecal) color */
1380 hdmi_reg_writeb(hdata, HDMI_V13_BLUE_SCREEN_0, 0x12);
1381 hdmi_reg_writeb(hdata, HDMI_V13_BLUE_SCREEN_1, 0x34);
1382 hdmi_reg_writeb(hdata, HDMI_V13_BLUE_SCREEN_2, 0x56);
1384 /* enable AVI packet every vsync, fixes purple line problem */
1385 hdmi_reg_writeb(hdata, HDMI_V13_AVI_CON, 0x02);
1386 /* force RGB, look to CEA-861-D, table 7 for more detail */
1387 hdmi_reg_writeb(hdata, HDMI_V13_AVI_BYTE(0), 0 << 5);
1388 hdmi_reg_writemask(hdata, HDMI_CON_1, 0x10 << 5, 0x11 << 5);
1390 hdmi_reg_writeb(hdata, HDMI_V13_SPD_CON, 0x02);
1391 hdmi_reg_writeb(hdata, HDMI_V13_AUI_CON, 0x02);
1392 hdmi_reg_writeb(hdata, HDMI_V13_ACR_CON, 0x04);
1394 infoframe.any.type = HDMI_INFOFRAME_TYPE_AVI;
1395 infoframe.any.version = HDMI_AVI_VERSION;
1396 infoframe.any.length = HDMI_AVI_LENGTH;
1397 hdmi_reg_infoframe(hdata, &infoframe);
1399 infoframe.any.type = HDMI_INFOFRAME_TYPE_AUDIO;
1400 infoframe.any.version = HDMI_AUI_VERSION;
1401 infoframe.any.length = HDMI_AUI_LENGTH;
1402 hdmi_reg_infoframe(hdata, &infoframe);
1404 /* enable AVI packet every vsync, fixes purple line problem */
1405 hdmi_reg_writemask(hdata, HDMI_CON_1, 2, 3 << 5);
1409 static void hdmi_v13_mode_apply(struct hdmi_context *hdata)
1411 const struct hdmi_tg_regs *tg = &hdata->mode_conf.conf.v13_conf.tg;
1412 const struct hdmi_v13_core_regs *core =
1413 &hdata->mode_conf.conf.v13_conf.core;
1416 /* setting core registers */
1417 hdmi_reg_writeb(hdata, HDMI_H_BLANK_0, core->h_blank[0]);
1418 hdmi_reg_writeb(hdata, HDMI_H_BLANK_1, core->h_blank[1]);
1419 hdmi_reg_writeb(hdata, HDMI_V13_V_BLANK_0, core->v_blank[0]);
1420 hdmi_reg_writeb(hdata, HDMI_V13_V_BLANK_1, core->v_blank[1]);
1421 hdmi_reg_writeb(hdata, HDMI_V13_V_BLANK_2, core->v_blank[2]);
1422 hdmi_reg_writeb(hdata, HDMI_V13_H_V_LINE_0, core->h_v_line[0]);
1423 hdmi_reg_writeb(hdata, HDMI_V13_H_V_LINE_1, core->h_v_line[1]);
1424 hdmi_reg_writeb(hdata, HDMI_V13_H_V_LINE_2, core->h_v_line[2]);
1425 hdmi_reg_writeb(hdata, HDMI_VSYNC_POL, core->vsync_pol[0]);
1426 hdmi_reg_writeb(hdata, HDMI_INT_PRO_MODE, core->int_pro_mode[0]);
1427 hdmi_reg_writeb(hdata, HDMI_V13_V_BLANK_F_0, core->v_blank_f[0]);
1428 hdmi_reg_writeb(hdata, HDMI_V13_V_BLANK_F_1, core->v_blank_f[1]);
1429 hdmi_reg_writeb(hdata, HDMI_V13_V_BLANK_F_2, core->v_blank_f[2]);
1430 hdmi_reg_writeb(hdata, HDMI_V13_H_SYNC_GEN_0, core->h_sync_gen[0]);
1431 hdmi_reg_writeb(hdata, HDMI_V13_H_SYNC_GEN_1, core->h_sync_gen[1]);
1432 hdmi_reg_writeb(hdata, HDMI_V13_H_SYNC_GEN_2, core->h_sync_gen[2]);
1433 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_1_0, core->v_sync_gen1[0]);
1434 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_1_1, core->v_sync_gen1[1]);
1435 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_1_2, core->v_sync_gen1[2]);
1436 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_2_0, core->v_sync_gen2[0]);
1437 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_2_1, core->v_sync_gen2[1]);
1438 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_2_2, core->v_sync_gen2[2]);
1439 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_3_0, core->v_sync_gen3[0]);
1440 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_3_1, core->v_sync_gen3[1]);
1441 hdmi_reg_writeb(hdata, HDMI_V13_V_SYNC_GEN_3_2, core->v_sync_gen3[2]);
1442 /* Timing generator registers */
1443 hdmi_reg_writeb(hdata, HDMI_TG_H_FSZ_L, tg->h_fsz[0]);
1444 hdmi_reg_writeb(hdata, HDMI_TG_H_FSZ_H, tg->h_fsz[1]);
1445 hdmi_reg_writeb(hdata, HDMI_TG_HACT_ST_L, tg->hact_st[0]);
1446 hdmi_reg_writeb(hdata, HDMI_TG_HACT_ST_H, tg->hact_st[1]);
1447 hdmi_reg_writeb(hdata, HDMI_TG_HACT_SZ_L, tg->hact_sz[0]);
1448 hdmi_reg_writeb(hdata, HDMI_TG_HACT_SZ_H, tg->hact_sz[1]);
1449 hdmi_reg_writeb(hdata, HDMI_TG_V_FSZ_L, tg->v_fsz[0]);
1450 hdmi_reg_writeb(hdata, HDMI_TG_V_FSZ_H, tg->v_fsz[1]);
1451 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_L, tg->vsync[0]);
1452 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_H, tg->vsync[1]);
1453 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC2_L, tg->vsync2[0]);
1454 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC2_H, tg->vsync2[1]);
1455 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST_L, tg->vact_st[0]);
1456 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST_H, tg->vact_st[1]);
1457 hdmi_reg_writeb(hdata, HDMI_TG_VACT_SZ_L, tg->vact_sz[0]);
1458 hdmi_reg_writeb(hdata, HDMI_TG_VACT_SZ_H, tg->vact_sz[1]);
1459 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_CHG_L, tg->field_chg[0]);
1460 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_CHG_H, tg->field_chg[1]);
1461 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST2_L, tg->vact_st2[0]);
1462 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST2_H, tg->vact_st2[1]);
1463 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_TOP_HDMI_L, tg->vsync_top_hdmi[0]);
1464 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_TOP_HDMI_H, tg->vsync_top_hdmi[1]);
1465 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_BOT_HDMI_L, tg->vsync_bot_hdmi[0]);
1466 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_BOT_HDMI_H, tg->vsync_bot_hdmi[1]);
1467 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_TOP_HDMI_L, tg->field_top_hdmi[0]);
1468 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_TOP_HDMI_H, tg->field_top_hdmi[1]);
1469 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_BOT_HDMI_L, tg->field_bot_hdmi[0]);
1470 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_BOT_HDMI_H, tg->field_bot_hdmi[1]);
1472 /* waiting for HDMIPHY's PLL to get to steady state */
1473 for (tries = 100; tries; --tries) {
1474 u32 val = hdmi_reg_read(hdata, HDMI_V13_PHY_STATUS);
1475 if (val & HDMI_PHY_STATUS_READY)
1477 usleep_range(1000, 2000);
1479 /* steady state not achieved */
1481 DRM_ERROR("hdmiphy's pll could not reach steady state.\n");
1482 hdmi_regs_dump(hdata, "timing apply");
1485 clk_disable_unprepare(hdata->res.sclk_hdmi);
1486 clk_set_parent(hdata->res.mout_hdmi, hdata->res.sclk_hdmiphy);
1487 clk_prepare_enable(hdata->res.sclk_hdmi);
1489 /* enable HDMI and timing generator */
1490 hdmi_start(hdata, true);
1493 static void hdmi_v14_mode_apply(struct hdmi_context *hdata)
1495 const struct hdmi_tg_regs *tg = &hdata->mode_conf.conf.v14_conf.tg;
1496 const struct hdmi_v14_core_regs *core =
1497 &hdata->mode_conf.conf.v14_conf.core;
1500 /* setting core registers */
1501 hdmi_reg_writeb(hdata, HDMI_H_BLANK_0, core->h_blank[0]);
1502 hdmi_reg_writeb(hdata, HDMI_H_BLANK_1, core->h_blank[1]);
1503 hdmi_reg_writeb(hdata, HDMI_V2_BLANK_0, core->v2_blank[0]);
1504 hdmi_reg_writeb(hdata, HDMI_V2_BLANK_1, core->v2_blank[1]);
1505 hdmi_reg_writeb(hdata, HDMI_V1_BLANK_0, core->v1_blank[0]);
1506 hdmi_reg_writeb(hdata, HDMI_V1_BLANK_1, core->v1_blank[1]);
1507 hdmi_reg_writeb(hdata, HDMI_V_LINE_0, core->v_line[0]);
1508 hdmi_reg_writeb(hdata, HDMI_V_LINE_1, core->v_line[1]);
1509 hdmi_reg_writeb(hdata, HDMI_H_LINE_0, core->h_line[0]);
1510 hdmi_reg_writeb(hdata, HDMI_H_LINE_1, core->h_line[1]);
1511 hdmi_reg_writeb(hdata, HDMI_HSYNC_POL, core->hsync_pol[0]);
1512 hdmi_reg_writeb(hdata, HDMI_VSYNC_POL, core->vsync_pol[0]);
1513 hdmi_reg_writeb(hdata, HDMI_INT_PRO_MODE, core->int_pro_mode[0]);
1514 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F0_0, core->v_blank_f0[0]);
1515 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F0_1, core->v_blank_f0[1]);
1516 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F1_0, core->v_blank_f1[0]);
1517 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F1_1, core->v_blank_f1[1]);
1518 hdmi_reg_writeb(hdata, HDMI_H_SYNC_START_0, core->h_sync_start[0]);
1519 hdmi_reg_writeb(hdata, HDMI_H_SYNC_START_1, core->h_sync_start[1]);
1520 hdmi_reg_writeb(hdata, HDMI_H_SYNC_END_0, core->h_sync_end[0]);
1521 hdmi_reg_writeb(hdata, HDMI_H_SYNC_END_1, core->h_sync_end[1]);
1522 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_BEF_2_0,
1523 core->v_sync_line_bef_2[0]);
1524 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_BEF_2_1,
1525 core->v_sync_line_bef_2[1]);
1526 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_BEF_1_0,
1527 core->v_sync_line_bef_1[0]);
1528 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_BEF_1_1,
1529 core->v_sync_line_bef_1[1]);
1530 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_2_0,
1531 core->v_sync_line_aft_2[0]);
1532 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_2_1,
1533 core->v_sync_line_aft_2[1]);
1534 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_1_0,
1535 core->v_sync_line_aft_1[0]);
1536 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_1_1,
1537 core->v_sync_line_aft_1[1]);
1538 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_2_0,
1539 core->v_sync_line_aft_pxl_2[0]);
1540 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_2_1,
1541 core->v_sync_line_aft_pxl_2[1]);
1542 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_1_0,
1543 core->v_sync_line_aft_pxl_1[0]);
1544 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_1_1,
1545 core->v_sync_line_aft_pxl_1[1]);
1546 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F2_0, core->v_blank_f2[0]);
1547 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F2_1, core->v_blank_f2[1]);
1548 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F3_0, core->v_blank_f3[0]);
1549 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F3_1, core->v_blank_f3[1]);
1550 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F4_0, core->v_blank_f4[0]);
1551 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F4_1, core->v_blank_f4[1]);
1552 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F5_0, core->v_blank_f5[0]);
1553 hdmi_reg_writeb(hdata, HDMI_V_BLANK_F5_1, core->v_blank_f5[1]);
1554 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_3_0,
1555 core->v_sync_line_aft_3[0]);
1556 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_3_1,
1557 core->v_sync_line_aft_3[1]);
1558 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_4_0,
1559 core->v_sync_line_aft_4[0]);
1560 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_4_1,
1561 core->v_sync_line_aft_4[1]);
1562 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_5_0,
1563 core->v_sync_line_aft_5[0]);
1564 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_5_1,
1565 core->v_sync_line_aft_5[1]);
1566 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_6_0,
1567 core->v_sync_line_aft_6[0]);
1568 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_6_1,
1569 core->v_sync_line_aft_6[1]);
1570 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_3_0,
1571 core->v_sync_line_aft_pxl_3[0]);
1572 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_3_1,
1573 core->v_sync_line_aft_pxl_3[1]);
1574 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_4_0,
1575 core->v_sync_line_aft_pxl_4[0]);
1576 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_4_1,
1577 core->v_sync_line_aft_pxl_4[1]);
1578 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_5_0,
1579 core->v_sync_line_aft_pxl_5[0]);
1580 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_5_1,
1581 core->v_sync_line_aft_pxl_5[1]);
1582 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_6_0,
1583 core->v_sync_line_aft_pxl_6[0]);
1584 hdmi_reg_writeb(hdata, HDMI_V_SYNC_LINE_AFT_PXL_6_1,
1585 core->v_sync_line_aft_pxl_6[1]);
1586 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_1_0, core->vact_space_1[0]);
1587 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_1_1, core->vact_space_1[1]);
1588 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_2_0, core->vact_space_2[0]);
1589 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_2_1, core->vact_space_2[1]);
1590 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_3_0, core->vact_space_3[0]);
1591 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_3_1, core->vact_space_3[1]);
1592 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_4_0, core->vact_space_4[0]);
1593 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_4_1, core->vact_space_4[1]);
1594 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_5_0, core->vact_space_5[0]);
1595 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_5_1, core->vact_space_5[1]);
1596 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_6_0, core->vact_space_6[0]);
1597 hdmi_reg_writeb(hdata, HDMI_VACT_SPACE_6_1, core->vact_space_6[1]);
1599 /* Timing generator registers */
1600 hdmi_reg_writeb(hdata, HDMI_TG_H_FSZ_L, tg->h_fsz[0]);
1601 hdmi_reg_writeb(hdata, HDMI_TG_H_FSZ_H, tg->h_fsz[1]);
1602 hdmi_reg_writeb(hdata, HDMI_TG_HACT_ST_L, tg->hact_st[0]);
1603 hdmi_reg_writeb(hdata, HDMI_TG_HACT_ST_H, tg->hact_st[1]);
1604 hdmi_reg_writeb(hdata, HDMI_TG_HACT_SZ_L, tg->hact_sz[0]);
1605 hdmi_reg_writeb(hdata, HDMI_TG_HACT_SZ_H, tg->hact_sz[1]);
1606 hdmi_reg_writeb(hdata, HDMI_TG_V_FSZ_L, tg->v_fsz[0]);
1607 hdmi_reg_writeb(hdata, HDMI_TG_V_FSZ_H, tg->v_fsz[1]);
1608 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_L, tg->vsync[0]);
1609 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_H, tg->vsync[1]);
1610 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC2_L, tg->vsync2[0]);
1611 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC2_H, tg->vsync2[1]);
1612 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST_L, tg->vact_st[0]);
1613 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST_H, tg->vact_st[1]);
1614 hdmi_reg_writeb(hdata, HDMI_TG_VACT_SZ_L, tg->vact_sz[0]);
1615 hdmi_reg_writeb(hdata, HDMI_TG_VACT_SZ_H, tg->vact_sz[1]);
1616 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_CHG_L, tg->field_chg[0]);
1617 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_CHG_H, tg->field_chg[1]);
1618 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST2_L, tg->vact_st2[0]);
1619 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST2_H, tg->vact_st2[1]);
1620 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST3_L, tg->vact_st3[0]);
1621 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST3_H, tg->vact_st3[1]);
1622 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST4_L, tg->vact_st4[0]);
1623 hdmi_reg_writeb(hdata, HDMI_TG_VACT_ST4_H, tg->vact_st4[1]);
1624 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_TOP_HDMI_L, tg->vsync_top_hdmi[0]);
1625 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_TOP_HDMI_H, tg->vsync_top_hdmi[1]);
1626 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_BOT_HDMI_L, tg->vsync_bot_hdmi[0]);
1627 hdmi_reg_writeb(hdata, HDMI_TG_VSYNC_BOT_HDMI_H, tg->vsync_bot_hdmi[1]);
1628 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_TOP_HDMI_L, tg->field_top_hdmi[0]);
1629 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_TOP_HDMI_H, tg->field_top_hdmi[1]);
1630 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_BOT_HDMI_L, tg->field_bot_hdmi[0]);
1631 hdmi_reg_writeb(hdata, HDMI_TG_FIELD_BOT_HDMI_H, tg->field_bot_hdmi[1]);
1632 hdmi_reg_writeb(hdata, HDMI_TG_3D, tg->tg_3d[0]);
1634 /* waiting for HDMIPHY's PLL to get to steady state */
1635 for (tries = 100; tries; --tries) {
1636 u32 val = hdmi_reg_read(hdata, HDMI_PHY_STATUS_0);
1637 if (val & HDMI_PHY_STATUS_READY)
1639 usleep_range(1000, 2000);
1641 /* steady state not achieved */
1643 DRM_ERROR("hdmiphy's pll could not reach steady state.\n");
1644 hdmi_regs_dump(hdata, "timing apply");
1647 clk_disable_unprepare(hdata->res.sclk_hdmi);
1648 clk_set_parent(hdata->res.mout_hdmi, hdata->res.sclk_hdmiphy);
1649 clk_prepare_enable(hdata->res.sclk_hdmi);
1651 /* enable HDMI and timing generator */
1652 hdmi_start(hdata, true);
1655 static void hdmi_mode_apply(struct hdmi_context *hdata)
1657 if (hdata->type == HDMI_TYPE13)
1658 hdmi_v13_mode_apply(hdata);
1660 hdmi_v14_mode_apply(hdata);
1663 static void hdmiphy_conf_reset(struct hdmi_context *hdata)
1668 clk_disable_unprepare(hdata->res.sclk_hdmi);
1669 clk_set_parent(hdata->res.mout_hdmi, hdata->res.sclk_pixel);
1670 clk_prepare_enable(hdata->res.sclk_hdmi);
1672 /* operation mode */
1676 if (hdata->hdmiphy_port)
1677 i2c_master_send(hdata->hdmiphy_port, buffer, 2);
1679 if (hdata->type == HDMI_TYPE13)
1680 reg = HDMI_V13_PHY_RSTOUT;
1682 reg = HDMI_PHY_RSTOUT;
1685 hdmi_reg_writemask(hdata, reg, ~0, HDMI_PHY_SW_RSTOUT);
1686 usleep_range(10000, 12000);
1687 hdmi_reg_writemask(hdata, reg, 0, HDMI_PHY_SW_RSTOUT);
1688 usleep_range(10000, 12000);
1691 static void hdmiphy_poweron(struct hdmi_context *hdata)
1693 if (hdata->type != HDMI_TYPE14)
1696 DRM_DEBUG_KMS("\n");
1698 /* For PHY Mode Setting */
1699 hdmiphy_reg_writeb(hdata, HDMIPHY_MODE_SET_DONE,
1700 HDMI_PHY_ENABLE_MODE_SET);
1702 hdmiphy_reg_writeb(hdata, HDMIPHY_POWER,
1704 /* For PHY Mode Setting */
1705 hdmiphy_reg_writeb(hdata, HDMIPHY_MODE_SET_DONE,
1706 HDMI_PHY_DISABLE_MODE_SET);
1708 hdmiphy_conf_reset(hdata);
1711 static void hdmiphy_poweroff(struct hdmi_context *hdata)
1713 if (hdata->type != HDMI_TYPE14)
1716 DRM_DEBUG_KMS("\n");
1719 hdmiphy_conf_reset(hdata);
1720 /* For PHY Mode Setting */
1721 hdmiphy_reg_writeb(hdata, HDMIPHY_MODE_SET_DONE,
1722 HDMI_PHY_ENABLE_MODE_SET);
1725 hdmiphy_reg_writeb(hdata, HDMIPHY_POWER,
1726 HDMI_PHY_POWER_OFF);
1728 /* For PHY Mode Setting */
1729 hdmiphy_reg_writeb(hdata, HDMIPHY_MODE_SET_DONE,
1730 HDMI_PHY_DISABLE_MODE_SET);
1733 static void hdmiphy_conf_apply(struct hdmi_context *hdata)
1739 i = hdmi_find_phy_conf(hdata, hdata->mode_conf.pixel_clock);
1741 DRM_ERROR("failed to find hdmiphy conf\n");
1745 ret = hdmiphy_reg_write_buf(hdata, 0, hdata->phy_confs[i].conf, 32);
1747 DRM_ERROR("failed to configure hdmiphy\n");
1751 usleep_range(10000, 12000);
1753 ret = hdmiphy_reg_writeb(hdata, HDMIPHY_MODE_SET_DONE,
1754 HDMI_PHY_DISABLE_MODE_SET);
1756 DRM_ERROR("failed to enable hdmiphy\n");
1762 static void hdmi_conf_apply(struct hdmi_context *hdata)
1764 hdmiphy_conf_reset(hdata);
1765 hdmiphy_conf_apply(hdata);
1767 mutex_lock(&hdata->hdmi_mutex);
1768 hdmi_start(hdata, false);
1769 hdmi_conf_init(hdata);
1770 mutex_unlock(&hdata->hdmi_mutex);
1772 hdmi_audio_init(hdata);
1774 /* setting core registers */
1775 hdmi_mode_apply(hdata);
1776 hdmi_audio_control(hdata, true);
1778 hdmi_regs_dump(hdata, "start");
1781 static void hdmi_set_reg(u8 *reg_pair, int num_bytes, u32 value)
1784 BUG_ON(num_bytes > 4);
1785 for (i = 0; i < num_bytes; i++)
1786 reg_pair[i] = (value >> (8 * i)) & 0xff;
1789 static void hdmi_v13_mode_set(struct hdmi_context *hdata,
1790 struct drm_display_mode *m)
1792 struct hdmi_v13_core_regs *core = &hdata->mode_conf.conf.v13_conf.core;
1793 struct hdmi_tg_regs *tg = &hdata->mode_conf.conf.v13_conf.tg;
1796 hdata->mode_conf.cea_video_id =
1797 drm_match_cea_mode((struct drm_display_mode *)m);
1798 hdata->mode_conf.pixel_clock = m->clock * 1000;
1799 hdata->mode_conf.aspect_ratio = m->picture_aspect_ratio;
1801 hdmi_set_reg(core->h_blank, 2, m->htotal - m->hdisplay);
1802 hdmi_set_reg(core->h_v_line, 3, (m->htotal << 12) | m->vtotal);
1804 val = (m->flags & DRM_MODE_FLAG_NVSYNC) ? 1 : 0;
1805 hdmi_set_reg(core->vsync_pol, 1, val);
1807 val = (m->flags & DRM_MODE_FLAG_INTERLACE) ? 1 : 0;
1808 hdmi_set_reg(core->int_pro_mode, 1, val);
1810 val = (m->hsync_start - m->hdisplay - 2);
1811 val |= ((m->hsync_end - m->hdisplay - 2) << 10);
1812 val |= ((m->flags & DRM_MODE_FLAG_NHSYNC) ? 1 : 0)<<20;
1813 hdmi_set_reg(core->h_sync_gen, 3, val);
1816 * Quirk requirement for exynos HDMI IP design,
1817 * 2 pixels less than the actual calculation for hsync_start
1821 /* Following values & calculations differ for different type of modes */
1822 if (m->flags & DRM_MODE_FLAG_INTERLACE) {
1823 /* Interlaced Mode */
1824 val = ((m->vsync_end - m->vdisplay) / 2);
1825 val |= ((m->vsync_start - m->vdisplay) / 2) << 12;
1826 hdmi_set_reg(core->v_sync_gen1, 3, val);
1828 val = m->vtotal / 2;
1829 val |= ((m->vtotal - m->vdisplay) / 2) << 11;
1830 hdmi_set_reg(core->v_blank, 3, val);
1833 ((m->vsync_end - m->vsync_start) * 4) + 5) / 2;
1834 val |= m->vtotal << 11;
1835 hdmi_set_reg(core->v_blank_f, 3, val);
1837 val = ((m->vtotal / 2) + 7);
1838 val |= ((m->vtotal / 2) + 2) << 12;
1839 hdmi_set_reg(core->v_sync_gen2, 3, val);
1841 val = ((m->htotal / 2) + (m->hsync_start - m->hdisplay));
1842 val |= ((m->htotal / 2) +
1843 (m->hsync_start - m->hdisplay)) << 12;
1844 hdmi_set_reg(core->v_sync_gen3, 3, val);
1846 hdmi_set_reg(tg->vact_st, 2, (m->vtotal - m->vdisplay) / 2);
1847 hdmi_set_reg(tg->vact_sz, 2, m->vdisplay / 2);
1849 hdmi_set_reg(tg->vact_st2, 2, 0x249);/* Reset value + 1*/
1851 /* Progressive Mode */
1854 val |= (m->vtotal - m->vdisplay) << 11;
1855 hdmi_set_reg(core->v_blank, 3, val);
1857 hdmi_set_reg(core->v_blank_f, 3, 0);
1859 val = (m->vsync_end - m->vdisplay);
1860 val |= ((m->vsync_start - m->vdisplay) << 12);
1861 hdmi_set_reg(core->v_sync_gen1, 3, val);
1863 hdmi_set_reg(core->v_sync_gen2, 3, 0x1001);/* Reset value */
1864 hdmi_set_reg(core->v_sync_gen3, 3, 0x1001);/* Reset value */
1865 hdmi_set_reg(tg->vact_st, 2, m->vtotal - m->vdisplay);
1866 hdmi_set_reg(tg->vact_sz, 2, m->vdisplay);
1867 hdmi_set_reg(tg->vact_st2, 2, 0x248); /* Reset value */
1870 /* Timing generator registers */
1871 hdmi_set_reg(tg->cmd, 1, 0x0);
1872 hdmi_set_reg(tg->h_fsz, 2, m->htotal);
1873 hdmi_set_reg(tg->hact_st, 2, m->htotal - m->hdisplay);
1874 hdmi_set_reg(tg->hact_sz, 2, m->hdisplay);
1875 hdmi_set_reg(tg->v_fsz, 2, m->vtotal);
1876 hdmi_set_reg(tg->vsync, 2, 0x1);
1877 hdmi_set_reg(tg->vsync2, 2, 0x233); /* Reset value */
1878 hdmi_set_reg(tg->field_chg, 2, 0x233); /* Reset value */
1879 hdmi_set_reg(tg->vsync_top_hdmi, 2, 0x1); /* Reset value */
1880 hdmi_set_reg(tg->vsync_bot_hdmi, 2, 0x233); /* Reset value */
1881 hdmi_set_reg(tg->field_top_hdmi, 2, 0x1); /* Reset value */
1882 hdmi_set_reg(tg->field_bot_hdmi, 2, 0x233); /* Reset value */
1883 hdmi_set_reg(tg->tg_3d, 1, 0x0); /* Not used */
1886 static void hdmi_v14_mode_set(struct hdmi_context *hdata,
1887 struct drm_display_mode *m)
1889 struct hdmi_tg_regs *tg = &hdata->mode_conf.conf.v14_conf.tg;
1890 struct hdmi_v14_core_regs *core =
1891 &hdata->mode_conf.conf.v14_conf.core;
1893 hdata->mode_conf.cea_video_id =
1894 drm_match_cea_mode((struct drm_display_mode *)m);
1895 hdata->mode_conf.pixel_clock = m->clock * 1000;
1896 hdata->mode_conf.aspect_ratio = m->picture_aspect_ratio;
1898 hdmi_set_reg(core->h_blank, 2, m->htotal - m->hdisplay);
1899 hdmi_set_reg(core->v_line, 2, m->vtotal);
1900 hdmi_set_reg(core->h_line, 2, m->htotal);
1901 hdmi_set_reg(core->hsync_pol, 1,
1902 (m->flags & DRM_MODE_FLAG_NHSYNC) ? 1 : 0);
1903 hdmi_set_reg(core->vsync_pol, 1,
1904 (m->flags & DRM_MODE_FLAG_NVSYNC) ? 1 : 0);
1905 hdmi_set_reg(core->int_pro_mode, 1,
1906 (m->flags & DRM_MODE_FLAG_INTERLACE) ? 1 : 0);
1909 * Quirk requirement for exynos 5 HDMI IP design,
1910 * 2 pixels less than the actual calculation for hsync_start
1914 /* Following values & calculations differ for different type of modes */
1915 if (m->flags & DRM_MODE_FLAG_INTERLACE) {
1916 /* Interlaced Mode */
1917 hdmi_set_reg(core->v_sync_line_bef_2, 2,
1918 (m->vsync_end - m->vdisplay) / 2);
1919 hdmi_set_reg(core->v_sync_line_bef_1, 2,
1920 (m->vsync_start - m->vdisplay) / 2);
1921 hdmi_set_reg(core->v2_blank, 2, m->vtotal / 2);
1922 hdmi_set_reg(core->v1_blank, 2, (m->vtotal - m->vdisplay) / 2);
1923 hdmi_set_reg(core->v_blank_f0, 2, m->vtotal - m->vdisplay / 2);
1924 hdmi_set_reg(core->v_blank_f1, 2, m->vtotal);
1925 hdmi_set_reg(core->v_sync_line_aft_2, 2, (m->vtotal / 2) + 7);
1926 hdmi_set_reg(core->v_sync_line_aft_1, 2, (m->vtotal / 2) + 2);
1927 hdmi_set_reg(core->v_sync_line_aft_pxl_2, 2,
1928 (m->htotal / 2) + (m->hsync_start - m->hdisplay));
1929 hdmi_set_reg(core->v_sync_line_aft_pxl_1, 2,
1930 (m->htotal / 2) + (m->hsync_start - m->hdisplay));
1931 hdmi_set_reg(tg->vact_st, 2, (m->vtotal - m->vdisplay) / 2);
1932 hdmi_set_reg(tg->vact_sz, 2, m->vdisplay / 2);
1933 hdmi_set_reg(tg->vact_st2, 2, m->vtotal - m->vdisplay / 2);
1934 hdmi_set_reg(tg->vsync2, 2, (m->vtotal / 2) + 1);
1935 hdmi_set_reg(tg->vsync_bot_hdmi, 2, (m->vtotal / 2) + 1);
1936 hdmi_set_reg(tg->field_bot_hdmi, 2, (m->vtotal / 2) + 1);
1937 hdmi_set_reg(tg->vact_st3, 2, 0x0);
1938 hdmi_set_reg(tg->vact_st4, 2, 0x0);
1940 /* Progressive Mode */
1941 hdmi_set_reg(core->v_sync_line_bef_2, 2,
1942 m->vsync_end - m->vdisplay);
1943 hdmi_set_reg(core->v_sync_line_bef_1, 2,
1944 m->vsync_start - m->vdisplay);
1945 hdmi_set_reg(core->v2_blank, 2, m->vtotal);
1946 hdmi_set_reg(core->v1_blank, 2, m->vtotal - m->vdisplay);
1947 hdmi_set_reg(core->v_blank_f0, 2, 0xffff);
1948 hdmi_set_reg(core->v_blank_f1, 2, 0xffff);
1949 hdmi_set_reg(core->v_sync_line_aft_2, 2, 0xffff);
1950 hdmi_set_reg(core->v_sync_line_aft_1, 2, 0xffff);
1951 hdmi_set_reg(core->v_sync_line_aft_pxl_2, 2, 0xffff);
1952 hdmi_set_reg(core->v_sync_line_aft_pxl_1, 2, 0xffff);
1953 hdmi_set_reg(tg->vact_st, 2, m->vtotal - m->vdisplay);
1954 hdmi_set_reg(tg->vact_sz, 2, m->vdisplay);
1955 hdmi_set_reg(tg->vact_st2, 2, 0x248); /* Reset value */
1956 hdmi_set_reg(tg->vact_st3, 2, 0x47b); /* Reset value */
1957 hdmi_set_reg(tg->vact_st4, 2, 0x6ae); /* Reset value */
1958 hdmi_set_reg(tg->vsync2, 2, 0x233); /* Reset value */
1959 hdmi_set_reg(tg->vsync_bot_hdmi, 2, 0x233); /* Reset value */
1960 hdmi_set_reg(tg->field_bot_hdmi, 2, 0x233); /* Reset value */
1963 /* Following values & calculations are same irrespective of mode type */
1964 hdmi_set_reg(core->h_sync_start, 2, m->hsync_start - m->hdisplay - 2);
1965 hdmi_set_reg(core->h_sync_end, 2, m->hsync_end - m->hdisplay - 2);
1966 hdmi_set_reg(core->vact_space_1, 2, 0xffff);
1967 hdmi_set_reg(core->vact_space_2, 2, 0xffff);
1968 hdmi_set_reg(core->vact_space_3, 2, 0xffff);
1969 hdmi_set_reg(core->vact_space_4, 2, 0xffff);
1970 hdmi_set_reg(core->vact_space_5, 2, 0xffff);
1971 hdmi_set_reg(core->vact_space_6, 2, 0xffff);
1972 hdmi_set_reg(core->v_blank_f2, 2, 0xffff);
1973 hdmi_set_reg(core->v_blank_f3, 2, 0xffff);
1974 hdmi_set_reg(core->v_blank_f4, 2, 0xffff);
1975 hdmi_set_reg(core->v_blank_f5, 2, 0xffff);
1976 hdmi_set_reg(core->v_sync_line_aft_3, 2, 0xffff);
1977 hdmi_set_reg(core->v_sync_line_aft_4, 2, 0xffff);
1978 hdmi_set_reg(core->v_sync_line_aft_5, 2, 0xffff);
1979 hdmi_set_reg(core->v_sync_line_aft_6, 2, 0xffff);
1980 hdmi_set_reg(core->v_sync_line_aft_pxl_3, 2, 0xffff);
1981 hdmi_set_reg(core->v_sync_line_aft_pxl_4, 2, 0xffff);
1982 hdmi_set_reg(core->v_sync_line_aft_pxl_5, 2, 0xffff);
1983 hdmi_set_reg(core->v_sync_line_aft_pxl_6, 2, 0xffff);
1985 /* Timing generator registers */
1986 hdmi_set_reg(tg->cmd, 1, 0x0);
1987 hdmi_set_reg(tg->h_fsz, 2, m->htotal);
1988 hdmi_set_reg(tg->hact_st, 2, m->htotal - m->hdisplay);
1989 hdmi_set_reg(tg->hact_sz, 2, m->hdisplay);
1990 hdmi_set_reg(tg->v_fsz, 2, m->vtotal);
1991 hdmi_set_reg(tg->vsync, 2, 0x1);
1992 hdmi_set_reg(tg->field_chg, 2, 0x233); /* Reset value */
1993 hdmi_set_reg(tg->vsync_top_hdmi, 2, 0x1); /* Reset value */
1994 hdmi_set_reg(tg->field_top_hdmi, 2, 0x1); /* Reset value */
1995 hdmi_set_reg(tg->tg_3d, 1, 0x0);
1998 static void hdmi_mode_set(struct exynos_drm_display *display,
1999 struct drm_display_mode *mode)
2001 struct hdmi_context *hdata = display->ctx;
2002 struct drm_display_mode *m = mode;
2004 DRM_DEBUG_KMS("xres=%d, yres=%d, refresh=%d, intl=%s\n",
2005 m->hdisplay, m->vdisplay,
2006 m->vrefresh, (m->flags & DRM_MODE_FLAG_INTERLACE) ?
2007 "INTERLACED" : "PROGERESSIVE");
2009 /* preserve mode information for later use. */
2010 drm_mode_copy(&hdata->current_mode, mode);
2012 if (hdata->type == HDMI_TYPE13)
2013 hdmi_v13_mode_set(hdata, mode);
2015 hdmi_v14_mode_set(hdata, mode);
2018 static void hdmi_commit(struct exynos_drm_display *display)
2020 struct hdmi_context *hdata = display->ctx;
2022 mutex_lock(&hdata->hdmi_mutex);
2023 if (!hdata->powered) {
2024 mutex_unlock(&hdata->hdmi_mutex);
2027 mutex_unlock(&hdata->hdmi_mutex);
2029 hdmi_conf_apply(hdata);
2032 static void hdmi_poweron(struct exynos_drm_display *display)
2034 struct hdmi_context *hdata = display->ctx;
2035 struct hdmi_resources *res = &hdata->res;
2037 mutex_lock(&hdata->hdmi_mutex);
2038 if (hdata->powered) {
2039 mutex_unlock(&hdata->hdmi_mutex);
2043 hdata->powered = true;
2045 mutex_unlock(&hdata->hdmi_mutex);
2047 pm_runtime_get_sync(hdata->dev);
2049 if (regulator_bulk_enable(res->regul_count, res->regul_bulk))
2050 DRM_DEBUG_KMS("failed to enable regulator bulk\n");
2052 /* set pmu hdmiphy control bit to enable hdmiphy */
2053 regmap_update_bits(hdata->pmureg, PMU_HDMI_PHY_CONTROL,
2054 PMU_HDMI_PHY_ENABLE_BIT, 1);
2056 clk_prepare_enable(res->hdmi);
2057 clk_prepare_enable(res->sclk_hdmi);
2059 hdmiphy_poweron(hdata);
2060 hdmi_commit(display);
2063 static void hdmi_poweroff(struct exynos_drm_display *display)
2065 struct hdmi_context *hdata = display->ctx;
2066 struct hdmi_resources *res = &hdata->res;
2068 mutex_lock(&hdata->hdmi_mutex);
2069 if (!hdata->powered)
2071 mutex_unlock(&hdata->hdmi_mutex);
2073 /* HDMI System Disable */
2074 hdmi_reg_writemask(hdata, HDMI_CON_0, 0, HDMI_EN);
2076 hdmiphy_poweroff(hdata);
2078 cancel_delayed_work(&hdata->hotplug_work);
2080 clk_disable_unprepare(res->sclk_hdmi);
2081 clk_disable_unprepare(res->hdmi);
2083 /* reset pmu hdmiphy control bit to disable hdmiphy */
2084 regmap_update_bits(hdata->pmureg, PMU_HDMI_PHY_CONTROL,
2085 PMU_HDMI_PHY_ENABLE_BIT, 0);
2087 regulator_bulk_disable(res->regul_count, res->regul_bulk);
2089 pm_runtime_put_sync(hdata->dev);
2091 mutex_lock(&hdata->hdmi_mutex);
2092 hdata->powered = false;
2095 mutex_unlock(&hdata->hdmi_mutex);
2098 static void hdmi_dpms(struct exynos_drm_display *display, int mode)
2100 struct hdmi_context *hdata = display->ctx;
2101 struct drm_encoder *encoder = hdata->encoder;
2102 struct drm_crtc *crtc = encoder->crtc;
2103 struct drm_crtc_helper_funcs *funcs = NULL;
2105 DRM_DEBUG_KMS("mode %d\n", mode);
2108 case DRM_MODE_DPMS_ON:
2109 hdmi_poweron(display);
2111 case DRM_MODE_DPMS_STANDBY:
2112 case DRM_MODE_DPMS_SUSPEND:
2113 case DRM_MODE_DPMS_OFF:
2115 * The SFRs of VP and Mixer are updated by Vertical Sync of
2116 * Timing generator which is a part of HDMI so the sequence
2117 * to disable TV Subsystem should be as following,
2118 * VP -> Mixer -> HDMI
2120 * Below codes will try to disable Mixer and VP(if used)
2121 * prior to disabling HDMI.
2124 funcs = crtc->helper_private;
2125 if (funcs && funcs->dpms)
2126 (*funcs->dpms)(crtc, mode);
2128 hdmi_poweroff(display);
2131 DRM_DEBUG_KMS("unknown dpms mode: %d\n", mode);
2136 static struct exynos_drm_display_ops hdmi_display_ops = {
2137 .create_connector = hdmi_create_connector,
2138 .mode_fixup = hdmi_mode_fixup,
2139 .mode_set = hdmi_mode_set,
2141 .commit = hdmi_commit,
2144 static struct exynos_drm_display hdmi_display = {
2145 .type = EXYNOS_DISPLAY_TYPE_HDMI,
2146 .ops = &hdmi_display_ops,
2149 static void hdmi_hotplug_work_func(struct work_struct *work)
2151 struct hdmi_context *hdata;
2153 hdata = container_of(work, struct hdmi_context, hotplug_work.work);
2155 mutex_lock(&hdata->hdmi_mutex);
2156 hdata->hpd = gpio_get_value(hdata->hpd_gpio);
2157 mutex_unlock(&hdata->hdmi_mutex);
2160 drm_helper_hpd_irq_event(hdata->drm_dev);
2163 static irqreturn_t hdmi_irq_thread(int irq, void *arg)
2165 struct hdmi_context *hdata = arg;
2167 mod_delayed_work(system_wq, &hdata->hotplug_work,
2168 msecs_to_jiffies(HOTPLUG_DEBOUNCE_MS));
2173 static int hdmi_resources_init(struct hdmi_context *hdata)
2175 struct device *dev = hdata->dev;
2176 struct hdmi_resources *res = &hdata->res;
2177 static char *supply[] = {
2184 DRM_DEBUG_KMS("HDMI resource init\n");
2186 /* get clocks, power */
2187 res->hdmi = devm_clk_get(dev, "hdmi");
2188 if (IS_ERR(res->hdmi)) {
2189 DRM_ERROR("failed to get clock 'hdmi'\n");
2190 ret = PTR_ERR(res->hdmi);
2193 res->sclk_hdmi = devm_clk_get(dev, "sclk_hdmi");
2194 if (IS_ERR(res->sclk_hdmi)) {
2195 DRM_ERROR("failed to get clock 'sclk_hdmi'\n");
2196 ret = PTR_ERR(res->sclk_hdmi);
2199 res->sclk_pixel = devm_clk_get(dev, "sclk_pixel");
2200 if (IS_ERR(res->sclk_pixel)) {
2201 DRM_ERROR("failed to get clock 'sclk_pixel'\n");
2202 ret = PTR_ERR(res->sclk_pixel);
2205 res->sclk_hdmiphy = devm_clk_get(dev, "sclk_hdmiphy");
2206 if (IS_ERR(res->sclk_hdmiphy)) {
2207 DRM_ERROR("failed to get clock 'sclk_hdmiphy'\n");
2208 ret = PTR_ERR(res->sclk_hdmiphy);
2211 res->mout_hdmi = devm_clk_get(dev, "mout_hdmi");
2212 if (IS_ERR(res->mout_hdmi)) {
2213 DRM_ERROR("failed to get clock 'mout_hdmi'\n");
2214 ret = PTR_ERR(res->mout_hdmi);
2218 clk_set_parent(res->mout_hdmi, res->sclk_pixel);
2220 res->regul_bulk = devm_kzalloc(dev, ARRAY_SIZE(supply) *
2221 sizeof(res->regul_bulk[0]), GFP_KERNEL);
2222 if (!res->regul_bulk) {
2226 for (i = 0; i < ARRAY_SIZE(supply); ++i) {
2227 res->regul_bulk[i].supply = supply[i];
2228 res->regul_bulk[i].consumer = NULL;
2230 ret = devm_regulator_bulk_get(dev, ARRAY_SIZE(supply), res->regul_bulk);
2232 DRM_ERROR("failed to get regulators\n");
2235 res->regul_count = ARRAY_SIZE(supply);
2237 res->reg_hdmi_en = devm_regulator_get(dev, "hdmi-en");
2238 if (IS_ERR(res->reg_hdmi_en) && PTR_ERR(res->reg_hdmi_en) != -ENOENT) {
2239 DRM_ERROR("failed to get hdmi-en regulator\n");
2240 return PTR_ERR(res->reg_hdmi_en);
2242 if (!IS_ERR(res->reg_hdmi_en)) {
2243 ret = regulator_enable(res->reg_hdmi_en);
2245 DRM_ERROR("failed to enable hdmi-en regulator\n");
2249 res->reg_hdmi_en = NULL;
2253 DRM_ERROR("HDMI resource init - failed\n");
2257 static struct s5p_hdmi_platform_data *drm_hdmi_dt_parse_pdata
2258 (struct device *dev)
2260 struct device_node *np = dev->of_node;
2261 struct s5p_hdmi_platform_data *pd;
2264 pd = devm_kzalloc(dev, sizeof(*pd), GFP_KERNEL);
2268 if (!of_find_property(np, "hpd-gpio", &value)) {
2269 DRM_ERROR("no hpd gpio property found\n");
2273 pd->hpd_gpio = of_get_named_gpio(np, "hpd-gpio", 0);
2281 static struct of_device_id hdmi_match_types[] = {
2283 .compatible = "samsung,exynos5-hdmi",
2284 .data = &exynos5_hdmi_driver_data,
2286 .compatible = "samsung,exynos4210-hdmi",
2287 .data = &exynos4210_hdmi_driver_data,
2289 .compatible = "samsung,exynos4212-hdmi",
2290 .data = &exynos4212_hdmi_driver_data,
2292 .compatible = "samsung,exynos5420-hdmi",
2293 .data = &exynos5420_hdmi_driver_data,
2298 MODULE_DEVICE_TABLE (of, hdmi_match_types);
2300 static int hdmi_bind(struct device *dev, struct device *master, void *data)
2302 struct drm_device *drm_dev = data;
2303 struct hdmi_context *hdata;
2305 hdata = hdmi_display.ctx;
2306 hdata->drm_dev = drm_dev;
2308 return exynos_drm_create_enc_conn(drm_dev, &hdmi_display);
2311 static void hdmi_unbind(struct device *dev, struct device *master, void *data)
2313 struct exynos_drm_display *display = get_hdmi_display(dev);
2314 struct drm_encoder *encoder = display->encoder;
2315 struct hdmi_context *hdata = display->ctx;
2317 encoder->funcs->destroy(encoder);
2318 drm_connector_cleanup(&hdata->connector);
2321 static const struct component_ops hdmi_component_ops = {
2323 .unbind = hdmi_unbind,
2326 static struct device_node *hdmi_legacy_ddc_dt_binding(struct device *dev)
2328 const char *compatible_str = "samsung,exynos4210-hdmiddc";
2329 struct device_node *np;
2331 np = of_find_compatible_node(NULL, NULL, compatible_str);
2333 return of_get_next_parent(np);
2338 static struct device_node *hdmi_legacy_phy_dt_binding(struct device *dev)
2340 const char *compatible_str = "samsung,exynos4212-hdmiphy";
2342 return of_find_compatible_node(NULL, NULL, compatible_str);
2345 static int hdmi_probe(struct platform_device *pdev)
2347 struct device_node *ddc_node, *phy_node;
2348 struct s5p_hdmi_platform_data *pdata;
2349 struct hdmi_driver_data *drv_data;
2350 const struct of_device_id *match;
2351 struct device *dev = &pdev->dev;
2352 struct hdmi_context *hdata;
2353 struct resource *res;
2356 ret = exynos_drm_component_add(&pdev->dev, EXYNOS_DEVICE_TYPE_CONNECTOR,
2361 if (!dev->of_node) {
2363 goto err_del_component;
2366 pdata = drm_hdmi_dt_parse_pdata(dev);
2369 goto err_del_component;
2372 hdata = devm_kzalloc(dev, sizeof(struct hdmi_context), GFP_KERNEL);
2375 goto err_del_component;
2378 mutex_init(&hdata->hdmi_mutex);
2380 platform_set_drvdata(pdev, &hdmi_display);
2382 match = of_match_node(hdmi_match_types, dev->of_node);
2385 goto err_del_component;
2388 drv_data = (struct hdmi_driver_data *)match->data;
2389 hdata->type = drv_data->type;
2390 hdata->phy_confs = drv_data->phy_confs;
2391 hdata->phy_conf_count = drv_data->phy_conf_count;
2393 hdata->hpd_gpio = pdata->hpd_gpio;
2396 ret = hdmi_resources_init(hdata);
2398 DRM_ERROR("hdmi_resources_init failed\n");
2402 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
2403 hdata->regs = devm_ioremap_resource(dev, res);
2404 if (IS_ERR(hdata->regs)) {
2405 ret = PTR_ERR(hdata->regs);
2406 goto err_del_component;
2409 ret = devm_gpio_request(dev, hdata->hpd_gpio, "HPD");
2411 DRM_ERROR("failed to request HPD gpio\n");
2412 goto err_del_component;
2415 ddc_node = hdmi_legacy_ddc_dt_binding(dev);
2417 goto out_get_ddc_adpt;
2419 /* DDC i2c driver */
2420 ddc_node = of_parse_phandle(dev->of_node, "ddc", 0);
2422 DRM_ERROR("Failed to find ddc node in device tree\n");
2424 goto err_del_component;
2428 hdata->ddc_adpt = of_find_i2c_adapter_by_node(ddc_node);
2429 if (!hdata->ddc_adpt) {
2430 DRM_ERROR("Failed to get ddc i2c adapter by node\n");
2431 return -EPROBE_DEFER;
2434 phy_node = hdmi_legacy_phy_dt_binding(dev);
2436 goto out_get_phy_port;
2438 /* hdmiphy i2c driver */
2439 phy_node = of_parse_phandle(dev->of_node, "phy", 0);
2441 DRM_ERROR("Failed to find hdmiphy node in device tree\n");
2447 if (drv_data->is_apb_phy) {
2448 hdata->regs_hdmiphy = of_iomap(phy_node, 0);
2449 if (!hdata->regs_hdmiphy) {
2450 DRM_ERROR("failed to ioremap hdmi phy\n");
2455 hdata->hdmiphy_port = of_find_i2c_device_by_node(phy_node);
2456 if (!hdata->hdmiphy_port) {
2457 DRM_ERROR("Failed to get hdmi phy i2c client\n");
2458 ret = -EPROBE_DEFER;
2463 hdata->irq = gpio_to_irq(hdata->hpd_gpio);
2464 if (hdata->irq < 0) {
2465 DRM_ERROR("failed to get GPIO irq\n");
2470 hdata->hpd = gpio_get_value(hdata->hpd_gpio);
2472 INIT_DELAYED_WORK(&hdata->hotplug_work, hdmi_hotplug_work_func);
2474 ret = devm_request_threaded_irq(dev, hdata->irq, NULL,
2475 hdmi_irq_thread, IRQF_TRIGGER_RISING |
2476 IRQF_TRIGGER_FALLING | IRQF_ONESHOT,
2479 DRM_ERROR("failed to register hdmi interrupt\n");
2483 hdata->pmureg = syscon_regmap_lookup_by_phandle(dev->of_node,
2484 "samsung,syscon-phandle");
2485 if (IS_ERR(hdata->pmureg)) {
2486 DRM_ERROR("syscon regmap lookup failed.\n");
2487 ret = -EPROBE_DEFER;
2491 pm_runtime_enable(dev);
2492 hdmi_display.ctx = hdata;
2494 ret = component_add(&pdev->dev, &hdmi_component_ops);
2496 goto err_disable_pm_runtime;
2500 err_disable_pm_runtime:
2501 pm_runtime_disable(dev);
2504 if (hdata->hdmiphy_port)
2505 put_device(&hdata->hdmiphy_port->dev);
2507 put_device(&hdata->ddc_adpt->dev);
2510 exynos_drm_component_del(&pdev->dev, EXYNOS_DEVICE_TYPE_CONNECTOR);
2515 static int hdmi_remove(struct platform_device *pdev)
2517 struct hdmi_context *hdata = hdmi_display.ctx;
2519 cancel_delayed_work_sync(&hdata->hotplug_work);
2521 if (hdata->res.reg_hdmi_en)
2522 regulator_disable(hdata->res.reg_hdmi_en);
2524 if (hdata->hdmiphy_port)
2525 put_device(&hdata->hdmiphy_port->dev);
2526 put_device(&hdata->ddc_adpt->dev);
2528 pm_runtime_disable(&pdev->dev);
2529 component_del(&pdev->dev, &hdmi_component_ops);
2531 exynos_drm_component_del(&pdev->dev, EXYNOS_DEVICE_TYPE_CONNECTOR);
2535 struct platform_driver hdmi_driver = {
2536 .probe = hdmi_probe,
2537 .remove = hdmi_remove,
2539 .name = "exynos-hdmi",
2540 .owner = THIS_MODULE,
2541 .of_match_table = hdmi_match_types,