xref: /openbmc/linux/drivers/gpu/drm/meson/meson_venc.c (revision 664dba66)
11ccea77eSThomas Gleixner // SPDX-License-Identifier: GPL-2.0-or-later
2bbbe775eSNeil Armstrong /*
3bbbe775eSNeil Armstrong  * Copyright (C) 2016 BayLibre, SAS
4bbbe775eSNeil Armstrong  * Author: Neil Armstrong <narmstrong@baylibre.com>
5bbbe775eSNeil Armstrong  * Copyright (C) 2015 Amlogic, Inc. All rights reserved.
6bbbe775eSNeil Armstrong  */
7bbbe775eSNeil Armstrong 
8*664dba66SArnd Bergmann #include <linux/bitfield.h>
966620f48SSam Ravnborg #include <linux/export.h>
1051fc01a0SNeil Armstrong #include <linux/iopoll.h>
1166620f48SSam Ravnborg 
1266620f48SSam Ravnborg #include <drm/drm_modes.h>
1366620f48SSam Ravnborg 
14bbbe775eSNeil Armstrong #include "meson_drv.h"
1566620f48SSam Ravnborg #include "meson_registers.h"
16bbbe775eSNeil Armstrong #include "meson_venc.h"
17bbbe775eSNeil Armstrong #include "meson_vpp.h"
18bbbe775eSNeil Armstrong 
192021d5b7SNeil Armstrong /**
202021d5b7SNeil Armstrong  * DOC: Video Encoder
212021d5b7SNeil Armstrong  *
22bbbe775eSNeil Armstrong  * VENC Handle the pixels encoding to the output formats.
23bbbe775eSNeil Armstrong  * We handle the following encodings :
242021d5b7SNeil Armstrong  *
25bbbe775eSNeil Armstrong  * - CVBS Encoding via the ENCI encoder and VDAC digital to analog converter
26bbbe775eSNeil Armstrong  * - TMDS/HDMI Encoding via ENCI_DIV and ENCP
27bbbe775eSNeil Armstrong  * - Setup of more clock rates for HDMI modes
28335e3713SNeil Armstrong  *
29335e3713SNeil Armstrong  * What is missing :
302021d5b7SNeil Armstrong  *
31bbbe775eSNeil Armstrong  * - LCD Panel encoding via ENCL
32bbbe775eSNeil Armstrong  * - TV Panel encoding via ENCT
33335e3713SNeil Armstrong  *
34335e3713SNeil Armstrong  * VENC paths :
352021d5b7SNeil Armstrong  *
362021d5b7SNeil Armstrong  * .. code::
372021d5b7SNeil Armstrong  *
38335e3713SNeil Armstrong  *          _____   _____   ____________________
39335e3713SNeil Armstrong  *   vd1---|     |-|     | | VENC     /---------|----VDAC
402021d5b7SNeil Armstrong  *   vd2---| VIU |-| VPP |-|-----ENCI/-ENCI_DVI-|-|
41335e3713SNeil Armstrong  *   osd1--|     |-|     | | \                  | X--HDMI-TX
422021d5b7SNeil Armstrong  *   osd2--|_____|-|_____| |  |\-ENCP--ENCP_DVI-|-|
43335e3713SNeil Armstrong  *                         |  |                 |
44335e3713SNeil Armstrong  *                         |  \--ENCL-----------|----LVDS
45335e3713SNeil Armstrong  *                         |____________________|
46335e3713SNeil Armstrong  *
47335e3713SNeil Armstrong  * The ENCI is designed for PAl or NTSC encoding and can go through the VDAC
48335e3713SNeil Armstrong  * directly for CVBS encoding or through the ENCI_DVI encoder for HDMI.
49335e3713SNeil Armstrong  * The ENCP is designed for Progressive encoding but can also generate
5067a175a9SBhaskar Chowdhury  * 1080i interlaced pixels, and was initially designed to encode pixels for
51335e3713SNeil Armstrong  * VDAC to output RGB ou YUV analog outputs.
52335e3713SNeil Armstrong  * It's output is only used through the ENCP_DVI encoder for HDMI.
53335e3713SNeil Armstrong  * The ENCL LVDS encoder is not implemented.
54335e3713SNeil Armstrong  *
55335e3713SNeil Armstrong  * The ENCI and ENCP encoders needs specially defined parameters for each
56335e3713SNeil Armstrong  * supported mode and thus cannot be determined from standard video timings.
57335e3713SNeil Armstrong  *
58335e3713SNeil Armstrong  * The ENCI end ENCP DVI encoders are more generic and can generate any timings
59335e3713SNeil Armstrong  * from the pixel data generated by ENCI or ENCP, so can use the standard video
60335e3713SNeil Armstrong  * timings are source for HW parameters.
61bbbe775eSNeil Armstrong  */
62bbbe775eSNeil Armstrong 
630c931a29SNeil Armstrong /* HHI Registers */
642bcd3ecaSNeil Armstrong #define HHI_GCLK_MPEG2		0x148 /* 0x52 offset in data sheet */
650c931a29SNeil Armstrong #define HHI_VDAC_CNTL0		0x2F4 /* 0xbd offset in data sheet */
66e1012141SJulien Masson #define HHI_VDAC_CNTL0_G12A	0x2EC /* 0xbb offset in data sheet */
670c931a29SNeil Armstrong #define HHI_VDAC_CNTL1		0x2F8 /* 0xbe offset in data sheet */
68e1012141SJulien Masson #define HHI_VDAC_CNTL1_G12A	0x2F0 /* 0xbc offset in data sheet */
690c931a29SNeil Armstrong #define HHI_HDMI_PHY_CNTL0	0x3a0 /* 0xe8 offset in data sheet */
700c931a29SNeil Armstrong 
71bbbe775eSNeil Armstrong struct meson_cvbs_enci_mode meson_cvbs_enci_pal = {
72bbbe775eSNeil Armstrong 	.mode_tag = MESON_VENC_MODE_CVBS_PAL,
73bbbe775eSNeil Armstrong 	.hso_begin = 3,
74bbbe775eSNeil Armstrong 	.hso_end = 129,
75bbbe775eSNeil Armstrong 	.vso_even = 3,
76bbbe775eSNeil Armstrong 	.vso_odd = 260,
77bbbe775eSNeil Armstrong 	.macv_max_amp = 7,
78bbbe775eSNeil Armstrong 	.video_prog_mode = 0xff,
79bbbe775eSNeil Armstrong 	.video_mode = 0x13,
80bbbe775eSNeil Armstrong 	.sch_adjust = 0x28,
81bbbe775eSNeil Armstrong 	.yc_delay = 0x343,
82bbbe775eSNeil Armstrong 	.pixel_start = 251,
83bbbe775eSNeil Armstrong 	.pixel_end = 1691,
84bbbe775eSNeil Armstrong 	.top_field_line_start = 22,
85bbbe775eSNeil Armstrong 	.top_field_line_end = 310,
86bbbe775eSNeil Armstrong 	.bottom_field_line_start = 23,
87bbbe775eSNeil Armstrong 	.bottom_field_line_end = 311,
88bbbe775eSNeil Armstrong 	.video_saturation = 9,
89bbbe775eSNeil Armstrong 	.video_contrast = 0,
90bbbe775eSNeil Armstrong 	.video_brightness = 0,
91bbbe775eSNeil Armstrong 	.video_hue = 0,
92bbbe775eSNeil Armstrong 	.analog_sync_adj = 0x8080,
93bbbe775eSNeil Armstrong };
94bbbe775eSNeil Armstrong 
95bbbe775eSNeil Armstrong struct meson_cvbs_enci_mode meson_cvbs_enci_ntsc = {
96bbbe775eSNeil Armstrong 	.mode_tag = MESON_VENC_MODE_CVBS_NTSC,
97bbbe775eSNeil Armstrong 	.hso_begin = 5,
98bbbe775eSNeil Armstrong 	.hso_end = 129,
99bbbe775eSNeil Armstrong 	.vso_even = 3,
100bbbe775eSNeil Armstrong 	.vso_odd = 260,
101bbbe775eSNeil Armstrong 	.macv_max_amp = 0xb,
102bbbe775eSNeil Armstrong 	.video_prog_mode = 0xf0,
103bbbe775eSNeil Armstrong 	.video_mode = 0x8,
104bbbe775eSNeil Armstrong 	.sch_adjust = 0x20,
105bbbe775eSNeil Armstrong 	.yc_delay = 0x333,
106bbbe775eSNeil Armstrong 	.pixel_start = 227,
107bbbe775eSNeil Armstrong 	.pixel_end = 1667,
108bbbe775eSNeil Armstrong 	.top_field_line_start = 18,
109bbbe775eSNeil Armstrong 	.top_field_line_end = 258,
110bbbe775eSNeil Armstrong 	.bottom_field_line_start = 19,
111bbbe775eSNeil Armstrong 	.bottom_field_line_end = 259,
112bbbe775eSNeil Armstrong 	.video_saturation = 18,
113bbbe775eSNeil Armstrong 	.video_contrast = 3,
114bbbe775eSNeil Armstrong 	.video_brightness = 0,
115bbbe775eSNeil Armstrong 	.video_hue = 0,
116bbbe775eSNeil Armstrong 	.analog_sync_adj = 0x9c00,
117bbbe775eSNeil Armstrong };
118bbbe775eSNeil Armstrong 
119335e3713SNeil Armstrong union meson_hdmi_venc_mode {
120335e3713SNeil Armstrong 	struct {
121335e3713SNeil Armstrong 		unsigned int mode_tag;
122335e3713SNeil Armstrong 		unsigned int hso_begin;
123335e3713SNeil Armstrong 		unsigned int hso_end;
124335e3713SNeil Armstrong 		unsigned int vso_even;
125335e3713SNeil Armstrong 		unsigned int vso_odd;
126335e3713SNeil Armstrong 		unsigned int macv_max_amp;
127335e3713SNeil Armstrong 		unsigned int video_prog_mode;
128335e3713SNeil Armstrong 		unsigned int video_mode;
129335e3713SNeil Armstrong 		unsigned int sch_adjust;
130335e3713SNeil Armstrong 		unsigned int yc_delay;
131335e3713SNeil Armstrong 		unsigned int pixel_start;
132335e3713SNeil Armstrong 		unsigned int pixel_end;
133335e3713SNeil Armstrong 		unsigned int top_field_line_start;
134335e3713SNeil Armstrong 		unsigned int top_field_line_end;
135335e3713SNeil Armstrong 		unsigned int bottom_field_line_start;
136335e3713SNeil Armstrong 		unsigned int bottom_field_line_end;
137335e3713SNeil Armstrong 	} enci;
138335e3713SNeil Armstrong 	struct {
139335e3713SNeil Armstrong 		unsigned int dvi_settings;
140335e3713SNeil Armstrong 		unsigned int video_mode;
141335e3713SNeil Armstrong 		unsigned int video_mode_adv;
142335e3713SNeil Armstrong 		unsigned int video_prog_mode;
143335e3713SNeil Armstrong 		bool video_prog_mode_present;
144335e3713SNeil Armstrong 		unsigned int video_sync_mode;
145335e3713SNeil Armstrong 		bool video_sync_mode_present;
146335e3713SNeil Armstrong 		unsigned int video_yc_dly;
147335e3713SNeil Armstrong 		bool video_yc_dly_present;
148335e3713SNeil Armstrong 		unsigned int video_rgb_ctrl;
149335e3713SNeil Armstrong 		bool video_rgb_ctrl_present;
150335e3713SNeil Armstrong 		unsigned int video_filt_ctrl;
151335e3713SNeil Armstrong 		bool video_filt_ctrl_present;
152335e3713SNeil Armstrong 		unsigned int video_ofld_voav_ofst;
153335e3713SNeil Armstrong 		bool video_ofld_voav_ofst_present;
154335e3713SNeil Armstrong 		unsigned int yfp1_htime;
155335e3713SNeil Armstrong 		unsigned int yfp2_htime;
156335e3713SNeil Armstrong 		unsigned int max_pxcnt;
157335e3713SNeil Armstrong 		unsigned int hspuls_begin;
158335e3713SNeil Armstrong 		unsigned int hspuls_end;
159335e3713SNeil Armstrong 		unsigned int hspuls_switch;
160335e3713SNeil Armstrong 		unsigned int vspuls_begin;
161335e3713SNeil Armstrong 		unsigned int vspuls_end;
162335e3713SNeil Armstrong 		unsigned int vspuls_bline;
163335e3713SNeil Armstrong 		unsigned int vspuls_eline;
164335e3713SNeil Armstrong 		unsigned int eqpuls_begin;
165335e3713SNeil Armstrong 		bool eqpuls_begin_present;
166335e3713SNeil Armstrong 		unsigned int eqpuls_end;
167335e3713SNeil Armstrong 		bool eqpuls_end_present;
168335e3713SNeil Armstrong 		unsigned int eqpuls_bline;
169335e3713SNeil Armstrong 		bool eqpuls_bline_present;
170335e3713SNeil Armstrong 		unsigned int eqpuls_eline;
171335e3713SNeil Armstrong 		bool eqpuls_eline_present;
172335e3713SNeil Armstrong 		unsigned int havon_begin;
173335e3713SNeil Armstrong 		unsigned int havon_end;
174335e3713SNeil Armstrong 		unsigned int vavon_bline;
175335e3713SNeil Armstrong 		unsigned int vavon_eline;
176335e3713SNeil Armstrong 		unsigned int hso_begin;
177335e3713SNeil Armstrong 		unsigned int hso_end;
178335e3713SNeil Armstrong 		unsigned int vso_begin;
179335e3713SNeil Armstrong 		unsigned int vso_end;
180335e3713SNeil Armstrong 		unsigned int vso_bline;
181335e3713SNeil Armstrong 		unsigned int vso_eline;
182335e3713SNeil Armstrong 		bool vso_eline_present;
183335e3713SNeil Armstrong 		unsigned int sy_val;
184335e3713SNeil Armstrong 		bool sy_val_present;
185335e3713SNeil Armstrong 		unsigned int sy2_val;
186335e3713SNeil Armstrong 		bool sy2_val_present;
187335e3713SNeil Armstrong 		unsigned int max_lncnt;
188335e3713SNeil Armstrong 	} encp;
189335e3713SNeil Armstrong };
190335e3713SNeil Armstrong 
1914b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_enci_mode_480i = {
192335e3713SNeil Armstrong 	.enci = {
193335e3713SNeil Armstrong 		.hso_begin = 5,
194335e3713SNeil Armstrong 		.hso_end = 129,
195335e3713SNeil Armstrong 		.vso_even = 3,
196335e3713SNeil Armstrong 		.vso_odd = 260,
197a84ddb83SJulien Masson 		.macv_max_amp = 0xb,
198335e3713SNeil Armstrong 		.video_prog_mode = 0xf0,
199335e3713SNeil Armstrong 		.video_mode = 0x8,
200335e3713SNeil Armstrong 		.sch_adjust = 0x20,
201335e3713SNeil Armstrong 		.yc_delay = 0,
202335e3713SNeil Armstrong 		.pixel_start = 227,
203335e3713SNeil Armstrong 		.pixel_end = 1667,
204335e3713SNeil Armstrong 		.top_field_line_start = 18,
205335e3713SNeil Armstrong 		.top_field_line_end = 258,
206335e3713SNeil Armstrong 		.bottom_field_line_start = 19,
207335e3713SNeil Armstrong 		.bottom_field_line_end = 259,
208335e3713SNeil Armstrong 	},
209335e3713SNeil Armstrong };
210335e3713SNeil Armstrong 
2114b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_enci_mode_576i = {
212335e3713SNeil Armstrong 	.enci = {
213335e3713SNeil Armstrong 		.hso_begin = 3,
214335e3713SNeil Armstrong 		.hso_end = 129,
215335e3713SNeil Armstrong 		.vso_even = 3,
216335e3713SNeil Armstrong 		.vso_odd = 260,
217a84ddb83SJulien Masson 		.macv_max_amp = 0x7,
218335e3713SNeil Armstrong 		.video_prog_mode = 0xff,
219335e3713SNeil Armstrong 		.video_mode = 0x13,
220335e3713SNeil Armstrong 		.sch_adjust = 0x28,
221335e3713SNeil Armstrong 		.yc_delay = 0x333,
222335e3713SNeil Armstrong 		.pixel_start = 251,
223335e3713SNeil Armstrong 		.pixel_end = 1691,
224335e3713SNeil Armstrong 		.top_field_line_start = 22,
225335e3713SNeil Armstrong 		.top_field_line_end = 310,
226335e3713SNeil Armstrong 		.bottom_field_line_start = 23,
227335e3713SNeil Armstrong 		.bottom_field_line_end = 311,
228335e3713SNeil Armstrong 	},
229335e3713SNeil Armstrong };
230335e3713SNeil Armstrong 
2314b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_480p = {
232335e3713SNeil Armstrong 	.encp = {
233335e3713SNeil Armstrong 		.dvi_settings = 0x21,
234335e3713SNeil Armstrong 		.video_mode = 0x4000,
235335e3713SNeil Armstrong 		.video_mode_adv = 0x9,
236335e3713SNeil Armstrong 		.video_prog_mode = 0,
237335e3713SNeil Armstrong 		.video_prog_mode_present = true,
238335e3713SNeil Armstrong 		.video_sync_mode = 7,
239335e3713SNeil Armstrong 		.video_sync_mode_present = true,
240335e3713SNeil Armstrong 		/* video_yc_dly */
241335e3713SNeil Armstrong 		/* video_rgb_ctrl */
242335e3713SNeil Armstrong 		.video_filt_ctrl = 0x2052,
243335e3713SNeil Armstrong 		.video_filt_ctrl_present = true,
244335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
245335e3713SNeil Armstrong 		.yfp1_htime = 244,
246335e3713SNeil Armstrong 		.yfp2_htime = 1630,
247335e3713SNeil Armstrong 		.max_pxcnt = 1715,
248335e3713SNeil Armstrong 		.hspuls_begin = 0x22,
249335e3713SNeil Armstrong 		.hspuls_end = 0xa0,
250335e3713SNeil Armstrong 		.hspuls_switch = 88,
251335e3713SNeil Armstrong 		.vspuls_begin = 0,
252335e3713SNeil Armstrong 		.vspuls_end = 1589,
253335e3713SNeil Armstrong 		.vspuls_bline = 0,
254335e3713SNeil Armstrong 		.vspuls_eline = 5,
255335e3713SNeil Armstrong 		.havon_begin = 249,
256335e3713SNeil Armstrong 		.havon_end = 1689,
257335e3713SNeil Armstrong 		.vavon_bline = 42,
258335e3713SNeil Armstrong 		.vavon_eline = 521,
259335e3713SNeil Armstrong 		/* eqpuls_begin */
260335e3713SNeil Armstrong 		/* eqpuls_end */
261335e3713SNeil Armstrong 		/* eqpuls_bline */
262335e3713SNeil Armstrong 		/* eqpuls_eline */
263335e3713SNeil Armstrong 		.hso_begin = 3,
264335e3713SNeil Armstrong 		.hso_end = 5,
265335e3713SNeil Armstrong 		.vso_begin = 3,
266335e3713SNeil Armstrong 		.vso_end = 5,
267335e3713SNeil Armstrong 		.vso_bline = 0,
268335e3713SNeil Armstrong 		/* vso_eline */
269335e3713SNeil Armstrong 		.sy_val	= 8,
270335e3713SNeil Armstrong 		.sy_val_present = true,
271335e3713SNeil Armstrong 		.sy2_val = 0x1d8,
272335e3713SNeil Armstrong 		.sy2_val_present = true,
273335e3713SNeil Armstrong 		.max_lncnt = 524,
274335e3713SNeil Armstrong 	},
275335e3713SNeil Armstrong };
276335e3713SNeil Armstrong 
2774b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_576p = {
278335e3713SNeil Armstrong 	.encp = {
279335e3713SNeil Armstrong 		.dvi_settings = 0x21,
280335e3713SNeil Armstrong 		.video_mode = 0x4000,
281335e3713SNeil Armstrong 		.video_mode_adv = 0x9,
282335e3713SNeil Armstrong 		.video_prog_mode = 0,
283335e3713SNeil Armstrong 		.video_prog_mode_present = true,
284335e3713SNeil Armstrong 		.video_sync_mode = 7,
285335e3713SNeil Armstrong 		.video_sync_mode_present = true,
286335e3713SNeil Armstrong 		/* video_yc_dly */
287335e3713SNeil Armstrong 		/* video_rgb_ctrl */
288335e3713SNeil Armstrong 		.video_filt_ctrl = 0x52,
289335e3713SNeil Armstrong 		.video_filt_ctrl_present = true,
290335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
291335e3713SNeil Armstrong 		.yfp1_htime = 235,
292335e3713SNeil Armstrong 		.yfp2_htime = 1674,
293335e3713SNeil Armstrong 		.max_pxcnt = 1727,
294335e3713SNeil Armstrong 		.hspuls_begin = 0,
295335e3713SNeil Armstrong 		.hspuls_end = 0x80,
296335e3713SNeil Armstrong 		.hspuls_switch = 88,
297335e3713SNeil Armstrong 		.vspuls_begin = 0,
298335e3713SNeil Armstrong 		.vspuls_end = 1599,
299335e3713SNeil Armstrong 		.vspuls_bline = 0,
300335e3713SNeil Armstrong 		.vspuls_eline = 4,
301335e3713SNeil Armstrong 		.havon_begin = 235,
302335e3713SNeil Armstrong 		.havon_end = 1674,
303335e3713SNeil Armstrong 		.vavon_bline = 44,
304335e3713SNeil Armstrong 		.vavon_eline = 619,
305335e3713SNeil Armstrong 		/* eqpuls_begin */
306335e3713SNeil Armstrong 		/* eqpuls_end */
307335e3713SNeil Armstrong 		/* eqpuls_bline */
308335e3713SNeil Armstrong 		/* eqpuls_eline */
309335e3713SNeil Armstrong 		.hso_begin = 0x80,
310335e3713SNeil Armstrong 		.hso_end = 0,
311335e3713SNeil Armstrong 		.vso_begin = 0,
312335e3713SNeil Armstrong 		.vso_end = 5,
313335e3713SNeil Armstrong 		.vso_bline = 0,
314335e3713SNeil Armstrong 		/* vso_eline */
315335e3713SNeil Armstrong 		.sy_val	= 8,
316335e3713SNeil Armstrong 		.sy_val_present = true,
317335e3713SNeil Armstrong 		.sy2_val = 0x1d8,
318335e3713SNeil Armstrong 		.sy2_val_present = true,
319335e3713SNeil Armstrong 		.max_lncnt = 624,
320335e3713SNeil Armstrong 	},
321335e3713SNeil Armstrong };
322335e3713SNeil Armstrong 
3234b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_720p60 = {
324335e3713SNeil Armstrong 	.encp = {
325335e3713SNeil Armstrong 		.dvi_settings = 0x2029,
326335e3713SNeil Armstrong 		.video_mode = 0x4040,
327335e3713SNeil Armstrong 		.video_mode_adv = 0x19,
328335e3713SNeil Armstrong 		/* video_prog_mode */
329335e3713SNeil Armstrong 		/* video_sync_mode */
330335e3713SNeil Armstrong 		/* video_yc_dly */
331335e3713SNeil Armstrong 		/* video_rgb_ctrl */
332335e3713SNeil Armstrong 		/* video_filt_ctrl */
333335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
334335e3713SNeil Armstrong 		.yfp1_htime = 648,
335335e3713SNeil Armstrong 		.yfp2_htime = 3207,
336335e3713SNeil Armstrong 		.max_pxcnt = 3299,
337335e3713SNeil Armstrong 		.hspuls_begin = 80,
338335e3713SNeil Armstrong 		.hspuls_end = 240,
339335e3713SNeil Armstrong 		.hspuls_switch = 80,
340335e3713SNeil Armstrong 		.vspuls_begin = 688,
341335e3713SNeil Armstrong 		.vspuls_end = 3248,
342335e3713SNeil Armstrong 		.vspuls_bline = 4,
343335e3713SNeil Armstrong 		.vspuls_eline = 8,
344335e3713SNeil Armstrong 		.havon_begin = 648,
345335e3713SNeil Armstrong 		.havon_end = 3207,
346335e3713SNeil Armstrong 		.vavon_bline = 29,
347335e3713SNeil Armstrong 		.vavon_eline = 748,
348335e3713SNeil Armstrong 		/* eqpuls_begin */
349335e3713SNeil Armstrong 		/* eqpuls_end */
350335e3713SNeil Armstrong 		/* eqpuls_bline */
351335e3713SNeil Armstrong 		/* eqpuls_eline */
352335e3713SNeil Armstrong 		.hso_begin = 256,
353335e3713SNeil Armstrong 		.hso_end = 168,
354335e3713SNeil Armstrong 		.vso_begin = 168,
355335e3713SNeil Armstrong 		.vso_end = 256,
356335e3713SNeil Armstrong 		.vso_bline = 0,
357335e3713SNeil Armstrong 		.vso_eline = 5,
358335e3713SNeil Armstrong 		.vso_eline_present = true,
359335e3713SNeil Armstrong 		/* sy_val */
360335e3713SNeil Armstrong 		/* sy2_val */
361335e3713SNeil Armstrong 		.max_lncnt = 749,
362335e3713SNeil Armstrong 	},
363335e3713SNeil Armstrong };
364335e3713SNeil Armstrong 
3654b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_720p50 = {
366335e3713SNeil Armstrong 	.encp = {
367335e3713SNeil Armstrong 		.dvi_settings = 0x202d,
368335e3713SNeil Armstrong 		.video_mode = 0x4040,
369335e3713SNeil Armstrong 		.video_mode_adv = 0x19,
370335e3713SNeil Armstrong 		.video_prog_mode = 0x100,
371335e3713SNeil Armstrong 		.video_prog_mode_present = true,
372335e3713SNeil Armstrong 		.video_sync_mode = 0x407,
373335e3713SNeil Armstrong 		.video_sync_mode_present = true,
374335e3713SNeil Armstrong 		.video_yc_dly = 0,
375335e3713SNeil Armstrong 		.video_yc_dly_present = true,
376335e3713SNeil Armstrong 		/* video_rgb_ctrl */
377335e3713SNeil Armstrong 		/* video_filt_ctrl */
378335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
379335e3713SNeil Armstrong 		.yfp1_htime = 648,
380335e3713SNeil Armstrong 		.yfp2_htime = 3207,
381335e3713SNeil Armstrong 		.max_pxcnt = 3959,
382335e3713SNeil Armstrong 		.hspuls_begin = 80,
383335e3713SNeil Armstrong 		.hspuls_end = 240,
384335e3713SNeil Armstrong 		.hspuls_switch = 80,
385335e3713SNeil Armstrong 		.vspuls_begin = 688,
386335e3713SNeil Armstrong 		.vspuls_end = 3248,
387335e3713SNeil Armstrong 		.vspuls_bline = 4,
388335e3713SNeil Armstrong 		.vspuls_eline = 8,
389335e3713SNeil Armstrong 		.havon_begin = 648,
390335e3713SNeil Armstrong 		.havon_end = 3207,
391335e3713SNeil Armstrong 		.vavon_bline = 29,
392335e3713SNeil Armstrong 		.vavon_eline = 748,
393335e3713SNeil Armstrong 		/* eqpuls_begin */
394335e3713SNeil Armstrong 		/* eqpuls_end */
395335e3713SNeil Armstrong 		/* eqpuls_bline */
396335e3713SNeil Armstrong 		/* eqpuls_eline */
397335e3713SNeil Armstrong 		.hso_begin = 128,
398335e3713SNeil Armstrong 		.hso_end = 208,
399335e3713SNeil Armstrong 		.vso_begin = 128,
400335e3713SNeil Armstrong 		.vso_end = 128,
401335e3713SNeil Armstrong 		.vso_bline = 0,
402335e3713SNeil Armstrong 		.vso_eline = 5,
403335e3713SNeil Armstrong 		.vso_eline_present = true,
404335e3713SNeil Armstrong 		/* sy_val */
405335e3713SNeil Armstrong 		/* sy2_val */
406335e3713SNeil Armstrong 		.max_lncnt = 749,
407335e3713SNeil Armstrong 	},
408335e3713SNeil Armstrong };
409335e3713SNeil Armstrong 
4104b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080i60 = {
411335e3713SNeil Armstrong 	.encp = {
412335e3713SNeil Armstrong 		.dvi_settings = 0x2029,
413335e3713SNeil Armstrong 		.video_mode = 0x5ffc,
414335e3713SNeil Armstrong 		.video_mode_adv = 0x19,
415335e3713SNeil Armstrong 		.video_prog_mode = 0x100,
416335e3713SNeil Armstrong 		.video_prog_mode_present = true,
417335e3713SNeil Armstrong 		.video_sync_mode = 0x207,
418335e3713SNeil Armstrong 		.video_sync_mode_present = true,
419335e3713SNeil Armstrong 		/* video_yc_dly */
420335e3713SNeil Armstrong 		/* video_rgb_ctrl */
421335e3713SNeil Armstrong 		/* video_filt_ctrl */
422335e3713SNeil Armstrong 		.video_ofld_voav_ofst = 0x11,
423335e3713SNeil Armstrong 		.video_ofld_voav_ofst_present = true,
424335e3713SNeil Armstrong 		.yfp1_htime = 516,
425335e3713SNeil Armstrong 		.yfp2_htime = 4355,
426335e3713SNeil Armstrong 		.max_pxcnt = 4399,
427335e3713SNeil Armstrong 		.hspuls_begin = 88,
428335e3713SNeil Armstrong 		.hspuls_end = 264,
429335e3713SNeil Armstrong 		.hspuls_switch = 88,
430335e3713SNeil Armstrong 		.vspuls_begin = 440,
431335e3713SNeil Armstrong 		.vspuls_end = 2200,
432335e3713SNeil Armstrong 		.vspuls_bline = 0,
433335e3713SNeil Armstrong 		.vspuls_eline = 4,
434335e3713SNeil Armstrong 		.havon_begin = 516,
435335e3713SNeil Armstrong 		.havon_end = 4355,
436335e3713SNeil Armstrong 		.vavon_bline = 20,
437335e3713SNeil Armstrong 		.vavon_eline = 559,
438335e3713SNeil Armstrong 		.eqpuls_begin = 2288,
439335e3713SNeil Armstrong 		.eqpuls_begin_present = true,
440335e3713SNeil Armstrong 		.eqpuls_end = 2464,
441335e3713SNeil Armstrong 		.eqpuls_end_present = true,
442335e3713SNeil Armstrong 		.eqpuls_bline = 0,
443335e3713SNeil Armstrong 		.eqpuls_bline_present = true,
444335e3713SNeil Armstrong 		.eqpuls_eline = 4,
445335e3713SNeil Armstrong 		.eqpuls_eline_present = true,
446335e3713SNeil Armstrong 		.hso_begin = 264,
447335e3713SNeil Armstrong 		.hso_end = 176,
448335e3713SNeil Armstrong 		.vso_begin = 88,
449335e3713SNeil Armstrong 		.vso_end = 88,
450335e3713SNeil Armstrong 		.vso_bline = 0,
451335e3713SNeil Armstrong 		.vso_eline = 5,
452335e3713SNeil Armstrong 		.vso_eline_present = true,
453335e3713SNeil Armstrong 		/* sy_val */
454335e3713SNeil Armstrong 		/* sy2_val */
455335e3713SNeil Armstrong 		.max_lncnt = 1124,
456335e3713SNeil Armstrong 	},
457335e3713SNeil Armstrong };
458335e3713SNeil Armstrong 
4594b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080i50 = {
460335e3713SNeil Armstrong 	.encp = {
461335e3713SNeil Armstrong 		.dvi_settings = 0x202d,
462335e3713SNeil Armstrong 		.video_mode = 0x5ffc,
463335e3713SNeil Armstrong 		.video_mode_adv = 0x19,
464335e3713SNeil Armstrong 		.video_prog_mode = 0x100,
465335e3713SNeil Armstrong 		.video_prog_mode_present = true,
466335e3713SNeil Armstrong 		.video_sync_mode = 0x7,
467335e3713SNeil Armstrong 		.video_sync_mode_present = true,
468335e3713SNeil Armstrong 		/* video_yc_dly */
469335e3713SNeil Armstrong 		/* video_rgb_ctrl */
470335e3713SNeil Armstrong 		/* video_filt_ctrl */
471335e3713SNeil Armstrong 		.video_ofld_voav_ofst = 0x11,
472335e3713SNeil Armstrong 		.video_ofld_voav_ofst_present = true,
473335e3713SNeil Armstrong 		.yfp1_htime = 526,
474335e3713SNeil Armstrong 		.yfp2_htime = 4365,
475335e3713SNeil Armstrong 		.max_pxcnt = 5279,
476335e3713SNeil Armstrong 		.hspuls_begin = 88,
477335e3713SNeil Armstrong 		.hspuls_end = 264,
478335e3713SNeil Armstrong 		.hspuls_switch = 88,
479335e3713SNeil Armstrong 		.vspuls_begin = 440,
480335e3713SNeil Armstrong 		.vspuls_end = 2200,
481335e3713SNeil Armstrong 		.vspuls_bline = 0,
482335e3713SNeil Armstrong 		.vspuls_eline = 4,
483335e3713SNeil Armstrong 		.havon_begin = 526,
484335e3713SNeil Armstrong 		.havon_end = 4365,
485335e3713SNeil Armstrong 		.vavon_bline = 20,
486335e3713SNeil Armstrong 		.vavon_eline = 559,
487335e3713SNeil Armstrong 		.eqpuls_begin = 2288,
488335e3713SNeil Armstrong 		.eqpuls_begin_present = true,
489335e3713SNeil Armstrong 		.eqpuls_end = 2464,
490335e3713SNeil Armstrong 		.eqpuls_end_present = true,
491335e3713SNeil Armstrong 		.eqpuls_bline = 0,
492335e3713SNeil Armstrong 		.eqpuls_bline_present = true,
493335e3713SNeil Armstrong 		.eqpuls_eline = 4,
494335e3713SNeil Armstrong 		.eqpuls_eline_present = true,
495335e3713SNeil Armstrong 		.hso_begin = 142,
496335e3713SNeil Armstrong 		.hso_end = 230,
497335e3713SNeil Armstrong 		.vso_begin = 142,
498335e3713SNeil Armstrong 		.vso_end = 142,
499335e3713SNeil Armstrong 		.vso_bline = 0,
500335e3713SNeil Armstrong 		.vso_eline = 5,
501335e3713SNeil Armstrong 		.vso_eline_present = true,
502335e3713SNeil Armstrong 		/* sy_val */
503335e3713SNeil Armstrong 		/* sy2_val */
504335e3713SNeil Armstrong 		.max_lncnt = 1124,
505335e3713SNeil Armstrong 	},
506335e3713SNeil Armstrong };
507335e3713SNeil Armstrong 
5084b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080p24 = {
509335e3713SNeil Armstrong 	.encp = {
510335e3713SNeil Armstrong 		.dvi_settings = 0xd,
511335e3713SNeil Armstrong 		.video_mode = 0x4040,
512335e3713SNeil Armstrong 		.video_mode_adv = 0x18,
513335e3713SNeil Armstrong 		.video_prog_mode = 0x100,
514335e3713SNeil Armstrong 		.video_prog_mode_present = true,
515335e3713SNeil Armstrong 		.video_sync_mode = 0x7,
516335e3713SNeil Armstrong 		.video_sync_mode_present = true,
517335e3713SNeil Armstrong 		.video_yc_dly = 0,
518335e3713SNeil Armstrong 		.video_yc_dly_present = true,
519335e3713SNeil Armstrong 		.video_rgb_ctrl = 2,
520335e3713SNeil Armstrong 		.video_rgb_ctrl_present = true,
521335e3713SNeil Armstrong 		.video_filt_ctrl = 0x1052,
522335e3713SNeil Armstrong 		.video_filt_ctrl_present = true,
523335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
524335e3713SNeil Armstrong 		.yfp1_htime = 271,
525335e3713SNeil Armstrong 		.yfp2_htime = 2190,
526335e3713SNeil Armstrong 		.max_pxcnt = 2749,
527335e3713SNeil Armstrong 		.hspuls_begin = 44,
528335e3713SNeil Armstrong 		.hspuls_end = 132,
529335e3713SNeil Armstrong 		.hspuls_switch = 44,
530335e3713SNeil Armstrong 		.vspuls_begin = 220,
531335e3713SNeil Armstrong 		.vspuls_end = 2140,
532335e3713SNeil Armstrong 		.vspuls_bline = 0,
533335e3713SNeil Armstrong 		.vspuls_eline = 4,
534335e3713SNeil Armstrong 		.havon_begin = 271,
535335e3713SNeil Armstrong 		.havon_end = 2190,
536335e3713SNeil Armstrong 		.vavon_bline = 41,
537335e3713SNeil Armstrong 		.vavon_eline = 1120,
538335e3713SNeil Armstrong 		/* eqpuls_begin */
539335e3713SNeil Armstrong 		/* eqpuls_end */
540335e3713SNeil Armstrong 		.eqpuls_bline = 0,
541335e3713SNeil Armstrong 		.eqpuls_bline_present = true,
542335e3713SNeil Armstrong 		.eqpuls_eline = 4,
543335e3713SNeil Armstrong 		.eqpuls_eline_present = true,
544335e3713SNeil Armstrong 		.hso_begin = 79,
545335e3713SNeil Armstrong 		.hso_end = 123,
546335e3713SNeil Armstrong 		.vso_begin = 79,
547335e3713SNeil Armstrong 		.vso_end = 79,
548335e3713SNeil Armstrong 		.vso_bline = 0,
549335e3713SNeil Armstrong 		.vso_eline = 5,
550335e3713SNeil Armstrong 		.vso_eline_present = true,
551335e3713SNeil Armstrong 		/* sy_val */
552335e3713SNeil Armstrong 		/* sy2_val */
553335e3713SNeil Armstrong 		.max_lncnt = 1124,
554335e3713SNeil Armstrong 	},
555335e3713SNeil Armstrong };
556335e3713SNeil Armstrong 
5574b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080p30 = {
558335e3713SNeil Armstrong 	.encp = {
559335e3713SNeil Armstrong 		.dvi_settings = 0x1,
560335e3713SNeil Armstrong 		.video_mode = 0x4040,
561335e3713SNeil Armstrong 		.video_mode_adv = 0x18,
562335e3713SNeil Armstrong 		.video_prog_mode = 0x100,
563335e3713SNeil Armstrong 		.video_prog_mode_present = true,
564335e3713SNeil Armstrong 		/* video_sync_mode */
565335e3713SNeil Armstrong 		/* video_yc_dly */
566335e3713SNeil Armstrong 		/* video_rgb_ctrl */
567335e3713SNeil Armstrong 		.video_filt_ctrl = 0x1052,
568335e3713SNeil Armstrong 		.video_filt_ctrl_present = true,
569335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
570335e3713SNeil Armstrong 		.yfp1_htime = 140,
571335e3713SNeil Armstrong 		.yfp2_htime = 2060,
572335e3713SNeil Armstrong 		.max_pxcnt = 2199,
573335e3713SNeil Armstrong 		.hspuls_begin = 2156,
574335e3713SNeil Armstrong 		.hspuls_end = 44,
575335e3713SNeil Armstrong 		.hspuls_switch = 44,
576335e3713SNeil Armstrong 		.vspuls_begin = 140,
577335e3713SNeil Armstrong 		.vspuls_end = 2059,
578335e3713SNeil Armstrong 		.vspuls_bline = 0,
579335e3713SNeil Armstrong 		.vspuls_eline = 4,
580335e3713SNeil Armstrong 		.havon_begin = 148,
581335e3713SNeil Armstrong 		.havon_end = 2067,
582335e3713SNeil Armstrong 		.vavon_bline = 41,
583335e3713SNeil Armstrong 		.vavon_eline = 1120,
584335e3713SNeil Armstrong 		/* eqpuls_begin */
585335e3713SNeil Armstrong 		/* eqpuls_end */
586335e3713SNeil Armstrong 		/* eqpuls_bline */
587335e3713SNeil Armstrong 		/* eqpuls_eline */
588335e3713SNeil Armstrong 		.hso_begin = 44,
589335e3713SNeil Armstrong 		.hso_end = 2156,
590335e3713SNeil Armstrong 		.vso_begin = 2100,
591335e3713SNeil Armstrong 		.vso_end = 2164,
592335e3713SNeil Armstrong 		.vso_bline = 0,
593335e3713SNeil Armstrong 		.vso_eline = 5,
594335e3713SNeil Armstrong 		.vso_eline_present = true,
595335e3713SNeil Armstrong 		/* sy_val */
596335e3713SNeil Armstrong 		/* sy2_val */
597335e3713SNeil Armstrong 		.max_lncnt = 1124,
598335e3713SNeil Armstrong 	},
599335e3713SNeil Armstrong };
600335e3713SNeil Armstrong 
6014b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080p50 = {
602335e3713SNeil Armstrong 	.encp = {
603335e3713SNeil Armstrong 		.dvi_settings = 0xd,
604335e3713SNeil Armstrong 		.video_mode = 0x4040,
605335e3713SNeil Armstrong 		.video_mode_adv = 0x18,
606335e3713SNeil Armstrong 		.video_prog_mode = 0x100,
607335e3713SNeil Armstrong 		.video_prog_mode_present = true,
608335e3713SNeil Armstrong 		.video_sync_mode = 0x7,
609335e3713SNeil Armstrong 		.video_sync_mode_present = true,
610335e3713SNeil Armstrong 		.video_yc_dly = 0,
611335e3713SNeil Armstrong 		.video_yc_dly_present = true,
612335e3713SNeil Armstrong 		.video_rgb_ctrl = 2,
613335e3713SNeil Armstrong 		.video_rgb_ctrl_present = true,
614335e3713SNeil Armstrong 		/* video_filt_ctrl */
615335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
616335e3713SNeil Armstrong 		.yfp1_htime = 271,
617335e3713SNeil Armstrong 		.yfp2_htime = 2190,
618335e3713SNeil Armstrong 		.max_pxcnt = 2639,
619335e3713SNeil Armstrong 		.hspuls_begin = 44,
620335e3713SNeil Armstrong 		.hspuls_end = 132,
621335e3713SNeil Armstrong 		.hspuls_switch = 44,
622335e3713SNeil Armstrong 		.vspuls_begin = 220,
623335e3713SNeil Armstrong 		.vspuls_end = 2140,
624335e3713SNeil Armstrong 		.vspuls_bline = 0,
625335e3713SNeil Armstrong 		.vspuls_eline = 4,
626335e3713SNeil Armstrong 		.havon_begin = 271,
627335e3713SNeil Armstrong 		.havon_end = 2190,
628335e3713SNeil Armstrong 		.vavon_bline = 41,
629335e3713SNeil Armstrong 		.vavon_eline = 1120,
630335e3713SNeil Armstrong 		/* eqpuls_begin */
631335e3713SNeil Armstrong 		/* eqpuls_end */
632335e3713SNeil Armstrong 		.eqpuls_bline = 0,
633335e3713SNeil Armstrong 		.eqpuls_bline_present = true,
634335e3713SNeil Armstrong 		.eqpuls_eline = 4,
635335e3713SNeil Armstrong 		.eqpuls_eline_present = true,
636335e3713SNeil Armstrong 		.hso_begin = 79,
637335e3713SNeil Armstrong 		.hso_end = 123,
638335e3713SNeil Armstrong 		.vso_begin = 79,
639335e3713SNeil Armstrong 		.vso_end = 79,
640335e3713SNeil Armstrong 		.vso_bline = 0,
641335e3713SNeil Armstrong 		.vso_eline = 5,
642335e3713SNeil Armstrong 		.vso_eline_present = true,
643335e3713SNeil Armstrong 		/* sy_val */
644335e3713SNeil Armstrong 		/* sy2_val */
645335e3713SNeil Armstrong 		.max_lncnt = 1124,
646335e3713SNeil Armstrong 	},
647335e3713SNeil Armstrong };
648335e3713SNeil Armstrong 
6494b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080p60 = {
650335e3713SNeil Armstrong 	.encp = {
651335e3713SNeil Armstrong 		.dvi_settings = 0x1,
652335e3713SNeil Armstrong 		.video_mode = 0x4040,
653335e3713SNeil Armstrong 		.video_mode_adv = 0x18,
654335e3713SNeil Armstrong 		.video_prog_mode = 0x100,
655335e3713SNeil Armstrong 		.video_prog_mode_present = true,
656335e3713SNeil Armstrong 		/* video_sync_mode */
657335e3713SNeil Armstrong 		/* video_yc_dly */
658335e3713SNeil Armstrong 		/* video_rgb_ctrl */
659335e3713SNeil Armstrong 		.video_filt_ctrl = 0x1052,
660335e3713SNeil Armstrong 		.video_filt_ctrl_present = true,
661335e3713SNeil Armstrong 		/* video_ofld_voav_ofst */
662335e3713SNeil Armstrong 		.yfp1_htime = 140,
663335e3713SNeil Armstrong 		.yfp2_htime = 2060,
664335e3713SNeil Armstrong 		.max_pxcnt = 2199,
665335e3713SNeil Armstrong 		.hspuls_begin = 2156,
666335e3713SNeil Armstrong 		.hspuls_end = 44,
667335e3713SNeil Armstrong 		.hspuls_switch = 44,
668335e3713SNeil Armstrong 		.vspuls_begin = 140,
669335e3713SNeil Armstrong 		.vspuls_end = 2059,
670335e3713SNeil Armstrong 		.vspuls_bline = 0,
671335e3713SNeil Armstrong 		.vspuls_eline = 4,
672335e3713SNeil Armstrong 		.havon_begin = 148,
673335e3713SNeil Armstrong 		.havon_end = 2067,
674335e3713SNeil Armstrong 		.vavon_bline = 41,
675335e3713SNeil Armstrong 		.vavon_eline = 1120,
676335e3713SNeil Armstrong 		/* eqpuls_begin */
677335e3713SNeil Armstrong 		/* eqpuls_end */
678335e3713SNeil Armstrong 		/* eqpuls_bline */
679335e3713SNeil Armstrong 		/* eqpuls_eline */
680335e3713SNeil Armstrong 		.hso_begin = 44,
681335e3713SNeil Armstrong 		.hso_end = 2156,
682335e3713SNeil Armstrong 		.vso_begin = 2100,
683335e3713SNeil Armstrong 		.vso_end = 2164,
684335e3713SNeil Armstrong 		.vso_bline = 0,
685335e3713SNeil Armstrong 		.vso_eline = 5,
686335e3713SNeil Armstrong 		.vso_eline_present = true,
687335e3713SNeil Armstrong 		/* sy_val */
688335e3713SNeil Armstrong 		/* sy2_val */
689335e3713SNeil Armstrong 		.max_lncnt = 1124,
690335e3713SNeil Armstrong 	},
691335e3713SNeil Armstrong };
692335e3713SNeil Armstrong 
6934b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_2160p24 = {
6945d0bfe44SNeil Armstrong 	.encp = {
6955d0bfe44SNeil Armstrong 		.dvi_settings = 0x1,
6965d0bfe44SNeil Armstrong 		.video_mode = 0x4040,
6975d0bfe44SNeil Armstrong 		.video_mode_adv = 0x8,
6985d0bfe44SNeil Armstrong 		/* video_sync_mode */
6995d0bfe44SNeil Armstrong 		/* video_yc_dly */
7005d0bfe44SNeil Armstrong 		/* video_rgb_ctrl */
7015d0bfe44SNeil Armstrong 		.video_filt_ctrl = 0x1000,
7025d0bfe44SNeil Armstrong 		.video_filt_ctrl_present = true,
7035d0bfe44SNeil Armstrong 		/* video_ofld_voav_ofst */
7045d0bfe44SNeil Armstrong 		.yfp1_htime = 140,
7055d0bfe44SNeil Armstrong 		.yfp2_htime = 140+3840,
7065d0bfe44SNeil Armstrong 		.max_pxcnt = 3840+1660-1,
7075d0bfe44SNeil Armstrong 		.hspuls_begin = 2156+1920,
7085d0bfe44SNeil Armstrong 		.hspuls_end = 44,
7095d0bfe44SNeil Armstrong 		.hspuls_switch = 44,
7105d0bfe44SNeil Armstrong 		.vspuls_begin = 140,
7115d0bfe44SNeil Armstrong 		.vspuls_end = 2059+1920,
7125d0bfe44SNeil Armstrong 		.vspuls_bline = 0,
7135d0bfe44SNeil Armstrong 		.vspuls_eline = 4,
7145d0bfe44SNeil Armstrong 		.havon_begin = 148,
7155d0bfe44SNeil Armstrong 		.havon_end = 3987,
7165d0bfe44SNeil Armstrong 		.vavon_bline = 89,
7175d0bfe44SNeil Armstrong 		.vavon_eline = 2248,
7185d0bfe44SNeil Armstrong 		/* eqpuls_begin */
7195d0bfe44SNeil Armstrong 		/* eqpuls_end */
7205d0bfe44SNeil Armstrong 		/* eqpuls_bline */
7215d0bfe44SNeil Armstrong 		/* eqpuls_eline */
7225d0bfe44SNeil Armstrong 		.hso_begin = 44,
7235d0bfe44SNeil Armstrong 		.hso_end = 2156+1920,
7245d0bfe44SNeil Armstrong 		.vso_begin = 2100+1920,
7255d0bfe44SNeil Armstrong 		.vso_end = 2164+1920,
7265d0bfe44SNeil Armstrong 		.vso_bline = 51,
7275d0bfe44SNeil Armstrong 		.vso_eline = 53,
7285d0bfe44SNeil Armstrong 		.vso_eline_present = true,
7295d0bfe44SNeil Armstrong 		/* sy_val */
7305d0bfe44SNeil Armstrong 		/* sy2_val */
7315d0bfe44SNeil Armstrong 		.max_lncnt = 2249,
7325d0bfe44SNeil Armstrong 	},
7335d0bfe44SNeil Armstrong };
7345d0bfe44SNeil Armstrong 
7354b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_2160p25 = {
7365d0bfe44SNeil Armstrong 	.encp = {
7375d0bfe44SNeil Armstrong 		.dvi_settings = 0x1,
7385d0bfe44SNeil Armstrong 		.video_mode = 0x4040,
7395d0bfe44SNeil Armstrong 		.video_mode_adv = 0x8,
7405d0bfe44SNeil Armstrong 		/* video_sync_mode */
7415d0bfe44SNeil Armstrong 		/* video_yc_dly */
7425d0bfe44SNeil Armstrong 		/* video_rgb_ctrl */
7435d0bfe44SNeil Armstrong 		.video_filt_ctrl = 0x1000,
7445d0bfe44SNeil Armstrong 		.video_filt_ctrl_present = true,
7455d0bfe44SNeil Armstrong 		/* video_ofld_voav_ofst */
7465d0bfe44SNeil Armstrong 		.yfp1_htime = 140,
7475d0bfe44SNeil Armstrong 		.yfp2_htime = 140+3840,
7485d0bfe44SNeil Armstrong 		.max_pxcnt = 3840+1440-1,
7495d0bfe44SNeil Armstrong 		.hspuls_begin = 2156+1920,
7505d0bfe44SNeil Armstrong 		.hspuls_end = 44,
7515d0bfe44SNeil Armstrong 		.hspuls_switch = 44,
7525d0bfe44SNeil Armstrong 		.vspuls_begin = 140,
7535d0bfe44SNeil Armstrong 		.vspuls_end = 2059+1920,
7545d0bfe44SNeil Armstrong 		.vspuls_bline = 0,
7555d0bfe44SNeil Armstrong 		.vspuls_eline = 4,
7565d0bfe44SNeil Armstrong 		.havon_begin = 148,
7575d0bfe44SNeil Armstrong 		.havon_end = 3987,
7585d0bfe44SNeil Armstrong 		.vavon_bline = 89,
7595d0bfe44SNeil Armstrong 		.vavon_eline = 2248,
7605d0bfe44SNeil Armstrong 		/* eqpuls_begin */
7615d0bfe44SNeil Armstrong 		/* eqpuls_end */
7625d0bfe44SNeil Armstrong 		/* eqpuls_bline */
7635d0bfe44SNeil Armstrong 		/* eqpuls_eline */
7645d0bfe44SNeil Armstrong 		.hso_begin = 44,
7655d0bfe44SNeil Armstrong 		.hso_end = 2156+1920,
7665d0bfe44SNeil Armstrong 		.vso_begin = 2100+1920,
7675d0bfe44SNeil Armstrong 		.vso_end = 2164+1920,
7685d0bfe44SNeil Armstrong 		.vso_bline = 51,
7695d0bfe44SNeil Armstrong 		.vso_eline = 53,
7705d0bfe44SNeil Armstrong 		.vso_eline_present = true,
7715d0bfe44SNeil Armstrong 		/* sy_val */
7725d0bfe44SNeil Armstrong 		/* sy2_val */
7735d0bfe44SNeil Armstrong 		.max_lncnt = 2249,
7745d0bfe44SNeil Armstrong 	},
7755d0bfe44SNeil Armstrong };
7765d0bfe44SNeil Armstrong 
7774b733b2cSTom Rix static union meson_hdmi_venc_mode meson_hdmi_encp_mode_2160p30 = {
7785d0bfe44SNeil Armstrong 	.encp = {
7795d0bfe44SNeil Armstrong 		.dvi_settings = 0x1,
7805d0bfe44SNeil Armstrong 		.video_mode = 0x4040,
7815d0bfe44SNeil Armstrong 		.video_mode_adv = 0x8,
7825d0bfe44SNeil Armstrong 		/* video_sync_mode */
7835d0bfe44SNeil Armstrong 		/* video_yc_dly */
7845d0bfe44SNeil Armstrong 		/* video_rgb_ctrl */
7855d0bfe44SNeil Armstrong 		.video_filt_ctrl = 0x1000,
7865d0bfe44SNeil Armstrong 		.video_filt_ctrl_present = true,
7875d0bfe44SNeil Armstrong 		/* video_ofld_voav_ofst */
7885d0bfe44SNeil Armstrong 		.yfp1_htime = 140,
7895d0bfe44SNeil Armstrong 		.yfp2_htime = 140+3840,
7905d0bfe44SNeil Armstrong 		.max_pxcnt = 3840+560-1,
7915d0bfe44SNeil Armstrong 		.hspuls_begin = 2156+1920,
7925d0bfe44SNeil Armstrong 		.hspuls_end = 44,
7935d0bfe44SNeil Armstrong 		.hspuls_switch = 44,
7945d0bfe44SNeil Armstrong 		.vspuls_begin = 140,
7955d0bfe44SNeil Armstrong 		.vspuls_end = 2059+1920,
7965d0bfe44SNeil Armstrong 		.vspuls_bline = 0,
7975d0bfe44SNeil Armstrong 		.vspuls_eline = 4,
7985d0bfe44SNeil Armstrong 		.havon_begin = 148,
7995d0bfe44SNeil Armstrong 		.havon_end = 3987,
8005d0bfe44SNeil Armstrong 		.vavon_bline = 89,
8015d0bfe44SNeil Armstrong 		.vavon_eline = 2248,
8025d0bfe44SNeil Armstrong 		/* eqpuls_begin */
8035d0bfe44SNeil Armstrong 		/* eqpuls_end */
8045d0bfe44SNeil Armstrong 		/* eqpuls_bline */
8055d0bfe44SNeil Armstrong 		/* eqpuls_eline */
8065d0bfe44SNeil Armstrong 		.hso_begin = 44,
8075d0bfe44SNeil Armstrong 		.hso_end = 2156+1920,
8085d0bfe44SNeil Armstrong 		.vso_begin = 2100+1920,
8095d0bfe44SNeil Armstrong 		.vso_end = 2164+1920,
8105d0bfe44SNeil Armstrong 		.vso_bline = 51,
8115d0bfe44SNeil Armstrong 		.vso_eline = 53,
8125d0bfe44SNeil Armstrong 		.vso_eline_present = true,
8135d0bfe44SNeil Armstrong 		/* sy_val */
8145d0bfe44SNeil Armstrong 		/* sy2_val */
8155d0bfe44SNeil Armstrong 		.max_lncnt = 2249,
8165d0bfe44SNeil Armstrong 	},
8175d0bfe44SNeil Armstrong };
8185d0bfe44SNeil Armstrong 
8194b733b2cSTom Rix static struct meson_hdmi_venc_vic_mode {
820335e3713SNeil Armstrong 	unsigned int vic;
821335e3713SNeil Armstrong 	union meson_hdmi_venc_mode *mode;
822335e3713SNeil Armstrong } meson_hdmi_venc_vic_modes[] = {
823335e3713SNeil Armstrong 	{ 6, &meson_hdmi_enci_mode_480i },
824335e3713SNeil Armstrong 	{ 7, &meson_hdmi_enci_mode_480i },
825335e3713SNeil Armstrong 	{ 21, &meson_hdmi_enci_mode_576i },
826335e3713SNeil Armstrong 	{ 22, &meson_hdmi_enci_mode_576i },
827335e3713SNeil Armstrong 	{ 2, &meson_hdmi_encp_mode_480p },
828335e3713SNeil Armstrong 	{ 3, &meson_hdmi_encp_mode_480p },
829335e3713SNeil Armstrong 	{ 17, &meson_hdmi_encp_mode_576p },
830335e3713SNeil Armstrong 	{ 18, &meson_hdmi_encp_mode_576p },
831335e3713SNeil Armstrong 	{ 4, &meson_hdmi_encp_mode_720p60 },
832335e3713SNeil Armstrong 	{ 19, &meson_hdmi_encp_mode_720p50 },
833335e3713SNeil Armstrong 	{ 5, &meson_hdmi_encp_mode_1080i60 },
834335e3713SNeil Armstrong 	{ 20, &meson_hdmi_encp_mode_1080i50 },
835335e3713SNeil Armstrong 	{ 32, &meson_hdmi_encp_mode_1080p24 },
83631e1ab49SChristian Hewitt 	{ 33, &meson_hdmi_encp_mode_1080p50 },
837335e3713SNeil Armstrong 	{ 34, &meson_hdmi_encp_mode_1080p30 },
838335e3713SNeil Armstrong 	{ 31, &meson_hdmi_encp_mode_1080p50 },
839335e3713SNeil Armstrong 	{ 16, &meson_hdmi_encp_mode_1080p60 },
8405d0bfe44SNeil Armstrong 	{ 93, &meson_hdmi_encp_mode_2160p24 },
8415d0bfe44SNeil Armstrong 	{ 94, &meson_hdmi_encp_mode_2160p25 },
8425d0bfe44SNeil Armstrong 	{ 95, &meson_hdmi_encp_mode_2160p30 },
84374f6d1e1SNeil Armstrong 	{ 96, &meson_hdmi_encp_mode_2160p25 },
84474f6d1e1SNeil Armstrong 	{ 97, &meson_hdmi_encp_mode_2160p30 },
845335e3713SNeil Armstrong 	{ 0, NULL}, /* sentinel */
846335e3713SNeil Armstrong };
847335e3713SNeil Armstrong 
to_signed(unsigned int a)848335e3713SNeil Armstrong static signed int to_signed(unsigned int a)
849335e3713SNeil Armstrong {
850335e3713SNeil Armstrong 	if (a <= 7)
851335e3713SNeil Armstrong 		return a;
852335e3713SNeil Armstrong 	else
853335e3713SNeil Armstrong 		return a - 16;
854335e3713SNeil Armstrong }
855335e3713SNeil Armstrong 
modulo(unsigned long a,unsigned long b)856335e3713SNeil Armstrong static unsigned long modulo(unsigned long a, unsigned long b)
857335e3713SNeil Armstrong {
858335e3713SNeil Armstrong 	if (a >= b)
859335e3713SNeil Armstrong 		return a - b;
860335e3713SNeil Armstrong 	else
861335e3713SNeil Armstrong 		return a;
862335e3713SNeil Armstrong }
863335e3713SNeil Armstrong 
8643273fc63SNeil Armstrong enum drm_mode_status
meson_venc_hdmi_supported_mode(const struct drm_display_mode * mode)8653273fc63SNeil Armstrong meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode)
8669c936b12SNeil Armstrong {
8673273fc63SNeil Armstrong 	if (mode->flags & ~(DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NHSYNC |
8683273fc63SNeil Armstrong 			    DRM_MODE_FLAG_PVSYNC | DRM_MODE_FLAG_NVSYNC))
8693273fc63SNeil Armstrong 		return MODE_BAD;
8709c936b12SNeil Armstrong 
871bf458e5bSCarlo Caione 	if (mode->hdisplay < 400 || mode->hdisplay > 1920)
8723273fc63SNeil Armstrong 		return MODE_BAD_HVALUE;
8739c936b12SNeil Armstrong 
874bf458e5bSCarlo Caione 	if (mode->vdisplay < 480 || mode->vdisplay > 1920)
8753273fc63SNeil Armstrong 		return MODE_BAD_VVALUE;
8763273fc63SNeil Armstrong 
8773273fc63SNeil Armstrong 	return MODE_OK;
8789c936b12SNeil Armstrong }
8799c936b12SNeil Armstrong EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_mode);
8809c936b12SNeil Armstrong 
meson_venc_hdmi_supported_vic(int vic)881335e3713SNeil Armstrong bool meson_venc_hdmi_supported_vic(int vic)
882335e3713SNeil Armstrong {
883335e3713SNeil Armstrong 	struct meson_hdmi_venc_vic_mode *vmode = meson_hdmi_venc_vic_modes;
884335e3713SNeil Armstrong 
885335e3713SNeil Armstrong 	while (vmode->vic && vmode->mode) {
886335e3713SNeil Armstrong 		if (vmode->vic == vic)
887335e3713SNeil Armstrong 			return true;
888335e3713SNeil Armstrong 		vmode++;
889335e3713SNeil Armstrong 	}
890335e3713SNeil Armstrong 
891335e3713SNeil Armstrong 	return false;
892335e3713SNeil Armstrong }
893335e3713SNeil Armstrong EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_vic);
894335e3713SNeil Armstrong 
meson_venc_hdmi_get_dmt_vmode(const struct drm_display_mode * mode,union meson_hdmi_venc_mode * dmt_mode)8952bc5f1c9SLee Jones static void meson_venc_hdmi_get_dmt_vmode(const struct drm_display_mode *mode,
8963273fc63SNeil Armstrong 					  union meson_hdmi_venc_mode *dmt_mode)
8979c936b12SNeil Armstrong {
8983273fc63SNeil Armstrong 	memset(dmt_mode, 0, sizeof(*dmt_mode));
8999c936b12SNeil Armstrong 
9003273fc63SNeil Armstrong 	dmt_mode->encp.dvi_settings = 0x21;
9013273fc63SNeil Armstrong 	dmt_mode->encp.video_mode = 0x4040;
9023273fc63SNeil Armstrong 	dmt_mode->encp.video_mode_adv = 0x18;
9033273fc63SNeil Armstrong 	dmt_mode->encp.max_pxcnt = mode->htotal - 1;
9043273fc63SNeil Armstrong 	dmt_mode->encp.havon_begin = mode->htotal - mode->hsync_start;
9053273fc63SNeil Armstrong 	dmt_mode->encp.havon_end = dmt_mode->encp.havon_begin +
9063273fc63SNeil Armstrong 				   mode->hdisplay - 1;
9073273fc63SNeil Armstrong 	dmt_mode->encp.vavon_bline = mode->vtotal - mode->vsync_start;
9083273fc63SNeil Armstrong 	dmt_mode->encp.vavon_eline = dmt_mode->encp.vavon_bline +
9093273fc63SNeil Armstrong 				     mode->vdisplay - 1;
9103273fc63SNeil Armstrong 	dmt_mode->encp.hso_begin = 0;
9113273fc63SNeil Armstrong 	dmt_mode->encp.hso_end = mode->hsync_end - mode->hsync_start;
9123273fc63SNeil Armstrong 	dmt_mode->encp.vso_begin = 30;
9133273fc63SNeil Armstrong 	dmt_mode->encp.vso_end = 50;
9143273fc63SNeil Armstrong 	dmt_mode->encp.vso_bline = 0;
9153273fc63SNeil Armstrong 	dmt_mode->encp.vso_eline = mode->vsync_end - mode->vsync_start;
9163273fc63SNeil Armstrong 	dmt_mode->encp.vso_eline_present = true;
9173273fc63SNeil Armstrong 	dmt_mode->encp.max_lncnt = mode->vtotal - 1;
9189c936b12SNeil Armstrong }
9199c936b12SNeil Armstrong 
meson_venc_hdmi_get_vic_vmode(int vic)920335e3713SNeil Armstrong static union meson_hdmi_venc_mode *meson_venc_hdmi_get_vic_vmode(int vic)
921335e3713SNeil Armstrong {
922335e3713SNeil Armstrong 	struct meson_hdmi_venc_vic_mode *vmode = meson_hdmi_venc_vic_modes;
923335e3713SNeil Armstrong 
924335e3713SNeil Armstrong 	while (vmode->vic && vmode->mode) {
925335e3713SNeil Armstrong 		if (vmode->vic == vic)
926335e3713SNeil Armstrong 			return vmode->mode;
927335e3713SNeil Armstrong 		vmode++;
928335e3713SNeil Armstrong 	}
929335e3713SNeil Armstrong 
930335e3713SNeil Armstrong 	return NULL;
931335e3713SNeil Armstrong }
932335e3713SNeil Armstrong 
meson_venc_hdmi_venc_repeat(int vic)933335e3713SNeil Armstrong bool meson_venc_hdmi_venc_repeat(int vic)
934335e3713SNeil Armstrong {
935335e3713SNeil Armstrong 	/* Repeat VENC pixels for 480/576i/p, 720p50/60 and 1080p50/60 */
936335e3713SNeil Armstrong 	if (vic == 6 || vic == 7 || /* 480i */
937335e3713SNeil Armstrong 	    vic == 21 || vic == 22 || /* 576i */
938335e3713SNeil Armstrong 	    vic == 17 || vic == 18 || /* 576p */
939335e3713SNeil Armstrong 	    vic == 2 || vic == 3 || /* 480p */
940335e3713SNeil Armstrong 	    vic == 4 || /* 720p60 */
941335e3713SNeil Armstrong 	    vic == 19 || /* 720p50 */
942335e3713SNeil Armstrong 	    vic == 5 || /* 1080i60 */
943335e3713SNeil Armstrong 	    vic == 20)	/* 1080i50 */
944335e3713SNeil Armstrong 		return true;
945335e3713SNeil Armstrong 
946335e3713SNeil Armstrong 	return false;
947335e3713SNeil Armstrong }
948335e3713SNeil Armstrong EXPORT_SYMBOL_GPL(meson_venc_hdmi_venc_repeat);
949335e3713SNeil Armstrong 
meson_venc_hdmi_mode_set(struct meson_drm * priv,int vic,unsigned int ycrcb_map,bool yuv420_mode,const struct drm_display_mode * mode)950335e3713SNeil Armstrong void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic,
95164db601aSNeil Armstrong 			      unsigned int ycrcb_map,
95264db601aSNeil Armstrong 			      bool yuv420_mode,
9530fad640bSNeil Armstrong 			      const struct drm_display_mode *mode)
954335e3713SNeil Armstrong {
955335e3713SNeil Armstrong 	union meson_hdmi_venc_mode *vmode = NULL;
9563273fc63SNeil Armstrong 	union meson_hdmi_venc_mode vmode_dmt;
957335e3713SNeil Armstrong 	bool use_enci = false;
958335e3713SNeil Armstrong 	bool venc_repeat = false;
959335e3713SNeil Armstrong 	bool hdmi_repeat = false;
960335e3713SNeil Armstrong 	unsigned int venc_hdmi_latency = 2;
961335e3713SNeil Armstrong 	unsigned long total_pixels_venc = 0;
962335e3713SNeil Armstrong 	unsigned long active_pixels_venc = 0;
963335e3713SNeil Armstrong 	unsigned long front_porch_venc = 0;
964335e3713SNeil Armstrong 	unsigned long hsync_pixels_venc = 0;
965335e3713SNeil Armstrong 	unsigned long de_h_begin = 0;
966335e3713SNeil Armstrong 	unsigned long de_h_end = 0;
967335e3713SNeil Armstrong 	unsigned long de_v_begin_even = 0;
968335e3713SNeil Armstrong 	unsigned long de_v_end_even = 0;
969335e3713SNeil Armstrong 	unsigned long de_v_begin_odd = 0;
970335e3713SNeil Armstrong 	unsigned long de_v_end_odd = 0;
971335e3713SNeil Armstrong 	unsigned long hs_begin = 0;
972335e3713SNeil Armstrong 	unsigned long hs_end = 0;
973335e3713SNeil Armstrong 	unsigned long vs_adjust = 0;
974335e3713SNeil Armstrong 	unsigned long vs_bline_evn = 0;
975335e3713SNeil Armstrong 	unsigned long vs_eline_evn = 0;
976335e3713SNeil Armstrong 	unsigned long vs_bline_odd = 0;
977335e3713SNeil Armstrong 	unsigned long vs_eline_odd = 0;
978335e3713SNeil Armstrong 	unsigned long vso_begin_evn = 0;
979335e3713SNeil Armstrong 	unsigned long vso_begin_odd = 0;
980335e3713SNeil Armstrong 	unsigned int eof_lines;
981335e3713SNeil Armstrong 	unsigned int sof_lines;
982335e3713SNeil Armstrong 	unsigned int vsync_lines;
9837eef9e61SJulien Masson 	u32 reg;
984335e3713SNeil Armstrong 
985adf59dd2SJorge Ramirez-Ortiz 	/* Use VENCI for 480i and 576i and double HDMI pixels */
986adf59dd2SJorge Ramirez-Ortiz 	if (mode->flags & DRM_MODE_FLAG_DBLCLK) {
987adf59dd2SJorge Ramirez-Ortiz 		hdmi_repeat = true;
988adf59dd2SJorge Ramirez-Ortiz 		use_enci = true;
989adf59dd2SJorge Ramirez-Ortiz 		venc_hdmi_latency = 1;
990adf59dd2SJorge Ramirez-Ortiz 	}
991adf59dd2SJorge Ramirez-Ortiz 
9923273fc63SNeil Armstrong 	if (meson_venc_hdmi_supported_vic(vic)) {
993335e3713SNeil Armstrong 		vmode = meson_venc_hdmi_get_vic_vmode(vic);
994335e3713SNeil Armstrong 		if (!vmode) {
9959c936b12SNeil Armstrong 			dev_err(priv->dev, "%s: Fatal Error, unsupported mode "
9963273fc63SNeil Armstrong 				DRM_MODE_FMT "\n", __func__,
9973273fc63SNeil Armstrong 				DRM_MODE_ARG(mode));
998335e3713SNeil Armstrong 			return;
999335e3713SNeil Armstrong 		}
10003273fc63SNeil Armstrong 	} else {
10013273fc63SNeil Armstrong 		meson_venc_hdmi_get_dmt_vmode(mode, &vmode_dmt);
10023273fc63SNeil Armstrong 		vmode = &vmode_dmt;
1003adf59dd2SJorge Ramirez-Ortiz 		use_enci = false;
1004335e3713SNeil Armstrong 	}
1005335e3713SNeil Armstrong 
1006335e3713SNeil Armstrong 	/* Repeat VENC pixels for 480/576i/p, 720p50/60 and 1080p50/60 */
1007335e3713SNeil Armstrong 	if (meson_venc_hdmi_venc_repeat(vic))
1008335e3713SNeil Armstrong 		venc_repeat = true;
1009335e3713SNeil Armstrong 
1010335e3713SNeil Armstrong 	eof_lines = mode->vsync_start - mode->vdisplay;
1011335e3713SNeil Armstrong 	if (mode->flags & DRM_MODE_FLAG_INTERLACE)
1012335e3713SNeil Armstrong 		eof_lines /= 2;
1013335e3713SNeil Armstrong 	sof_lines = mode->vtotal - mode->vsync_end;
1014335e3713SNeil Armstrong 	if (mode->flags & DRM_MODE_FLAG_INTERLACE)
1015335e3713SNeil Armstrong 		sof_lines /= 2;
1016335e3713SNeil Armstrong 	vsync_lines = mode->vsync_end - mode->vsync_start;
1017335e3713SNeil Armstrong 	if (mode->flags & DRM_MODE_FLAG_INTERLACE)
1018335e3713SNeil Armstrong 		vsync_lines /= 2;
1019335e3713SNeil Armstrong 
1020335e3713SNeil Armstrong 	total_pixels_venc = mode->htotal;
1021335e3713SNeil Armstrong 	if (hdmi_repeat)
1022335e3713SNeil Armstrong 		total_pixels_venc /= 2;
1023335e3713SNeil Armstrong 	if (venc_repeat)
1024335e3713SNeil Armstrong 		total_pixels_venc *= 2;
1025335e3713SNeil Armstrong 
1026335e3713SNeil Armstrong 	active_pixels_venc = mode->hdisplay;
1027335e3713SNeil Armstrong 	if (hdmi_repeat)
1028335e3713SNeil Armstrong 		active_pixels_venc /= 2;
1029335e3713SNeil Armstrong 	if (venc_repeat)
1030335e3713SNeil Armstrong 		active_pixels_venc *= 2;
1031335e3713SNeil Armstrong 
1032335e3713SNeil Armstrong 	front_porch_venc = (mode->hsync_start - mode->hdisplay);
1033335e3713SNeil Armstrong 	if (hdmi_repeat)
1034335e3713SNeil Armstrong 		front_porch_venc /= 2;
1035335e3713SNeil Armstrong 	if (venc_repeat)
1036335e3713SNeil Armstrong 		front_porch_venc *= 2;
1037335e3713SNeil Armstrong 
1038335e3713SNeil Armstrong 	hsync_pixels_venc = (mode->hsync_end - mode->hsync_start);
1039335e3713SNeil Armstrong 	if (hdmi_repeat)
1040335e3713SNeil Armstrong 		hsync_pixels_venc /= 2;
1041335e3713SNeil Armstrong 	if (venc_repeat)
1042335e3713SNeil Armstrong 		hsync_pixels_venc *= 2;
1043335e3713SNeil Armstrong 
1044335e3713SNeil Armstrong 	/* Disable VDACs */
10459c936b12SNeil Armstrong 	writel_bits_relaxed(0xff, 0xff,
1046335e3713SNeil Armstrong 			priv->io_base + _REG(VENC_VDAC_SETTING));
1047335e3713SNeil Armstrong 
1048335e3713SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCI_VIDEO_EN));
1049335e3713SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCP_VIDEO_EN));
1050335e3713SNeil Armstrong 
1051335e3713SNeil Armstrong 	if (use_enci) {
1052335e3713SNeil Armstrong 		unsigned int lines_f0;
1053335e3713SNeil Armstrong 		unsigned int lines_f1;
1054335e3713SNeil Armstrong 
1055335e3713SNeil Armstrong 		/* CVBS Filter settings */
10567eef9e61SJulien Masson 		writel_relaxed(ENCI_CFILT_CMPT_SEL_HIGH | 0x10,
10577eef9e61SJulien Masson 			       priv->io_base + _REG(ENCI_CFILT_CTRL));
10587eef9e61SJulien Masson 		writel_relaxed(ENCI_CFILT_CMPT_CR_DLY(2) |
10597eef9e61SJulien Masson 			       ENCI_CFILT_CMPT_CB_DLY(1),
10607eef9e61SJulien Masson 			       priv->io_base + _REG(ENCI_CFILT_CTRL2));
1061335e3713SNeil Armstrong 
1062335e3713SNeil Armstrong 		/* Digital Video Select : Interlace, clk27 clk, external */
1063335e3713SNeil Armstrong 		writel_relaxed(0, priv->io_base + _REG(VENC_DVI_SETTING));
1064335e3713SNeil Armstrong 
1065335e3713SNeil Armstrong 		/* Reset Video Mode */
1066335e3713SNeil Armstrong 		writel_relaxed(0, priv->io_base + _REG(ENCI_VIDEO_MODE));
1067335e3713SNeil Armstrong 		writel_relaxed(0, priv->io_base + _REG(ENCI_VIDEO_MODE_ADV));
1068335e3713SNeil Armstrong 
1069335e3713SNeil Armstrong 		/* Horizontal sync signal output */
1070335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.hso_begin,
1071335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_SYNC_HSO_BEGIN));
1072335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.hso_end,
1073335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_SYNC_HSO_END));
1074335e3713SNeil Armstrong 
1075335e3713SNeil Armstrong 		/* Vertical Sync lines */
1076335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.vso_even,
1077335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_SYNC_VSO_EVNLN));
1078335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.vso_odd,
1079335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_SYNC_VSO_ODDLN));
1080335e3713SNeil Armstrong 
1081335e3713SNeil Armstrong 		/* Macrovision max amplitude change */
10827eef9e61SJulien Masson 		writel_relaxed(ENCI_MACV_MAX_AMP_ENABLE_CHANGE |
10837eef9e61SJulien Masson 			       ENCI_MACV_MAX_AMP_VAL(vmode->enci.macv_max_amp),
1084335e3713SNeil Armstrong 			       priv->io_base + _REG(ENCI_MACV_MAX_AMP));
1085335e3713SNeil Armstrong 
1086335e3713SNeil Armstrong 		/* Video mode */
1087335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.video_prog_mode,
1088335e3713SNeil Armstrong 				priv->io_base + _REG(VENC_VIDEO_PROG_MODE));
1089335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.video_mode,
1090335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_VIDEO_MODE));
1091335e3713SNeil Armstrong 
1092e1012141SJulien Masson 		/*
1093e1012141SJulien Masson 		 * Advanced Video Mode :
1094335e3713SNeil Armstrong 		 * Demux shifting 0x2
1095335e3713SNeil Armstrong 		 * Blank line end at line17/22
1096335e3713SNeil Armstrong 		 * High bandwidth Luma Filter
1097335e3713SNeil Armstrong 		 * Low bandwidth Chroma Filter
1098335e3713SNeil Armstrong 		 * Bypass luma low pass filter
1099335e3713SNeil Armstrong 		 * No macrovision on CSYNC
1100335e3713SNeil Armstrong 		 */
11017eef9e61SJulien Masson 		writel_relaxed(ENCI_VIDEO_MODE_ADV_DMXMD(2) |
11027eef9e61SJulien Masson 			       ENCI_VIDEO_MODE_ADV_VBICTL_LINE_17_22 |
11037eef9e61SJulien Masson 			       ENCI_VIDEO_MODE_ADV_YBW_HIGH,
11047eef9e61SJulien Masson 			       priv->io_base + _REG(ENCI_VIDEO_MODE_ADV));
1105335e3713SNeil Armstrong 
1106335e3713SNeil Armstrong 		writel(vmode->enci.sch_adjust,
1107335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_VIDEO_SCH));
1108335e3713SNeil Armstrong 
1109335e3713SNeil Armstrong 		/* Sync mode : MASTER Master mode, free run, send HSO/VSO out */
1110335e3713SNeil Armstrong 		writel_relaxed(0x07, priv->io_base + _REG(ENCI_SYNC_MODE));
1111335e3713SNeil Armstrong 
1112335e3713SNeil Armstrong 		if (vmode->enci.yc_delay)
1113335e3713SNeil Armstrong 			writel_relaxed(vmode->enci.yc_delay,
1114335e3713SNeil Armstrong 					priv->io_base + _REG(ENCI_YC_DELAY));
1115335e3713SNeil Armstrong 
1116335e3713SNeil Armstrong 
1117335e3713SNeil Armstrong 		/* UNreset Interlaced TV Encoder */
1118335e3713SNeil Armstrong 		writel_relaxed(0, priv->io_base + _REG(ENCI_DBG_PX_RST));
1119335e3713SNeil Armstrong 
11207eef9e61SJulien Masson 		/*
11217eef9e61SJulien Masson 		 * Enable Vfifo2vd and set Y_Cb_Y_Cr:
11227eef9e61SJulien Masson 		 * Corresponding value:
11237eef9e61SJulien Masson 		 * Y  => 00 or 10
11247eef9e61SJulien Masson 		 * Cb => 01
11257eef9e61SJulien Masson 		 * Cr => 11
11267eef9e61SJulien Masson 		 * Ex: 0x4e => 01001110 would mean Cb/Y/Cr/Y
11277eef9e61SJulien Masson 		 */
11287eef9e61SJulien Masson 		writel_relaxed(ENCI_VFIFO2VD_CTL_ENABLE |
11297eef9e61SJulien Masson 			       ENCI_VFIFO2VD_CTL_VD_SEL(0x4e),
11307eef9e61SJulien Masson 			       priv->io_base + _REG(ENCI_VFIFO2VD_CTL));
1131335e3713SNeil Armstrong 
1132335e3713SNeil Armstrong 		/* Timings */
1133335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.pixel_start,
1134335e3713SNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_PIXEL_START));
1135335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.pixel_end,
1136335e3713SNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_PIXEL_END));
1137335e3713SNeil Armstrong 
1138335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.top_field_line_start,
1139335e3713SNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_TOP_START));
1140335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.top_field_line_end,
1141335e3713SNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_TOP_END));
1142335e3713SNeil Armstrong 
1143335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.bottom_field_line_start,
1144335e3713SNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_BOT_START));
1145335e3713SNeil Armstrong 		writel_relaxed(vmode->enci.bottom_field_line_end,
1146335e3713SNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_BOT_END));
1147335e3713SNeil Armstrong 
1148335e3713SNeil Armstrong 		/* Select ENCI for VIU */
1149335e3713SNeil Armstrong 		meson_vpp_setup_mux(priv, MESON_VIU_VPP_MUX_ENCI);
1150335e3713SNeil Armstrong 
1151335e3713SNeil Armstrong 		/* Interlace video enable */
11527eef9e61SJulien Masson 		writel_relaxed(ENCI_VIDEO_EN_ENABLE,
11537eef9e61SJulien Masson 			       priv->io_base + _REG(ENCI_VIDEO_EN));
1154335e3713SNeil Armstrong 
1155335e3713SNeil Armstrong 		lines_f0 = mode->vtotal >> 1;
1156335e3713SNeil Armstrong 		lines_f1 = lines_f0 + 1;
1157335e3713SNeil Armstrong 
1158335e3713SNeil Armstrong 		de_h_begin = modulo(readl_relaxed(priv->io_base +
1159335e3713SNeil Armstrong 					_REG(ENCI_VFIFO2VD_PIXEL_START))
1160335e3713SNeil Armstrong 					+ venc_hdmi_latency,
1161335e3713SNeil Armstrong 				    total_pixels_venc);
1162335e3713SNeil Armstrong 		de_h_end  = modulo(de_h_begin + active_pixels_venc,
1163335e3713SNeil Armstrong 				   total_pixels_venc);
1164335e3713SNeil Armstrong 
1165335e3713SNeil Armstrong 		writel_relaxed(de_h_begin,
1166335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DE_H_BEGIN));
1167335e3713SNeil Armstrong 		writel_relaxed(de_h_end,
1168335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DE_H_END));
1169335e3713SNeil Armstrong 
1170335e3713SNeil Armstrong 		de_v_begin_even = readl_relaxed(priv->io_base +
1171335e3713SNeil Armstrong 					_REG(ENCI_VFIFO2VD_LINE_TOP_START));
1172335e3713SNeil Armstrong 		de_v_end_even  = de_v_begin_even + mode->vdisplay;
1173335e3713SNeil Armstrong 		de_v_begin_odd = readl_relaxed(priv->io_base +
1174335e3713SNeil Armstrong 					_REG(ENCI_VFIFO2VD_LINE_BOT_START));
1175335e3713SNeil Armstrong 		de_v_end_odd = de_v_begin_odd + mode->vdisplay;
1176335e3713SNeil Armstrong 
1177335e3713SNeil Armstrong 		writel_relaxed(de_v_begin_even,
1178335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DE_V_BEGIN_EVEN));
1179335e3713SNeil Armstrong 		writel_relaxed(de_v_end_even,
1180335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DE_V_END_EVEN));
1181335e3713SNeil Armstrong 		writel_relaxed(de_v_begin_odd,
1182335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DE_V_BEGIN_ODD));
1183335e3713SNeil Armstrong 		writel_relaxed(de_v_end_odd,
1184335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DE_V_END_ODD));
1185335e3713SNeil Armstrong 
1186335e3713SNeil Armstrong 		/* Program Hsync timing */
1187335e3713SNeil Armstrong 		hs_begin = de_h_end + front_porch_venc;
1188335e3713SNeil Armstrong 		if (de_h_end + front_porch_venc >= total_pixels_venc) {
1189335e3713SNeil Armstrong 			hs_begin -= total_pixels_venc;
1190335e3713SNeil Armstrong 			vs_adjust  = 1;
1191335e3713SNeil Armstrong 		} else {
1192335e3713SNeil Armstrong 			hs_begin = de_h_end + front_porch_venc;
1193335e3713SNeil Armstrong 			vs_adjust  = 0;
1194335e3713SNeil Armstrong 		}
1195335e3713SNeil Armstrong 
1196335e3713SNeil Armstrong 		hs_end = modulo(hs_begin + hsync_pixels_venc,
1197335e3713SNeil Armstrong 				total_pixels_venc);
1198335e3713SNeil Armstrong 		writel_relaxed(hs_begin,
1199335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_HSO_BEGIN));
1200335e3713SNeil Armstrong 		writel_relaxed(hs_end,
1201335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_HSO_END));
1202335e3713SNeil Armstrong 
1203335e3713SNeil Armstrong 		/* Program Vsync timing for even field */
1204335e3713SNeil Armstrong 		if (((de_v_end_odd - 1) + eof_lines + vs_adjust) >= lines_f1) {
1205335e3713SNeil Armstrong 			vs_bline_evn = (de_v_end_odd - 1)
1206335e3713SNeil Armstrong 					+ eof_lines
1207335e3713SNeil Armstrong 					+ vs_adjust
1208335e3713SNeil Armstrong 					- lines_f1;
1209335e3713SNeil Armstrong 			vs_eline_evn = vs_bline_evn + vsync_lines;
1210335e3713SNeil Armstrong 
1211335e3713SNeil Armstrong 			writel_relaxed(vs_bline_evn,
1212335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_BLINE_EVN));
1213335e3713SNeil Armstrong 
1214335e3713SNeil Armstrong 			writel_relaxed(vs_eline_evn,
1215335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_ELINE_EVN));
1216335e3713SNeil Armstrong 
1217335e3713SNeil Armstrong 			writel_relaxed(hs_begin,
1218335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_BEGIN_EVN));
1219335e3713SNeil Armstrong 			writel_relaxed(hs_begin,
1220335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_END_EVN));
1221335e3713SNeil Armstrong 		} else {
1222335e3713SNeil Armstrong 			vs_bline_odd = (de_v_end_odd - 1)
1223335e3713SNeil Armstrong 					+ eof_lines
1224335e3713SNeil Armstrong 					+ vs_adjust;
1225335e3713SNeil Armstrong 
1226335e3713SNeil Armstrong 			writel_relaxed(vs_bline_odd,
1227335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_BLINE_ODD));
1228335e3713SNeil Armstrong 
1229335e3713SNeil Armstrong 			writel_relaxed(hs_begin,
1230335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_BEGIN_ODD));
1231335e3713SNeil Armstrong 
1232335e3713SNeil Armstrong 			if ((vs_bline_odd + vsync_lines) >= lines_f1) {
1233335e3713SNeil Armstrong 				vs_eline_evn = vs_bline_odd
1234335e3713SNeil Armstrong 						+ vsync_lines
1235335e3713SNeil Armstrong 						- lines_f1;
1236335e3713SNeil Armstrong 
1237335e3713SNeil Armstrong 				writel_relaxed(vs_eline_evn, priv->io_base
1238335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_ELINE_EVN));
1239335e3713SNeil Armstrong 
1240335e3713SNeil Armstrong 				writel_relaxed(hs_begin, priv->io_base
1241335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_END_EVN));
1242335e3713SNeil Armstrong 			} else {
1243335e3713SNeil Armstrong 				vs_eline_odd = vs_bline_odd
1244335e3713SNeil Armstrong 						+ vsync_lines;
1245335e3713SNeil Armstrong 
1246335e3713SNeil Armstrong 				writel_relaxed(vs_eline_odd, priv->io_base
1247335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_ELINE_ODD));
1248335e3713SNeil Armstrong 
1249335e3713SNeil Armstrong 				writel_relaxed(hs_begin, priv->io_base
1250335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_END_ODD));
1251335e3713SNeil Armstrong 			}
1252335e3713SNeil Armstrong 		}
1253335e3713SNeil Armstrong 
1254335e3713SNeil Armstrong 		/* Program Vsync timing for odd field */
1255335e3713SNeil Armstrong 		if (((de_v_end_even - 1) + (eof_lines + 1)) >= lines_f0) {
1256335e3713SNeil Armstrong 			vs_bline_odd = (de_v_end_even - 1)
1257335e3713SNeil Armstrong 					+ (eof_lines + 1)
1258335e3713SNeil Armstrong 					- lines_f0;
1259335e3713SNeil Armstrong 			vs_eline_odd = vs_bline_odd + vsync_lines;
1260335e3713SNeil Armstrong 
1261335e3713SNeil Armstrong 			writel_relaxed(vs_bline_odd,
1262335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_BLINE_ODD));
1263335e3713SNeil Armstrong 
1264335e3713SNeil Armstrong 			writel_relaxed(vs_eline_odd,
1265335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_ELINE_ODD));
1266335e3713SNeil Armstrong 
1267335e3713SNeil Armstrong 			vso_begin_odd  = modulo(hs_begin
1268335e3713SNeil Armstrong 						+ (total_pixels_venc >> 1),
1269335e3713SNeil Armstrong 						total_pixels_venc);
1270335e3713SNeil Armstrong 
1271335e3713SNeil Armstrong 			writel_relaxed(vso_begin_odd,
1272335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_BEGIN_ODD));
1273335e3713SNeil Armstrong 			writel_relaxed(vso_begin_odd,
1274335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_END_ODD));
1275335e3713SNeil Armstrong 		} else {
1276335e3713SNeil Armstrong 			vs_bline_evn = (de_v_end_even - 1)
1277335e3713SNeil Armstrong 					+ (eof_lines + 1);
1278335e3713SNeil Armstrong 
1279335e3713SNeil Armstrong 			writel_relaxed(vs_bline_evn,
1280335e3713SNeil Armstrong 				priv->io_base + _REG(ENCI_DVI_VSO_BLINE_EVN));
1281335e3713SNeil Armstrong 
1282335e3713SNeil Armstrong 			vso_begin_evn  = modulo(hs_begin
1283335e3713SNeil Armstrong 						+ (total_pixels_venc >> 1),
1284335e3713SNeil Armstrong 						total_pixels_venc);
1285335e3713SNeil Armstrong 
1286335e3713SNeil Armstrong 			writel_relaxed(vso_begin_evn, priv->io_base
1287335e3713SNeil Armstrong 					+ _REG(ENCI_DVI_VSO_BEGIN_EVN));
1288335e3713SNeil Armstrong 
1289335e3713SNeil Armstrong 			if (vs_bline_evn + vsync_lines >= lines_f0) {
1290335e3713SNeil Armstrong 				vs_eline_odd = vs_bline_evn
1291335e3713SNeil Armstrong 						+ vsync_lines
1292335e3713SNeil Armstrong 						- lines_f0;
1293335e3713SNeil Armstrong 
1294335e3713SNeil Armstrong 				writel_relaxed(vs_eline_odd, priv->io_base
1295335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_ELINE_ODD));
1296335e3713SNeil Armstrong 
1297335e3713SNeil Armstrong 				writel_relaxed(vso_begin_evn, priv->io_base
1298335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_END_ODD));
1299335e3713SNeil Armstrong 			} else {
1300335e3713SNeil Armstrong 				vs_eline_evn = vs_bline_evn + vsync_lines;
1301335e3713SNeil Armstrong 
1302335e3713SNeil Armstrong 				writel_relaxed(vs_eline_evn, priv->io_base
1303335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_ELINE_EVN));
1304335e3713SNeil Armstrong 
1305335e3713SNeil Armstrong 				writel_relaxed(vso_begin_evn, priv->io_base
1306335e3713SNeil Armstrong 						+ _REG(ENCI_DVI_VSO_END_EVN));
1307335e3713SNeil Armstrong 			}
1308335e3713SNeil Armstrong 		}
1309335e3713SNeil Armstrong 	} else {
1310335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.dvi_settings,
1311335e3713SNeil Armstrong 				priv->io_base + _REG(VENC_DVI_SETTING));
1312335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.video_mode,
1313335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_MODE));
1314335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.video_mode_adv,
1315335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_MODE_ADV));
1316335e3713SNeil Armstrong 		if (vmode->encp.video_prog_mode_present)
1317335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.video_prog_mode,
1318335e3713SNeil Armstrong 				priv->io_base + _REG(VENC_VIDEO_PROG_MODE));
1319335e3713SNeil Armstrong 		if (vmode->encp.video_sync_mode_present)
1320335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.video_sync_mode,
1321335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_SYNC_MODE));
1322335e3713SNeil Armstrong 		if (vmode->encp.video_yc_dly_present)
1323335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.video_yc_dly,
1324335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_YC_DLY));
1325335e3713SNeil Armstrong 		if (vmode->encp.video_rgb_ctrl_present)
1326335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.video_rgb_ctrl,
1327335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_RGB_CTRL));
1328335e3713SNeil Armstrong 		if (vmode->encp.video_filt_ctrl_present)
1329335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.video_filt_ctrl,
1330335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_FILT_CTRL));
1331335e3713SNeil Armstrong 		if (vmode->encp.video_ofld_voav_ofst_present)
1332335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.video_ofld_voav_ofst,
1333335e3713SNeil Armstrong 				priv->io_base
1334335e3713SNeil Armstrong 				+ _REG(ENCP_VIDEO_OFLD_VOAV_OFST));
1335335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.yfp1_htime,
1336335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_YFP1_HTIME));
1337335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.yfp2_htime,
1338335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_YFP2_HTIME));
1339335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.max_pxcnt,
1340335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_MAX_PXCNT));
1341335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.hspuls_begin,
1342335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_HSPULS_BEGIN));
1343335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.hspuls_end,
1344335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_HSPULS_END));
1345335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.hspuls_switch,
1346335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_HSPULS_SWITCH));
1347335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vspuls_begin,
1348335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSPULS_BEGIN));
1349335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vspuls_end,
1350335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSPULS_END));
1351335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vspuls_bline,
1352335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSPULS_BLINE));
1353335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vspuls_eline,
1354335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSPULS_ELINE));
1355335e3713SNeil Armstrong 		if (vmode->encp.eqpuls_begin_present)
1356335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.eqpuls_begin,
1357335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_EQPULS_BEGIN));
1358335e3713SNeil Armstrong 		if (vmode->encp.eqpuls_end_present)
1359335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.eqpuls_end,
1360335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_EQPULS_END));
1361335e3713SNeil Armstrong 		if (vmode->encp.eqpuls_bline_present)
1362335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.eqpuls_bline,
1363335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_EQPULS_BLINE));
1364335e3713SNeil Armstrong 		if (vmode->encp.eqpuls_eline_present)
1365335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.eqpuls_eline,
1366335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_EQPULS_ELINE));
1367335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.havon_begin,
1368335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_HAVON_BEGIN));
1369335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.havon_end,
1370335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_HAVON_END));
1371335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vavon_bline,
1372335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VAVON_BLINE));
1373335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vavon_eline,
1374335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VAVON_ELINE));
1375335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.hso_begin,
1376335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_HSO_BEGIN));
1377335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.hso_end,
1378335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_HSO_END));
1379335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vso_begin,
1380335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSO_BEGIN));
1381335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vso_end,
1382335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSO_END));
1383335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.vso_bline,
1384335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSO_BLINE));
1385335e3713SNeil Armstrong 		if (vmode->encp.vso_eline_present)
1386335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.vso_eline,
1387335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_VSO_ELINE));
1388335e3713SNeil Armstrong 		if (vmode->encp.sy_val_present)
1389335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.sy_val,
1390335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_SY_VAL));
1391335e3713SNeil Armstrong 		if (vmode->encp.sy2_val_present)
1392335e3713SNeil Armstrong 			writel_relaxed(vmode->encp.sy2_val,
1393335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_SY2_VAL));
1394335e3713SNeil Armstrong 		writel_relaxed(vmode->encp.max_lncnt,
1395335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_VIDEO_MAX_LNCNT));
1396335e3713SNeil Armstrong 
1397335e3713SNeil Armstrong 		writel_relaxed(1, priv->io_base + _REG(ENCP_VIDEO_EN));
1398335e3713SNeil Armstrong 
1399335e3713SNeil Armstrong 		/* Set DE signal’s polarity is active high */
14007eef9e61SJulien Masson 		writel_bits_relaxed(ENCP_VIDEO_MODE_DE_V_HIGH,
14017eef9e61SJulien Masson 				    ENCP_VIDEO_MODE_DE_V_HIGH,
1402335e3713SNeil Armstrong 				    priv->io_base + _REG(ENCP_VIDEO_MODE));
1403335e3713SNeil Armstrong 
1404335e3713SNeil Armstrong 		/* Program DE timing */
1405335e3713SNeil Armstrong 		de_h_begin = modulo(readl_relaxed(priv->io_base +
1406335e3713SNeil Armstrong 					_REG(ENCP_VIDEO_HAVON_BEGIN))
1407335e3713SNeil Armstrong 					+ venc_hdmi_latency,
1408335e3713SNeil Armstrong 				    total_pixels_venc);
1409335e3713SNeil Armstrong 		de_h_end = modulo(de_h_begin + active_pixels_venc,
1410335e3713SNeil Armstrong 				  total_pixels_venc);
1411335e3713SNeil Armstrong 
1412335e3713SNeil Armstrong 		writel_relaxed(de_h_begin,
1413335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DE_H_BEGIN));
1414335e3713SNeil Armstrong 		writel_relaxed(de_h_end,
1415335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DE_H_END));
1416335e3713SNeil Armstrong 
1417335e3713SNeil Armstrong 		/* Program DE timing for even field */
1418335e3713SNeil Armstrong 		de_v_begin_even = readl_relaxed(priv->io_base
1419335e3713SNeil Armstrong 						+ _REG(ENCP_VIDEO_VAVON_BLINE));
1420335e3713SNeil Armstrong 		if (mode->flags & DRM_MODE_FLAG_INTERLACE)
1421335e3713SNeil Armstrong 			de_v_end_even = de_v_begin_even +
1422335e3713SNeil Armstrong 					(mode->vdisplay / 2);
1423335e3713SNeil Armstrong 		else
1424335e3713SNeil Armstrong 			de_v_end_even = de_v_begin_even + mode->vdisplay;
1425335e3713SNeil Armstrong 
1426335e3713SNeil Armstrong 		writel_relaxed(de_v_begin_even,
1427335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DE_V_BEGIN_EVEN));
1428335e3713SNeil Armstrong 		writel_relaxed(de_v_end_even,
1429335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DE_V_END_EVEN));
1430335e3713SNeil Armstrong 
1431335e3713SNeil Armstrong 		/* Program DE timing for odd field if needed */
1432335e3713SNeil Armstrong 		if (mode->flags & DRM_MODE_FLAG_INTERLACE) {
1433335e3713SNeil Armstrong 			unsigned int ofld_voav_ofst =
1434335e3713SNeil Armstrong 				readl_relaxed(priv->io_base +
1435335e3713SNeil Armstrong 					_REG(ENCP_VIDEO_OFLD_VOAV_OFST));
1436335e3713SNeil Armstrong 			de_v_begin_odd = to_signed((ofld_voav_ofst & 0xf0) >> 4)
1437335e3713SNeil Armstrong 						+ de_v_begin_even
1438335e3713SNeil Armstrong 						+ ((mode->vtotal - 1) / 2);
1439335e3713SNeil Armstrong 			de_v_end_odd = de_v_begin_odd + (mode->vdisplay / 2);
1440335e3713SNeil Armstrong 
1441335e3713SNeil Armstrong 			writel_relaxed(de_v_begin_odd,
1442335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DE_V_BEGIN_ODD));
1443335e3713SNeil Armstrong 			writel_relaxed(de_v_end_odd,
1444335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DE_V_END_ODD));
1445335e3713SNeil Armstrong 		}
1446335e3713SNeil Armstrong 
1447335e3713SNeil Armstrong 		/* Program Hsync timing */
1448335e3713SNeil Armstrong 		if ((de_h_end + front_porch_venc) >= total_pixels_venc) {
1449335e3713SNeil Armstrong 			hs_begin = de_h_end
1450335e3713SNeil Armstrong 				   + front_porch_venc
1451335e3713SNeil Armstrong 				   - total_pixels_venc;
1452335e3713SNeil Armstrong 			vs_adjust  = 1;
1453335e3713SNeil Armstrong 		} else {
1454335e3713SNeil Armstrong 			hs_begin = de_h_end
1455335e3713SNeil Armstrong 				   + front_porch_venc;
1456335e3713SNeil Armstrong 			vs_adjust  = 0;
1457335e3713SNeil Armstrong 		}
1458335e3713SNeil Armstrong 
1459335e3713SNeil Armstrong 		hs_end = modulo(hs_begin + hsync_pixels_venc,
1460335e3713SNeil Armstrong 				total_pixels_venc);
1461335e3713SNeil Armstrong 
1462335e3713SNeil Armstrong 		writel_relaxed(hs_begin,
1463335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_HSO_BEGIN));
1464335e3713SNeil Armstrong 		writel_relaxed(hs_end,
1465335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_HSO_END));
1466335e3713SNeil Armstrong 
1467335e3713SNeil Armstrong 		/* Program Vsync timing for even field */
1468335e3713SNeil Armstrong 		if (de_v_begin_even >=
1469335e3713SNeil Armstrong 				(sof_lines + vsync_lines + (1 - vs_adjust)))
1470335e3713SNeil Armstrong 			vs_bline_evn = de_v_begin_even
1471335e3713SNeil Armstrong 					- sof_lines
1472335e3713SNeil Armstrong 					- vsync_lines
1473335e3713SNeil Armstrong 					- (1 - vs_adjust);
1474335e3713SNeil Armstrong 		else
1475335e3713SNeil Armstrong 			vs_bline_evn = mode->vtotal
1476335e3713SNeil Armstrong 					+ de_v_begin_even
1477335e3713SNeil Armstrong 					- sof_lines
1478335e3713SNeil Armstrong 					- vsync_lines
1479335e3713SNeil Armstrong 					- (1 - vs_adjust);
1480335e3713SNeil Armstrong 
1481335e3713SNeil Armstrong 		vs_eline_evn = modulo(vs_bline_evn + vsync_lines,
1482335e3713SNeil Armstrong 					mode->vtotal);
1483335e3713SNeil Armstrong 
1484335e3713SNeil Armstrong 		writel_relaxed(vs_bline_evn,
1485335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_BLINE_EVN));
1486335e3713SNeil Armstrong 		writel_relaxed(vs_eline_evn,
1487335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_ELINE_EVN));
1488335e3713SNeil Armstrong 
1489335e3713SNeil Armstrong 		vso_begin_evn = hs_begin;
1490335e3713SNeil Armstrong 		writel_relaxed(vso_begin_evn,
1491335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_BEGIN_EVN));
1492335e3713SNeil Armstrong 		writel_relaxed(vso_begin_evn,
1493335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_END_EVN));
1494335e3713SNeil Armstrong 
1495335e3713SNeil Armstrong 		/* Program Vsync timing for odd field if needed */
1496335e3713SNeil Armstrong 		if (mode->flags & DRM_MODE_FLAG_INTERLACE) {
1497335e3713SNeil Armstrong 			vs_bline_odd = (de_v_begin_odd - 1)
1498335e3713SNeil Armstrong 					- sof_lines
1499335e3713SNeil Armstrong 					- vsync_lines;
1500335e3713SNeil Armstrong 			vs_eline_odd = (de_v_begin_odd - 1)
1501335e3713SNeil Armstrong 					- vsync_lines;
1502335e3713SNeil Armstrong 			vso_begin_odd  = modulo(hs_begin
1503335e3713SNeil Armstrong 						+ (total_pixels_venc >> 1),
1504335e3713SNeil Armstrong 						total_pixels_venc);
1505335e3713SNeil Armstrong 
1506335e3713SNeil Armstrong 			writel_relaxed(vs_bline_odd,
1507335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_BLINE_ODD));
1508335e3713SNeil Armstrong 			writel_relaxed(vs_eline_odd,
1509335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_ELINE_ODD));
1510335e3713SNeil Armstrong 			writel_relaxed(vso_begin_odd,
1511335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_BEGIN_ODD));
1512335e3713SNeil Armstrong 			writel_relaxed(vso_begin_odd,
1513335e3713SNeil Armstrong 				priv->io_base + _REG(ENCP_DVI_VSO_END_ODD));
1514335e3713SNeil Armstrong 		}
1515335e3713SNeil Armstrong 
1516335e3713SNeil Armstrong 		/* Select ENCP for VIU */
1517335e3713SNeil Armstrong 		meson_vpp_setup_mux(priv, MESON_VIU_VPP_MUX_ENCP);
1518335e3713SNeil Armstrong 	}
1519335e3713SNeil Armstrong 
15207eef9e61SJulien Masson 	/* Set VPU HDMI setting */
15217eef9e61SJulien Masson 	/* Select ENCP or ENCI data to HDMI */
15227eef9e61SJulien Masson 	if (use_enci)
15237eef9e61SJulien Masson 		reg = VPU_HDMI_ENCI_DATA_TO_HDMI;
15247eef9e61SJulien Masson 	else
15257eef9e61SJulien Masson 		reg = VPU_HDMI_ENCP_DATA_TO_HDMI;
15267eef9e61SJulien Masson 
15277eef9e61SJulien Masson 	/* Invert polarity of HSYNC from VENC */
15287eef9e61SJulien Masson 	if (mode->flags & DRM_MODE_FLAG_PHSYNC)
15297eef9e61SJulien Masson 		reg |= VPU_HDMI_INV_HSYNC;
15307eef9e61SJulien Masson 
15317eef9e61SJulien Masson 	/* Invert polarity of VSYNC from VENC */
15327eef9e61SJulien Masson 	if (mode->flags & DRM_MODE_FLAG_PVSYNC)
15337eef9e61SJulien Masson 		reg |= VPU_HDMI_INV_VSYNC;
15347eef9e61SJulien Masson 
153564db601aSNeil Armstrong 	/* Output data format */
153664db601aSNeil Armstrong 	reg |= ycrcb_map;
15377eef9e61SJulien Masson 
15387eef9e61SJulien Masson 	/*
15397eef9e61SJulien Masson 	 * Write rate to the async FIFO between VENC and HDMI.
15407eef9e61SJulien Masson 	 * One write every 2 wr_clk.
15417eef9e61SJulien Masson 	 */
154264db601aSNeil Armstrong 	if (venc_repeat || yuv420_mode)
15437eef9e61SJulien Masson 		reg |= VPU_HDMI_WR_RATE(2);
15447eef9e61SJulien Masson 
15457eef9e61SJulien Masson 	/*
15467eef9e61SJulien Masson 	 * Read rate to the async FIFO between VENC and HDMI.
15477eef9e61SJulien Masson 	 * One read every 2 wr_clk.
15487eef9e61SJulien Masson 	 */
15497eef9e61SJulien Masson 	if (hdmi_repeat)
15507eef9e61SJulien Masson 		reg |= VPU_HDMI_RD_RATE(2);
15517eef9e61SJulien Masson 
15527eef9e61SJulien Masson 	writel_relaxed(reg, priv->io_base + _REG(VPU_HDMI_SETTING));
1553335e3713SNeil Armstrong 
1554335e3713SNeil Armstrong 	priv->venc.hdmi_repeat = hdmi_repeat;
1555335e3713SNeil Armstrong 	priv->venc.venc_repeat = venc_repeat;
1556335e3713SNeil Armstrong 	priv->venc.hdmi_use_enci = use_enci;
1557335e3713SNeil Armstrong 
1558335e3713SNeil Armstrong 	priv->venc.current_mode = MESON_VENC_MODE_HDMI;
1559335e3713SNeil Armstrong }
1560335e3713SNeil Armstrong EXPORT_SYMBOL_GPL(meson_venc_hdmi_mode_set);
1561335e3713SNeil Armstrong 
156251fc01a0SNeil Armstrong static unsigned short meson_encl_gamma_table[256] = {
156351fc01a0SNeil Armstrong 	0, 4, 8, 12, 16, 20, 24, 28, 32, 36, 40, 44, 48, 52, 56, 60,
156451fc01a0SNeil Armstrong 	64, 68, 72, 76, 80, 84, 88, 92, 96, 100, 104, 108, 112, 116, 120, 124,
156551fc01a0SNeil Armstrong 	128, 132, 136, 140, 144, 148, 152, 156, 160, 164, 168, 172, 176, 180, 184, 188,
156651fc01a0SNeil Armstrong 	192, 196, 200, 204, 208, 212, 216, 220, 224, 228, 232, 236, 240, 244, 248, 252,
156751fc01a0SNeil Armstrong 	256, 260, 264, 268, 272, 276, 280, 284, 288, 292, 296, 300, 304, 308, 312, 316,
156851fc01a0SNeil Armstrong 	320, 324, 328, 332, 336, 340, 344, 348, 352, 356, 360, 364, 368, 372, 376, 380,
156951fc01a0SNeil Armstrong 	384, 388, 392, 396, 400, 404, 408, 412, 416, 420, 424, 428, 432, 436, 440, 444,
157051fc01a0SNeil Armstrong 	448, 452, 456, 460, 464, 468, 472, 476, 480, 484, 488, 492, 496, 500, 504, 508,
157151fc01a0SNeil Armstrong 	512, 516, 520, 524, 528, 532, 536, 540, 544, 548, 552, 556, 560, 564, 568, 572,
157251fc01a0SNeil Armstrong 	576, 580, 584, 588, 592, 596, 600, 604, 608, 612, 616, 620, 624, 628, 632, 636,
157351fc01a0SNeil Armstrong 	640, 644, 648, 652, 656, 660, 664, 668, 672, 676, 680, 684, 688, 692, 696, 700,
157451fc01a0SNeil Armstrong 	704, 708, 712, 716, 720, 724, 728, 732, 736, 740, 744, 748, 752, 756, 760, 764,
157551fc01a0SNeil Armstrong 	768, 772, 776, 780, 784, 788, 792, 796, 800, 804, 808, 812, 816, 820, 824, 828,
157651fc01a0SNeil Armstrong 	832, 836, 840, 844, 848, 852, 856, 860, 864, 868, 872, 876, 880, 884, 888, 892,
157751fc01a0SNeil Armstrong 	896, 900, 904, 908, 912, 916, 920, 924, 928, 932, 936, 940, 944, 948, 952, 956,
157851fc01a0SNeil Armstrong 	960, 964, 968, 972, 976, 980, 984, 988, 992, 996, 1000, 1004, 1008, 1012, 1016, 1020,
157951fc01a0SNeil Armstrong };
158051fc01a0SNeil Armstrong 
meson_encl_set_gamma_table(struct meson_drm * priv,u16 * data,u32 rgb_mask)158151fc01a0SNeil Armstrong static void meson_encl_set_gamma_table(struct meson_drm *priv, u16 *data,
158251fc01a0SNeil Armstrong 				       u32 rgb_mask)
158351fc01a0SNeil Armstrong {
158451fc01a0SNeil Armstrong 	int i, ret;
158551fc01a0SNeil Armstrong 	u32 reg;
158651fc01a0SNeil Armstrong 
158751fc01a0SNeil Armstrong 	writel_bits_relaxed(L_GAMMA_CNTL_PORT_EN, 0,
158851fc01a0SNeil Armstrong 			    priv->io_base + _REG(L_GAMMA_CNTL_PORT));
158951fc01a0SNeil Armstrong 
159051fc01a0SNeil Armstrong 	ret = readl_relaxed_poll_timeout(priv->io_base + _REG(L_GAMMA_CNTL_PORT),
159151fc01a0SNeil Armstrong 					 reg, reg & L_GAMMA_CNTL_PORT_ADR_RDY, 10, 10000);
159251fc01a0SNeil Armstrong 	if (ret)
159351fc01a0SNeil Armstrong 		pr_warn("%s: GAMMA ADR_RDY timeout\n", __func__);
159451fc01a0SNeil Armstrong 
159551fc01a0SNeil Armstrong 	writel_relaxed(L_GAMMA_ADDR_PORT_AUTO_INC | rgb_mask |
159651fc01a0SNeil Armstrong 		       FIELD_PREP(L_GAMMA_ADDR_PORT_ADDR, 0),
159751fc01a0SNeil Armstrong 		       priv->io_base + _REG(L_GAMMA_ADDR_PORT));
159851fc01a0SNeil Armstrong 
159951fc01a0SNeil Armstrong 	for (i = 0; i < 256; i++) {
160051fc01a0SNeil Armstrong 		ret = readl_relaxed_poll_timeout(priv->io_base + _REG(L_GAMMA_CNTL_PORT),
160151fc01a0SNeil Armstrong 						 reg, reg & L_GAMMA_CNTL_PORT_WR_RDY,
160251fc01a0SNeil Armstrong 						 10, 10000);
160351fc01a0SNeil Armstrong 		if (ret)
160451fc01a0SNeil Armstrong 			pr_warn_once("%s: GAMMA WR_RDY timeout\n", __func__);
160551fc01a0SNeil Armstrong 
160651fc01a0SNeil Armstrong 		writel_relaxed(data[i], priv->io_base + _REG(L_GAMMA_DATA_PORT));
160751fc01a0SNeil Armstrong 	}
160851fc01a0SNeil Armstrong 
160951fc01a0SNeil Armstrong 	ret = readl_relaxed_poll_timeout(priv->io_base + _REG(L_GAMMA_CNTL_PORT),
161051fc01a0SNeil Armstrong 					 reg, reg & L_GAMMA_CNTL_PORT_ADR_RDY, 10, 10000);
161151fc01a0SNeil Armstrong 	if (ret)
161251fc01a0SNeil Armstrong 		pr_warn("%s: GAMMA ADR_RDY timeout\n", __func__);
161351fc01a0SNeil Armstrong 
161451fc01a0SNeil Armstrong 	writel_relaxed(L_GAMMA_ADDR_PORT_AUTO_INC | rgb_mask |
161551fc01a0SNeil Armstrong 		       FIELD_PREP(L_GAMMA_ADDR_PORT_ADDR, 0x23),
161651fc01a0SNeil Armstrong 		       priv->io_base + _REG(L_GAMMA_ADDR_PORT));
161751fc01a0SNeil Armstrong }
161851fc01a0SNeil Armstrong 
meson_encl_load_gamma(struct meson_drm * priv)161951fc01a0SNeil Armstrong void meson_encl_load_gamma(struct meson_drm *priv)
162051fc01a0SNeil Armstrong {
162151fc01a0SNeil Armstrong 	meson_encl_set_gamma_table(priv, meson_encl_gamma_table, L_GAMMA_ADDR_PORT_SEL_R);
162251fc01a0SNeil Armstrong 	meson_encl_set_gamma_table(priv, meson_encl_gamma_table, L_GAMMA_ADDR_PORT_SEL_G);
162351fc01a0SNeil Armstrong 	meson_encl_set_gamma_table(priv, meson_encl_gamma_table, L_GAMMA_ADDR_PORT_SEL_B);
162451fc01a0SNeil Armstrong 
162551fc01a0SNeil Armstrong 	writel_bits_relaxed(L_GAMMA_CNTL_PORT_EN, L_GAMMA_CNTL_PORT_EN,
162651fc01a0SNeil Armstrong 			    priv->io_base + _REG(L_GAMMA_CNTL_PORT));
162751fc01a0SNeil Armstrong }
162851fc01a0SNeil Armstrong 
meson_venc_mipi_dsi_mode_set(struct meson_drm * priv,const struct drm_display_mode * mode)162951fc01a0SNeil Armstrong void meson_venc_mipi_dsi_mode_set(struct meson_drm *priv,
163051fc01a0SNeil Armstrong 				  const struct drm_display_mode *mode)
163151fc01a0SNeil Armstrong {
163251fc01a0SNeil Armstrong 	unsigned int max_pxcnt;
163351fc01a0SNeil Armstrong 	unsigned int max_lncnt;
163451fc01a0SNeil Armstrong 	unsigned int havon_begin;
163551fc01a0SNeil Armstrong 	unsigned int havon_end;
163651fc01a0SNeil Armstrong 	unsigned int vavon_bline;
163751fc01a0SNeil Armstrong 	unsigned int vavon_eline;
163851fc01a0SNeil Armstrong 	unsigned int hso_begin;
163951fc01a0SNeil Armstrong 	unsigned int hso_end;
164051fc01a0SNeil Armstrong 	unsigned int vso_begin;
164151fc01a0SNeil Armstrong 	unsigned int vso_end;
164251fc01a0SNeil Armstrong 	unsigned int vso_bline;
164351fc01a0SNeil Armstrong 	unsigned int vso_eline;
164451fc01a0SNeil Armstrong 
164551fc01a0SNeil Armstrong 	max_pxcnt = mode->htotal - 1;
164651fc01a0SNeil Armstrong 	max_lncnt = mode->vtotal - 1;
164751fc01a0SNeil Armstrong 	havon_begin = mode->htotal - mode->hsync_start;
164851fc01a0SNeil Armstrong 	havon_end = havon_begin + mode->hdisplay - 1;
164951fc01a0SNeil Armstrong 	vavon_bline = mode->vtotal - mode->vsync_start;
165051fc01a0SNeil Armstrong 	vavon_eline = vavon_bline + mode->vdisplay - 1;
165151fc01a0SNeil Armstrong 	hso_begin = 0;
165251fc01a0SNeil Armstrong 	hso_end = mode->hsync_end - mode->hsync_start;
165351fc01a0SNeil Armstrong 	vso_begin = 0;
165451fc01a0SNeil Armstrong 	vso_end = 0;
165551fc01a0SNeil Armstrong 	vso_bline = 0;
165651fc01a0SNeil Armstrong 	vso_eline = mode->vsync_end - mode->vsync_start;
165751fc01a0SNeil Armstrong 
165851fc01a0SNeil Armstrong 	meson_vpp_setup_mux(priv, MESON_VIU_VPP_MUX_ENCL);
165951fc01a0SNeil Armstrong 
166051fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCL_VIDEO_EN));
166151fc01a0SNeil Armstrong 
166251fc01a0SNeil Armstrong 	writel_relaxed(ENCL_PX_LN_CNT_SHADOW_EN, priv->io_base + _REG(ENCL_VIDEO_MODE));
166351fc01a0SNeil Armstrong 	writel_relaxed(ENCL_VIDEO_MODE_ADV_VFIFO_EN |
166451fc01a0SNeil Armstrong 		       ENCL_VIDEO_MODE_ADV_GAIN_HDTV |
166551fc01a0SNeil Armstrong 		       ENCL_SEL_GAMMA_RGB_IN, priv->io_base + _REG(ENCL_VIDEO_MODE_ADV));
166651fc01a0SNeil Armstrong 
166751fc01a0SNeil Armstrong 	writel_relaxed(ENCL_VIDEO_FILT_CTRL_BYPASS_FILTER,
166851fc01a0SNeil Armstrong 		       priv->io_base + _REG(ENCL_VIDEO_FILT_CTRL));
166951fc01a0SNeil Armstrong 	writel_relaxed(max_pxcnt, priv->io_base + _REG(ENCL_VIDEO_MAX_PXCNT));
167051fc01a0SNeil Armstrong 	writel_relaxed(max_lncnt, priv->io_base + _REG(ENCL_VIDEO_MAX_LNCNT));
167151fc01a0SNeil Armstrong 	writel_relaxed(havon_begin, priv->io_base + _REG(ENCL_VIDEO_HAVON_BEGIN));
167251fc01a0SNeil Armstrong 	writel_relaxed(havon_end, priv->io_base + _REG(ENCL_VIDEO_HAVON_END));
167351fc01a0SNeil Armstrong 	writel_relaxed(vavon_bline, priv->io_base + _REG(ENCL_VIDEO_VAVON_BLINE));
167451fc01a0SNeil Armstrong 	writel_relaxed(vavon_eline, priv->io_base + _REG(ENCL_VIDEO_VAVON_ELINE));
167551fc01a0SNeil Armstrong 
167651fc01a0SNeil Armstrong 	writel_relaxed(hso_begin, priv->io_base + _REG(ENCL_VIDEO_HSO_BEGIN));
167751fc01a0SNeil Armstrong 	writel_relaxed(hso_end, priv->io_base + _REG(ENCL_VIDEO_HSO_END));
167851fc01a0SNeil Armstrong 	writel_relaxed(vso_begin, priv->io_base + _REG(ENCL_VIDEO_VSO_BEGIN));
167951fc01a0SNeil Armstrong 	writel_relaxed(vso_end, priv->io_base + _REG(ENCL_VIDEO_VSO_END));
168051fc01a0SNeil Armstrong 	writel_relaxed(vso_bline, priv->io_base + _REG(ENCL_VIDEO_VSO_BLINE));
168151fc01a0SNeil Armstrong 	writel_relaxed(vso_eline, priv->io_base + _REG(ENCL_VIDEO_VSO_ELINE));
168251fc01a0SNeil Armstrong 	writel_relaxed(ENCL_VIDEO_RGBIN_RGB | ENCL_VIDEO_RGBIN_ZBLK,
168351fc01a0SNeil Armstrong 		       priv->io_base + _REG(ENCL_VIDEO_RGBIN_CTRL));
168451fc01a0SNeil Armstrong 
168551fc01a0SNeil Armstrong 	/* default black pattern */
168651fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCL_TST_MDSEL));
168751fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCL_TST_Y));
168851fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCL_TST_CB));
168951fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCL_TST_CR));
169051fc01a0SNeil Armstrong 	writel_relaxed(1, priv->io_base + _REG(ENCL_TST_EN));
169151fc01a0SNeil Armstrong 	writel_bits_relaxed(ENCL_VIDEO_MODE_ADV_VFIFO_EN, 0,
169251fc01a0SNeil Armstrong 			    priv->io_base + _REG(ENCL_VIDEO_MODE_ADV));
169351fc01a0SNeil Armstrong 
169451fc01a0SNeil Armstrong 	writel_relaxed(1, priv->io_base + _REG(ENCL_VIDEO_EN));
169551fc01a0SNeil Armstrong 
169651fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(L_RGB_BASE_ADDR));
169751fc01a0SNeil Armstrong 	writel_relaxed(0x400, priv->io_base + _REG(L_RGB_COEFF_ADDR)); /* Magic value */
169851fc01a0SNeil Armstrong 
169951fc01a0SNeil Armstrong 	writel_relaxed(L_DITH_CNTL_DITH10_EN, priv->io_base + _REG(L_DITH_CNTL_ADDR));
170051fc01a0SNeil Armstrong 
170151fc01a0SNeil Armstrong 	/* DE signal for TTL */
170251fc01a0SNeil Armstrong 	writel_relaxed(havon_begin, priv->io_base + _REG(L_OEH_HS_ADDR));
170351fc01a0SNeil Armstrong 	writel_relaxed(havon_end + 1, priv->io_base + _REG(L_OEH_HE_ADDR));
170451fc01a0SNeil Armstrong 	writel_relaxed(vavon_bline, priv->io_base + _REG(L_OEH_VS_ADDR));
170551fc01a0SNeil Armstrong 	writel_relaxed(vavon_eline, priv->io_base + _REG(L_OEH_VE_ADDR));
170651fc01a0SNeil Armstrong 
170751fc01a0SNeil Armstrong 	/* DE signal for TTL */
170851fc01a0SNeil Armstrong 	writel_relaxed(havon_begin, priv->io_base + _REG(L_OEV1_HS_ADDR));
170951fc01a0SNeil Armstrong 	writel_relaxed(havon_end + 1, priv->io_base + _REG(L_OEV1_HE_ADDR));
171051fc01a0SNeil Armstrong 	writel_relaxed(vavon_bline, priv->io_base + _REG(L_OEV1_VS_ADDR));
171151fc01a0SNeil Armstrong 	writel_relaxed(vavon_eline, priv->io_base + _REG(L_OEV1_VE_ADDR));
171251fc01a0SNeil Armstrong 
171351fc01a0SNeil Armstrong 	/* Hsync signal for TTL */
171451fc01a0SNeil Armstrong 	if (mode->flags & DRM_MODE_FLAG_PHSYNC) {
171551fc01a0SNeil Armstrong 		writel_relaxed(hso_begin, priv->io_base + _REG(L_STH1_HS_ADDR));
171651fc01a0SNeil Armstrong 		writel_relaxed(hso_end, priv->io_base + _REG(L_STH1_HE_ADDR));
171751fc01a0SNeil Armstrong 	} else {
171851fc01a0SNeil Armstrong 		writel_relaxed(hso_end, priv->io_base + _REG(L_STH1_HS_ADDR));
171951fc01a0SNeil Armstrong 		writel_relaxed(hso_begin, priv->io_base + _REG(L_STH1_HE_ADDR));
172051fc01a0SNeil Armstrong 	}
172151fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(L_STH1_VS_ADDR));
172251fc01a0SNeil Armstrong 	writel_relaxed(max_lncnt, priv->io_base + _REG(L_STH1_VE_ADDR));
172351fc01a0SNeil Armstrong 
172451fc01a0SNeil Armstrong 	/* Vsync signal for TTL */
172551fc01a0SNeil Armstrong 	writel_relaxed(vso_begin, priv->io_base + _REG(L_STV1_HS_ADDR));
172651fc01a0SNeil Armstrong 	writel_relaxed(vso_end, priv->io_base + _REG(L_STV1_HE_ADDR));
172751fc01a0SNeil Armstrong 	if (mode->flags & DRM_MODE_FLAG_PVSYNC) {
172851fc01a0SNeil Armstrong 		writel_relaxed(vso_bline, priv->io_base + _REG(L_STV1_VS_ADDR));
172951fc01a0SNeil Armstrong 		writel_relaxed(vso_eline, priv->io_base + _REG(L_STV1_VE_ADDR));
173051fc01a0SNeil Armstrong 	} else {
173151fc01a0SNeil Armstrong 		writel_relaxed(vso_eline, priv->io_base + _REG(L_STV1_VS_ADDR));
173251fc01a0SNeil Armstrong 		writel_relaxed(vso_bline, priv->io_base + _REG(L_STV1_VE_ADDR));
173351fc01a0SNeil Armstrong 	}
173451fc01a0SNeil Armstrong 
173551fc01a0SNeil Armstrong 	/* DE signal */
173651fc01a0SNeil Armstrong 	writel_relaxed(havon_begin, priv->io_base + _REG(L_DE_HS_ADDR));
173751fc01a0SNeil Armstrong 	writel_relaxed(havon_end + 1, priv->io_base + _REG(L_DE_HE_ADDR));
173851fc01a0SNeil Armstrong 	writel_relaxed(vavon_bline, priv->io_base + _REG(L_DE_VS_ADDR));
173951fc01a0SNeil Armstrong 	writel_relaxed(vavon_eline, priv->io_base + _REG(L_DE_VE_ADDR));
174051fc01a0SNeil Armstrong 
174151fc01a0SNeil Armstrong 	/* Hsync signal */
174251fc01a0SNeil Armstrong 	writel_relaxed(hso_begin, priv->io_base + _REG(L_HSYNC_HS_ADDR));
174351fc01a0SNeil Armstrong 	writel_relaxed(hso_end, priv->io_base + _REG(L_HSYNC_HE_ADDR));
174451fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(L_HSYNC_VS_ADDR));
174551fc01a0SNeil Armstrong 	writel_relaxed(max_lncnt, priv->io_base + _REG(L_HSYNC_VE_ADDR));
174651fc01a0SNeil Armstrong 
174751fc01a0SNeil Armstrong 	/* Vsync signal */
174851fc01a0SNeil Armstrong 	writel_relaxed(vso_begin, priv->io_base + _REG(L_VSYNC_HS_ADDR));
174951fc01a0SNeil Armstrong 	writel_relaxed(vso_end, priv->io_base + _REG(L_VSYNC_HE_ADDR));
175051fc01a0SNeil Armstrong 	writel_relaxed(vso_bline, priv->io_base + _REG(L_VSYNC_VS_ADDR));
175151fc01a0SNeil Armstrong 	writel_relaxed(vso_eline, priv->io_base + _REG(L_VSYNC_VE_ADDR));
175251fc01a0SNeil Armstrong 
175351fc01a0SNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(L_INV_CNT_ADDR));
175451fc01a0SNeil Armstrong 	writel_relaxed(L_TCON_MISC_SEL_STV1 | L_TCON_MISC_SEL_STV2,
175551fc01a0SNeil Armstrong 		       priv->io_base + _REG(L_TCON_MISC_SEL_ADDR));
175651fc01a0SNeil Armstrong 
175751fc01a0SNeil Armstrong 	priv->venc.current_mode = MESON_VENC_MODE_MIPI_DSI;
175851fc01a0SNeil Armstrong }
175951fc01a0SNeil Armstrong EXPORT_SYMBOL_GPL(meson_venc_mipi_dsi_mode_set);
176051fc01a0SNeil Armstrong 
meson_venci_cvbs_mode_set(struct meson_drm * priv,struct meson_cvbs_enci_mode * mode)1761bbbe775eSNeil Armstrong void meson_venci_cvbs_mode_set(struct meson_drm *priv,
1762bbbe775eSNeil Armstrong 			       struct meson_cvbs_enci_mode *mode)
1763bbbe775eSNeil Armstrong {
17647eef9e61SJulien Masson 	u32 reg;
17657eef9e61SJulien Masson 
1766bbbe775eSNeil Armstrong 	if (mode->mode_tag == priv->venc.current_mode)
1767bbbe775eSNeil Armstrong 		return;
1768bbbe775eSNeil Armstrong 
1769bbbe775eSNeil Armstrong 	/* CVBS Filter settings */
17707eef9e61SJulien Masson 	writel_relaxed(ENCI_CFILT_CMPT_SEL_HIGH | 0x10,
17717eef9e61SJulien Masson 		       priv->io_base + _REG(ENCI_CFILT_CTRL));
17727eef9e61SJulien Masson 	writel_relaxed(ENCI_CFILT_CMPT_CR_DLY(2) |
17737eef9e61SJulien Masson 		       ENCI_CFILT_CMPT_CB_DLY(1),
17747eef9e61SJulien Masson 		       priv->io_base + _REG(ENCI_CFILT_CTRL2));
1775bbbe775eSNeil Armstrong 
1776bbbe775eSNeil Armstrong 	/* Digital Video Select : Interlace, clk27 clk, external */
1777bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_DVI_SETTING));
1778bbbe775eSNeil Armstrong 
1779bbbe775eSNeil Armstrong 	/* Reset Video Mode */
1780bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCI_VIDEO_MODE));
1781bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCI_VIDEO_MODE_ADV));
1782bbbe775eSNeil Armstrong 
1783bbbe775eSNeil Armstrong 	/* Horizontal sync signal output */
1784bbbe775eSNeil Armstrong 	writel_relaxed(mode->hso_begin,
1785bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_SYNC_HSO_BEGIN));
1786bbbe775eSNeil Armstrong 	writel_relaxed(mode->hso_end,
1787bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_SYNC_HSO_END));
1788bbbe775eSNeil Armstrong 
1789bbbe775eSNeil Armstrong 	/* Vertical Sync lines */
1790bbbe775eSNeil Armstrong 	writel_relaxed(mode->vso_even,
1791bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_SYNC_VSO_EVNLN));
1792bbbe775eSNeil Armstrong 	writel_relaxed(mode->vso_odd,
1793bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_SYNC_VSO_ODDLN));
1794bbbe775eSNeil Armstrong 
1795bbbe775eSNeil Armstrong 	/* Macrovision max amplitude change */
17967eef9e61SJulien Masson 	writel_relaxed(ENCI_MACV_MAX_AMP_ENABLE_CHANGE |
17977eef9e61SJulien Masson 		       ENCI_MACV_MAX_AMP_VAL(mode->macv_max_amp),
1798bbbe775eSNeil Armstrong 		       priv->io_base + _REG(ENCI_MACV_MAX_AMP));
1799bbbe775eSNeil Armstrong 
1800bbbe775eSNeil Armstrong 	/* Video mode */
1801bbbe775eSNeil Armstrong 	writel_relaxed(mode->video_prog_mode,
1802bbbe775eSNeil Armstrong 			priv->io_base + _REG(VENC_VIDEO_PROG_MODE));
1803bbbe775eSNeil Armstrong 	writel_relaxed(mode->video_mode,
1804bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VIDEO_MODE));
1805bbbe775eSNeil Armstrong 
1806e1012141SJulien Masson 	/*
1807e1012141SJulien Masson 	 * Advanced Video Mode :
1808bbbe775eSNeil Armstrong 	 * Demux shifting 0x2
1809bbbe775eSNeil Armstrong 	 * Blank line end at line17/22
1810bbbe775eSNeil Armstrong 	 * High bandwidth Luma Filter
1811bbbe775eSNeil Armstrong 	 * Low bandwidth Chroma Filter
1812bbbe775eSNeil Armstrong 	 * Bypass luma low pass filter
1813bbbe775eSNeil Armstrong 	 * No macrovision on CSYNC
1814bbbe775eSNeil Armstrong 	 */
18157eef9e61SJulien Masson 	writel_relaxed(ENCI_VIDEO_MODE_ADV_DMXMD(2) |
18167eef9e61SJulien Masson 		       ENCI_VIDEO_MODE_ADV_VBICTL_LINE_17_22 |
18177eef9e61SJulien Masson 		       ENCI_VIDEO_MODE_ADV_YBW_HIGH,
18187eef9e61SJulien Masson 		       priv->io_base + _REG(ENCI_VIDEO_MODE_ADV));
1819bbbe775eSNeil Armstrong 
1820bbbe775eSNeil Armstrong 	writel(mode->sch_adjust, priv->io_base + _REG(ENCI_VIDEO_SCH));
1821bbbe775eSNeil Armstrong 
1822bbbe775eSNeil Armstrong 	/* Sync mode : MASTER Master mode, free run, send HSO/VSO out */
1823bbbe775eSNeil Armstrong 	writel_relaxed(0x07, priv->io_base + _REG(ENCI_SYNC_MODE));
1824bbbe775eSNeil Armstrong 
1825bbbe775eSNeil Armstrong 	/* 0x3 Y, C, and Component Y delay */
1826bbbe775eSNeil Armstrong 	writel_relaxed(mode->yc_delay, priv->io_base + _REG(ENCI_YC_DELAY));
1827bbbe775eSNeil Armstrong 
1828bbbe775eSNeil Armstrong 	/* Timings */
1829bbbe775eSNeil Armstrong 	writel_relaxed(mode->pixel_start,
1830bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_PIXEL_START));
1831bbbe775eSNeil Armstrong 	writel_relaxed(mode->pixel_end,
1832bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_PIXEL_END));
1833bbbe775eSNeil Armstrong 
1834bbbe775eSNeil Armstrong 	writel_relaxed(mode->top_field_line_start,
1835bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_TOP_START));
1836bbbe775eSNeil Armstrong 	writel_relaxed(mode->top_field_line_end,
1837bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_TOP_END));
1838bbbe775eSNeil Armstrong 
1839bbbe775eSNeil Armstrong 	writel_relaxed(mode->bottom_field_line_start,
1840bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_BOT_START));
1841bbbe775eSNeil Armstrong 	writel_relaxed(mode->bottom_field_line_end,
1842bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VFIFO2VD_LINE_BOT_END));
1843bbbe775eSNeil Armstrong 
1844bbbe775eSNeil Armstrong 	/* Internal Venc, Internal VIU Sync, Internal Vencoder */
1845bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_SYNC_ROUTE));
1846bbbe775eSNeil Armstrong 
1847bbbe775eSNeil Armstrong 	/* UNreset Interlaced TV Encoder */
1848bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCI_DBG_PX_RST));
1849bbbe775eSNeil Armstrong 
18507eef9e61SJulien Masson 	/*
18517eef9e61SJulien Masson 	 * Enable Vfifo2vd and set Y_Cb_Y_Cr:
18527eef9e61SJulien Masson 	 * Corresponding value:
18537eef9e61SJulien Masson 	 * Y  => 00 or 10
18547eef9e61SJulien Masson 	 * Cb => 01
18557eef9e61SJulien Masson 	 * Cr => 11
18567eef9e61SJulien Masson 	 * Ex: 0x4e => 01001110 would mean Cb/Y/Cr/Y
18577eef9e61SJulien Masson 	 */
18587eef9e61SJulien Masson 	writel_relaxed(ENCI_VFIFO2VD_CTL_ENABLE |
18597eef9e61SJulien Masson 		       ENCI_VFIFO2VD_CTL_VD_SEL(0x4e),
18607eef9e61SJulien Masson 		       priv->io_base + _REG(ENCI_VFIFO2VD_CTL));
1861bbbe775eSNeil Armstrong 
1862bbbe775eSNeil Armstrong 	/* Power UP Dacs */
1863bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_VDAC_SETTING));
1864bbbe775eSNeil Armstrong 
1865bbbe775eSNeil Armstrong 	/* Video Upsampling */
18667eef9e61SJulien Masson 	/*
18677eef9e61SJulien Masson 	 * CTRL0, CTRL1 and CTRL2:
18687eef9e61SJulien Masson 	 * Filter0: input data sample every 2 cloks
18697eef9e61SJulien Masson 	 * Filter1: filtering and upsample enable
18707eef9e61SJulien Masson 	 */
18717eef9e61SJulien Masson 	reg = VENC_UPSAMPLE_CTRL_F0_2_CLK_RATIO | VENC_UPSAMPLE_CTRL_F1_EN |
18727eef9e61SJulien Masson 		VENC_UPSAMPLE_CTRL_F1_UPSAMPLE_EN;
18737eef9e61SJulien Masson 
18747eef9e61SJulien Masson 	/*
18757eef9e61SJulien Masson 	 * Upsample CTRL0:
18767eef9e61SJulien Masson 	 * Interlace High Bandwidth Luma
18777eef9e61SJulien Masson 	 */
18787eef9e61SJulien Masson 	writel_relaxed(VENC_UPSAMPLE_CTRL_INTERLACE_HIGH_LUMA | reg,
18797eef9e61SJulien Masson 		       priv->io_base + _REG(VENC_UPSAMPLE_CTRL0));
18807eef9e61SJulien Masson 
18817eef9e61SJulien Masson 	/*
18827eef9e61SJulien Masson 	 * Upsample CTRL1:
18837eef9e61SJulien Masson 	 * Interlace Pb
18847eef9e61SJulien Masson 	 */
18857eef9e61SJulien Masson 	writel_relaxed(VENC_UPSAMPLE_CTRL_INTERLACE_PB | reg,
18867eef9e61SJulien Masson 		       priv->io_base + _REG(VENC_UPSAMPLE_CTRL1));
18877eef9e61SJulien Masson 
18887eef9e61SJulien Masson 	/*
18897eef9e61SJulien Masson 	 * Upsample CTRL2:
18907eef9e61SJulien Masson 	 * Interlace R
18917eef9e61SJulien Masson 	 */
18927eef9e61SJulien Masson 	writel_relaxed(VENC_UPSAMPLE_CTRL_INTERLACE_PR | reg,
18937eef9e61SJulien Masson 		       priv->io_base + _REG(VENC_UPSAMPLE_CTRL2));
1894bbbe775eSNeil Armstrong 
1895bbbe775eSNeil Armstrong 	/* Select Interlace Y DACs */
1896bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_VDAC_DACSEL0));
1897bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_VDAC_DACSEL1));
1898bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_VDAC_DACSEL2));
1899bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_VDAC_DACSEL3));
1900bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_VDAC_DACSEL4));
1901bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_VDAC_DACSEL5));
1902bbbe775eSNeil Armstrong 
1903bbbe775eSNeil Armstrong 	/* Select ENCI for VIU */
1904bbbe775eSNeil Armstrong 	meson_vpp_setup_mux(priv, MESON_VIU_VPP_MUX_ENCI);
1905bbbe775eSNeil Armstrong 
1906bbbe775eSNeil Armstrong 	/* Enable ENCI FIFO */
19077eef9e61SJulien Masson 	writel_relaxed(VENC_VDAC_FIFO_EN_ENCI_ENABLE,
19087eef9e61SJulien Masson 		       priv->io_base + _REG(VENC_VDAC_FIFO_CTRL));
1909bbbe775eSNeil Armstrong 
1910bbbe775eSNeil Armstrong 	/* Select ENCI DACs 0, 1, 4, and 5 */
1911bbbe775eSNeil Armstrong 	writel_relaxed(0x11, priv->io_base + _REG(ENCI_DACSEL_0));
1912bbbe775eSNeil Armstrong 	writel_relaxed(0x11, priv->io_base + _REG(ENCI_DACSEL_1));
1913bbbe775eSNeil Armstrong 
1914bbbe775eSNeil Armstrong 	/* Interlace video enable */
19157eef9e61SJulien Masson 	writel_relaxed(ENCI_VIDEO_EN_ENABLE,
19167eef9e61SJulien Masson 		       priv->io_base + _REG(ENCI_VIDEO_EN));
1917bbbe775eSNeil Armstrong 
1918bbbe775eSNeil Armstrong 	/* Configure Video Saturation / Contrast / Brightness / Hue */
1919bbbe775eSNeil Armstrong 	writel_relaxed(mode->video_saturation,
1920bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VIDEO_SAT));
1921bbbe775eSNeil Armstrong 	writel_relaxed(mode->video_contrast,
1922bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VIDEO_CONT));
1923bbbe775eSNeil Armstrong 	writel_relaxed(mode->video_brightness,
1924bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VIDEO_BRIGHT));
1925bbbe775eSNeil Armstrong 	writel_relaxed(mode->video_hue,
1926bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_VIDEO_HUE));
1927bbbe775eSNeil Armstrong 
1928bbbe775eSNeil Armstrong 	/* Enable DAC0 Filter */
19297eef9e61SJulien Masson 	writel_relaxed(VENC_VDAC_DAC0_FILT_CTRL0_EN,
19307eef9e61SJulien Masson 		       priv->io_base + _REG(VENC_VDAC_DAC0_FILT_CTRL0));
1931bbbe775eSNeil Armstrong 	writel_relaxed(0xfc48, priv->io_base + _REG(VENC_VDAC_DAC0_FILT_CTRL1));
1932bbbe775eSNeil Armstrong 
1933bbbe775eSNeil Armstrong 	/* 0 in Macrovision register 0 */
1934bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCI_MACV_N0));
1935bbbe775eSNeil Armstrong 
1936bbbe775eSNeil Armstrong 	/* Analog Synchronization and color burst value adjust */
1937bbbe775eSNeil Armstrong 	writel_relaxed(mode->analog_sync_adj,
1938bbbe775eSNeil Armstrong 			priv->io_base + _REG(ENCI_SYNC_ADJ));
1939bbbe775eSNeil Armstrong 
1940bbbe775eSNeil Armstrong 	priv->venc.current_mode = mode->mode_tag;
1941bbbe775eSNeil Armstrong }
1942bbbe775eSNeil Armstrong 
1943bbbe775eSNeil Armstrong /* Returns the current ENCI field polarity */
meson_venci_get_field(struct meson_drm * priv)1944bbbe775eSNeil Armstrong unsigned int meson_venci_get_field(struct meson_drm *priv)
1945bbbe775eSNeil Armstrong {
1946bbbe775eSNeil Armstrong 	return readl_relaxed(priv->io_base + _REG(ENCI_INFO_READ)) & BIT(29);
1947bbbe775eSNeil Armstrong }
1948bbbe775eSNeil Armstrong 
meson_venc_enable_vsync(struct meson_drm * priv)1949bbbe775eSNeil Armstrong void meson_venc_enable_vsync(struct meson_drm *priv)
1950bbbe775eSNeil Armstrong {
195151fc01a0SNeil Armstrong 	switch (priv->venc.current_mode) {
195251fc01a0SNeil Armstrong 	case MESON_VENC_MODE_MIPI_DSI:
195351fc01a0SNeil Armstrong 		writel_relaxed(VENC_INTCTRL_ENCP_LNRST_INT_EN,
195451fc01a0SNeil Armstrong 			       priv->io_base + _REG(VENC_INTCTRL));
195551fc01a0SNeil Armstrong 		break;
195651fc01a0SNeil Armstrong 	default:
19577eef9e61SJulien Masson 		writel_relaxed(VENC_INTCTRL_ENCI_LNRST_INT_EN,
19587eef9e61SJulien Masson 			       priv->io_base + _REG(VENC_INTCTRL));
195951fc01a0SNeil Armstrong 	}
19602bcd3ecaSNeil Armstrong 	regmap_update_bits(priv->hhi, HHI_GCLK_MPEG2, BIT(25), BIT(25));
1961bbbe775eSNeil Armstrong }
1962bbbe775eSNeil Armstrong 
meson_venc_disable_vsync(struct meson_drm * priv)1963bbbe775eSNeil Armstrong void meson_venc_disable_vsync(struct meson_drm *priv)
1964bbbe775eSNeil Armstrong {
19652bcd3ecaSNeil Armstrong 	regmap_update_bits(priv->hhi, HHI_GCLK_MPEG2, BIT(25), 0);
1966bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(VENC_INTCTRL));
1967bbbe775eSNeil Armstrong }
1968bbbe775eSNeil Armstrong 
meson_venc_init(struct meson_drm * priv)1969bbbe775eSNeil Armstrong void meson_venc_init(struct meson_drm *priv)
1970bbbe775eSNeil Armstrong {
19710c931a29SNeil Armstrong 	/* Disable CVBS VDAC */
1972528a25d0SJulien Masson 	if (meson_vpu_is_compatible(priv, VPU_COMPATIBLE_G12A)) {
197364d598a1SNeil Armstrong 		regmap_write(priv->hhi, HHI_VDAC_CNTL0_G12A, 0);
197464d598a1SNeil Armstrong 		regmap_write(priv->hhi, HHI_VDAC_CNTL1_G12A, 8);
197564d598a1SNeil Armstrong 	} else {
19760c931a29SNeil Armstrong 		regmap_write(priv->hhi, HHI_VDAC_CNTL0, 0);
19770c931a29SNeil Armstrong 		regmap_write(priv->hhi, HHI_VDAC_CNTL1, 8);
197864d598a1SNeil Armstrong 	}
19790c931a29SNeil Armstrong 
19800c931a29SNeil Armstrong 	/* Power Down Dacs */
19810c931a29SNeil Armstrong 	writel_relaxed(0xff, priv->io_base + _REG(VENC_VDAC_SETTING));
19820c931a29SNeil Armstrong 
19830c931a29SNeil Armstrong 	/* Disable HDMI PHY */
19840c931a29SNeil Armstrong 	regmap_write(priv->hhi, HHI_HDMI_PHY_CNTL0, 0);
19850c931a29SNeil Armstrong 
19860c931a29SNeil Armstrong 	/* Disable HDMI */
19877eef9e61SJulien Masson 	writel_bits_relaxed(VPU_HDMI_ENCI_DATA_TO_HDMI |
19887eef9e61SJulien Masson 			    VPU_HDMI_ENCP_DATA_TO_HDMI, 0,
19890c931a29SNeil Armstrong 			    priv->io_base + _REG(VPU_HDMI_SETTING));
19900c931a29SNeil Armstrong 
1991bbbe775eSNeil Armstrong 	/* Disable all encoders */
1992bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCI_VIDEO_EN));
1993bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCP_VIDEO_EN));
1994bbbe775eSNeil Armstrong 	writel_relaxed(0, priv->io_base + _REG(ENCL_VIDEO_EN));
1995bbbe775eSNeil Armstrong 
1996bbbe775eSNeil Armstrong 	/* Disable VSync IRQ */
1997bbbe775eSNeil Armstrong 	meson_venc_disable_vsync(priv);
1998bbbe775eSNeil Armstrong 
1999bbbe775eSNeil Armstrong 	priv->venc.current_mode = MESON_VENC_MODE_NONE;
2000bbbe775eSNeil Armstrong }
2001