1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3 * Copyright (C) 2020 Rockchip Electronics Co., Ltd
4 *
5 * Author: Wyon Bi <bivvy.bi@rock-chips.com>
6 */
7
8 #include <dm.h>
9 #include <dm/device-internal.h>
10 #include <asm/unaligned.h>
11 #include <linux/math64.h>
12
13 #include "rk628_hdmirx.h"
14 #include "rk628_cru.h"
15
hdmirx_phy_write(struct rk628_hdmirx * hdmirx,u32 offset,u32 val)16 static void hdmirx_phy_write(struct rk628_hdmirx *hdmirx, u32 offset, u32 val)
17 {
18 struct rk628 *rk628 = hdmirx->parent;
19
20 rk628_i2c_write(rk628, HDMI_RX_I2CM_PHYG3_ADDRESS, offset);
21 rk628_i2c_write(rk628, HDMI_RX_I2CM_PHYG3_DATAO, val);
22 rk628_i2c_write(rk628, HDMI_RX_I2CM_PHYG3_OPERATION, 1);
23 }
24
rk628_hdmirx_reset_control_assert(struct rk628 * rk628)25 static void rk628_hdmirx_reset_control_assert(struct rk628 *rk628)
26 {
27 /* presetn_hdmirx */
28 rk628_i2c_write(rk628, CRU_SOFTRST_CON02, 0x40004);
29 /* resetn_hdmirx_pon */
30 rk628_i2c_write(rk628, CRU_SOFTRST_CON02, 0x10001000);
31 }
32
rk628_hdmirx_reset_control_deassert(struct rk628 * rk628)33 static void rk628_hdmirx_reset_control_deassert(struct rk628 *rk628)
34 {
35 /* presetn_hdmirx */
36 rk628_i2c_write(rk628, CRU_SOFTRST_CON02, 0x40000);
37 /* resetn_hdmirx_pon */
38 rk628_i2c_write(rk628, CRU_SOFTRST_CON02, 0x10000000);
39 }
40
rk628_hdmirx_ctrl_enable(struct rk628_hdmirx * hdmirx)41 static void rk628_hdmirx_ctrl_enable(struct rk628_hdmirx *hdmirx)
42 {
43 struct rk628 *rk628 = hdmirx->parent;
44
45 rk628_i2c_update_bits(rk628, GRF_SYSTEM_CON0,
46 SW_INPUT_MODE_MASK,
47 SW_INPUT_MODE(INPUT_MODE_HDMI));
48
49 rk628_i2c_write(rk628, HDMI_RX_HDMI20_CONTROL, 0x10001f11);
50 /* Support DVI mode */
51 rk628_i2c_write(rk628, HDMI_RX_HDMI_TIMER_CTRL, 0xa78);
52 rk628_i2c_write(rk628, HDMI_RX_HDMI_MODE_RECOVER, 0x00000021);
53 rk628_i2c_write(rk628, HDMI_RX_PDEC_CTRL, 0xbfff8011);
54 rk628_i2c_write(rk628, HDMI_RX_PDEC_ASP_CTRL, 0x00000040);
55 rk628_i2c_write(rk628, HDMI_RX_HDMI_RESMPL_CTRL, 0x00000001);
56 rk628_i2c_write(rk628, HDMI_RX_HDMI_SYNC_CTRL, 0x00000014);
57 rk628_i2c_write(rk628, HDMI_RX_PDEC_ERR_FILTER, 0x00000008);
58 rk628_i2c_write(rk628, HDMI_RX_SCDC_I2CCONFIG, 0x01000000);
59 rk628_i2c_write(rk628, HDMI_RX_SCDC_CONFIG, 0x00000001);
60 rk628_i2c_write(rk628, HDMI_RX_SCDC_WRDATA0, 0xabcdef01);
61 rk628_i2c_write(rk628, HDMI_RX_CHLOCK_CONFIG, 0x0030c15c);
62 rk628_i2c_write(rk628, HDMI_RX_HDMI_ERROR_PROTECT, 0x000d0c98);
63 rk628_i2c_write(rk628, HDMI_RX_MD_HCTRL1, 0x00000010);
64 /*
65 * rk628f should set start of horizontal measurement to 3/8 of frame duration
66 * to pass hdmi 2.0 cts
67 */
68 if (rk628->version == RK628D_VERSION)
69 rk628_i2c_write(rk628, HDMI_RX_MD_HCTRL2, 0x00001738);
70 else
71 rk628_i2c_write(rk628, HDMI_RX_MD_HCTRL2, 0x0000173a);
72 rk628_i2c_write(rk628, HDMI_RX_MD_VCTRL, 0x00000002);
73 rk628_i2c_write(rk628, HDMI_RX_MD_VTH, 0x0000073a);
74 rk628_i2c_write(rk628, HDMI_RX_MD_IL_POL, 0x00000004);
75 rk628_i2c_write(rk628, HDMI_RX_PDEC_ACRM_CTRL, 0x00000000);
76 rk628_i2c_write(rk628, HDMI_RX_HDMI_DCM_CTRL, 0x00040414);
77 rk628_i2c_write(rk628, HDMI_RX_HDMI_CKM_EVLTM, 0x00103e70);
78 rk628_i2c_write(rk628, HDMI_RX_HDMI_CKM_F, 0x0c1c0b54);
79 rk628_i2c_write(rk628, HDMI_RX_HDMI_RESMPL_CTRL, 0x00000001);
80
81 rk628_i2c_update_bits(rk628, HDMI_RX_HDCP_SETTINGS,
82 HDMI_RESERVED_MASK |
83 FAST_I2C_MASK |
84 ONE_DOT_ONE_MASK |
85 FAST_REAUTH_MASK,
86 HDMI_RESERVED(1) |
87 FAST_I2C(0) |
88 ONE_DOT_ONE(1) |
89 FAST_REAUTH(1));
90 }
91
rk628_hdmirx_phy_enable(struct rk628_hdmirx * hdmirx,bool is_hdmi2)92 static void rk628_hdmirx_phy_enable(struct rk628_hdmirx *hdmirx, bool is_hdmi2)
93 {
94 hdmirx_phy_write(hdmirx, 0x02, 0x1860);
95 hdmirx_phy_write(hdmirx, 0x03, 0x0060);
96 hdmirx_phy_write(hdmirx, 0x27, 0x1c94);
97 hdmirx_phy_write(hdmirx, 0x28, 0x3713);
98 hdmirx_phy_write(hdmirx, 0x29, 0x24da);
99 hdmirx_phy_write(hdmirx, 0x2a, 0x5492);
100 hdmirx_phy_write(hdmirx, 0x2b, 0x4b0d);
101 hdmirx_phy_write(hdmirx, 0x2d, 0x008c);
102 hdmirx_phy_write(hdmirx, 0x2e, 0x0001);
103
104 if (is_hdmi2)
105 hdmirx_phy_write(hdmirx, 0x0e, 0x0108);
106 else
107 hdmirx_phy_write(hdmirx, 0x0e, 0x0008);
108 }
109
rk628f_hdmirx_phy_power_on(struct rk628_hdmirx * hdmirx)110 static void rk628f_hdmirx_phy_power_on(struct rk628_hdmirx *hdmirx)
111 {
112 struct rk628 *rk628 = hdmirx->parent;
113
114 /* power down phy */
115 rk628_i2c_write(rk628, GRF_SW_HDMIRXPHY_CRTL, 0x17);
116 udelay(30);
117 rk628_i2c_write(rk628, GRF_SW_HDMIRXPHY_CRTL, 0x15);
118 /* init phy i2c */
119 rk628_i2c_write(rk628, HDMI_RX_SNPS_PHYG3_CTRL, 0);
120 rk628_i2c_write(rk628, HDMI_RX_I2CM_PHYG3_SS_CNTS, 0x018c01d2);
121 rk628_i2c_write(rk628, HDMI_RX_I2CM_PHYG3_FS_HCNT, 0x003c0081);
122 rk628_i2c_write(rk628, HDMI_RX_I2CM_PHYG3_MODE, 1);
123 rk628_i2c_write(rk628, GRF_SW_HDMIRXPHY_CRTL, 0x11);
124 /* enable rx phy */
125 rk628_hdmirx_phy_enable(hdmirx, hdmirx->is_hdmi2);
126 rk628_i2c_write(rk628, GRF_SW_HDMIRXPHY_CRTL, 0x14);
127 }
128
rk628_hdmirx_get_timing(struct rk628_hdmirx * hdmirx)129 static void rk628_hdmirx_get_timing(struct rk628_hdmirx *hdmirx)
130 {
131 u32 hact, vact, htotal, vtotal, fps, status;
132 u32 val = 0;
133 u32 modetclk_cnt_hs, modetclk_cnt_vs, hs, vs;
134 u32 hofs_pix, hbp, hfp, vbp, vfp;
135 u32 tmds_clk, tmdsclk_cnt, modetclk_hz;
136 u64 tmp_data;
137 u32 interlaced;
138 u32 hfrontporch, hsync, hbackporch, vfrontporch, vsync, vbackporch;
139 struct rk628 *rk628 = hdmirx->parent;
140 unsigned long long pixelclock, clock;
141 unsigned long flags = 0;
142
143 rk628_i2c_read(rk628, HDMI_RX_SCDC_REGS1, &val);
144 status = val;
145
146 rk628_i2c_read(rk628, HDMI_RX_MD_STS, &val);
147 interlaced = val & ILACE_STS ? 1 : 0;
148
149 rk628_i2c_read(rk628, HDMI_RX_MD_HACT_PX, &val);
150 hact = val & 0xffff;
151 rk628_i2c_read(rk628, HDMI_RX_MD_VAL, &val);
152 vact = val & 0xffff;
153 rk628_i2c_read(rk628, HDMI_RX_MD_HT1, &val);
154 htotal = (val >> 16) & 0xffff;
155 rk628_i2c_read(rk628, HDMI_RX_MD_VTL, &val);
156 vtotal = val & 0xffff;
157 rk628_i2c_read(rk628, HDMI_RX_MD_HT1, &val);
158 hofs_pix = val & 0xffff;
159 rk628_i2c_read(rk628, HDMI_RX_MD_VOL, &val);
160 vbp = (val & 0xffff) + 1;
161
162 modetclk_hz = rk628_cru_clk_get_rate(rk628, CGU_CLK_CPLL) / 24;
163 rk628_i2c_read(rk628, HDMI_RX_HDMI_CKM_RESULT, &val);
164 tmdsclk_cnt = val & 0xffff;
165 tmp_data = tmdsclk_cnt;
166 /* rk628d modet clk is always 49.5m, rk628f's freq changes with ref clock */
167 if (hdmirx->parent->version != RK628D_VERSION)
168 tmp_data = ((tmp_data * modetclk_hz) + MODETCLK_CNT_NUM / 2);
169 else
170 tmp_data = ((tmp_data * MODETCLK_HZ) + MODETCLK_CNT_NUM / 2);
171 do_div(tmp_data, MODETCLK_CNT_NUM);
172 tmds_clk = tmp_data;
173 if (!(htotal && vtotal)) {
174 printf("rk628_hdmirx timing err, htotal:%d, vtotal:%d\n", htotal, vtotal);
175 return;
176 }
177 /* rk628f should get exact frame rate frequency to pass hdmi2.0 cts */
178 if (hdmirx->parent->version != RK628D_VERSION)
179 fps = tmds_clk / (htotal * vtotal);
180 else
181 fps = (tmds_clk + (htotal * vtotal) / 2) / (htotal * vtotal);
182
183 rk628_i2c_read(rk628, HDMI_RX_MD_HT0, &val);
184 modetclk_cnt_hs = val & 0xffff;
185 hs = (tmdsclk_cnt * modetclk_cnt_hs + MODETCLK_CNT_NUM / 2) /
186 MODETCLK_CNT_NUM;
187
188 rk628_i2c_read(rk628, HDMI_RX_MD_VSC, &val);
189 modetclk_cnt_vs = val & 0xffff;
190 vs = (tmdsclk_cnt * modetclk_cnt_vs + MODETCLK_CNT_NUM / 2) /
191 MODETCLK_CNT_NUM;
192 vs = (vs + htotal / 2) / htotal;
193
194 rk628_i2c_read(rk628, HDMI_RX_HDMI_STS, &val);
195 if (val & BIT(8))
196 flags |= DRM_MODE_FLAG_PHSYNC;
197 else
198 flags |= DRM_MODE_FLAG_NHSYNC;
199 if (val & BIT(9))
200 flags |= DRM_MODE_FLAG_PVSYNC;
201 else
202 flags |= DRM_MODE_FLAG_NVSYNC;
203
204 if ((hofs_pix < hs) || (htotal < (hact + hofs_pix)) ||
205 (vtotal < (vact + vs + vbp))) {
206 printf("rk628_hdmi timing err, total:%dx%d, act:%dx%d, hofs:%d, hs:%d, vs:%d, vbp:%d\n",
207 htotal, vtotal, hact, vact, hofs_pix, hs, vs, vbp);
208 return;
209 }
210
211 hbp = hofs_pix - hs;
212 hfp = htotal - hact - hofs_pix;
213 vfp = vtotal - vact - vs - vbp;
214
215 printf("rk628_hdmirx cnt_num:%d, tmds_cnt:%d, hs_cnt:%d, vs_cnt:%d, hofs:%d\n",
216 MODETCLK_CNT_NUM, tmdsclk_cnt, modetclk_cnt_hs, modetclk_cnt_vs, hofs_pix);
217
218 hfrontporch = hfp;
219 hsync = hs;
220 hbackporch = hbp;
221 vfrontporch = vfp;
222 vsync = vs;
223 vbackporch = vbp;
224 /* rk628f should get exact pixel clk frequency to pass hdmi2.0 cts */
225 if (hdmirx->parent->version != RK628D_VERSION)
226 pixelclock = tmds_clk;
227 else
228 pixelclock = htotal * vtotal * fps;
229
230 if (interlaced == 1) {
231 vsync = vsync + 1;
232 pixelclock /= 2;
233 }
234
235 clock = pixelclock;
236 do_div(clock, 1000);
237
238 hdmirx->mode.clock = clock;
239 hdmirx->mode.hdisplay = hact;
240 hdmirx->mode.hstart = hdmirx->mode.hdisplay + hfrontporch;
241 hdmirx->mode.hend = hdmirx->mode.hstart + hsync;
242 hdmirx->mode.htotal = hdmirx->mode.hend + hbackporch;
243
244 hdmirx->mode.vdisplay = vact;
245 hdmirx->mode.vstart = hdmirx->mode.vdisplay + vfrontporch;
246 hdmirx->mode.vend = hdmirx->mode.vstart + vsync;
247 hdmirx->mode.vtotal = hdmirx->mode.vend + vbackporch;
248 hdmirx->mode.flags = flags;
249
250 printf("rk628_hdmirx SCDC_REGS1:%#x, act:%dx%d, total:%dx%d, fps:%d, pixclk:%llu\n",
251 status, hact, vact, htotal, vtotal, fps, pixelclock);
252 printf("rk628_hdmirx hfp:%d, hs:%d, hbp:%d, vfp:%d, vs:%d, vbp:%d, interlace:%d\n",
253 hfrontporch, hsync, hbackporch, vfrontporch, vsync, vbackporch, interlaced);
254 }
255
rk628_hdmirx_phy_setup(struct rk628_hdmirx * hdmirx)256 static int rk628_hdmirx_phy_setup(struct rk628_hdmirx *hdmirx)
257 {
258 u32 i, cnt, val = 0, status, vs;
259 u32 width, height, frame_width, frame_height, tmdsclk_cnt, modetclk_cnt_hs, modetclk_cnt_vs;
260 struct drm_display_mode *src_mode;
261 struct rk628 *rk628 = hdmirx->parent;
262 u32 f, tmds_rate;
263 bool timing_detected;
264
265 src_mode = &rk628->src_mode;
266 f = src_mode->clock;
267 /*
268 * force 594m mode to yuv420 format.
269 * bit30 is used to indicate whether it is yuv420 format.
270 */
271 if (hdmirx->src_mode_4K_yuv420) {
272 f /= 2;
273 f |= BIT(30);
274 }
275
276 tmds_rate = src_mode->clock;
277
278 if (hdmirx->src_mode_4K_yuv420)
279 tmds_rate /= 2;
280 if (hdmirx->src_depth_10bit)
281 tmds_rate = tmds_rate * 10 / 8;
282
283 if (tmds_rate >= 340000)
284 hdmirx->is_hdmi2 = true;
285 else
286 hdmirx->is_hdmi2 = false;
287
288 /* enable scramble in hdmi2.0 mode */
289 if (hdmirx->is_hdmi2)
290 rk628_i2c_write(rk628, HDMI_RX_HDMI20_CONTROL, 0x10001f13);
291
292 for (i = 0; i < RXPHY_CFG_MAX_TIMES; i++) {
293 rk628f_hdmirx_phy_power_on(hdmirx);
294 cnt = 0;
295
296 do {
297 cnt++;
298
299 mdelay(100);
300 rk628_i2c_read(rk628, HDMI_RX_MD_HACT_PX, &val);
301 width = val & 0xffff;
302 rk628_i2c_read(rk628, HDMI_RX_MD_HT1, &val);
303 frame_width = (val >> 16) & 0xffff;
304
305 rk628_i2c_read(rk628, HDMI_RX_MD_VAL, &val);
306 height = val & 0xffff;
307 rk628_i2c_read(rk628, HDMI_RX_MD_VTL, &val);
308 frame_height = val & 0xffff;
309
310 rk628_i2c_read(rk628, HDMI_RX_HDMI_CKM_RESULT, &val);
311 tmdsclk_cnt = val & 0xffff;
312 rk628_i2c_read(rk628, HDMI_RX_MD_HT0, &val);
313 modetclk_cnt_hs = val & 0xffff;
314 rk628_i2c_read(rk628, HDMI_RX_MD_VSC, &val);
315 modetclk_cnt_vs = val & 0xffff;
316
317 if (frame_width) {
318 vs = (tmdsclk_cnt * modetclk_cnt_vs + MODETCLK_CNT_NUM / 2) /
319 MODETCLK_CNT_NUM;
320 vs = (vs + frame_width / 2) / frame_width;
321 } else {
322 vs = 0;
323 }
324
325 if (width && height && frame_width && frame_height && tmdsclk_cnt &&
326 modetclk_cnt_hs && modetclk_cnt_vs && vs)
327 timing_detected = true;
328 else
329 timing_detected = false;
330
331 rk628_i2c_read(rk628, HDMI_RX_SCDC_REGS1, &val);
332 status = val;
333
334 printf("rk628_hdmirx tmdsclk_cnt:%d, modetclk_cnt_hs:%d, modetclk_cnt_vs:%d,vs:%d\n",
335 tmdsclk_cnt, modetclk_cnt_hs, modetclk_cnt_vs, vs);
336 printf("rk628_hdmirx read wxh:%dx%d, total:%dx%d, SCDC_REGS1:%#x, cnt:%d\n",
337 width, height, frame_width, frame_height, status, cnt);
338
339 if (cnt >= 15)
340 break;
341 } while (((status & 0xfff) != 0xf00) || !timing_detected);
342
343 if (((status & 0xfff) != 0xf00) || (((status >> 16) > 0xc000) &&
344 hdmirx->parent->version != RK628D_VERSION)) {
345 printf("rk628_hdmirx %s hdmi rxphy lock failed, retry:%d, status:0x%x\n",
346 __func__, i, status);
347 if (((status >> 16) > 0xc000))
348 printf("rk628_hdmirx ((status >> 16) > 0xc000)\n");
349 continue;
350 } else {
351 rk628_hdmirx_get_timing(hdmirx);
352
353 if (hdmirx->mode.flags & DRM_MODE_FLAG_INTERLACE) {
354 printf("rk628_hdmirx interlace mode is unsupported\n");
355 continue;
356 }
357
358 if (hdmirx->mode.clock == 0)
359 return -EINVAL;
360
361 src_mode->clock = hdmirx->mode.clock;
362 src_mode->hdisplay = hdmirx->mode.hdisplay;
363 src_mode->hsync_start = hdmirx->mode.hstart;
364 src_mode->hsync_end = hdmirx->mode.hend;
365 src_mode->htotal = hdmirx->mode.htotal;
366
367 src_mode->vdisplay = hdmirx->mode.vdisplay;
368 src_mode->vsync_start = hdmirx->mode.vstart;
369 src_mode->vsync_end = hdmirx->mode.vend;
370 src_mode->vtotal = hdmirx->mode.vtotal;
371 src_mode->flags = hdmirx->mode.flags;
372
373 break;
374 }
375 }
376
377 if (i == RXPHY_CFG_MAX_TIMES) {
378 hdmirx->phy_lock = false;
379 return -1;
380 }
381
382 hdmirx->phy_lock = true;
383
384 return 0;
385 }
386
rk628_hdmirx_phy_set_clrdpt(struct rk628_hdmirx * hdmirx,bool is_8bit)387 static void rk628_hdmirx_phy_set_clrdpt(struct rk628_hdmirx *hdmirx, bool is_8bit)
388 {
389 if (is_8bit)
390 hdmirx_phy_write(hdmirx, 0x03, 0x0000);
391 else
392 hdmirx_phy_write(hdmirx, 0x03, 0x0060);
393 }
394
rk628_hdmirx_phy_prepclk_cfg(struct rk628_hdmirx * hdmirx)395 static void rk628_hdmirx_phy_prepclk_cfg(struct rk628_hdmirx *hdmirx)
396 {
397 struct rk628 *rk628 = hdmirx->parent;
398 u32 format = 0;
399 bool is_clrdpt_8bit = false;
400
401 rk628_i2c_read(rk628, HDMI_RX_PDEC_AVI_PB, &format);
402 format = (format & VIDEO_FORMAT) >> 5;
403
404 /* yuv420 should set phy color depth 8bit */
405 if (format == 3)
406 is_clrdpt_8bit = true;
407
408 rk628_i2c_read(rk628, HDMI_RX_PDEC_GCP_AVMUTE, &format);
409 format = (format & PKTDEC_GCP_CD_MASK) >> 4;
410
411 /* 10bit color depth should set phy color depth 8bit */
412 if (format == 5)
413 is_clrdpt_8bit = true;
414
415 rk628_hdmirx_phy_set_clrdpt(hdmirx, is_clrdpt_8bit);
416 }
417
rk628_check_signal_get(struct rk628_hdmirx * hdmirx)418 static bool rk628_check_signal_get(struct rk628_hdmirx *hdmirx)
419 {
420 struct rk628 *rk628 = hdmirx->parent;
421 u32 hact, vact, val = 0;
422
423 rk628_i2c_read(rk628, HDMI_RX_MD_HACT_PX, &val);
424 hact = val & 0xffff;
425 rk628_i2c_read(rk628, HDMI_RX_MD_VAL, &val);
426 vact = val & 0xffff;
427
428 if (!hact || !vact) {
429 printf("rk628_hdmirx no signal\n");
430 return false;
431 }
432
433 return true;
434 }
435
rk628_hdmirx_video_unmute(struct rk628_hdmirx * hdmirx,u8 unmute)436 static void rk628_hdmirx_video_unmute(struct rk628_hdmirx *hdmirx, u8 unmute)
437 {
438 struct rk628 *rk628 = hdmirx->parent;
439
440 rk628_i2c_update_bits(rk628, HDMI_RX_DMI_DISABLE_IF, VID_ENABLE_MASK, VID_ENABLE(unmute));
441 }
442
rk628_hdmirx_get_input_format(struct rk628_hdmirx * hdmirx)443 static u32 rk628_hdmirx_get_input_format(struct rk628_hdmirx *hdmirx)
444 {
445 struct rk628 *rk628 = hdmirx->parent;
446 u32 val = 0, format = 0, avi_pb = 0;
447 u8 i;
448 u8 cnt = 0, max_cnt = 2;
449
450 rk628_i2c_read(rk628, HDMI_RX_PDEC_ISTS, &val);
451 if (val & AVI_RCV_ISTS) {
452 for (i = 0; i < 100; i++) {
453 rk628_i2c_read(rk628, HDMI_RX_PDEC_AVI_PB, &format);
454 dev_dbg(hdmirx->dev, "%s PDEC_AVI_PB:%#x\n", __func__, format);
455 if (format && format == avi_pb) {
456 if (++cnt >= max_cnt)
457 break;
458 } else {
459 cnt = 0;
460 avi_pb = format;
461 }
462 mdelay(30);
463 }
464 format = (avi_pb & VIDEO_FORMAT) >> 5;
465 switch (format) {
466 case 0:
467 hdmirx->input_format = BUS_FMT_RGB;
468 break;
469 case 1:
470 hdmirx->input_format = BUS_FMT_YUV422;
471 break;
472 case 2:
473 hdmirx->input_format = BUS_FMT_YUV444;
474 break;
475 case 3:
476 hdmirx->input_format = BUS_FMT_YUV420;
477 break;
478 default:
479 hdmirx->input_format = BUS_FMT_RGB;
480 break;
481 }
482
483 rk628_i2c_write(rk628, HDMI_RX_PDEC_ICLR, AVI_RCV_ISTS);
484 }
485
486 return hdmirx->input_format;
487 }
488
rk628_hdmirx_init(struct rk628 * rk628)489 static int rk628_hdmirx_init(struct rk628 *rk628)
490 {
491 struct rk628_hdmirx *hdmirx = &rk628->hdmirx;
492
493 hdmirx->parent = rk628;
494
495 hdmirx->src_mode_4K_yuv420 = dev_read_bool(rk628->dev, "src-mode-4k-yuv420");
496
497 hdmirx->src_depth_10bit = dev_read_bool(rk628->dev, "src-depth-10bit");
498
499 /* HDMIRX IOMUX */
500 rk628_i2c_write(rk628, GRF_GPIO1AB_SEL_CON, HIWORD_UPDATE(0x7, 10, 8));
501 //i2s pinctrl
502 rk628_i2c_write(rk628, GRF_GPIO0AB_SEL_CON, 0x155c155c);
503
504 /* enable */
505 rk628_i2c_write(rk628, GRF_GPIO1AB_SEL_CON, HIWORD_UPDATE(0, 0, 0));
506 rk628_i2c_write(rk628, GRF_GPIO3AB_SEL_CON, HIWORD_UPDATE(1, 14, 14));
507
508 /* if GVI and HDMITX OUT, HDMIRX missing signal */
509 rk628_i2c_update_bits(rk628, GRF_SYSTEM_CON0,
510 SW_OUTPUT_RGB_MODE_MASK,
511 SW_OUTPUT_RGB_MODE(OUTPUT_MODE_RGB >> 3));
512
513 rk628_i2c_update_bits(rk628, GRF_SYSTEM_CON0,
514 SW_INPUT_MODE_MASK, SW_INPUT_MODE(INPUT_MODE_HDMI));
515 return 0;
516 }
517
rk628_hdmirx_enable(struct rk628 * rk628)518 int rk628_hdmirx_enable(struct rk628 *rk628)
519 {
520 int ret;
521
522 rk628_hdmirx_init(rk628);
523
524 rk628_hdmirx_reset_control_assert(rk628);
525 udelay(40);
526 rk628_hdmirx_reset_control_deassert(rk628);
527 udelay(40);
528
529 rk628_hdmirx_ctrl_enable(&rk628->hdmirx);
530 ret = rk628_hdmirx_phy_setup(&rk628->hdmirx);
531 if (ret < 0) {
532 dev_err(hdmirx->dev, "hdmirx channel can't lock!\n");
533 return -EINVAL;
534 }
535
536 rk628_hdmirx_get_input_format(&rk628->hdmirx);
537 if (rk628->version != RK628D_VERSION)
538 rk628_hdmirx_phy_prepclk_cfg(&rk628->hdmirx);
539
540 if (!rk628_check_signal_get(&rk628->hdmirx) || !rk628->hdmirx.phy_lock)
541 return -EINVAL;
542
543 printf("rk628_hdmirx success\n");
544
545 rk628_hdmirx_video_unmute(&rk628->hdmirx, 1);
546
547 return 0;
548 }
549