Commit | Line | Data |
---|---|---|
559d6701 TV |
1 | /* |
2 | * linux/drivers/video/omap2/dss/dss.h | |
3 | * | |
4 | * Copyright (C) 2009 Nokia Corporation | |
5 | * Author: Tomi Valkeinen <tomi.valkeinen@nokia.com> | |
6 | * | |
7 | * Some code and ideas taken from drivers/video/omap/ driver | |
8 | * by Imre Deak. | |
9 | * | |
10 | * This program is free software; you can redistribute it and/or modify it | |
11 | * under the terms of the GNU General Public License version 2 as published by | |
12 | * the Free Software Foundation. | |
13 | * | |
14 | * This program is distributed in the hope that it will be useful, but WITHOUT | |
15 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
16 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for | |
17 | * more details. | |
18 | * | |
19 | * You should have received a copy of the GNU General Public License along with | |
20 | * this program. If not, see <http://www.gnu.org/licenses/>. | |
21 | */ | |
22 | ||
23 | #ifndef __OMAP2_DSS_H | |
24 | #define __OMAP2_DSS_H | |
25 | ||
96e2e637 TV |
26 | #include <linux/interrupt.h> |
27 | ||
35a339ac TV |
28 | #include "omapdss.h" |
29 | ||
702d267e CM |
30 | #ifdef pr_fmt |
31 | #undef pr_fmt | |
559d6701 TV |
32 | #endif |
33 | ||
702d267e CM |
34 | #ifdef DSS_SUBSYS_NAME |
35 | #define pr_fmt(fmt) DSS_SUBSYS_NAME ": " fmt | |
36 | #else | |
37 | #define pr_fmt(fmt) fmt | |
559d6701 TV |
38 | #endif |
39 | ||
702d267e CM |
40 | #define DSSDBG(format, ...) \ |
41 | pr_debug(format, ## __VA_ARGS__) | |
559d6701 TV |
42 | |
43 | #ifdef DSS_SUBSYS_NAME | |
44 | #define DSSERR(format, ...) \ | |
45 | printk(KERN_ERR "omapdss " DSS_SUBSYS_NAME " error: " format, \ | |
46 | ## __VA_ARGS__) | |
47 | #else | |
48 | #define DSSERR(format, ...) \ | |
49 | printk(KERN_ERR "omapdss error: " format, ## __VA_ARGS__) | |
50 | #endif | |
51 | ||
52 | #ifdef DSS_SUBSYS_NAME | |
53 | #define DSSINFO(format, ...) \ | |
54 | printk(KERN_INFO "omapdss " DSS_SUBSYS_NAME ": " format, \ | |
55 | ## __VA_ARGS__) | |
56 | #else | |
57 | #define DSSINFO(format, ...) \ | |
58 | printk(KERN_INFO "omapdss: " format, ## __VA_ARGS__) | |
59 | #endif | |
60 | ||
61 | #ifdef DSS_SUBSYS_NAME | |
62 | #define DSSWARN(format, ...) \ | |
63 | printk(KERN_WARNING "omapdss " DSS_SUBSYS_NAME ": " format, \ | |
64 | ## __VA_ARGS__) | |
65 | #else | |
66 | #define DSSWARN(format, ...) \ | |
67 | printk(KERN_WARNING "omapdss: " format, ## __VA_ARGS__) | |
68 | #endif | |
69 | ||
70 | /* OMAP TRM gives bitfields as start:end, where start is the higher bit | |
71 | number. For example 7:0 */ | |
72 | #define FLD_MASK(start, end) (((1 << ((start) - (end) + 1)) - 1) << (end)) | |
73 | #define FLD_VAL(val, start, end) (((val) << (end)) & FLD_MASK(start, end)) | |
74 | #define FLD_GET(val, start, end) (((val) & FLD_MASK(start, end)) >> (end)) | |
75 | #define FLD_MOD(orig, val, start, end) \ | |
76 | (((orig) & ~FLD_MASK(start, end)) | FLD_VAL(val, start, end)) | |
77 | ||
569969d6 AT |
78 | enum dss_io_pad_mode { |
79 | DSS_IO_PAD_MODE_RESET, | |
80 | DSS_IO_PAD_MODE_RFBI, | |
81 | DSS_IO_PAD_MODE_BYPASS, | |
559d6701 TV |
82 | }; |
83 | ||
7ed024aa M |
84 | enum dss_hdmi_venc_clk_source_select { |
85 | DSS_VENC_TV_CLK = 0, | |
86 | DSS_HDMI_M_PCLK = 1, | |
87 | }; | |
88 | ||
6ff8aa31 AT |
89 | enum dss_dsi_content_type { |
90 | DSS_DSI_CONTENT_DCS, | |
91 | DSS_DSI_CONTENT_GENERIC, | |
92 | }; | |
93 | ||
d9ac773c AT |
94 | enum dss_writeback_channel { |
95 | DSS_WB_LCD1_MGR = 0, | |
96 | DSS_WB_LCD2_MGR = 1, | |
97 | DSS_WB_TV_MGR = 2, | |
98 | DSS_WB_OVL0 = 3, | |
99 | DSS_WB_OVL1 = 4, | |
100 | DSS_WB_OVL2 = 5, | |
101 | DSS_WB_OVL3 = 6, | |
102 | DSS_WB_LCD3_MGR = 7, | |
103 | }; | |
104 | ||
64e22ffd TV |
105 | enum dss_pll_id { |
106 | DSS_PLL_DSI1, | |
107 | DSS_PLL_DSI2, | |
108 | DSS_PLL_HDMI, | |
6d817880 TV |
109 | DSS_PLL_VIDEO1, |
110 | DSS_PLL_VIDEO2, | |
64e22ffd TV |
111 | }; |
112 | ||
0a20170a TV |
113 | struct dss_pll; |
114 | ||
115 | #define DSS_PLL_MAX_HSDIVS 4 | |
116 | ||
117 | /* | |
118 | * Type-A PLLs: clkout[]/mX[] refer to hsdiv outputs m4, m5, m6, m7. | |
119 | * Type-B PLLs: clkout[0] refers to m2. | |
120 | */ | |
121 | struct dss_pll_clock_info { | |
122 | /* rates that we get with dividers below */ | |
123 | unsigned long fint; | |
124 | unsigned long clkdco; | |
125 | unsigned long clkout[DSS_PLL_MAX_HSDIVS]; | |
126 | ||
127 | /* dividers */ | |
128 | u16 n; | |
129 | u16 m; | |
130 | u32 mf; | |
131 | u16 mX[DSS_PLL_MAX_HSDIVS]; | |
132 | u16 sd; | |
133 | }; | |
134 | ||
135 | struct dss_pll_ops { | |
136 | int (*enable)(struct dss_pll *pll); | |
137 | void (*disable)(struct dss_pll *pll); | |
138 | int (*set_config)(struct dss_pll *pll, | |
139 | const struct dss_pll_clock_info *cinfo); | |
140 | }; | |
141 | ||
142 | struct dss_pll_hw { | |
143 | unsigned n_max; | |
144 | unsigned m_min; | |
145 | unsigned m_max; | |
146 | unsigned mX_max; | |
147 | ||
148 | unsigned long fint_min, fint_max; | |
149 | unsigned long clkdco_min, clkdco_low, clkdco_max; | |
150 | ||
151 | u8 n_msb, n_lsb; | |
152 | u8 m_msb, m_lsb; | |
153 | u8 mX_msb[DSS_PLL_MAX_HSDIVS], mX_lsb[DSS_PLL_MAX_HSDIVS]; | |
154 | ||
155 | bool has_stopmode; | |
156 | bool has_freqsel; | |
157 | bool has_selfreqdco; | |
158 | bool has_refsel; | |
159 | }; | |
160 | ||
161 | struct dss_pll { | |
162 | const char *name; | |
64e22ffd | 163 | enum dss_pll_id id; |
0a20170a TV |
164 | |
165 | struct clk *clkin; | |
166 | struct regulator *regulator; | |
167 | ||
168 | void __iomem *base; | |
169 | ||
170 | const struct dss_pll_hw *hw; | |
171 | ||
172 | const struct dss_pll_ops *ops; | |
173 | ||
174 | struct dss_pll_clock_info cinfo; | |
175 | }; | |
176 | ||
559d6701 TV |
177 | struct dispc_clock_info { |
178 | /* rates that we get with dividers below */ | |
179 | unsigned long lck; | |
180 | unsigned long pck; | |
181 | ||
182 | /* dividers */ | |
183 | u16 lck_div; | |
184 | u16 pck_div; | |
185 | }; | |
186 | ||
c56fb3ef AT |
187 | struct dss_lcd_mgr_config { |
188 | enum dss_io_pad_mode io_pad_mode; | |
189 | ||
190 | bool stallmode; | |
191 | bool fifohandcheck; | |
192 | ||
193 | struct dispc_clock_info clock_info; | |
194 | ||
195 | int video_port_width; | |
196 | ||
197 | int lcden_sig_polarity; | |
198 | }; | |
199 | ||
559d6701 TV |
200 | struct seq_file; |
201 | struct platform_device; | |
202 | ||
203 | /* core */ | |
8f46efad | 204 | struct platform_device *dss_get_core_pdev(void); |
00928eaf TV |
205 | int dss_dsi_enable_pads(int dsi_id, unsigned lane_mask); |
206 | void dss_dsi_disable_pads(int dsi_id, unsigned lane_mask); | |
a8081d31 | 207 | int dss_set_min_bus_tput(struct device *dev, unsigned long tput); |
e40402cf | 208 | int dss_debugfs_create_file(const char *name, void (*write)(struct seq_file *)); |
559d6701 | 209 | |
f476ae9d AT |
210 | static inline bool dss_mgr_is_lcd(enum omap_channel id) |
211 | { | |
212 | if (id == OMAP_DSS_CHANNEL_LCD || id == OMAP_DSS_CHANNEL_LCD2 || | |
213 | id == OMAP_DSS_CHANNEL_LCD3) | |
214 | return true; | |
215 | else | |
216 | return false; | |
217 | } | |
218 | ||
559d6701 | 219 | /* DSS */ |
6e7e8f06 | 220 | int dss_init_platform_driver(void) __init; |
96c401bc | 221 | void dss_uninit_platform_driver(void); |
559d6701 | 222 | |
99767548 TV |
223 | int dss_runtime_get(void); |
224 | void dss_runtime_put(void); | |
225 | ||
5aaee69d | 226 | unsigned long dss_get_dispc_clk_rate(void); |
064c2a47 | 227 | int dss_dpi_select_source(int port, enum omap_channel channel); |
7ed024aa | 228 | void dss_select_hdmi_venc_clk_source(enum dss_hdmi_venc_clk_source_select); |
4a61e267 | 229 | enum dss_hdmi_venc_clk_source_select dss_get_hdmi_venc_clk_source(void); |
89a35e51 | 230 | const char *dss_get_generic_clk_source_name(enum omap_dss_clk_source clk_src); |
8b9cb3a8 | 231 | void dss_dump_clocks(struct seq_file *s); |
559d6701 | 232 | |
99767548 TV |
233 | /* DSS VIDEO PLL */ |
234 | struct dss_pll *dss_video_pll_init(struct platform_device *pdev, int id, | |
235 | struct regulator *regulator); | |
236 | void dss_video_pll_uninit(struct dss_pll *pll); | |
237 | ||
ef691ff4 AT |
238 | /* dss-of */ |
239 | struct device_node *dss_of_port_get_parent_device(struct device_node *port); | |
240 | u32 dss_of_port_get_port_number(struct device_node *port); | |
241 | ||
1b3bcb33 | 242 | #if defined(CONFIG_OMAP2_DSS_DEBUGFS) |
8b9cb3a8 SG |
243 | void dss_debug_dump_clocks(struct seq_file *s); |
244 | #endif | |
559d6701 | 245 | |
be40eecf TV |
246 | void dss_ctrl_pll_enable(enum dss_pll_id pll_id, bool enable); |
247 | void dss_ctrl_pll_set_control_mux(enum dss_pll_id pll_id, | |
248 | enum omap_channel channel); | |
249 | ||
889b4fd7 | 250 | void dss_sdi_init(int datapairs); |
559d6701 TV |
251 | int dss_sdi_enable(void); |
252 | void dss_sdi_disable(void); | |
253 | ||
5a8b572d AT |
254 | void dss_select_dsi_clk_source(int dsi_module, |
255 | enum omap_dss_clk_source clk_src); | |
ea75159e | 256 | void dss_select_lcd_clk_source(enum omap_channel channel, |
89a35e51 AT |
257 | enum omap_dss_clk_source clk_src); |
258 | enum omap_dss_clk_source dss_get_dispc_clk_source(void); | |
5a8b572d | 259 | enum omap_dss_clk_source dss_get_dsi_clk_source(int dsi_module); |
89a35e51 | 260 | enum omap_dss_clk_source dss_get_lcd_clk_source(enum omap_channel channel); |
2f18c4d8 | 261 | |
559d6701 TV |
262 | void dss_set_venc_output(enum omap_dss_venc_type type); |
263 | void dss_set_dac_pwrdn_bgz(bool enable); | |
264 | ||
d0f58bd3 | 265 | int dss_set_fck_rate(unsigned long rate); |
559d6701 | 266 | |
d0f58bd3 | 267 | typedef bool (*dss_div_calc_func)(unsigned long fck, void *data); |
688af02d TV |
268 | bool dss_div_calc(unsigned long pck, unsigned long fck_min, |
269 | dss_div_calc_func func, void *data); | |
43417823 | 270 | |
559d6701 | 271 | /* SDI */ |
6e7e8f06 | 272 | int sdi_init_platform_driver(void) __init; |
ede92695 | 273 | void sdi_uninit_platform_driver(void); |
559d6701 | 274 | |
387ce9f2 | 275 | #ifdef CONFIG_OMAP2_DSS_SDI |
ede92695 TV |
276 | int sdi_init_port(struct platform_device *pdev, struct device_node *port); |
277 | void sdi_uninit_port(struct device_node *port); | |
387ce9f2 | 278 | #else |
ede92695 | 279 | static inline int sdi_init_port(struct platform_device *pdev, |
387ce9f2 AT |
280 | struct device_node *port) |
281 | { | |
282 | return 0; | |
283 | } | |
ede92695 | 284 | static inline void sdi_uninit_port(struct device_node *port) |
387ce9f2 AT |
285 | { |
286 | } | |
287 | #endif | |
2ecef246 | 288 | |
559d6701 | 289 | /* DSI */ |
989c79a8 | 290 | |
368a148e | 291 | #ifdef CONFIG_OMAP2_DSS_DSI |
5a8b572d AT |
292 | |
293 | struct dentry; | |
294 | struct file_operations; | |
295 | ||
6e7e8f06 | 296 | int dsi_init_platform_driver(void) __init; |
ede92695 | 297 | void dsi_uninit_platform_driver(void); |
559d6701 TV |
298 | |
299 | void dsi_dump_clocks(struct seq_file *s); | |
559d6701 | 300 | |
559d6701 | 301 | void dsi_irq_handler(void); |
a3b3cc2b AT |
302 | u8 dsi_get_pixel_size(enum omap_dss_dsi_pixel_format fmt); |
303 | ||
368a148e | 304 | #else |
a3b3cc2b AT |
305 | static inline u8 dsi_get_pixel_size(enum omap_dss_dsi_pixel_format fmt) |
306 | { | |
85d90b12 DC |
307 | WARN(1, "%s: DSI not compiled in, returning pixel_size as 0\n", |
308 | __func__); | |
a3b3cc2b AT |
309 | return 0; |
310 | } | |
368a148e | 311 | #endif |
559d6701 TV |
312 | |
313 | /* DPI */ | |
6e7e8f06 | 314 | int dpi_init_platform_driver(void) __init; |
ede92695 | 315 | void dpi_uninit_platform_driver(void); |
559d6701 | 316 | |
387ce9f2 | 317 | #ifdef CONFIG_OMAP2_DSS_DPI |
ede92695 TV |
318 | int dpi_init_port(struct platform_device *pdev, struct device_node *port); |
319 | void dpi_uninit_port(struct device_node *port); | |
387ce9f2 | 320 | #else |
ede92695 | 321 | static inline int dpi_init_port(struct platform_device *pdev, |
387ce9f2 AT |
322 | struct device_node *port) |
323 | { | |
324 | return 0; | |
325 | } | |
ede92695 | 326 | static inline void dpi_uninit_port(struct device_node *port) |
387ce9f2 AT |
327 | { |
328 | } | |
329 | #endif | |
2ecef246 | 330 | |
559d6701 | 331 | /* DISPC */ |
6e7e8f06 | 332 | int dispc_init_platform_driver(void) __init; |
ede92695 | 333 | void dispc_uninit_platform_driver(void); |
559d6701 | 334 | void dispc_dump_clocks(struct seq_file *s); |
559d6701 TV |
335 | |
336 | void dispc_enable_sidle(void); | |
337 | void dispc_disable_sidle(void); | |
338 | ||
559d6701 TV |
339 | void dispc_lcd_enable_signal(bool enable); |
340 | void dispc_pck_free_enable(bool enable); | |
cd295aeb TV |
341 | void dispc_enable_fifomerge(bool enable); |
342 | void dispc_enable_gamma_table(bool enable); | |
cd295aeb | 343 | |
7c284e6e TV |
344 | typedef bool (*dispc_div_calc_func)(int lckd, int pckd, unsigned long lck, |
345 | unsigned long pck, void *data); | |
346 | bool dispc_div_calc(unsigned long dispc, | |
347 | unsigned long pck_min, unsigned long pck_max, | |
348 | dispc_div_calc_func func, void *data); | |
349 | ||
8f366162 | 350 | bool dispc_mgr_timings_ok(enum omap_channel channel, |
b917fa39 | 351 | const struct omap_video_timings *timings); |
cd295aeb TV |
352 | int dispc_calc_clock_rates(unsigned long dispc_fclk_rate, |
353 | struct dispc_clock_info *cinfo); | |
354 | ||
355 | ||
6f04e1bf | 356 | void dispc_ovl_set_fifo_threshold(enum omap_plane plane, u32 low, u32 high); |
83fa2f2e | 357 | void dispc_ovl_compute_fifo_thresholds(enum omap_plane plane, |
3568f2a4 TV |
358 | u32 *fifo_low, u32 *fifo_high, bool use_fifomerge, |
359 | bool manual_update); | |
348be69d | 360 | |
f0d08f89 | 361 | void dispc_mgr_set_clock_div(enum omap_channel channel, |
a8f3fcd1 | 362 | const struct dispc_clock_info *cinfo); |
26d9dd0d | 363 | int dispc_mgr_get_clock_div(enum omap_channel channel, |
ff1b2cde | 364 | struct dispc_clock_info *cinfo); |
5391e87d | 365 | void dispc_set_tv_pclk(unsigned long pclk); |
559d6701 | 366 | |
0b23e5b8 AT |
367 | u32 dispc_wb_get_framedone_irq(void); |
368 | bool dispc_wb_go_busy(void); | |
369 | void dispc_wb_go(void); | |
370 | void dispc_wb_enable(bool enable); | |
371 | bool dispc_wb_is_enabled(void); | |
d9ac773c | 372 | void dispc_wb_set_channel_in(enum dss_writeback_channel channel); |
749feffa | 373 | int dispc_wb_setup(const struct omap_dss_writeback_info *wi, |
9e4a0fc7 | 374 | bool mem_to_mem, const struct omap_video_timings *timings); |
d9ac773c | 375 | |
559d6701 | 376 | /* VENC */ |
6e7e8f06 | 377 | int venc_init_platform_driver(void) __init; |
ede92695 | 378 | void venc_uninit_platform_driver(void); |
559d6701 | 379 | |
c3198a5e | 380 | /* HDMI */ |
ef26958a | 381 | int hdmi4_init_platform_driver(void) __init; |
ede92695 | 382 | void hdmi4_uninit_platform_driver(void); |
c3198a5e | 383 | |
f5bab222 | 384 | int hdmi5_init_platform_driver(void) __init; |
ede92695 | 385 | void hdmi5_uninit_platform_driver(void); |
f5bab222 | 386 | |
559d6701 | 387 | /* RFBI */ |
6e7e8f06 | 388 | int rfbi_init_platform_driver(void) __init; |
ede92695 | 389 | void rfbi_uninit_platform_driver(void); |
559d6701 | 390 | |
dfc0fd8d TV |
391 | |
392 | #ifdef CONFIG_OMAP2_DSS_COLLECT_IRQ_STATS | |
393 | static inline void dss_collect_irq_stats(u32 irqstatus, unsigned *irq_arr) | |
394 | { | |
395 | int b; | |
396 | for (b = 0; b < 32; ++b) { | |
397 | if (irqstatus & (1 << b)) | |
398 | irq_arr[b]++; | |
399 | } | |
400 | } | |
401 | #endif | |
402 | ||
0a20170a TV |
403 | /* PLL */ |
404 | typedef bool (*dss_pll_calc_func)(int n, int m, unsigned long fint, | |
405 | unsigned long clkdco, void *data); | |
406 | typedef bool (*dss_hsdiv_calc_func)(int m_dispc, unsigned long dispc, | |
407 | void *data); | |
408 | ||
409 | int dss_pll_register(struct dss_pll *pll); | |
410 | void dss_pll_unregister(struct dss_pll *pll); | |
411 | struct dss_pll *dss_pll_find(const char *name); | |
412 | int dss_pll_enable(struct dss_pll *pll); | |
413 | void dss_pll_disable(struct dss_pll *pll); | |
414 | int dss_pll_set_config(struct dss_pll *pll, | |
415 | const struct dss_pll_clock_info *cinfo); | |
416 | ||
417 | bool dss_pll_hsdiv_calc(const struct dss_pll *pll, unsigned long clkdco, | |
418 | unsigned long out_min, unsigned long out_max, | |
419 | dss_hsdiv_calc_func func, void *data); | |
420 | bool dss_pll_calc(const struct dss_pll *pll, unsigned long clkin, | |
421 | unsigned long pll_min, unsigned long pll_max, | |
422 | dss_pll_calc_func func, void *data); | |
423 | int dss_pll_write_config_type_a(struct dss_pll *pll, | |
424 | const struct dss_pll_clock_info *cinfo); | |
425 | int dss_pll_write_config_type_b(struct dss_pll *pll, | |
426 | const struct dss_pll_clock_info *cinfo); | |
eb30199b | 427 | int dss_pll_wait_reset_done(struct dss_pll *pll); |
0a20170a | 428 | |
559d6701 | 429 | #endif |