1/*
2 * linux/drivers/video/omap2/dss/dss_features.c
3 *
4 * Copyright (C) 2010 Texas Instruments
5 * Author: Archit Taneja <archit@ti.com>
6 *
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms of the GNU General Public License version 2 as published by
9 * the Free Software Foundation.
10 *
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14 * more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * this program.  If not, see <http://www.gnu.org/licenses/>.
18 */
19
20#include <linux/kernel.h>
21#include <linux/module.h>
22#include <linux/types.h>
23#include <linux/err.h>
24#include <linux/slab.h>
25
26#include <video/omapdss.h>
27
28#include "dss.h"
29#include "dss_features.h"
30
31/* Defines a generic omap register field */
32struct dss_reg_field {
33	u8 start, end;
34};
35
36struct dss_param_range {
37	int min, max;
38};
39
40struct omap_dss_features {
41	const struct dss_reg_field *reg_fields;
42	const int num_reg_fields;
43
44	const enum dss_feat_id *features;
45	const int num_features;
46
47	const int num_mgrs;
48	const int num_ovls;
49	const int num_wbs;
50	const enum omap_display_type *supported_displays;
51	const enum omap_dss_output_id *supported_outputs;
52	const enum omap_color_mode *supported_color_modes;
53	const enum omap_overlay_caps *overlay_caps;
54	const char * const *clksrc_names;
55	const struct dss_param_range *dss_params;
56
57	const enum omap_dss_rotation_type supported_rotation_types;
58
59	const u32 buffer_size_unit;
60	const u32 burst_size_unit;
61};
62
63/* This struct is assigned to one of the below during initialization */
64static const struct omap_dss_features *omap_current_dss_features;
65
66static const struct dss_reg_field omap2_dss_reg_fields[] = {
67	[FEAT_REG_FIRHINC]			= { 11, 0 },
68	[FEAT_REG_FIRVINC]			= { 27, 16 },
69	[FEAT_REG_FIFOLOWTHRESHOLD]		= { 8, 0 },
70	[FEAT_REG_FIFOHIGHTHRESHOLD]		= { 24, 16 },
71	[FEAT_REG_FIFOSIZE]			= { 8, 0 },
72	[FEAT_REG_HORIZONTALACCU]		= { 9, 0 },
73	[FEAT_REG_VERTICALACCU]			= { 25, 16 },
74	[FEAT_REG_DISPC_CLK_SWITCH]		= { 0, 0 },
75};
76
77static const struct dss_reg_field omap3_dss_reg_fields[] = {
78	[FEAT_REG_FIRHINC]			= { 12, 0 },
79	[FEAT_REG_FIRVINC]			= { 28, 16 },
80	[FEAT_REG_FIFOLOWTHRESHOLD]		= { 11, 0 },
81	[FEAT_REG_FIFOHIGHTHRESHOLD]		= { 27, 16 },
82	[FEAT_REG_FIFOSIZE]			= { 10, 0 },
83	[FEAT_REG_HORIZONTALACCU]		= { 9, 0 },
84	[FEAT_REG_VERTICALACCU]			= { 25, 16 },
85	[FEAT_REG_DISPC_CLK_SWITCH]		= { 0, 0 },
86};
87
88static const struct dss_reg_field am43xx_dss_reg_fields[] = {
89	[FEAT_REG_FIRHINC]			= { 12, 0 },
90	[FEAT_REG_FIRVINC]			= { 28, 16 },
91	[FEAT_REG_FIFOLOWTHRESHOLD]	= { 11, 0 },
92	[FEAT_REG_FIFOHIGHTHRESHOLD]		= { 27, 16 },
93	[FEAT_REG_FIFOSIZE]		= { 10, 0 },
94	[FEAT_REG_HORIZONTALACCU]		= { 9, 0 },
95	[FEAT_REG_VERTICALACCU]			= { 25, 16 },
96	[FEAT_REG_DISPC_CLK_SWITCH]		= { 0, 0 },
97};
98
99static const struct dss_reg_field omap4_dss_reg_fields[] = {
100	[FEAT_REG_FIRHINC]			= { 12, 0 },
101	[FEAT_REG_FIRVINC]			= { 28, 16 },
102	[FEAT_REG_FIFOLOWTHRESHOLD]		= { 15, 0 },
103	[FEAT_REG_FIFOHIGHTHRESHOLD]		= { 31, 16 },
104	[FEAT_REG_FIFOSIZE]			= { 15, 0 },
105	[FEAT_REG_HORIZONTALACCU]		= { 10, 0 },
106	[FEAT_REG_VERTICALACCU]			= { 26, 16 },
107	[FEAT_REG_DISPC_CLK_SWITCH]		= { 9, 8 },
108};
109
110static const struct dss_reg_field omap5_dss_reg_fields[] = {
111	[FEAT_REG_FIRHINC]			= { 12, 0 },
112	[FEAT_REG_FIRVINC]			= { 28, 16 },
113	[FEAT_REG_FIFOLOWTHRESHOLD]		= { 15, 0 },
114	[FEAT_REG_FIFOHIGHTHRESHOLD]		= { 31, 16 },
115	[FEAT_REG_FIFOSIZE]			= { 15, 0 },
116	[FEAT_REG_HORIZONTALACCU]		= { 10, 0 },
117	[FEAT_REG_VERTICALACCU]			= { 26, 16 },
118	[FEAT_REG_DISPC_CLK_SWITCH]		= { 9, 7 },
119};
120
121static const enum omap_display_type omap2_dss_supported_displays[] = {
122	/* OMAP_DSS_CHANNEL_LCD */
123	OMAP_DISPLAY_TYPE_DPI | OMAP_DISPLAY_TYPE_DBI,
124
125	/* OMAP_DSS_CHANNEL_DIGIT */
126	OMAP_DISPLAY_TYPE_VENC,
127};
128
129static const enum omap_display_type omap3430_dss_supported_displays[] = {
130	/* OMAP_DSS_CHANNEL_LCD */
131	OMAP_DISPLAY_TYPE_DPI | OMAP_DISPLAY_TYPE_DBI |
132	OMAP_DISPLAY_TYPE_SDI | OMAP_DISPLAY_TYPE_DSI,
133
134	/* OMAP_DSS_CHANNEL_DIGIT */
135	OMAP_DISPLAY_TYPE_VENC,
136};
137
138static const enum omap_display_type omap3630_dss_supported_displays[] = {
139	/* OMAP_DSS_CHANNEL_LCD */
140	OMAP_DISPLAY_TYPE_DPI | OMAP_DISPLAY_TYPE_DBI |
141	OMAP_DISPLAY_TYPE_DSI,
142
143	/* OMAP_DSS_CHANNEL_DIGIT */
144	OMAP_DISPLAY_TYPE_VENC,
145};
146
147static const enum omap_display_type am43xx_dss_supported_displays[] = {
148	/* OMAP_DSS_CHANNEL_LCD */
149	OMAP_DISPLAY_TYPE_DPI | OMAP_DISPLAY_TYPE_DBI,
150};
151
152static const enum omap_display_type omap4_dss_supported_displays[] = {
153	/* OMAP_DSS_CHANNEL_LCD */
154	OMAP_DISPLAY_TYPE_DBI | OMAP_DISPLAY_TYPE_DSI,
155
156	/* OMAP_DSS_CHANNEL_DIGIT */
157	OMAP_DISPLAY_TYPE_VENC | OMAP_DISPLAY_TYPE_HDMI,
158
159	/* OMAP_DSS_CHANNEL_LCD2 */
160	OMAP_DISPLAY_TYPE_DPI | OMAP_DISPLAY_TYPE_DBI |
161	OMAP_DISPLAY_TYPE_DSI,
162};
163
164static const enum omap_display_type omap5_dss_supported_displays[] = {
165	/* OMAP_DSS_CHANNEL_LCD */
166	OMAP_DISPLAY_TYPE_DPI | OMAP_DISPLAY_TYPE_DBI |
167	OMAP_DISPLAY_TYPE_DSI,
168
169	/* OMAP_DSS_CHANNEL_DIGIT */
170	OMAP_DISPLAY_TYPE_HDMI | OMAP_DISPLAY_TYPE_DPI,
171
172	/* OMAP_DSS_CHANNEL_LCD2 */
173	OMAP_DISPLAY_TYPE_DPI | OMAP_DISPLAY_TYPE_DBI |
174	OMAP_DISPLAY_TYPE_DSI,
175};
176
177static const enum omap_dss_output_id omap2_dss_supported_outputs[] = {
178	/* OMAP_DSS_CHANNEL_LCD */
179	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI,
180
181	/* OMAP_DSS_CHANNEL_DIGIT */
182	OMAP_DSS_OUTPUT_VENC,
183};
184
185static const enum omap_dss_output_id omap3430_dss_supported_outputs[] = {
186	/* OMAP_DSS_CHANNEL_LCD */
187	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI |
188	OMAP_DSS_OUTPUT_SDI | OMAP_DSS_OUTPUT_DSI1,
189
190	/* OMAP_DSS_CHANNEL_DIGIT */
191	OMAP_DSS_OUTPUT_VENC,
192};
193
194static const enum omap_dss_output_id omap3630_dss_supported_outputs[] = {
195	/* OMAP_DSS_CHANNEL_LCD */
196	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI |
197	OMAP_DSS_OUTPUT_DSI1,
198
199	/* OMAP_DSS_CHANNEL_DIGIT */
200	OMAP_DSS_OUTPUT_VENC,
201};
202
203static const enum omap_dss_output_id am43xx_dss_supported_outputs[] = {
204	/* OMAP_DSS_CHANNEL_LCD */
205	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI,
206};
207
208static const enum omap_dss_output_id omap4_dss_supported_outputs[] = {
209	/* OMAP_DSS_CHANNEL_LCD */
210	OMAP_DSS_OUTPUT_DBI | OMAP_DSS_OUTPUT_DSI1,
211
212	/* OMAP_DSS_CHANNEL_DIGIT */
213	OMAP_DSS_OUTPUT_VENC | OMAP_DSS_OUTPUT_HDMI,
214
215	/* OMAP_DSS_CHANNEL_LCD2 */
216	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI |
217	OMAP_DSS_OUTPUT_DSI2,
218};
219
220static const enum omap_dss_output_id omap5_dss_supported_outputs[] = {
221	/* OMAP_DSS_CHANNEL_LCD */
222	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI |
223	OMAP_DSS_OUTPUT_DSI1 | OMAP_DSS_OUTPUT_DSI2,
224
225	/* OMAP_DSS_CHANNEL_DIGIT */
226	OMAP_DSS_OUTPUT_HDMI,
227
228	/* OMAP_DSS_CHANNEL_LCD2 */
229	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI |
230	OMAP_DSS_OUTPUT_DSI1,
231
232	/* OMAP_DSS_CHANNEL_LCD3 */
233	OMAP_DSS_OUTPUT_DPI | OMAP_DSS_OUTPUT_DBI |
234	OMAP_DSS_OUTPUT_DSI2,
235};
236
237static const enum omap_color_mode omap2_dss_supported_color_modes[] = {
238	/* OMAP_DSS_GFX */
239	OMAP_DSS_COLOR_CLUT1 | OMAP_DSS_COLOR_CLUT2 |
240	OMAP_DSS_COLOR_CLUT4 | OMAP_DSS_COLOR_CLUT8 |
241	OMAP_DSS_COLOR_RGB12U | OMAP_DSS_COLOR_RGB16 |
242	OMAP_DSS_COLOR_RGB24U | OMAP_DSS_COLOR_RGB24P,
243
244	/* OMAP_DSS_VIDEO1 */
245	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB24U |
246	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_YUV2 |
247	OMAP_DSS_COLOR_UYVY,
248
249	/* OMAP_DSS_VIDEO2 */
250	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB24U |
251	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_YUV2 |
252	OMAP_DSS_COLOR_UYVY,
253};
254
255static const enum omap_color_mode omap3_dss_supported_color_modes[] = {
256	/* OMAP_DSS_GFX */
257	OMAP_DSS_COLOR_CLUT1 | OMAP_DSS_COLOR_CLUT2 |
258	OMAP_DSS_COLOR_CLUT4 | OMAP_DSS_COLOR_CLUT8 |
259	OMAP_DSS_COLOR_RGB12U | OMAP_DSS_COLOR_ARGB16 |
260	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB24U |
261	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_ARGB32 |
262	OMAP_DSS_COLOR_RGBA32 | OMAP_DSS_COLOR_RGBX32,
263
264	/* OMAP_DSS_VIDEO1 */
265	OMAP_DSS_COLOR_RGB24U | OMAP_DSS_COLOR_RGB24P |
266	OMAP_DSS_COLOR_RGB12U | OMAP_DSS_COLOR_RGB16 |
267	OMAP_DSS_COLOR_YUV2 | OMAP_DSS_COLOR_UYVY,
268
269	/* OMAP_DSS_VIDEO2 */
270	OMAP_DSS_COLOR_RGB12U | OMAP_DSS_COLOR_ARGB16 |
271	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB24U |
272	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_YUV2 |
273	OMAP_DSS_COLOR_UYVY | OMAP_DSS_COLOR_ARGB32 |
274	OMAP_DSS_COLOR_RGBA32 | OMAP_DSS_COLOR_RGBX32,
275};
276
277static const enum omap_color_mode omap4_dss_supported_color_modes[] = {
278	/* OMAP_DSS_GFX */
279	OMAP_DSS_COLOR_CLUT1 | OMAP_DSS_COLOR_CLUT2 |
280	OMAP_DSS_COLOR_CLUT4 | OMAP_DSS_COLOR_CLUT8 |
281	OMAP_DSS_COLOR_RGB12U | OMAP_DSS_COLOR_ARGB16 |
282	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB24U |
283	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_ARGB32 |
284	OMAP_DSS_COLOR_RGBA32 | OMAP_DSS_COLOR_RGBX32 |
285	OMAP_DSS_COLOR_ARGB16_1555 | OMAP_DSS_COLOR_RGBX16 |
286	OMAP_DSS_COLOR_RGBA16 | OMAP_DSS_COLOR_XRGB16_1555,
287
288	/* OMAP_DSS_VIDEO1 */
289	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB12U |
290	OMAP_DSS_COLOR_YUV2 | OMAP_DSS_COLOR_ARGB16_1555 |
291	OMAP_DSS_COLOR_RGBA32 | OMAP_DSS_COLOR_NV12 |
292	OMAP_DSS_COLOR_RGBA16 | OMAP_DSS_COLOR_RGB24U |
293	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_UYVY |
294	OMAP_DSS_COLOR_ARGB16 | OMAP_DSS_COLOR_XRGB16_1555 |
295	OMAP_DSS_COLOR_ARGB32 | OMAP_DSS_COLOR_RGBX16 |
296	OMAP_DSS_COLOR_RGBX32,
297
298       /* OMAP_DSS_VIDEO2 */
299	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB12U |
300	OMAP_DSS_COLOR_YUV2 | OMAP_DSS_COLOR_ARGB16_1555 |
301	OMAP_DSS_COLOR_RGBA32 | OMAP_DSS_COLOR_NV12 |
302	OMAP_DSS_COLOR_RGBA16 | OMAP_DSS_COLOR_RGB24U |
303	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_UYVY |
304	OMAP_DSS_COLOR_ARGB16 | OMAP_DSS_COLOR_XRGB16_1555 |
305	OMAP_DSS_COLOR_ARGB32 | OMAP_DSS_COLOR_RGBX16 |
306	OMAP_DSS_COLOR_RGBX32,
307
308	/* OMAP_DSS_VIDEO3 */
309	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB12U |
310	OMAP_DSS_COLOR_YUV2 | OMAP_DSS_COLOR_ARGB16_1555 |
311	OMAP_DSS_COLOR_RGBA32 | OMAP_DSS_COLOR_NV12 |
312	OMAP_DSS_COLOR_RGBA16 | OMAP_DSS_COLOR_RGB24U |
313	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_UYVY |
314	OMAP_DSS_COLOR_ARGB16 | OMAP_DSS_COLOR_XRGB16_1555 |
315	OMAP_DSS_COLOR_ARGB32 | OMAP_DSS_COLOR_RGBX16 |
316	OMAP_DSS_COLOR_RGBX32,
317
318	/* OMAP_DSS_WB */
319	OMAP_DSS_COLOR_RGB16 | OMAP_DSS_COLOR_RGB12U |
320	OMAP_DSS_COLOR_YUV2 | OMAP_DSS_COLOR_ARGB16_1555 |
321	OMAP_DSS_COLOR_RGBA32 | OMAP_DSS_COLOR_NV12 |
322	OMAP_DSS_COLOR_RGBA16 | OMAP_DSS_COLOR_RGB24U |
323	OMAP_DSS_COLOR_RGB24P | OMAP_DSS_COLOR_UYVY |
324	OMAP_DSS_COLOR_ARGB16 | OMAP_DSS_COLOR_XRGB16_1555 |
325	OMAP_DSS_COLOR_ARGB32 | OMAP_DSS_COLOR_RGBX16 |
326	OMAP_DSS_COLOR_RGBX32,
327};
328
329static const enum omap_overlay_caps omap2_dss_overlay_caps[] = {
330	/* OMAP_DSS_GFX */
331	OMAP_DSS_OVL_CAP_POS | OMAP_DSS_OVL_CAP_REPLICATION,
332
333	/* OMAP_DSS_VIDEO1 */
334	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_POS |
335		OMAP_DSS_OVL_CAP_REPLICATION,
336
337	/* OMAP_DSS_VIDEO2 */
338	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_POS |
339		OMAP_DSS_OVL_CAP_REPLICATION,
340};
341
342static const enum omap_overlay_caps omap3430_dss_overlay_caps[] = {
343	/* OMAP_DSS_GFX */
344	OMAP_DSS_OVL_CAP_GLOBAL_ALPHA | OMAP_DSS_OVL_CAP_POS |
345		OMAP_DSS_OVL_CAP_REPLICATION,
346
347	/* OMAP_DSS_VIDEO1 */
348	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_POS |
349		OMAP_DSS_OVL_CAP_REPLICATION,
350
351	/* OMAP_DSS_VIDEO2 */
352	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_GLOBAL_ALPHA |
353		OMAP_DSS_OVL_CAP_POS | OMAP_DSS_OVL_CAP_REPLICATION,
354};
355
356static const enum omap_overlay_caps omap3630_dss_overlay_caps[] = {
357	/* OMAP_DSS_GFX */
358	OMAP_DSS_OVL_CAP_GLOBAL_ALPHA | OMAP_DSS_OVL_CAP_PRE_MULT_ALPHA |
359		OMAP_DSS_OVL_CAP_POS | OMAP_DSS_OVL_CAP_REPLICATION,
360
361	/* OMAP_DSS_VIDEO1 */
362	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_POS |
363		OMAP_DSS_OVL_CAP_REPLICATION,
364
365	/* OMAP_DSS_VIDEO2 */
366	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_GLOBAL_ALPHA |
367		OMAP_DSS_OVL_CAP_PRE_MULT_ALPHA | OMAP_DSS_OVL_CAP_POS |
368		OMAP_DSS_OVL_CAP_REPLICATION,
369};
370
371static const enum omap_overlay_caps omap4_dss_overlay_caps[] = {
372	/* OMAP_DSS_GFX */
373	OMAP_DSS_OVL_CAP_GLOBAL_ALPHA | OMAP_DSS_OVL_CAP_PRE_MULT_ALPHA |
374		OMAP_DSS_OVL_CAP_ZORDER | OMAP_DSS_OVL_CAP_POS |
375		OMAP_DSS_OVL_CAP_REPLICATION,
376
377	/* OMAP_DSS_VIDEO1 */
378	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_GLOBAL_ALPHA |
379		OMAP_DSS_OVL_CAP_PRE_MULT_ALPHA | OMAP_DSS_OVL_CAP_ZORDER |
380		OMAP_DSS_OVL_CAP_POS | OMAP_DSS_OVL_CAP_REPLICATION,
381
382	/* OMAP_DSS_VIDEO2 */
383	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_GLOBAL_ALPHA |
384		OMAP_DSS_OVL_CAP_PRE_MULT_ALPHA | OMAP_DSS_OVL_CAP_ZORDER |
385		OMAP_DSS_OVL_CAP_POS | OMAP_DSS_OVL_CAP_REPLICATION,
386
387	/* OMAP_DSS_VIDEO3 */
388	OMAP_DSS_OVL_CAP_SCALE | OMAP_DSS_OVL_CAP_GLOBAL_ALPHA |
389		OMAP_DSS_OVL_CAP_PRE_MULT_ALPHA | OMAP_DSS_OVL_CAP_ZORDER |
390		OMAP_DSS_OVL_CAP_POS | OMAP_DSS_OVL_CAP_REPLICATION,
391};
392
393static const char * const omap2_dss_clk_source_names[] = {
394	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DISPC]	= "N/A",
395	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DSI]	= "N/A",
396	[OMAP_DSS_CLK_SRC_FCK]			= "DSS_FCLK1",
397};
398
399static const char * const omap3_dss_clk_source_names[] = {
400	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DISPC]	= "DSI1_PLL_FCLK",
401	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DSI]	= "DSI2_PLL_FCLK",
402	[OMAP_DSS_CLK_SRC_FCK]			= "DSS1_ALWON_FCLK",
403};
404
405static const char * const omap4_dss_clk_source_names[] = {
406	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DISPC]	= "PLL1_CLK1",
407	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DSI]	= "PLL1_CLK2",
408	[OMAP_DSS_CLK_SRC_FCK]			= "DSS_FCLK",
409	[OMAP_DSS_CLK_SRC_DSI2_PLL_HSDIV_DISPC]	= "PLL2_CLK1",
410	[OMAP_DSS_CLK_SRC_DSI2_PLL_HSDIV_DSI]	= "PLL2_CLK2",
411};
412
413static const char * const omap5_dss_clk_source_names[] = {
414	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DISPC]	= "DPLL_DSI1_A_CLK1",
415	[OMAP_DSS_CLK_SRC_DSI_PLL_HSDIV_DSI]	= "DPLL_DSI1_A_CLK2",
416	[OMAP_DSS_CLK_SRC_FCK]			= "DSS_CLK",
417	[OMAP_DSS_CLK_SRC_DSI2_PLL_HSDIV_DISPC]	= "DPLL_DSI1_C_CLK1",
418	[OMAP_DSS_CLK_SRC_DSI2_PLL_HSDIV_DSI]	= "DPLL_DSI1_C_CLK2",
419};
420
421static const struct dss_param_range omap2_dss_param_range[] = {
422	[FEAT_PARAM_DSS_FCK]			= { 0, 133000000 },
423	[FEAT_PARAM_DSS_PCD]			= { 2, 255 },
424	[FEAT_PARAM_DOWNSCALE]			= { 1, 2 },
425	/*
426	 * Assuming the line width buffer to be 768 pixels as OMAP2 DISPC
427	 * scaler cannot scale a image with width more than 768.
428	 */
429	[FEAT_PARAM_LINEWIDTH]			= { 1, 768 },
430};
431
432static const struct dss_param_range omap3_dss_param_range[] = {
433	[FEAT_PARAM_DSS_FCK]			= { 0, 173000000 },
434	[FEAT_PARAM_DSS_PCD]			= { 1, 255 },
435	[FEAT_PARAM_DSIPLL_LPDIV]		= { 1, (1 << 13) - 1},
436	[FEAT_PARAM_DSI_FCK]			= { 0, 173000000 },
437	[FEAT_PARAM_DOWNSCALE]			= { 1, 4 },
438	[FEAT_PARAM_LINEWIDTH]			= { 1, 1024 },
439};
440
441static const struct dss_param_range am43xx_dss_param_range[] = {
442	[FEAT_PARAM_DSS_FCK]			= { 0, 200000000 },
443	[FEAT_PARAM_DSS_PCD]			= { 1, 255 },
444	[FEAT_PARAM_DOWNSCALE]			= { 1, 4 },
445	[FEAT_PARAM_LINEWIDTH]			= { 1, 1024 },
446};
447
448static const struct dss_param_range omap4_dss_param_range[] = {
449	[FEAT_PARAM_DSS_FCK]			= { 0, 186000000 },
450	[FEAT_PARAM_DSS_PCD]			= { 1, 255 },
451	[FEAT_PARAM_DSIPLL_LPDIV]		= { 0, (1 << 13) - 1 },
452	[FEAT_PARAM_DSI_FCK]			= { 0, 170000000 },
453	[FEAT_PARAM_DOWNSCALE]			= { 1, 4 },
454	[FEAT_PARAM_LINEWIDTH]			= { 1, 2048 },
455};
456
457static const struct dss_param_range omap5_dss_param_range[] = {
458	[FEAT_PARAM_DSS_FCK]			= { 0, 209250000 },
459	[FEAT_PARAM_DSS_PCD]			= { 1, 255 },
460	[FEAT_PARAM_DSIPLL_LPDIV]		= { 0, (1 << 13) - 1 },
461	[FEAT_PARAM_DSI_FCK]			= { 0, 209250000 },
462	[FEAT_PARAM_DOWNSCALE]			= { 1, 4 },
463	[FEAT_PARAM_LINEWIDTH]			= { 1, 2048 },
464};
465
466static const enum dss_feat_id omap2_dss_feat_list[] = {
467	FEAT_LCDENABLEPOL,
468	FEAT_LCDENABLESIGNAL,
469	FEAT_PCKFREEENABLE,
470	FEAT_FUNCGATED,
471	FEAT_ROWREPEATENABLE,
472	FEAT_RESIZECONF,
473};
474
475static const enum dss_feat_id omap3430_dss_feat_list[] = {
476	FEAT_LCDENABLEPOL,
477	FEAT_LCDENABLESIGNAL,
478	FEAT_PCKFREEENABLE,
479	FEAT_FUNCGATED,
480	FEAT_LINEBUFFERSPLIT,
481	FEAT_ROWREPEATENABLE,
482	FEAT_RESIZECONF,
483	FEAT_DSI_REVERSE_TXCLKESC,
484	FEAT_VENC_REQUIRES_TV_DAC_CLK,
485	FEAT_CPR,
486	FEAT_PRELOAD,
487	FEAT_FIR_COEF_V,
488	FEAT_ALPHA_FIXED_ZORDER,
489	FEAT_FIFO_MERGE,
490	FEAT_OMAP3_DSI_FIFO_BUG,
491	FEAT_DPI_USES_VDDS_DSI,
492};
493
494static const enum dss_feat_id am35xx_dss_feat_list[] = {
495	FEAT_LCDENABLEPOL,
496	FEAT_LCDENABLESIGNAL,
497	FEAT_PCKFREEENABLE,
498	FEAT_FUNCGATED,
499	FEAT_LINEBUFFERSPLIT,
500	FEAT_ROWREPEATENABLE,
501	FEAT_RESIZECONF,
502	FEAT_DSI_REVERSE_TXCLKESC,
503	FEAT_VENC_REQUIRES_TV_DAC_CLK,
504	FEAT_CPR,
505	FEAT_PRELOAD,
506	FEAT_FIR_COEF_V,
507	FEAT_ALPHA_FIXED_ZORDER,
508	FEAT_FIFO_MERGE,
509	FEAT_OMAP3_DSI_FIFO_BUG,
510};
511
512static const enum dss_feat_id am43xx_dss_feat_list[] = {
513	FEAT_LCDENABLEPOL,
514	FEAT_LCDENABLESIGNAL,
515	FEAT_PCKFREEENABLE,
516	FEAT_FUNCGATED,
517	FEAT_LINEBUFFERSPLIT,
518	FEAT_ROWREPEATENABLE,
519	FEAT_RESIZECONF,
520	FEAT_CPR,
521	FEAT_PRELOAD,
522	FEAT_FIR_COEF_V,
523	FEAT_ALPHA_FIXED_ZORDER,
524	FEAT_FIFO_MERGE,
525};
526
527static const enum dss_feat_id omap3630_dss_feat_list[] = {
528	FEAT_LCDENABLEPOL,
529	FEAT_LCDENABLESIGNAL,
530	FEAT_PCKFREEENABLE,
531	FEAT_FUNCGATED,
532	FEAT_LINEBUFFERSPLIT,
533	FEAT_ROWREPEATENABLE,
534	FEAT_RESIZECONF,
535	FEAT_DSI_PLL_PWR_BUG,
536	FEAT_CPR,
537	FEAT_PRELOAD,
538	FEAT_FIR_COEF_V,
539	FEAT_ALPHA_FIXED_ZORDER,
540	FEAT_FIFO_MERGE,
541	FEAT_OMAP3_DSI_FIFO_BUG,
542	FEAT_DPI_USES_VDDS_DSI,
543};
544
545static const enum dss_feat_id omap4430_es1_0_dss_feat_list[] = {
546	FEAT_MGR_LCD2,
547	FEAT_CORE_CLK_DIV,
548	FEAT_LCD_CLK_SRC,
549	FEAT_DSI_DCS_CMD_CONFIG_VC,
550	FEAT_DSI_VC_OCP_WIDTH,
551	FEAT_DSI_GNQ,
552	FEAT_HANDLE_UV_SEPARATE,
553	FEAT_ATTR2,
554	FEAT_CPR,
555	FEAT_PRELOAD,
556	FEAT_FIR_COEF_V,
557	FEAT_ALPHA_FREE_ZORDER,
558	FEAT_FIFO_MERGE,
559	FEAT_BURST_2D,
560};
561
562static const enum dss_feat_id omap4430_es2_0_1_2_dss_feat_list[] = {
563	FEAT_MGR_LCD2,
564	FEAT_CORE_CLK_DIV,
565	FEAT_LCD_CLK_SRC,
566	FEAT_DSI_DCS_CMD_CONFIG_VC,
567	FEAT_DSI_VC_OCP_WIDTH,
568	FEAT_DSI_GNQ,
569	FEAT_HDMI_CTS_SWMODE,
570	FEAT_HANDLE_UV_SEPARATE,
571	FEAT_ATTR2,
572	FEAT_CPR,
573	FEAT_PRELOAD,
574	FEAT_FIR_COEF_V,
575	FEAT_ALPHA_FREE_ZORDER,
576	FEAT_FIFO_MERGE,
577	FEAT_BURST_2D,
578};
579
580static const enum dss_feat_id omap4_dss_feat_list[] = {
581	FEAT_MGR_LCD2,
582	FEAT_CORE_CLK_DIV,
583	FEAT_LCD_CLK_SRC,
584	FEAT_DSI_DCS_CMD_CONFIG_VC,
585	FEAT_DSI_VC_OCP_WIDTH,
586	FEAT_DSI_GNQ,
587	FEAT_HDMI_CTS_SWMODE,
588	FEAT_HDMI_AUDIO_USE_MCLK,
589	FEAT_HANDLE_UV_SEPARATE,
590	FEAT_ATTR2,
591	FEAT_CPR,
592	FEAT_PRELOAD,
593	FEAT_FIR_COEF_V,
594	FEAT_ALPHA_FREE_ZORDER,
595	FEAT_FIFO_MERGE,
596	FEAT_BURST_2D,
597};
598
599static const enum dss_feat_id omap5_dss_feat_list[] = {
600	FEAT_MGR_LCD2,
601	FEAT_MGR_LCD3,
602	FEAT_CORE_CLK_DIV,
603	FEAT_LCD_CLK_SRC,
604	FEAT_DSI_DCS_CMD_CONFIG_VC,
605	FEAT_DSI_VC_OCP_WIDTH,
606	FEAT_DSI_GNQ,
607	FEAT_HDMI_CTS_SWMODE,
608	FEAT_HDMI_AUDIO_USE_MCLK,
609	FEAT_HANDLE_UV_SEPARATE,
610	FEAT_ATTR2,
611	FEAT_CPR,
612	FEAT_PRELOAD,
613	FEAT_FIR_COEF_V,
614	FEAT_ALPHA_FREE_ZORDER,
615	FEAT_FIFO_MERGE,
616	FEAT_BURST_2D,
617	FEAT_DSI_PHY_DCC,
618	FEAT_MFLAG,
619};
620
621/* OMAP2 DSS Features */
622static const struct omap_dss_features omap2_dss_features = {
623	.reg_fields = omap2_dss_reg_fields,
624	.num_reg_fields = ARRAY_SIZE(omap2_dss_reg_fields),
625
626	.features = omap2_dss_feat_list,
627	.num_features = ARRAY_SIZE(omap2_dss_feat_list),
628
629	.num_mgrs = 2,
630	.num_ovls = 3,
631	.supported_displays = omap2_dss_supported_displays,
632	.supported_outputs = omap2_dss_supported_outputs,
633	.supported_color_modes = omap2_dss_supported_color_modes,
634	.overlay_caps = omap2_dss_overlay_caps,
635	.clksrc_names = omap2_dss_clk_source_names,
636	.dss_params = omap2_dss_param_range,
637	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_VRFB,
638	.buffer_size_unit = 1,
639	.burst_size_unit = 8,
640};
641
642/* OMAP3 DSS Features */
643static const struct omap_dss_features omap3430_dss_features = {
644	.reg_fields = omap3_dss_reg_fields,
645	.num_reg_fields = ARRAY_SIZE(omap3_dss_reg_fields),
646
647	.features = omap3430_dss_feat_list,
648	.num_features = ARRAY_SIZE(omap3430_dss_feat_list),
649
650	.num_mgrs = 2,
651	.num_ovls = 3,
652	.supported_displays = omap3430_dss_supported_displays,
653	.supported_outputs = omap3430_dss_supported_outputs,
654	.supported_color_modes = omap3_dss_supported_color_modes,
655	.overlay_caps = omap3430_dss_overlay_caps,
656	.clksrc_names = omap3_dss_clk_source_names,
657	.dss_params = omap3_dss_param_range,
658	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_VRFB,
659	.buffer_size_unit = 1,
660	.burst_size_unit = 8,
661};
662
663/*
664 * AM35xx DSS Features. This is basically OMAP3 DSS Features without the
665 * vdds_dsi regulator.
666 */
667static const struct omap_dss_features am35xx_dss_features = {
668	.reg_fields = omap3_dss_reg_fields,
669	.num_reg_fields = ARRAY_SIZE(omap3_dss_reg_fields),
670
671	.features = am35xx_dss_feat_list,
672	.num_features = ARRAY_SIZE(am35xx_dss_feat_list),
673
674	.num_mgrs = 2,
675	.num_ovls = 3,
676	.supported_displays = omap3430_dss_supported_displays,
677	.supported_outputs = omap3430_dss_supported_outputs,
678	.supported_color_modes = omap3_dss_supported_color_modes,
679	.overlay_caps = omap3430_dss_overlay_caps,
680	.clksrc_names = omap3_dss_clk_source_names,
681	.dss_params = omap3_dss_param_range,
682	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_VRFB,
683	.buffer_size_unit = 1,
684	.burst_size_unit = 8,
685};
686
687static const struct omap_dss_features am43xx_dss_features = {
688	.reg_fields = am43xx_dss_reg_fields,
689	.num_reg_fields = ARRAY_SIZE(am43xx_dss_reg_fields),
690
691	.features = am43xx_dss_feat_list,
692	.num_features = ARRAY_SIZE(am43xx_dss_feat_list),
693
694	.num_mgrs = 1,
695	.num_ovls = 3,
696	.supported_displays = am43xx_dss_supported_displays,
697	.supported_outputs = am43xx_dss_supported_outputs,
698	.supported_color_modes = omap3_dss_supported_color_modes,
699	.overlay_caps = omap3430_dss_overlay_caps,
700	.clksrc_names = omap2_dss_clk_source_names,
701	.dss_params = am43xx_dss_param_range,
702	.supported_rotation_types = OMAP_DSS_ROT_DMA,
703	.buffer_size_unit = 1,
704	.burst_size_unit = 8,
705};
706
707static const struct omap_dss_features omap3630_dss_features = {
708	.reg_fields = omap3_dss_reg_fields,
709	.num_reg_fields = ARRAY_SIZE(omap3_dss_reg_fields),
710
711	.features = omap3630_dss_feat_list,
712	.num_features = ARRAY_SIZE(omap3630_dss_feat_list),
713
714	.num_mgrs = 2,
715	.num_ovls = 3,
716	.supported_displays = omap3630_dss_supported_displays,
717	.supported_outputs = omap3630_dss_supported_outputs,
718	.supported_color_modes = omap3_dss_supported_color_modes,
719	.overlay_caps = omap3630_dss_overlay_caps,
720	.clksrc_names = omap3_dss_clk_source_names,
721	.dss_params = omap3_dss_param_range,
722	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_VRFB,
723	.buffer_size_unit = 1,
724	.burst_size_unit = 8,
725};
726
727/* OMAP4 DSS Features */
728/* For OMAP4430 ES 1.0 revision */
729static const struct omap_dss_features omap4430_es1_0_dss_features  = {
730	.reg_fields = omap4_dss_reg_fields,
731	.num_reg_fields = ARRAY_SIZE(omap4_dss_reg_fields),
732
733	.features = omap4430_es1_0_dss_feat_list,
734	.num_features = ARRAY_SIZE(omap4430_es1_0_dss_feat_list),
735
736	.num_mgrs = 3,
737	.num_ovls = 4,
738	.num_wbs = 1,
739	.supported_displays = omap4_dss_supported_displays,
740	.supported_outputs = omap4_dss_supported_outputs,
741	.supported_color_modes = omap4_dss_supported_color_modes,
742	.overlay_caps = omap4_dss_overlay_caps,
743	.clksrc_names = omap4_dss_clk_source_names,
744	.dss_params = omap4_dss_param_range,
745	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_TILER,
746	.buffer_size_unit = 16,
747	.burst_size_unit = 16,
748};
749
750/* For OMAP4430 ES 2.0, 2.1 and 2.2 revisions */
751static const struct omap_dss_features omap4430_es2_0_1_2_dss_features = {
752	.reg_fields = omap4_dss_reg_fields,
753	.num_reg_fields = ARRAY_SIZE(omap4_dss_reg_fields),
754
755	.features = omap4430_es2_0_1_2_dss_feat_list,
756	.num_features = ARRAY_SIZE(omap4430_es2_0_1_2_dss_feat_list),
757
758	.num_mgrs = 3,
759	.num_ovls = 4,
760	.num_wbs = 1,
761	.supported_displays = omap4_dss_supported_displays,
762	.supported_outputs = omap4_dss_supported_outputs,
763	.supported_color_modes = omap4_dss_supported_color_modes,
764	.overlay_caps = omap4_dss_overlay_caps,
765	.clksrc_names = omap4_dss_clk_source_names,
766	.dss_params = omap4_dss_param_range,
767	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_TILER,
768	.buffer_size_unit = 16,
769	.burst_size_unit = 16,
770};
771
772/* For all the other OMAP4 versions */
773static const struct omap_dss_features omap4_dss_features = {
774	.reg_fields = omap4_dss_reg_fields,
775	.num_reg_fields = ARRAY_SIZE(omap4_dss_reg_fields),
776
777	.features = omap4_dss_feat_list,
778	.num_features = ARRAY_SIZE(omap4_dss_feat_list),
779
780	.num_mgrs = 3,
781	.num_ovls = 4,
782	.num_wbs = 1,
783	.supported_displays = omap4_dss_supported_displays,
784	.supported_outputs = omap4_dss_supported_outputs,
785	.supported_color_modes = omap4_dss_supported_color_modes,
786	.overlay_caps = omap4_dss_overlay_caps,
787	.clksrc_names = omap4_dss_clk_source_names,
788	.dss_params = omap4_dss_param_range,
789	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_TILER,
790	.buffer_size_unit = 16,
791	.burst_size_unit = 16,
792};
793
794/* OMAP5 DSS Features */
795static const struct omap_dss_features omap5_dss_features = {
796	.reg_fields = omap5_dss_reg_fields,
797	.num_reg_fields = ARRAY_SIZE(omap5_dss_reg_fields),
798
799	.features = omap5_dss_feat_list,
800	.num_features = ARRAY_SIZE(omap5_dss_feat_list),
801
802	.num_mgrs = 4,
803	.num_ovls = 4,
804	.supported_displays = omap5_dss_supported_displays,
805	.supported_outputs = omap5_dss_supported_outputs,
806	.supported_color_modes = omap4_dss_supported_color_modes,
807	.overlay_caps = omap4_dss_overlay_caps,
808	.clksrc_names = omap5_dss_clk_source_names,
809	.dss_params = omap5_dss_param_range,
810	.supported_rotation_types = OMAP_DSS_ROT_DMA | OMAP_DSS_ROT_TILER,
811	.buffer_size_unit = 16,
812	.burst_size_unit = 16,
813};
814
815/* Functions returning values related to a DSS feature */
816int dss_feat_get_num_mgrs(void)
817{
818	return omap_current_dss_features->num_mgrs;
819}
820EXPORT_SYMBOL(dss_feat_get_num_mgrs);
821
822int dss_feat_get_num_ovls(void)
823{
824	return omap_current_dss_features->num_ovls;
825}
826EXPORT_SYMBOL(dss_feat_get_num_ovls);
827
828int dss_feat_get_num_wbs(void)
829{
830	return omap_current_dss_features->num_wbs;
831}
832
833unsigned long dss_feat_get_param_min(enum dss_range_param param)
834{
835	return omap_current_dss_features->dss_params[param].min;
836}
837
838unsigned long dss_feat_get_param_max(enum dss_range_param param)
839{
840	return omap_current_dss_features->dss_params[param].max;
841}
842
843enum omap_display_type dss_feat_get_supported_displays(enum omap_channel channel)
844{
845	return omap_current_dss_features->supported_displays[channel];
846}
847EXPORT_SYMBOL(dss_feat_get_supported_displays);
848
849enum omap_dss_output_id dss_feat_get_supported_outputs(enum omap_channel channel)
850{
851	return omap_current_dss_features->supported_outputs[channel];
852}
853EXPORT_SYMBOL(dss_feat_get_supported_outputs);
854
855enum omap_color_mode dss_feat_get_supported_color_modes(enum omap_plane plane)
856{
857	return omap_current_dss_features->supported_color_modes[plane];
858}
859EXPORT_SYMBOL(dss_feat_get_supported_color_modes);
860
861enum omap_overlay_caps dss_feat_get_overlay_caps(enum omap_plane plane)
862{
863	return omap_current_dss_features->overlay_caps[plane];
864}
865
866bool dss_feat_color_mode_supported(enum omap_plane plane,
867		enum omap_color_mode color_mode)
868{
869	return omap_current_dss_features->supported_color_modes[plane] &
870			color_mode;
871}
872
873const char *dss_feat_get_clk_source_name(enum omap_dss_clk_source id)
874{
875	return omap_current_dss_features->clksrc_names[id];
876}
877
878u32 dss_feat_get_buffer_size_unit(void)
879{
880	return omap_current_dss_features->buffer_size_unit;
881}
882
883u32 dss_feat_get_burst_size_unit(void)
884{
885	return omap_current_dss_features->burst_size_unit;
886}
887
888/* DSS has_feature check */
889bool dss_has_feature(enum dss_feat_id id)
890{
891	int i;
892	const enum dss_feat_id *features = omap_current_dss_features->features;
893	const int num_features = omap_current_dss_features->num_features;
894
895	for (i = 0; i < num_features; i++) {
896		if (features[i] == id)
897			return true;
898	}
899
900	return false;
901}
902
903void dss_feat_get_reg_field(enum dss_feat_reg_field id, u8 *start, u8 *end)
904{
905	if (id >= omap_current_dss_features->num_reg_fields)
906		BUG();
907
908	*start = omap_current_dss_features->reg_fields[id].start;
909	*end = omap_current_dss_features->reg_fields[id].end;
910}
911
912bool dss_feat_rotation_type_supported(enum omap_dss_rotation_type rot_type)
913{
914	return omap_current_dss_features->supported_rotation_types & rot_type;
915}
916
917void dss_features_init(enum omapdss_version version)
918{
919	switch (version) {
920	case OMAPDSS_VER_OMAP24xx:
921		omap_current_dss_features = &omap2_dss_features;
922		break;
923
924	case OMAPDSS_VER_OMAP34xx_ES1:
925	case OMAPDSS_VER_OMAP34xx_ES3:
926		omap_current_dss_features = &omap3430_dss_features;
927		break;
928
929	case OMAPDSS_VER_OMAP3630:
930		omap_current_dss_features = &omap3630_dss_features;
931		break;
932
933	case OMAPDSS_VER_OMAP4430_ES1:
934		omap_current_dss_features = &omap4430_es1_0_dss_features;
935		break;
936
937	case OMAPDSS_VER_OMAP4430_ES2:
938		omap_current_dss_features = &omap4430_es2_0_1_2_dss_features;
939		break;
940
941	case OMAPDSS_VER_OMAP4:
942		omap_current_dss_features = &omap4_dss_features;
943		break;
944
945	case OMAPDSS_VER_OMAP5:
946	case OMAPDSS_VER_DRA7xx:
947		omap_current_dss_features = &omap5_dss_features;
948		break;
949
950	case OMAPDSS_VER_AM35xx:
951		omap_current_dss_features = &am35xx_dss_features;
952		break;
953
954	case OMAPDSS_VER_AM43xx:
955		omap_current_dss_features = &am43xx_dss_features;
956		break;
957
958	default:
959		DSSWARN("Unsupported OMAP version");
960		break;
961	}
962}
963