aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/video
diff options
context:
space:
mode:
authorTomi Valkeinen <tomi.valkeinen@ti.com>2014-03-20 02:09:19 -0400
committerTomi Valkeinen <tomi.valkeinen@ti.com>2014-03-20 02:13:50 -0400
commit17d5ca91cfc59ae91da5ff9da74ab09a9a2a17d9 (patch)
treea45f944e15a2600ec20ca4ec11b23d4641095e8e /drivers/video
parentb7e4ab50418d5b34ab0dae95193dd71190e1fb50 (diff)
parentc86907b59f505863ec7839471e889330982a596e (diff)
Merge branch '3.15/dss-dt' into 3.15/fbdev
Merge OMAP DSS DT support
Diffstat (limited to 'drivers/video')
-rw-r--r--drivers/video/Kconfig2
-rw-r--r--drivers/video/exynos/Kconfig3
-rw-r--r--drivers/video/omap2/displays-new/connector-analog-tv.c43
-rw-r--r--drivers/video/omap2/displays-new/connector-dvi.c43
-rw-r--r--drivers/video/omap2/displays-new/connector-hdmi.c30
-rw-r--r--drivers/video/omap2/displays-new/encoder-tfp410.c43
-rw-r--r--drivers/video/omap2/displays-new/encoder-tpd12s015.c56
-rw-r--r--drivers/video/omap2/displays-new/panel-dsi-cm.c60
-rw-r--r--drivers/video/omap2/displays-new/panel-sony-acx565akm.c33
-rw-r--r--drivers/video/omap2/dss/Makefile2
-rw-r--r--drivers/video/omap2/dss/dispc.c24
-rw-r--r--drivers/video/omap2/dss/display.c28
-rw-r--r--drivers/video/omap2/dss/dpi.c49
-rw-r--r--drivers/video/omap2/dss/dsi.c144
-rw-r--r--drivers/video/omap2/dss/dss-of.c159
-rw-r--r--drivers/video/omap2/dss/dss.c66
-rw-r--r--drivers/video/omap2/dss/dss.h6
-rw-r--r--drivers/video/omap2/dss/hdmi4.c11
-rw-r--r--drivers/video/omap2/dss/sdi.c47
-rw-r--r--drivers/video/omap2/dss/venc.c66
-rw-r--r--drivers/video/omap2/omapfb/omapfb-main.c67
21 files changed, 938 insertions, 44 deletions
diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig
index 78e2fc7a4840..7d4e33cba6ed 100644
--- a/drivers/video/Kconfig
+++ b/drivers/video/Kconfig
@@ -364,7 +364,7 @@ config FB_SA1100
364 364
365config FB_IMX 365config FB_IMX
366 tristate "Freescale i.MX1/21/25/27 LCD support" 366 tristate "Freescale i.MX1/21/25/27 LCD support"
367 depends on FB && IMX_HAVE_PLATFORM_IMX_FB 367 depends on FB && ARCH_MXC
368 select FB_CFB_FILLRECT 368 select FB_CFB_FILLRECT
369 select FB_CFB_COPYAREA 369 select FB_CFB_COPYAREA
370 select FB_CFB_IMAGEBLIT 370 select FB_CFB_IMAGEBLIT
diff --git a/drivers/video/exynos/Kconfig b/drivers/video/exynos/Kconfig
index 976594d578a9..eb6f2b059821 100644
--- a/drivers/video/exynos/Kconfig
+++ b/drivers/video/exynos/Kconfig
@@ -22,7 +22,8 @@ config EXYNOS_MIPI_DSI
22 22
23config EXYNOS_LCD_S6E8AX0 23config EXYNOS_LCD_S6E8AX0
24 bool "S6E8AX0 MIPI AMOLED LCD Driver" 24 bool "S6E8AX0 MIPI AMOLED LCD Driver"
25 depends on (EXYNOS_MIPI_DSI && BACKLIGHT_CLASS_DEVICE && LCD_CLASS_DEVICE) 25 depends on EXYNOS_MIPI_DSI && BACKLIGHT_CLASS_DEVICE
26 depends on (LCD_CLASS_DEVICE = y)
26 default n 27 default n
27 help 28 help
28 If you have an S6E8AX0 MIPI AMOLED LCD Panel, say Y to enable its 29 If you have an S6E8AX0 MIPI AMOLED LCD Panel, say Y to enable its
diff --git a/drivers/video/omap2/displays-new/connector-analog-tv.c b/drivers/video/omap2/displays-new/connector-analog-tv.c
index 27f33ef8fca1..5ee3b5505f7f 100644
--- a/drivers/video/omap2/displays-new/connector-analog-tv.c
+++ b/drivers/video/omap2/displays-new/connector-analog-tv.c
@@ -12,6 +12,7 @@
12#include <linux/slab.h> 12#include <linux/slab.h>
13#include <linux/module.h> 13#include <linux/module.h>
14#include <linux/platform_device.h> 14#include <linux/platform_device.h>
15#include <linux/of.h>
15 16
16#include <video/omapdss.h> 17#include <video/omapdss.h>
17#include <video/omap-panel-data.h> 18#include <video/omap-panel-data.h>
@@ -42,6 +43,12 @@ static const struct omap_video_timings tvc_pal_timings = {
42 .interlace = true, 43 .interlace = true,
43}; 44};
44 45
46static const struct of_device_id tvc_of_match[];
47
48struct tvc_of_data {
49 enum omap_dss_venc_type connector_type;
50};
51
45#define to_panel_data(x) container_of(x, struct panel_drv_data, dssdev) 52#define to_panel_data(x) container_of(x, struct panel_drv_data, dssdev)
46 53
47static int tvc_connect(struct omap_dss_device *dssdev) 54static int tvc_connect(struct omap_dss_device *dssdev)
@@ -91,8 +98,12 @@ static int tvc_enable(struct omap_dss_device *dssdev)
91 98
92 in->ops.atv->set_timings(in, &ddata->timings); 99 in->ops.atv->set_timings(in, &ddata->timings);
93 100
94 in->ops.atv->set_type(in, ddata->connector_type); 101 if (!ddata->dev->of_node) {
95 in->ops.atv->invert_vid_out_polarity(in, ddata->invert_polarity); 102 in->ops.atv->set_type(in, ddata->connector_type);
103
104 in->ops.atv->invert_vid_out_polarity(in,
105 ddata->invert_polarity);
106 }
96 107
97 r = in->ops.atv->enable(in); 108 r = in->ops.atv->enable(in);
98 if (r) 109 if (r)
@@ -205,6 +216,23 @@ static int tvc_probe_pdata(struct platform_device *pdev)
205 return 0; 216 return 0;
206} 217}
207 218
219static int tvc_probe_of(struct platform_device *pdev)
220{
221 struct panel_drv_data *ddata = platform_get_drvdata(pdev);
222 struct device_node *node = pdev->dev.of_node;
223 struct omap_dss_device *in;
224
225 in = omapdss_of_find_source_for_first_ep(node);
226 if (IS_ERR(in)) {
227 dev_err(&pdev->dev, "failed to find video source\n");
228 return PTR_ERR(in);
229 }
230
231 ddata->in = in;
232
233 return 0;
234}
235
208static int tvc_probe(struct platform_device *pdev) 236static int tvc_probe(struct platform_device *pdev)
209{ 237{
210 struct panel_drv_data *ddata; 238 struct panel_drv_data *ddata;
@@ -222,6 +250,10 @@ static int tvc_probe(struct platform_device *pdev)
222 r = tvc_probe_pdata(pdev); 250 r = tvc_probe_pdata(pdev);
223 if (r) 251 if (r)
224 return r; 252 return r;
253 } else if (pdev->dev.of_node) {
254 r = tvc_probe_of(pdev);
255 if (r)
256 return r;
225 } else { 257 } else {
226 return -ENODEV; 258 return -ENODEV;
227 } 259 }
@@ -263,12 +295,19 @@ static int __exit tvc_remove(struct platform_device *pdev)
263 return 0; 295 return 0;
264} 296}
265 297
298static const struct of_device_id tvc_of_match[] = {
299 { .compatible = "omapdss,svideo-connector", },
300 { .compatible = "omapdss,composite-video-connector", },
301 {},
302};
303
266static struct platform_driver tvc_connector_driver = { 304static struct platform_driver tvc_connector_driver = {
267 .probe = tvc_probe, 305 .probe = tvc_probe,
268 .remove = __exit_p(tvc_remove), 306 .remove = __exit_p(tvc_remove),
269 .driver = { 307 .driver = {
270 .name = "connector-analog-tv", 308 .name = "connector-analog-tv",
271 .owner = THIS_MODULE, 309 .owner = THIS_MODULE,
310 .of_match_table = tvc_of_match,
272 }, 311 },
273}; 312};
274 313
diff --git a/drivers/video/omap2/displays-new/connector-dvi.c b/drivers/video/omap2/displays-new/connector-dvi.c
index d18e4b8c0731..74de2bc50c4f 100644
--- a/drivers/video/omap2/displays-new/connector-dvi.c
+++ b/drivers/video/omap2/displays-new/connector-dvi.c
@@ -277,6 +277,37 @@ static int dvic_probe_pdata(struct platform_device *pdev)
277 return 0; 277 return 0;
278} 278}
279 279
280static int dvic_probe_of(struct platform_device *pdev)
281{
282 struct panel_drv_data *ddata = platform_get_drvdata(pdev);
283 struct device_node *node = pdev->dev.of_node;
284 struct omap_dss_device *in;
285 struct device_node *adapter_node;
286 struct i2c_adapter *adapter;
287
288 in = omapdss_of_find_source_for_first_ep(node);
289 if (IS_ERR(in)) {
290 dev_err(&pdev->dev, "failed to find video source\n");
291 return PTR_ERR(in);
292 }
293
294 ddata->in = in;
295
296 adapter_node = of_parse_phandle(node, "ddc-i2c-bus", 0);
297 if (adapter_node) {
298 adapter = of_find_i2c_adapter_by_node(adapter_node);
299 if (adapter == NULL) {
300 dev_err(&pdev->dev, "failed to parse ddc-i2c-bus\n");
301 omap_dss_put_device(ddata->in);
302 return -EPROBE_DEFER;
303 }
304
305 ddata->i2c_adapter = adapter;
306 }
307
308 return 0;
309}
310
280static int dvic_probe(struct platform_device *pdev) 311static int dvic_probe(struct platform_device *pdev)
281{ 312{
282 struct panel_drv_data *ddata; 313 struct panel_drv_data *ddata;
@@ -293,6 +324,10 @@ static int dvic_probe(struct platform_device *pdev)
293 r = dvic_probe_pdata(pdev); 324 r = dvic_probe_pdata(pdev);
294 if (r) 325 if (r)
295 return r; 326 return r;
327 } else if (pdev->dev.of_node) {
328 r = dvic_probe_of(pdev);
329 if (r)
330 return r;
296 } else { 331 } else {
297 return -ENODEV; 332 return -ENODEV;
298 } 333 }
@@ -342,12 +377,20 @@ static int __exit dvic_remove(struct platform_device *pdev)
342 return 0; 377 return 0;
343} 378}
344 379
380static const struct of_device_id dvic_of_match[] = {
381 { .compatible = "omapdss,dvi-connector", },
382 {},
383};
384
385MODULE_DEVICE_TABLE(of, dvic_of_match);
386
345static struct platform_driver dvi_connector_driver = { 387static struct platform_driver dvi_connector_driver = {
346 .probe = dvic_probe, 388 .probe = dvic_probe,
347 .remove = __exit_p(dvic_remove), 389 .remove = __exit_p(dvic_remove),
348 .driver = { 390 .driver = {
349 .name = "connector-dvi", 391 .name = "connector-dvi",
350 .owner = THIS_MODULE, 392 .owner = THIS_MODULE,
393 .of_match_table = dvic_of_match,
351 }, 394 },
352}; 395};
353 396
diff --git a/drivers/video/omap2/displays-new/connector-hdmi.c b/drivers/video/omap2/displays-new/connector-hdmi.c
index 9393e2d6473d..29ed21b9dce5 100644
--- a/drivers/video/omap2/displays-new/connector-hdmi.c
+++ b/drivers/video/omap2/displays-new/connector-hdmi.c
@@ -12,6 +12,7 @@
12#include <linux/slab.h> 12#include <linux/slab.h>
13#include <linux/module.h> 13#include <linux/module.h>
14#include <linux/platform_device.h> 14#include <linux/platform_device.h>
15#include <linux/of.h>
15 16
16#include <drm/drm_edid.h> 17#include <drm/drm_edid.h>
17 18
@@ -301,6 +302,23 @@ static int hdmic_probe_pdata(struct platform_device *pdev)
301 return 0; 302 return 0;
302} 303}
303 304
305static int hdmic_probe_of(struct platform_device *pdev)
306{
307 struct panel_drv_data *ddata = platform_get_drvdata(pdev);
308 struct device_node *node = pdev->dev.of_node;
309 struct omap_dss_device *in;
310
311 in = omapdss_of_find_source_for_first_ep(node);
312 if (IS_ERR(in)) {
313 dev_err(&pdev->dev, "failed to find video source\n");
314 return PTR_ERR(in);
315 }
316
317 ddata->in = in;
318
319 return 0;
320}
321
304static int hdmic_probe(struct platform_device *pdev) 322static int hdmic_probe(struct platform_device *pdev)
305{ 323{
306 struct panel_drv_data *ddata; 324 struct panel_drv_data *ddata;
@@ -318,6 +336,10 @@ static int hdmic_probe(struct platform_device *pdev)
318 r = hdmic_probe_pdata(pdev); 336 r = hdmic_probe_pdata(pdev);
319 if (r) 337 if (r)
320 return r; 338 return r;
339 } else if (pdev->dev.of_node) {
340 r = hdmic_probe_of(pdev);
341 if (r)
342 return r;
321 } else { 343 } else {
322 return -ENODEV; 344 return -ENODEV;
323 } 345 }
@@ -359,12 +381,20 @@ static int __exit hdmic_remove(struct platform_device *pdev)
359 return 0; 381 return 0;
360} 382}
361 383
384static const struct of_device_id hdmic_of_match[] = {
385 { .compatible = "omapdss,hdmi-connector", },
386 {},
387};
388
389MODULE_DEVICE_TABLE(of, hdmic_of_match);
390
362static struct platform_driver hdmi_connector_driver = { 391static struct platform_driver hdmi_connector_driver = {
363 .probe = hdmic_probe, 392 .probe = hdmic_probe,
364 .remove = __exit_p(hdmic_remove), 393 .remove = __exit_p(hdmic_remove),
365 .driver = { 394 .driver = {
366 .name = "connector-hdmi", 395 .name = "connector-hdmi",
367 .owner = THIS_MODULE, 396 .owner = THIS_MODULE,
397 .of_match_table = hdmic_of_match,
368 }, 398 },
369}; 399};
370 400
diff --git a/drivers/video/omap2/displays-new/encoder-tfp410.c b/drivers/video/omap2/displays-new/encoder-tfp410.c
index 4a291e756be9..b4e9a42a79e6 100644
--- a/drivers/video/omap2/displays-new/encoder-tfp410.c
+++ b/drivers/video/omap2/displays-new/encoder-tfp410.c
@@ -13,6 +13,7 @@
13#include <linux/module.h> 13#include <linux/module.h>
14#include <linux/platform_device.h> 14#include <linux/platform_device.h>
15#include <linux/slab.h> 15#include <linux/slab.h>
16#include <linux/of_gpio.h>
16 17
17#include <video/omapdss.h> 18#include <video/omapdss.h>
18#include <video/omap-panel-data.h> 19#include <video/omap-panel-data.h>
@@ -82,7 +83,8 @@ static int tfp410_enable(struct omap_dss_device *dssdev)
82 return 0; 83 return 0;
83 84
84 in->ops.dpi->set_timings(in, &ddata->timings); 85 in->ops.dpi->set_timings(in, &ddata->timings);
85 in->ops.dpi->set_data_lines(in, ddata->data_lines); 86 if (ddata->data_lines)
87 in->ops.dpi->set_data_lines(in, ddata->data_lines);
86 88
87 r = in->ops.dpi->enable(in); 89 r = in->ops.dpi->enable(in);
88 if (r) 90 if (r)
@@ -179,6 +181,33 @@ static int tfp410_probe_pdata(struct platform_device *pdev)
179 return 0; 181 return 0;
180} 182}
181 183
184static int tfp410_probe_of(struct platform_device *pdev)
185{
186 struct panel_drv_data *ddata = platform_get_drvdata(pdev);
187 struct device_node *node = pdev->dev.of_node;
188 struct omap_dss_device *in;
189 int gpio;
190
191 gpio = of_get_named_gpio(node, "powerdown-gpios", 0);
192
193 if (gpio_is_valid(gpio) || gpio == -ENOENT) {
194 ddata->pd_gpio = gpio;
195 } else {
196 dev_err(&pdev->dev, "failed to parse PD gpio\n");
197 return gpio;
198 }
199
200 in = omapdss_of_find_source_for_first_ep(node);
201 if (IS_ERR(in)) {
202 dev_err(&pdev->dev, "failed to find video source\n");
203 return PTR_ERR(in);
204 }
205
206 ddata->in = in;
207
208 return 0;
209}
210
182static int tfp410_probe(struct platform_device *pdev) 211static int tfp410_probe(struct platform_device *pdev)
183{ 212{
184 struct panel_drv_data *ddata; 213 struct panel_drv_data *ddata;
@@ -195,6 +224,10 @@ static int tfp410_probe(struct platform_device *pdev)
195 r = tfp410_probe_pdata(pdev); 224 r = tfp410_probe_pdata(pdev);
196 if (r) 225 if (r)
197 return r; 226 return r;
227 } else if (pdev->dev.of_node) {
228 r = tfp410_probe_of(pdev);
229 if (r)
230 return r;
198 } else { 231 } else {
199 return -ENODEV; 232 return -ENODEV;
200 } 233 }
@@ -251,12 +284,20 @@ static int __exit tfp410_remove(struct platform_device *pdev)
251 return 0; 284 return 0;
252} 285}
253 286
287static const struct of_device_id tfp410_of_match[] = {
288 { .compatible = "omapdss,ti,tfp410", },
289 {},
290};
291
292MODULE_DEVICE_TABLE(of, tfp410_of_match);
293
254static struct platform_driver tfp410_driver = { 294static struct platform_driver tfp410_driver = {
255 .probe = tfp410_probe, 295 .probe = tfp410_probe,
256 .remove = __exit_p(tfp410_remove), 296 .remove = __exit_p(tfp410_remove),
257 .driver = { 297 .driver = {
258 .name = "tfp410", 298 .name = "tfp410",
259 .owner = THIS_MODULE, 299 .owner = THIS_MODULE,
300 .of_match_table = tfp410_of_match,
260 }, 301 },
261}; 302};
262 303
diff --git a/drivers/video/omap2/displays-new/encoder-tpd12s015.c b/drivers/video/omap2/displays-new/encoder-tpd12s015.c
index d5c936cb217f..7e33686171e3 100644
--- a/drivers/video/omap2/displays-new/encoder-tpd12s015.c
+++ b/drivers/video/omap2/displays-new/encoder-tpd12s015.c
@@ -15,6 +15,7 @@
15#include <linux/slab.h> 15#include <linux/slab.h>
16#include <linux/gpio.h> 16#include <linux/gpio.h>
17#include <linux/platform_device.h> 17#include <linux/platform_device.h>
18#include <linux/of_gpio.h>
18 19
19#include <video/omapdss.h> 20#include <video/omapdss.h>
20#include <video/omap-panel-data.h> 21#include <video/omap-panel-data.h>
@@ -289,6 +290,49 @@ static int tpd_probe_pdata(struct platform_device *pdev)
289 return 0; 290 return 0;
290} 291}
291 292
293static int tpd_probe_of(struct platform_device *pdev)
294{
295 struct panel_drv_data *ddata = platform_get_drvdata(pdev);
296 struct device_node *node = pdev->dev.of_node;
297 struct omap_dss_device *in;
298 int gpio;
299
300 /* CT CP HPD GPIO */
301 gpio = of_get_gpio(node, 0);
302 if (!gpio_is_valid(gpio)) {
303 dev_err(&pdev->dev, "failed to parse CT CP HPD gpio\n");
304 return gpio;
305 }
306 ddata->ct_cp_hpd_gpio = gpio;
307
308 /* LS OE GPIO */
309 gpio = of_get_gpio(node, 1);
310 if (gpio_is_valid(gpio) || gpio == -ENOENT) {
311 ddata->ls_oe_gpio = gpio;
312 } else {
313 dev_err(&pdev->dev, "failed to parse LS OE gpio\n");
314 return gpio;
315 }
316
317 /* HPD GPIO */
318 gpio = of_get_gpio(node, 2);
319 if (!gpio_is_valid(gpio)) {
320 dev_err(&pdev->dev, "failed to parse HPD gpio\n");
321 return gpio;
322 }
323 ddata->hpd_gpio = gpio;
324
325 in = omapdss_of_find_source_for_first_ep(node);
326 if (IS_ERR(in)) {
327 dev_err(&pdev->dev, "failed to find video source\n");
328 return PTR_ERR(in);
329 }
330
331 ddata->in = in;
332
333 return 0;
334}
335
292static int tpd_probe(struct platform_device *pdev) 336static int tpd_probe(struct platform_device *pdev)
293{ 337{
294 struct omap_dss_device *in, *dssdev; 338 struct omap_dss_device *in, *dssdev;
@@ -307,6 +351,10 @@ static int tpd_probe(struct platform_device *pdev)
307 r = tpd_probe_pdata(pdev); 351 r = tpd_probe_pdata(pdev);
308 if (r) 352 if (r)
309 return r; 353 return r;
354 } else if (pdev->dev.of_node) {
355 r = tpd_probe_of(pdev);
356 if (r)
357 return r;
310 } else { 358 } else {
311 return -ENODEV; 359 return -ENODEV;
312 } 360 }
@@ -379,12 +427,20 @@ static int __exit tpd_remove(struct platform_device *pdev)
379 return 0; 427 return 0;
380} 428}
381 429
430static const struct of_device_id tpd_of_match[] = {
431 { .compatible = "omapdss,ti,tpd12s015", },
432 {},
433};
434
435MODULE_DEVICE_TABLE(of, tpd_of_match);
436
382static struct platform_driver tpd_driver = { 437static struct platform_driver tpd_driver = {
383 .probe = tpd_probe, 438 .probe = tpd_probe,
384 .remove = __exit_p(tpd_remove), 439 .remove = __exit_p(tpd_remove),
385 .driver = { 440 .driver = {
386 .name = "tpd12s015", 441 .name = "tpd12s015",
387 .owner = THIS_MODULE, 442 .owner = THIS_MODULE,
443 .of_match_table = tpd_of_match,
388 }, 444 },
389}; 445};
390 446
diff --git a/drivers/video/omap2/displays-new/panel-dsi-cm.c b/drivers/video/omap2/displays-new/panel-dsi-cm.c
index f317c878a259..d6f14e8717e8 100644
--- a/drivers/video/omap2/displays-new/panel-dsi-cm.c
+++ b/drivers/video/omap2/displays-new/panel-dsi-cm.c
@@ -22,6 +22,8 @@
22#include <linux/sched.h> 22#include <linux/sched.h>
23#include <linux/slab.h> 23#include <linux/slab.h>
24#include <linux/workqueue.h> 24#include <linux/workqueue.h>
25#include <linux/of_device.h>
26#include <linux/of_gpio.h>
25 27
26#include <video/omapdss.h> 28#include <video/omapdss.h>
27#include <video/omap-panel-data.h> 29#include <video/omap-panel-data.h>
@@ -595,10 +597,13 @@ static int dsicm_power_on(struct panel_drv_data *ddata)
595 .lp_clk_max = 10000000, 597 .lp_clk_max = 10000000,
596 }; 598 };
597 599
598 r = in->ops.dsi->configure_pins(in, &ddata->pin_config); 600 if (ddata->pin_config.num_pins > 0) {
599 if (r) { 601 r = in->ops.dsi->configure_pins(in, &ddata->pin_config);
600 dev_err(&ddata->pdev->dev, "failed to configure DSI pins\n"); 602 if (r) {
601 goto err0; 603 dev_err(&ddata->pdev->dev,
604 "failed to configure DSI pins\n");
605 goto err0;
606 }
602 } 607 }
603 608
604 r = in->ops.dsi->set_config(in, &dsi_config); 609 r = in->ops.dsi->set_config(in, &dsi_config);
@@ -1156,6 +1161,41 @@ static int dsicm_probe_pdata(struct platform_device *pdev)
1156 return 0; 1161 return 0;
1157} 1162}
1158 1163
1164static int dsicm_probe_of(struct platform_device *pdev)
1165{
1166 struct device_node *node = pdev->dev.of_node;
1167 struct panel_drv_data *ddata = platform_get_drvdata(pdev);
1168 struct omap_dss_device *in;
1169 int gpio;
1170
1171 gpio = of_get_named_gpio(node, "reset-gpios", 0);
1172 if (!gpio_is_valid(gpio)) {
1173 dev_err(&pdev->dev, "failed to parse reset gpio\n");
1174 return gpio;
1175 }
1176 ddata->reset_gpio = gpio;
1177
1178 gpio = of_get_named_gpio(node, "te-gpios", 0);
1179 if (gpio_is_valid(gpio) || gpio == -ENOENT) {
1180 ddata->ext_te_gpio = gpio;
1181 } else {
1182 dev_err(&pdev->dev, "failed to parse TE gpio\n");
1183 return gpio;
1184 }
1185
1186 in = omapdss_of_find_source_for_first_ep(node);
1187 if (IS_ERR(in)) {
1188 dev_err(&pdev->dev, "failed to find video source\n");
1189 return PTR_ERR(in);
1190 }
1191
1192 ddata->in = in;
1193
1194 /* TODO: ulps, backlight */
1195
1196 return 0;
1197}
1198
1159static int dsicm_probe(struct platform_device *pdev) 1199static int dsicm_probe(struct platform_device *pdev)
1160{ 1200{
1161 struct backlight_properties props; 1201 struct backlight_properties props;
@@ -1178,6 +1218,10 @@ static int dsicm_probe(struct platform_device *pdev)
1178 r = dsicm_probe_pdata(pdev); 1218 r = dsicm_probe_pdata(pdev);
1179 if (r) 1219 if (r)
1180 return r; 1220 return r;
1221 } else if (pdev->dev.of_node) {
1222 r = dsicm_probe_of(pdev);
1223 if (r)
1224 return r;
1181 } else { 1225 } else {
1182 return -ENODEV; 1226 return -ENODEV;
1183 } 1227 }
@@ -1320,12 +1364,20 @@ static int __exit dsicm_remove(struct platform_device *pdev)
1320 return 0; 1364 return 0;
1321} 1365}
1322 1366
1367static const struct of_device_id dsicm_of_match[] = {
1368 { .compatible = "omapdss,panel-dsi-cm", },
1369 {},
1370};
1371
1372MODULE_DEVICE_TABLE(of, dsicm_of_match);
1373
1323static struct platform_driver dsicm_driver = { 1374static struct platform_driver dsicm_driver = {
1324 .probe = dsicm_probe, 1375 .probe = dsicm_probe,
1325 .remove = __exit_p(dsicm_remove), 1376 .remove = __exit_p(dsicm_remove),
1326 .driver = { 1377 .driver = {
1327 .name = "panel-dsi-cm", 1378 .name = "panel-dsi-cm",
1328 .owner = THIS_MODULE, 1379 .owner = THIS_MODULE,
1380 .of_match_table = dsicm_of_match,
1329 }, 1381 },
1330}; 1382};
1331 1383
diff --git a/drivers/video/omap2/displays-new/panel-sony-acx565akm.c b/drivers/video/omap2/displays-new/panel-sony-acx565akm.c
index 27f60ad6b2ab..c7ba4d8b928a 100644
--- a/drivers/video/omap2/displays-new/panel-sony-acx565akm.c
+++ b/drivers/video/omap2/displays-new/panel-sony-acx565akm.c
@@ -30,6 +30,8 @@
30#include <linux/backlight.h> 30#include <linux/backlight.h>
31#include <linux/fb.h> 31#include <linux/fb.h>
32#include <linux/gpio.h> 32#include <linux/gpio.h>
33#include <linux/of.h>
34#include <linux/of_gpio.h>
33 35
34#include <video/omapdss.h> 36#include <video/omapdss.h>
35#include <video/omap-panel-data.h> 37#include <video/omap-panel-data.h>
@@ -547,7 +549,9 @@ static int acx565akm_panel_power_on(struct omap_dss_device *dssdev)
547 dev_dbg(&ddata->spi->dev, "%s\n", __func__); 549 dev_dbg(&ddata->spi->dev, "%s\n", __func__);
548 550
549 in->ops.sdi->set_timings(in, &ddata->videomode); 551 in->ops.sdi->set_timings(in, &ddata->videomode);
550 in->ops.sdi->set_datapairs(in, ddata->datapairs); 552
553 if (ddata->datapairs > 0)
554 in->ops.sdi->set_datapairs(in, ddata->datapairs);
551 555
552 r = in->ops.sdi->enable(in); 556 r = in->ops.sdi->enable(in);
553 if (r) { 557 if (r) {
@@ -726,6 +730,22 @@ static int acx565akm_probe_pdata(struct spi_device *spi)
726 return 0; 730 return 0;
727} 731}
728 732
733static int acx565akm_probe_of(struct spi_device *spi)
734{
735 struct panel_drv_data *ddata = dev_get_drvdata(&spi->dev);
736 struct device_node *np = spi->dev.of_node;
737
738 ddata->reset_gpio = of_get_named_gpio(np, "reset-gpios", 0);
739
740 ddata->in = omapdss_of_find_source_for_first_ep(np);
741 if (IS_ERR(ddata->in)) {
742 dev_err(&spi->dev, "failed to find video source\n");
743 return PTR_ERR(ddata->in);
744 }
745
746 return 0;
747}
748
729static int acx565akm_probe(struct spi_device *spi) 749static int acx565akm_probe(struct spi_device *spi)
730{ 750{
731 struct panel_drv_data *ddata; 751 struct panel_drv_data *ddata;
@@ -753,7 +773,12 @@ static int acx565akm_probe(struct spi_device *spi)
753 r = acx565akm_probe_pdata(spi); 773 r = acx565akm_probe_pdata(spi);
754 if (r) 774 if (r)
755 return r; 775 return r;
776 } else if (spi->dev.of_node) {
777 r = acx565akm_probe_of(spi);
778 if (r)
779 return r;
756 } else { 780 } else {
781 dev_err(&spi->dev, "platform data missing!\n");
757 return -ENODEV; 782 return -ENODEV;
758 } 783 }
759 784
@@ -864,10 +889,16 @@ static int acx565akm_remove(struct spi_device *spi)
864 return 0; 889 return 0;
865} 890}
866 891
892static const struct of_device_id acx565akm_of_match[] = {
893 { .compatible = "omapdss,sony,acx565akm", },
894 {},
895};
896
867static struct spi_driver acx565akm_driver = { 897static struct spi_driver acx565akm_driver = {
868 .driver = { 898 .driver = {
869 .name = "acx565akm", 899 .name = "acx565akm",
870 .owner = THIS_MODULE, 900 .owner = THIS_MODULE,
901 .of_match_table = acx565akm_of_match,
871 }, 902 },
872 .probe = acx565akm_probe, 903 .probe = acx565akm_probe,
873 .remove = acx565akm_remove, 904 .remove = acx565akm_remove,
diff --git a/drivers/video/omap2/dss/Makefile b/drivers/video/omap2/dss/Makefile
index d3aa91bdd6a8..8aec8bda27cc 100644
--- a/drivers/video/omap2/dss/Makefile
+++ b/drivers/video/omap2/dss/Makefile
@@ -1,7 +1,7 @@
1obj-$(CONFIG_OMAP2_DSS) += omapdss.o 1obj-$(CONFIG_OMAP2_DSS) += omapdss.o
2# Core DSS files 2# Core DSS files
3omapdss-y := core.o dss.o dss_features.o dispc.o dispc_coefs.o display.o \ 3omapdss-y := core.o dss.o dss_features.o dispc.o dispc_coefs.o display.o \
4 output.o 4 output.o dss-of.o
5# DSS compat layer files 5# DSS compat layer files
6omapdss-y += manager.o manager-sysfs.o overlay.o overlay-sysfs.o apply.o \ 6omapdss-y += manager.o manager-sysfs.o overlay.o overlay-sysfs.o apply.o \
7 dispc-compat.o display-sysfs.o 7 dispc-compat.o display-sysfs.o
diff --git a/drivers/video/omap2/dss/dispc.c b/drivers/video/omap2/dss/dispc.c
index b801be4660e9..2bbdb7ff7daf 100644
--- a/drivers/video/omap2/dss/dispc.c
+++ b/drivers/video/omap2/dss/dispc.c
@@ -2149,8 +2149,8 @@ static int dispc_ovl_calc_scaling_24xx(unsigned long pclk, unsigned long lclk,
2149 *five_taps = false; 2149 *five_taps = false;
2150 2150
2151 do { 2151 do {
2152 in_height = DIV_ROUND_UP(height, *decim_y); 2152 in_height = height / *decim_y;
2153 in_width = DIV_ROUND_UP(width, *decim_x); 2153 in_width = width / *decim_x;
2154 *core_clk = dispc.feat->calc_core_clk(pclk, in_width, 2154 *core_clk = dispc.feat->calc_core_clk(pclk, in_width,
2155 in_height, out_width, out_height, mem_to_mem); 2155 in_height, out_width, out_height, mem_to_mem);
2156 error = (in_width > maxsinglelinewidth || !*core_clk || 2156 error = (in_width > maxsinglelinewidth || !*core_clk ||
@@ -2188,8 +2188,8 @@ static int dispc_ovl_calc_scaling_34xx(unsigned long pclk, unsigned long lclk,
2188 dss_feat_get_param_max(FEAT_PARAM_LINEWIDTH); 2188 dss_feat_get_param_max(FEAT_PARAM_LINEWIDTH);
2189 2189
2190 do { 2190 do {
2191 in_height = DIV_ROUND_UP(height, *decim_y); 2191 in_height = height / *decim_y;
2192 in_width = DIV_ROUND_UP(width, *decim_x); 2192 in_width = width / *decim_x;
2193 *five_taps = in_height > out_height; 2193 *five_taps = in_height > out_height;
2194 2194
2195 if (in_width > maxsinglelinewidth) 2195 if (in_width > maxsinglelinewidth)
@@ -2257,7 +2257,7 @@ static int dispc_ovl_calc_scaling_44xx(unsigned long pclk, unsigned long lclk,
2257{ 2257{
2258 u16 in_width, in_width_max; 2258 u16 in_width, in_width_max;
2259 int decim_x_min = *decim_x; 2259 int decim_x_min = *decim_x;
2260 u16 in_height = DIV_ROUND_UP(height, *decim_y); 2260 u16 in_height = height / *decim_y;
2261 const int maxsinglelinewidth = 2261 const int maxsinglelinewidth =
2262 dss_feat_get_param_max(FEAT_PARAM_LINEWIDTH); 2262 dss_feat_get_param_max(FEAT_PARAM_LINEWIDTH);
2263 const int maxdownscale = dss_feat_get_param_max(FEAT_PARAM_DOWNSCALE); 2263 const int maxdownscale = dss_feat_get_param_max(FEAT_PARAM_DOWNSCALE);
@@ -2276,7 +2276,7 @@ static int dispc_ovl_calc_scaling_44xx(unsigned long pclk, unsigned long lclk,
2276 return -EINVAL; 2276 return -EINVAL;
2277 2277
2278 do { 2278 do {
2279 in_width = DIV_ROUND_UP(width, *decim_x); 2279 in_width = width / *decim_x;
2280 } while (*decim_x <= *x_predecim && 2280 } while (*decim_x <= *x_predecim &&
2281 in_width > maxsinglelinewidth && ++*decim_x); 2281 in_width > maxsinglelinewidth && ++*decim_x);
2282 2282
@@ -2455,8 +2455,8 @@ static int dispc_ovl_setup_common(enum omap_plane plane,
2455 if (r) 2455 if (r)
2456 return r; 2456 return r;
2457 2457
2458 in_width = DIV_ROUND_UP(in_width, x_predecim); 2458 in_width = in_width / x_predecim;
2459 in_height = DIV_ROUND_UP(in_height, y_predecim); 2459 in_height = in_height / y_predecim;
2460 2460
2461 if (color_mode == OMAP_DSS_COLOR_YUV2 || 2461 if (color_mode == OMAP_DSS_COLOR_YUV2 ||
2462 color_mode == OMAP_DSS_COLOR_UYVY || 2462 color_mode == OMAP_DSS_COLOR_UYVY ||
@@ -3778,12 +3778,20 @@ static const struct dev_pm_ops dispc_pm_ops = {
3778 .runtime_resume = dispc_runtime_resume, 3778 .runtime_resume = dispc_runtime_resume,
3779}; 3779};
3780 3780
3781static const struct of_device_id dispc_of_match[] = {
3782 { .compatible = "ti,omap2-dispc", },
3783 { .compatible = "ti,omap3-dispc", },
3784 { .compatible = "ti,omap4-dispc", },
3785 {},
3786};
3787
3781static struct platform_driver omap_dispchw_driver = { 3788static struct platform_driver omap_dispchw_driver = {
3782 .remove = __exit_p(omap_dispchw_remove), 3789 .remove = __exit_p(omap_dispchw_remove),
3783 .driver = { 3790 .driver = {
3784 .name = "omapdss_dispc", 3791 .name = "omapdss_dispc",
3785 .owner = THIS_MODULE, 3792 .owner = THIS_MODULE,
3786 .pm = &dispc_pm_ops, 3793 .pm = &dispc_pm_ops,
3794 .of_match_table = dispc_of_match,
3787 }, 3795 },
3788}; 3796};
3789 3797
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index 9f19ae22944c..2412a0dd0c13 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -26,6 +26,7 @@
26#include <linux/module.h> 26#include <linux/module.h>
27#include <linux/jiffies.h> 27#include <linux/jiffies.h>
28#include <linux/platform_device.h> 28#include <linux/platform_device.h>
29#include <linux/of.h>
29 30
30#include <video/omapdss.h> 31#include <video/omapdss.h>
31#include "dss.h" 32#include "dss.h"
@@ -133,9 +134,32 @@ static int disp_num_counter;
133int omapdss_register_display(struct omap_dss_device *dssdev) 134int omapdss_register_display(struct omap_dss_device *dssdev)
134{ 135{
135 struct omap_dss_driver *drv = dssdev->driver; 136 struct omap_dss_driver *drv = dssdev->driver;
137 int id;
136 138
137 snprintf(dssdev->alias, sizeof(dssdev->alias), 139 /*
138 "display%d", disp_num_counter++); 140 * Note: this presumes all the displays are either using DT or non-DT,
141 * which normally should be the case. This also presumes that all
142 * displays either have an DT alias, or none has.
143 */
144
145 if (dssdev->dev->of_node) {
146 id = of_alias_get_id(dssdev->dev->of_node, "display");
147
148 if (id < 0)
149 id = disp_num_counter++;
150 } else {
151 id = disp_num_counter++;
152 }
153
154 snprintf(dssdev->alias, sizeof(dssdev->alias), "display%d", id);
155
156 /* Use 'label' property for name, if it exists */
157 if (dssdev->dev->of_node)
158 of_property_read_string(dssdev->dev->of_node, "label",
159 &dssdev->name);
160
161 if (dssdev->name == NULL)
162 dssdev->name = dssdev->alias;
139 163
140 if (drv && drv->get_resolution == NULL) 164 if (drv && drv->get_resolution == NULL)
141 drv->get_resolution = omapdss_default_get_resolution; 165 drv->get_resolution = omapdss_default_get_resolution;
diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c
index d806fd50aa94..157921db447a 100644
--- a/drivers/video/omap2/dss/dpi.c
+++ b/drivers/video/omap2/dss/dpi.c
@@ -30,6 +30,7 @@
30#include <linux/platform_device.h> 30#include <linux/platform_device.h>
31#include <linux/regulator/consumer.h> 31#include <linux/regulator/consumer.h>
32#include <linux/string.h> 32#include <linux/string.h>
33#include <linux/of.h>
33 34
34#include <video/omapdss.h> 35#include <video/omapdss.h>
35 36
@@ -49,6 +50,8 @@ static struct {
49 int data_lines; 50 int data_lines;
50 51
51 struct omap_dss_device output; 52 struct omap_dss_device output;
53
54 bool port_initialized;
52} dpi; 55} dpi;
53 56
54static struct platform_device *dpi_get_dsidev(enum omap_channel channel) 57static struct platform_device *dpi_get_dsidev(enum omap_channel channel)
@@ -117,7 +120,7 @@ struct dpi_clk_calc_ctx {
117 /* outputs */ 120 /* outputs */
118 121
119 struct dsi_clock_info dsi_cinfo; 122 struct dsi_clock_info dsi_cinfo;
120 unsigned long long fck; 123 unsigned long fck;
121 struct dispc_clock_info dispc_cinfo; 124 struct dispc_clock_info dispc_cinfo;
122}; 125};
123 126
@@ -725,3 +728,47 @@ void __exit dpi_uninit_platform_driver(void)
725{ 728{
726 platform_driver_unregister(&omap_dpi_driver); 729 platform_driver_unregister(&omap_dpi_driver);
727} 730}
731
732int __init dpi_init_port(struct platform_device *pdev, struct device_node *port)
733{
734 struct device_node *ep;
735 u32 datalines;
736 int r;
737
738 ep = omapdss_of_get_next_endpoint(port, NULL);
739 if (!ep)
740 return 0;
741
742 r = of_property_read_u32(ep, "data-lines", &datalines);
743 if (r) {
744 DSSERR("failed to parse datalines\n");
745 goto err_datalines;
746 }
747
748 dpi.data_lines = datalines;
749
750 of_node_put(ep);
751
752 dpi.pdev = pdev;
753
754 mutex_init(&dpi.lock);
755
756 dpi_init_output(pdev);
757
758 dpi.port_initialized = true;
759
760 return 0;
761
762err_datalines:
763 of_node_put(ep);
764
765 return r;
766}
767
768void __exit dpi_uninit_port(void)
769{
770 if (!dpi.port_initialized)
771 return;
772
773 dpi_uninit_output(dpi.pdev);
774}
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index 0d82f731d2f0..f3e4e468b49a 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -38,6 +38,8 @@
38#include <linux/slab.h> 38#include <linux/slab.h>
39#include <linux/debugfs.h> 39#include <linux/debugfs.h>
40#include <linux/pm_runtime.h> 40#include <linux/pm_runtime.h>
41#include <linux/of.h>
42#include <linux/of_platform.h>
41 43
42#include <video/omapdss.h> 44#include <video/omapdss.h>
43#include <video/mipi_display.h> 45#include <video/mipi_display.h>
@@ -386,6 +388,13 @@ struct dsi_packet_sent_handler_data {
386 struct completion *completion; 388 struct completion *completion;
387}; 389};
388 390
391struct dsi_module_id_data {
392 u32 address;
393 int id;
394};
395
396static const struct of_device_id dsi_of_match[];
397
389#ifdef DSI_PERF_MEASURE 398#ifdef DSI_PERF_MEASURE
390static bool dsi_perf; 399static bool dsi_perf;
391module_param(dsi_perf, bool, 0644); 400module_param(dsi_perf, bool, 0644);
@@ -1151,7 +1160,10 @@ static int dsi_regulator_init(struct platform_device *dsidev)
1151 if (dsi->vdds_dsi_reg != NULL) 1160 if (dsi->vdds_dsi_reg != NULL)
1152 return 0; 1161 return 0;
1153 1162
1154 vdds_dsi = devm_regulator_get(&dsi->pdev->dev, "vdds_dsi"); 1163 if (dsi->pdev->dev.of_node)
1164 vdds_dsi = devm_regulator_get(&dsi->pdev->dev, "vdd");
1165 else
1166 vdds_dsi = devm_regulator_get(&dsi->pdev->dev, "vdds_dsi");
1155 1167
1156 /* DT HACK: try VCXIO to make omapdss work for o4 sdp/panda */ 1168 /* DT HACK: try VCXIO to make omapdss work for o4 sdp/panda */
1157 if (IS_ERR(vdds_dsi)) 1169 if (IS_ERR(vdds_dsi))
@@ -5370,12 +5382,69 @@ static void dsi_uninit_output(struct platform_device *dsidev)
5370 omapdss_unregister_output(out); 5382 omapdss_unregister_output(out);
5371} 5383}
5372 5384
5385static int dsi_probe_of(struct platform_device *pdev)
5386{
5387 struct device_node *node = pdev->dev.of_node;
5388 struct dsi_data *dsi = dsi_get_dsidrv_data(pdev);
5389 struct property *prop;
5390 u32 lane_arr[10];
5391 int len, num_pins;
5392 int r, i;
5393 struct device_node *ep;
5394 struct omap_dsi_pin_config pin_cfg;
5395
5396 ep = omapdss_of_get_first_endpoint(node);
5397 if (!ep)
5398 return 0;
5399
5400 prop = of_find_property(ep, "lanes", &len);
5401 if (prop == NULL) {
5402 dev_err(&pdev->dev, "failed to find lane data\n");
5403 r = -EINVAL;
5404 goto err;
5405 }
5406
5407 num_pins = len / sizeof(u32);
5408
5409 if (num_pins < 4 || num_pins % 2 != 0 ||
5410 num_pins > dsi->num_lanes_supported * 2) {
5411 dev_err(&pdev->dev, "bad number of lanes\n");
5412 r = -EINVAL;
5413 goto err;
5414 }
5415
5416 r = of_property_read_u32_array(ep, "lanes", lane_arr, num_pins);
5417 if (r) {
5418 dev_err(&pdev->dev, "failed to read lane data\n");
5419 goto err;
5420 }
5421
5422 pin_cfg.num_pins = num_pins;
5423 for (i = 0; i < num_pins; ++i)
5424 pin_cfg.pins[i] = (int)lane_arr[i];
5425
5426 r = dsi_configure_pins(&dsi->output, &pin_cfg);
5427 if (r) {
5428 dev_err(&pdev->dev, "failed to configure pins");
5429 goto err;
5430 }
5431
5432 of_node_put(ep);
5433
5434 return 0;
5435
5436err:
5437 of_node_put(ep);
5438 return r;
5439}
5440
5373/* DSI1 HW IP initialisation */ 5441/* DSI1 HW IP initialisation */
5374static int omap_dsihw_probe(struct platform_device *dsidev) 5442static int omap_dsihw_probe(struct platform_device *dsidev)
5375{ 5443{
5376 u32 rev; 5444 u32 rev;
5377 int r, i; 5445 int r, i;
5378 struct dsi_data *dsi; 5446 struct dsi_data *dsi;
5447 struct resource *dsi_mem;
5379 struct resource *res; 5448 struct resource *res;
5380 struct resource temp_res; 5449 struct resource temp_res;
5381 5450
@@ -5383,7 +5452,6 @@ static int omap_dsihw_probe(struct platform_device *dsidev)
5383 if (!dsi) 5452 if (!dsi)
5384 return -ENOMEM; 5453 return -ENOMEM;
5385 5454
5386 dsi->module_id = dsidev->id;
5387 dsi->pdev = dsidev; 5455 dsi->pdev = dsidev;
5388 dev_set_drvdata(&dsidev->dev, dsi); 5456 dev_set_drvdata(&dsidev->dev, dsi);
5389 5457
@@ -5421,6 +5489,8 @@ static int omap_dsihw_probe(struct platform_device *dsidev)
5421 res = &temp_res; 5489 res = &temp_res;
5422 } 5490 }
5423 5491
5492 dsi_mem = res;
5493
5424 dsi->proto_base = devm_ioremap(&dsidev->dev, res->start, 5494 dsi->proto_base = devm_ioremap(&dsidev->dev, res->start,
5425 resource_size(res)); 5495 resource_size(res));
5426 if (!dsi->proto_base) { 5496 if (!dsi->proto_base) {
@@ -5481,6 +5551,31 @@ static int omap_dsihw_probe(struct platform_device *dsidev)
5481 return r; 5551 return r;
5482 } 5552 }
5483 5553
5554 if (dsidev->dev.of_node) {
5555 const struct of_device_id *match;
5556 const struct dsi_module_id_data *d;
5557
5558 match = of_match_node(dsi_of_match, dsidev->dev.of_node);
5559 if (!match) {
5560 DSSERR("unsupported DSI module\n");
5561 return -ENODEV;
5562 }
5563
5564 d = match->data;
5565
5566 while (d->address != 0 && d->address != dsi_mem->start)
5567 d++;
5568
5569 if (d->address == 0) {
5570 DSSERR("unsupported DSI module\n");
5571 return -ENODEV;
5572 }
5573
5574 dsi->module_id = d->id;
5575 } else {
5576 dsi->module_id = dsidev->id;
5577 }
5578
5484 /* DSI VCs initialization */ 5579 /* DSI VCs initialization */
5485 for (i = 0; i < ARRAY_SIZE(dsi->vc); i++) { 5580 for (i = 0; i < ARRAY_SIZE(dsi->vc); i++) {
5486 dsi->vc[i].source = DSI_VC_SOURCE_L4; 5581 dsi->vc[i].source = DSI_VC_SOURCE_L4;
@@ -5516,6 +5611,19 @@ static int omap_dsihw_probe(struct platform_device *dsidev)
5516 5611
5517 dsi_init_output(dsidev); 5612 dsi_init_output(dsidev);
5518 5613
5614 if (dsidev->dev.of_node) {
5615 r = dsi_probe_of(dsidev);
5616 if (r) {
5617 DSSERR("Invalid DSI DT data\n");
5618 goto err_probe_of;
5619 }
5620
5621 r = of_platform_populate(dsidev->dev.of_node, NULL, NULL,
5622 &dsidev->dev);
5623 if (r)
5624 DSSERR("Failed to populate DSI child devices: %d\n", r);
5625 }
5626
5519 dsi_runtime_put(dsidev); 5627 dsi_runtime_put(dsidev);
5520 5628
5521 if (dsi->module_id == 0) 5629 if (dsi->module_id == 0)
@@ -5529,17 +5637,31 @@ static int omap_dsihw_probe(struct platform_device *dsidev)
5529 else if (dsi->module_id == 1) 5637 else if (dsi->module_id == 1)
5530 dss_debugfs_create_file("dsi2_irqs", dsi2_dump_irqs); 5638 dss_debugfs_create_file("dsi2_irqs", dsi2_dump_irqs);
5531#endif 5639#endif
5640
5532 return 0; 5641 return 0;
5533 5642
5643err_probe_of:
5644 dsi_uninit_output(dsidev);
5645 dsi_runtime_put(dsidev);
5646
5534err_runtime_get: 5647err_runtime_get:
5535 pm_runtime_disable(&dsidev->dev); 5648 pm_runtime_disable(&dsidev->dev);
5536 return r; 5649 return r;
5537} 5650}
5538 5651
5652static int dsi_unregister_child(struct device *dev, void *data)
5653{
5654 struct platform_device *pdev = to_platform_device(dev);
5655 platform_device_unregister(pdev);
5656 return 0;
5657}
5658
5539static int __exit omap_dsihw_remove(struct platform_device *dsidev) 5659static int __exit omap_dsihw_remove(struct platform_device *dsidev)
5540{ 5660{
5541 struct dsi_data *dsi = dsi_get_dsidrv_data(dsidev); 5661 struct dsi_data *dsi = dsi_get_dsidrv_data(dsidev);
5542 5662
5663 device_for_each_child(&dsidev->dev, NULL, dsi_unregister_child);
5664
5543 WARN_ON(dsi->scp_clk_refcount > 0); 5665 WARN_ON(dsi->scp_clk_refcount > 0);
5544 5666
5545 dsi_uninit_output(dsidev); 5667 dsi_uninit_output(dsidev);
@@ -5577,6 +5699,23 @@ static const struct dev_pm_ops dsi_pm_ops = {
5577 .runtime_resume = dsi_runtime_resume, 5699 .runtime_resume = dsi_runtime_resume,
5578}; 5700};
5579 5701
5702static const struct dsi_module_id_data dsi_of_data_omap3[] = {
5703 { .address = 0x4804fc00, .id = 0, },
5704 { },
5705};
5706
5707static const struct dsi_module_id_data dsi_of_data_omap4[] = {
5708 { .address = 0x58004000, .id = 0, },
5709 { .address = 0x58005000, .id = 1, },
5710 { },
5711};
5712
5713static const struct of_device_id dsi_of_match[] = {
5714 { .compatible = "ti,omap3-dsi", .data = dsi_of_data_omap3, },
5715 { .compatible = "ti,omap4-dsi", .data = dsi_of_data_omap4, },
5716 {},
5717};
5718
5580static struct platform_driver omap_dsihw_driver = { 5719static struct platform_driver omap_dsihw_driver = {
5581 .probe = omap_dsihw_probe, 5720 .probe = omap_dsihw_probe,
5582 .remove = __exit_p(omap_dsihw_remove), 5721 .remove = __exit_p(omap_dsihw_remove),
@@ -5584,6 +5723,7 @@ static struct platform_driver omap_dsihw_driver = {
5584 .name = "omapdss_dsi", 5723 .name = "omapdss_dsi",
5585 .owner = THIS_MODULE, 5724 .owner = THIS_MODULE,
5586 .pm = &dsi_pm_ops, 5725 .pm = &dsi_pm_ops,
5726 .of_match_table = dsi_of_match,
5587 }, 5727 },
5588}; 5728};
5589 5729
diff --git a/drivers/video/omap2/dss/dss-of.c b/drivers/video/omap2/dss/dss-of.c
new file mode 100644
index 000000000000..a4b20aaf6142
--- /dev/null
+++ b/drivers/video/omap2/dss/dss-of.c
@@ -0,0 +1,159 @@
1/*
2 * Copyright (C) 2013 Texas Instruments
3 * Author: Tomi Valkeinen <tomi.valkeinen@ti.com>
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 as published by
7 * the Free Software Foundation.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 */
14
15#include <linux/device.h>
16#include <linux/err.h>
17#include <linux/module.h>
18#include <linux/of.h>
19#include <linux/seq_file.h>
20
21#include <video/omapdss.h>
22
23struct device_node *
24omapdss_of_get_next_port(const struct device_node *parent,
25 struct device_node *prev)
26{
27 struct device_node *port = NULL;
28
29 if (!parent)
30 return NULL;
31
32 if (!prev) {
33 struct device_node *ports;
34 /*
35 * It's the first call, we have to find a port subnode
36 * within this node or within an optional 'ports' node.
37 */
38 ports = of_get_child_by_name(parent, "ports");
39 if (ports)
40 parent = ports;
41
42 port = of_get_child_by_name(parent, "port");
43
44 /* release the 'ports' node */
45 of_node_put(ports);
46 } else {
47 struct device_node *ports;
48
49 ports = of_get_parent(prev);
50 if (!ports)
51 return NULL;
52
53 do {
54 port = of_get_next_child(ports, prev);
55 if (!port) {
56 of_node_put(ports);
57 return NULL;
58 }
59 prev = port;
60 } while (of_node_cmp(port->name, "port") != 0);
61 }
62
63 return port;
64}
65EXPORT_SYMBOL_GPL(omapdss_of_get_next_port);
66
67struct device_node *
68omapdss_of_get_next_endpoint(const struct device_node *parent,
69 struct device_node *prev)
70{
71 struct device_node *ep = NULL;
72
73 if (!parent)
74 return NULL;
75
76 do {
77 ep = of_get_next_child(parent, prev);
78 if (!ep)
79 return NULL;
80 prev = ep;
81 } while (of_node_cmp(ep->name, "endpoint") != 0);
82
83 return ep;
84}
85EXPORT_SYMBOL_GPL(omapdss_of_get_next_endpoint);
86
87static struct device_node *
88omapdss_of_get_remote_device_node(const struct device_node *node)
89{
90 struct device_node *np;
91 int i;
92
93 np = of_parse_phandle(node, "remote-endpoint", 0);
94
95 if (!np)
96 return NULL;
97
98 np = of_get_next_parent(np);
99
100 for (i = 0; i < 3 && np; ++i) {
101 struct property *prop;
102
103 prop = of_find_property(np, "compatible", NULL);
104
105 if (prop)
106 return np;
107
108 np = of_get_next_parent(np);
109 }
110
111 return NULL;
112}
113
114struct device_node *
115omapdss_of_get_first_endpoint(const struct device_node *parent)
116{
117 struct device_node *port, *ep;
118
119 port = omapdss_of_get_next_port(parent, NULL);
120
121 if (!port)
122 return NULL;
123
124 ep = omapdss_of_get_next_endpoint(port, NULL);
125
126 of_node_put(port);
127
128 return ep;
129}
130EXPORT_SYMBOL_GPL(omapdss_of_get_first_endpoint);
131
132struct omap_dss_device *
133omapdss_of_find_source_for_first_ep(struct device_node *node)
134{
135 struct device_node *ep;
136 struct device_node *src_node;
137 struct omap_dss_device *src;
138
139 ep = omapdss_of_get_first_endpoint(node);
140 if (!ep)
141 return ERR_PTR(-EINVAL);
142
143 src_node = omapdss_of_get_remote_device_node(ep);
144
145 of_node_put(ep);
146
147 if (!src_node)
148 return ERR_PTR(-EINVAL);
149
150 src = omap_dss_find_output_by_node(src_node);
151
152 of_node_put(src_node);
153
154 if (!src)
155 return ERR_PTR(-EPROBE_DEFER);
156
157 return src;
158}
159EXPORT_SYMBOL_GPL(omapdss_of_find_source_for_first_ep);
diff --git a/drivers/video/omap2/dss/dss.c b/drivers/video/omap2/dss/dss.c
index 96e400c51001..32b4ff0606ab 100644
--- a/drivers/video/omap2/dss/dss.c
+++ b/drivers/video/omap2/dss/dss.c
@@ -23,6 +23,7 @@
23#define DSS_SUBSYS_NAME "DSS" 23#define DSS_SUBSYS_NAME "DSS"
24 24
25#include <linux/kernel.h> 25#include <linux/kernel.h>
26#include <linux/module.h>
26#include <linux/io.h> 27#include <linux/io.h>
27#include <linux/export.h> 28#include <linux/export.h>
28#include <linux/err.h> 29#include <linux/err.h>
@@ -33,6 +34,7 @@
33#include <linux/pm_runtime.h> 34#include <linux/pm_runtime.h>
34#include <linux/gfp.h> 35#include <linux/gfp.h>
35#include <linux/sizes.h> 36#include <linux/sizes.h>
37#include <linux/of.h>
36 38
37#include <video/omapdss.h> 39#include <video/omapdss.h>
38 40
@@ -772,6 +774,56 @@ static int __init dss_init_features(struct platform_device *pdev)
772 return 0; 774 return 0;
773} 775}
774 776
777static int dss_init_ports(struct platform_device *pdev)
778{
779 struct device_node *parent = pdev->dev.of_node;
780 struct device_node *port;
781 int r;
782
783 if (parent == NULL)
784 return 0;
785
786 port = omapdss_of_get_next_port(parent, NULL);
787 if (!port) {
788#ifdef CONFIG_OMAP2_DSS_DPI
789 dpi_init_port(pdev, parent);
790#endif
791 return 0;
792 }
793
794 do {
795 u32 reg;
796
797 r = of_property_read_u32(port, "reg", &reg);
798 if (r)
799 reg = 0;
800
801#ifdef CONFIG_OMAP2_DSS_DPI
802 if (reg == 0)
803 dpi_init_port(pdev, port);
804#endif
805
806#ifdef CONFIG_OMAP2_DSS_SDI
807 if (reg == 1)
808 sdi_init_port(pdev, port);
809#endif
810
811 } while ((port = omapdss_of_get_next_port(parent, port)) != NULL);
812
813 return 0;
814}
815
816static void dss_uninit_ports(void)
817{
818#ifdef CONFIG_OMAP2_DSS_DPI
819 dpi_uninit_port();
820#endif
821
822#ifdef CONFIG_OMAP2_DSS_SDI
823 sdi_uninit_port();
824#endif
825}
826
775/* DSS HW IP initialisation */ 827/* DSS HW IP initialisation */
776static int __init omap_dsshw_probe(struct platform_device *pdev) 828static int __init omap_dsshw_probe(struct platform_device *pdev)
777{ 829{
@@ -830,6 +882,8 @@ static int __init omap_dsshw_probe(struct platform_device *pdev)
830 dss.lcd_clk_source[0] = OMAP_DSS_CLK_SRC_FCK; 882 dss.lcd_clk_source[0] = OMAP_DSS_CLK_SRC_FCK;
831 dss.lcd_clk_source[1] = OMAP_DSS_CLK_SRC_FCK; 883 dss.lcd_clk_source[1] = OMAP_DSS_CLK_SRC_FCK;
832 884
885 dss_init_ports(pdev);
886
833 rev = dss_read_reg(DSS_REVISION); 887 rev = dss_read_reg(DSS_REVISION);
834 printk(KERN_INFO "OMAP DSS rev %d.%d\n", 888 printk(KERN_INFO "OMAP DSS rev %d.%d\n",
835 FLD_GET(rev, 7, 4), FLD_GET(rev, 3, 0)); 889 FLD_GET(rev, 7, 4), FLD_GET(rev, 3, 0));
@@ -849,6 +903,8 @@ err_setup_clocks:
849 903
850static int __exit omap_dsshw_remove(struct platform_device *pdev) 904static int __exit omap_dsshw_remove(struct platform_device *pdev)
851{ 905{
906 dss_uninit_ports();
907
852 pm_runtime_disable(&pdev->dev); 908 pm_runtime_disable(&pdev->dev);
853 909
854 dss_put_clocks(); 910 dss_put_clocks();
@@ -886,12 +942,22 @@ static const struct dev_pm_ops dss_pm_ops = {
886 .runtime_resume = dss_runtime_resume, 942 .runtime_resume = dss_runtime_resume,
887}; 943};
888 944
945static const struct of_device_id dss_of_match[] = {
946 { .compatible = "ti,omap2-dss", },
947 { .compatible = "ti,omap3-dss", },
948 { .compatible = "ti,omap4-dss", },
949 {},
950};
951
952MODULE_DEVICE_TABLE(of, dss_of_match);
953
889static struct platform_driver omap_dsshw_driver = { 954static struct platform_driver omap_dsshw_driver = {
890 .remove = __exit_p(omap_dsshw_remove), 955 .remove = __exit_p(omap_dsshw_remove),
891 .driver = { 956 .driver = {
892 .name = "omapdss_dss", 957 .name = "omapdss_dss",
893 .owner = THIS_MODULE, 958 .owner = THIS_MODULE,
894 .pm = &dss_pm_ops, 959 .pm = &dss_pm_ops,
960 .of_match_table = dss_of_match,
895 }, 961 },
896}; 962};
897 963
diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h
index 570f7ed2bcbc..918fec182424 100644
--- a/drivers/video/omap2/dss/dss.h
+++ b/drivers/video/omap2/dss/dss.h
@@ -250,6 +250,9 @@ bool dss_div_calc(unsigned long pck, unsigned long fck_min,
250int sdi_init_platform_driver(void) __init; 250int sdi_init_platform_driver(void) __init;
251void sdi_uninit_platform_driver(void) __exit; 251void sdi_uninit_platform_driver(void) __exit;
252 252
253int sdi_init_port(struct platform_device *pdev, struct device_node *port) __init;
254void sdi_uninit_port(void) __exit;
255
253/* DSI */ 256/* DSI */
254 257
255typedef bool (*dsi_pll_calc_func)(int regn, int regm, unsigned long fint, 258typedef bool (*dsi_pll_calc_func)(int regn, int regm, unsigned long fint,
@@ -361,6 +364,9 @@ static inline bool dsi_pll_calc(struct platform_device *dsidev,
361int dpi_init_platform_driver(void) __init; 364int dpi_init_platform_driver(void) __init;
362void dpi_uninit_platform_driver(void) __exit; 365void dpi_uninit_platform_driver(void) __exit;
363 366
367int dpi_init_port(struct platform_device *pdev, struct device_node *port) __init;
368void dpi_uninit_port(void) __exit;
369
364/* DISPC */ 370/* DISPC */
365int dispc_init_platform_driver(void) __init; 371int dispc_init_platform_driver(void) __init;
366void dispc_uninit_platform_driver(void) __exit; 372void dispc_uninit_platform_driver(void) __exit;
diff --git a/drivers/video/omap2/dss/hdmi4.c b/drivers/video/omap2/dss/hdmi4.c
index 895c252ae0a8..e9c3d9e6d450 100644
--- a/drivers/video/omap2/dss/hdmi4.c
+++ b/drivers/video/omap2/dss/hdmi4.c
@@ -88,7 +88,10 @@ static int hdmi_init_regulator(void)
88 if (hdmi.vdda_hdmi_dac_reg != NULL) 88 if (hdmi.vdda_hdmi_dac_reg != NULL)
89 return 0; 89 return 0;
90 90
91 reg = devm_regulator_get(&hdmi.pdev->dev, "vdda_hdmi_dac"); 91 if (hdmi.pdev->dev.of_node)
92 reg = devm_regulator_get(&hdmi.pdev->dev, "vdda");
93 else
94 reg = devm_regulator_get(&hdmi.pdev->dev, "vdda_hdmi_dac");
92 95
93 /* DT HACK: try VDAC to make omapdss work for o4 sdp/panda */ 96 /* DT HACK: try VDAC to make omapdss work for o4 sdp/panda */
94 if (IS_ERR(reg)) 97 if (IS_ERR(reg))
@@ -680,6 +683,11 @@ static const struct dev_pm_ops hdmi_pm_ops = {
680 .runtime_resume = hdmi_runtime_resume, 683 .runtime_resume = hdmi_runtime_resume,
681}; 684};
682 685
686static const struct of_device_id hdmi_of_match[] = {
687 { .compatible = "ti,omap4-hdmi", },
688 {},
689};
690
683static struct platform_driver omapdss_hdmihw_driver = { 691static struct platform_driver omapdss_hdmihw_driver = {
684 .probe = omapdss_hdmihw_probe, 692 .probe = omapdss_hdmihw_probe,
685 .remove = __exit_p(omapdss_hdmihw_remove), 693 .remove = __exit_p(omapdss_hdmihw_remove),
@@ -687,6 +695,7 @@ static struct platform_driver omapdss_hdmihw_driver = {
687 .name = "omapdss_hdmi", 695 .name = "omapdss_hdmi",
688 .owner = THIS_MODULE, 696 .owner = THIS_MODULE,
689 .pm = &hdmi_pm_ops, 697 .pm = &hdmi_pm_ops,
698 .of_match_table = hdmi_of_match,
690 }, 699 },
691}; 700};
692 701
diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c
index 800b2bb4ed93..911dcc9173a6 100644
--- a/drivers/video/omap2/dss/sdi.c
+++ b/drivers/video/omap2/dss/sdi.c
@@ -26,6 +26,7 @@
26#include <linux/export.h> 26#include <linux/export.h>
27#include <linux/platform_device.h> 27#include <linux/platform_device.h>
28#include <linux/string.h> 28#include <linux/string.h>
29#include <linux/of.h>
29 30
30#include <video/omapdss.h> 31#include <video/omapdss.h>
31#include "dss.h" 32#include "dss.h"
@@ -41,12 +42,14 @@ static struct {
41 int datapairs; 42 int datapairs;
42 43
43 struct omap_dss_device output; 44 struct omap_dss_device output;
45
46 bool port_initialized;
44} sdi; 47} sdi;
45 48
46struct sdi_clk_calc_ctx { 49struct sdi_clk_calc_ctx {
47 unsigned long pck_min, pck_max; 50 unsigned long pck_min, pck_max;
48 51
49 unsigned long long fck; 52 unsigned long fck;
50 struct dispc_clock_info dispc_cinfo; 53 struct dispc_clock_info dispc_cinfo;
51}; 54};
52 55
@@ -386,3 +389,45 @@ void __exit sdi_uninit_platform_driver(void)
386{ 389{
387 platform_driver_unregister(&omap_sdi_driver); 390 platform_driver_unregister(&omap_sdi_driver);
388} 391}
392
393int __init sdi_init_port(struct platform_device *pdev, struct device_node *port)
394{
395 struct device_node *ep;
396 u32 datapairs;
397 int r;
398
399 ep = omapdss_of_get_next_endpoint(port, NULL);
400 if (!ep)
401 return 0;
402
403 r = of_property_read_u32(ep, "datapairs", &datapairs);
404 if (r) {
405 DSSERR("failed to parse datapairs\n");
406 goto err_datapairs;
407 }
408
409 sdi.datapairs = datapairs;
410
411 of_node_put(ep);
412
413 sdi.pdev = pdev;
414
415 sdi_init_output(pdev);
416
417 sdi.port_initialized = true;
418
419 return 0;
420
421err_datapairs:
422 of_node_put(ep);
423
424 return r;
425}
426
427void __exit sdi_uninit_port(void)
428{
429 if (!sdi.port_initialized)
430 return;
431
432 sdi_uninit_output(sdi.pdev);
433}
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index 59ade34bd536..21d81113962b 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -34,6 +34,7 @@
34#include <linux/platform_device.h> 34#include <linux/platform_device.h>
35#include <linux/regulator/consumer.h> 35#include <linux/regulator/consumer.h>
36#include <linux/pm_runtime.h> 36#include <linux/pm_runtime.h>
37#include <linux/of.h>
37 38
38#include <video/omapdss.h> 39#include <video/omapdss.h>
39 40
@@ -636,7 +637,10 @@ static int venc_init_regulator(void)
636 if (venc.vdda_dac_reg != NULL) 637 if (venc.vdda_dac_reg != NULL)
637 return 0; 638 return 0;
638 639
639 vdda_dac = devm_regulator_get(&venc.pdev->dev, "vdda_dac"); 640 if (venc.pdev->dev.of_node)
641 vdda_dac = devm_regulator_get(&venc.pdev->dev, "vdda");
642 else
643 vdda_dac = devm_regulator_get(&venc.pdev->dev, "vdda_dac");
640 644
641 if (IS_ERR(vdda_dac)) { 645 if (IS_ERR(vdda_dac)) {
642 if (PTR_ERR(vdda_dac) != -EPROBE_DEFER) 646 if (PTR_ERR(vdda_dac) != -EPROBE_DEFER)
@@ -805,6 +809,48 @@ static void __exit venc_uninit_output(struct platform_device *pdev)
805 omapdss_unregister_output(out); 809 omapdss_unregister_output(out);
806} 810}
807 811
812static int venc_probe_of(struct platform_device *pdev)
813{
814 struct device_node *node = pdev->dev.of_node;
815 struct device_node *ep;
816 u32 channels;
817 int r;
818
819 ep = omapdss_of_get_first_endpoint(node);
820 if (!ep)
821 return 0;
822
823 venc.invert_polarity = of_property_read_bool(ep, "ti,invert-polarity");
824
825 r = of_property_read_u32(ep, "ti,channels", &channels);
826 if (r) {
827 dev_err(&pdev->dev,
828 "failed to read property 'ti,channels': %d\n", r);
829 goto err;
830 }
831
832 switch (channels) {
833 case 1:
834 venc.type = OMAP_DSS_VENC_TYPE_COMPOSITE;
835 break;
836 case 2:
837 venc.type = OMAP_DSS_VENC_TYPE_SVIDEO;
838 break;
839 default:
840 dev_err(&pdev->dev, "bad channel propert '%d'\n", channels);
841 r = -EINVAL;
842 goto err;
843 }
844
845 of_node_put(ep);
846
847 return 0;
848err:
849 of_node_put(ep);
850
851 return 0;
852}
853
808/* VENC HW IP initialisation */ 854/* VENC HW IP initialisation */
809static int omap_venchw_probe(struct platform_device *pdev) 855static int omap_venchw_probe(struct platform_device *pdev)
810{ 856{
@@ -846,12 +892,21 @@ static int omap_venchw_probe(struct platform_device *pdev)
846 892
847 venc_runtime_put(); 893 venc_runtime_put();
848 894
895 if (pdev->dev.of_node) {
896 r = venc_probe_of(pdev);
897 if (r) {
898 DSSERR("Invalid DT data\n");
899 goto err_probe_of;
900 }
901 }
902
849 dss_debugfs_create_file("venc", venc_dump_regs); 903 dss_debugfs_create_file("venc", venc_dump_regs);
850 904
851 venc_init_output(pdev); 905 venc_init_output(pdev);
852 906
853 return 0; 907 return 0;
854 908
909err_probe_of:
855err_runtime_get: 910err_runtime_get:
856 pm_runtime_disable(&pdev->dev); 911 pm_runtime_disable(&pdev->dev);
857 return r; 912 return r;
@@ -895,6 +950,14 @@ static const struct dev_pm_ops venc_pm_ops = {
895 .runtime_resume = venc_runtime_resume, 950 .runtime_resume = venc_runtime_resume,
896}; 951};
897 952
953
954static const struct of_device_id venc_of_match[] = {
955 { .compatible = "ti,omap2-venc", },
956 { .compatible = "ti,omap3-venc", },
957 { .compatible = "ti,omap4-venc", },
958 {},
959};
960
898static struct platform_driver omap_venchw_driver = { 961static struct platform_driver omap_venchw_driver = {
899 .probe = omap_venchw_probe, 962 .probe = omap_venchw_probe,
900 .remove = __exit_p(omap_venchw_remove), 963 .remove = __exit_p(omap_venchw_remove),
@@ -902,6 +965,7 @@ static struct platform_driver omap_venchw_driver = {
902 .name = "omapdss_venc", 965 .name = "omapdss_venc",
903 .owner = THIS_MODULE, 966 .owner = THIS_MODULE,
904 .pm = &venc_pm_ops, 967 .pm = &venc_pm_ops,
968 .of_match_table = venc_of_match,
905 }, 969 },
906}; 970};
907 971
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index 8d02f164c8c6..ec2d132c782d 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -2417,6 +2417,55 @@ static int omapfb_init_connections(struct omapfb2_device *fbdev,
2417 return 0; 2417 return 0;
2418} 2418}
2419 2419
2420static struct omap_dss_device *
2421omapfb_find_default_display(struct omapfb2_device *fbdev)
2422{
2423 const char *def_name;
2424 int i;
2425
2426 /*
2427 * Search with the display name from the user or the board file,
2428 * comparing to display names and aliases
2429 */
2430
2431 def_name = omapdss_get_default_display_name();
2432
2433 if (def_name) {
2434 for (i = 0; i < fbdev->num_displays; ++i) {
2435 struct omap_dss_device *dssdev;
2436
2437 dssdev = fbdev->displays[i].dssdev;
2438
2439 if (dssdev->name && strcmp(def_name, dssdev->name) == 0)
2440 return dssdev;
2441
2442 if (strcmp(def_name, dssdev->alias) == 0)
2443 return dssdev;
2444 }
2445
2446 /* def_name given but not found */
2447 return NULL;
2448 }
2449
2450 /* then look for DT alias display0 */
2451 for (i = 0; i < fbdev->num_displays; ++i) {
2452 struct omap_dss_device *dssdev;
2453 int id;
2454
2455 dssdev = fbdev->displays[i].dssdev;
2456
2457 if (dssdev->dev->of_node == NULL)
2458 continue;
2459
2460 id = of_alias_get_id(dssdev->dev->of_node, "display");
2461 if (id == 0)
2462 return dssdev;
2463 }
2464
2465 /* return the first display we have in the list */
2466 return fbdev->displays[0].dssdev;
2467}
2468
2420static int omapfb_probe(struct platform_device *pdev) 2469static int omapfb_probe(struct platform_device *pdev)
2421{ 2470{
2422 struct omapfb2_device *fbdev = NULL; 2471 struct omapfb2_device *fbdev = NULL;
@@ -2494,23 +2543,7 @@ static int omapfb_probe(struct platform_device *pdev)
2494 for (i = 0; i < fbdev->num_managers; i++) 2543 for (i = 0; i < fbdev->num_managers; i++)
2495 fbdev->managers[i] = omap_dss_get_overlay_manager(i); 2544 fbdev->managers[i] = omap_dss_get_overlay_manager(i);
2496 2545
2497 def_display = NULL; 2546 def_display = omapfb_find_default_display(fbdev);
2498
2499 for (i = 0; i < fbdev->num_displays; ++i) {
2500 struct omap_dss_device *dssdev;
2501 const char *def_name;
2502
2503 def_name = omapdss_get_default_display_name();
2504
2505 dssdev = fbdev->displays[i].dssdev;
2506
2507 if (def_name == NULL ||
2508 (dssdev->name && strcmp(def_name, dssdev->name) == 0)) {
2509 def_display = dssdev;
2510 break;
2511 }
2512 }
2513
2514 if (def_display == NULL) { 2547 if (def_display == NULL) {
2515 dev_err(fbdev->dev, "failed to find default display\n"); 2548 dev_err(fbdev->dev, "failed to find default display\n");
2516 r = -EPROBE_DEFER; 2549 r = -EPROBE_DEFER;