linux-omap.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 00/17] OMAP DSS2 model restructuring
@ 2010-02-08 15:57 Tomi Valkeinen
  2010-02-08 15:57 ` [PATCH 01/17] OMAP: DSS2: DSI: change DSI bus_lock to semaphore Tomi Valkeinen
  2010-02-13 15:34 ` [PATCH 00/17] OMAP DSS2 model restructuring Grazvydas Ignotas
  0 siblings, 2 replies; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Here are a bunch of patches that change the DSS2 driver's driver model a bit.
This change was triggered by trying to support new hardware, and realizing that
the current model just won't work.

Currently the omapdss driver is in control of most aspects of the DSS, and
omapdss calls necessary functions in display drivers. I made it that way to
keep the display drivers simple, and I, naively, thought that it will work
because the display panels are using standard bus interfaces and thus will be
very similar. I was so wrong =).

This patch set moves the control to the display driver. The display driver then
calls omapdss functions to perform whatever deed is needed at that time. This
will make display drivers slightly more complex, but it will be easier to
control the hardware properly with strange or complex display devices.

As a simple example, let's look at the update function.

Currently user space app issues OMAPFB_UPDATE_WINDOW ioctl, and omapfb driver
then calls update() in corresponding dss device struct, which goes to omapdss.
omapdss will configure the update, calling the panel driver if needed.

After these patches, omapfb will call update() in the panel driver. The panel
driver will then call functions in omapdss to setup the update, start the
update, and the panel driver will eventually get a callback informing that the
update is done.

These patches are still under work, but my basic tests on 3430SDP board seems
to work ok.

The patches can also be found from
http://gitorious.org/linux-omap-dss2/linux work branch

Tomi Valkeinen (17):
  OMAP: DSS2: DSI: change DSI bus_lock to semaphore
  OMAP: DSS2: DSI: remove auto-update perf measurement
  OMAP: DSS2: move run_test()
  OMAP: DSS2: move memory_read()
  OMAP: DSS2: move set/get_mirror()
  OMAP: DSS2: move get/set_rotate()
  OMAP: DSS2: move wait_vsync()
  OMAP: DSS2: move enable/disable_channel to overlay manager
  OMAP: DSS2: move get_resolution()
  OMAP: DSS2: move get_recommended_bpp()
  OMAP: DSS2: move enable/get_te()
  OMAP: DSS2: move set/get_update_mode()
  OMAP: DSS2: move update() and sync()
  OMAP: DSS2: move enable/disable/suspend/resume
  OMAP: DSS2: move set/get_wss()
  OMAP: DSS2: move timing functions
  OMAP: DSS2: DSI: Add VC support for update

 arch/arm/plat-omap/include/plat/display.h          |  108 ++--
 drivers/video/omap2/displays/panel-generic.c       |   56 ++-
 .../video/omap2/displays/panel-sharp-lq043t1dg01.c |   67 ++-
 .../video/omap2/displays/panel-sharp-ls037v7dw01.c |   42 +-
 drivers/video/omap2/displays/panel-taal.c          |  221 +++++--
 .../video/omap2/displays/panel-toppoly-tdo35s.c    |   56 ++-
 .../video/omap2/displays/panel-tpo-td043mtea1.c    |   61 ++-
 drivers/video/omap2/dss/core.c                     |    7 +
 drivers/video/omap2/dss/dispc.c                    |   36 +-
 drivers/video/omap2/dss/display.c                  |   87 +--
 drivers/video/omap2/dss/dpi.c                      |  149 +----
 drivers/video/omap2/dss/dsi.c                      |  829 ++++----------------
 drivers/video/omap2/dss/dss.h                      |    4 +-
 drivers/video/omap2/dss/manager.c                  |   48 +-
 drivers/video/omap2/dss/overlay.c                  |    2 +-
 drivers/video/omap2/dss/rfbi.c                     |  321 +-------
 drivers/video/omap2/dss/sdi.c                      |  115 +---
 drivers/video/omap2/dss/venc.c                     |  294 +++----
 drivers/video/omap2/omapfb/omapfb-ioctl.c          |   44 +-
 drivers/video/omap2/omapfb/omapfb-main.c           |   89 ++-
 drivers/video/omap2/omapfb/omapfb.h                |    6 +
 21 files changed, 1004 insertions(+), 1638 deletions(-)


^ permalink raw reply	[flat|nested] 22+ messages in thread

* [PATCH 01/17] OMAP: DSS2: DSI: change DSI bus_lock to semaphore
  2010-02-08 15:57 [PATCH 00/17] OMAP DSS2 model restructuring Tomi Valkeinen
@ 2010-02-08 15:57 ` Tomi Valkeinen
  2010-02-08 15:57   ` [PATCH 02/17] OMAP: DSS2: DSI: remove auto-update perf measurement Tomi Valkeinen
  2010-02-13 15:34 ` [PATCH 00/17] OMAP DSS2 model restructuring Grazvydas Ignotas
  1 sibling, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Physical DSI bus is protected by a mutex. This patch changed the mutex to
a semaphore, so that we can lock and unlock the bus_lock from different
threads.

This is needed as the update process is started by user space program, and
thus the lock is acquired in that context, but the lock can be released in
different context, a work thread via irq.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 drivers/video/omap2/dss/dsi.c |   20 ++++++--------------
 1 files changed, 6 insertions(+), 14 deletions(-)

diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index 4b85ed2..74df72b 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -27,6 +27,7 @@
 #include <linux/interrupt.h>
 #include <linux/delay.h>
 #include <linux/mutex.h>
+#include <linux/semaphore.h>
 #include <linux/seq_file.h>
 #include <linux/platform_device.h>
 #include <linux/regulator/consumer.h>
@@ -227,7 +228,7 @@ static struct
 	} vc[4];
 
 	struct mutex lock;
-	struct mutex bus_lock;
+	struct semaphore bus_lock;
 
 	unsigned pll_locked;
 
@@ -298,19 +299,19 @@ void dsi_restore_context(void)
 
 void dsi_bus_lock(void)
 {
-	mutex_lock(&dsi.bus_lock);
+	down(&dsi.bus_lock);
 }
 EXPORT_SYMBOL(dsi_bus_lock);
 
 void dsi_bus_unlock(void)
 {
-	mutex_unlock(&dsi.bus_lock);
+	up(&dsi.bus_lock);
 }
 EXPORT_SYMBOL(dsi_bus_unlock);
 
 static bool dsi_bus_is_locked(void)
 {
-	return mutex_is_locked(&dsi.bus_lock);
+	return dsi.bus_lock.count == 0;
 }
 
 static inline int wait_for_bit_change(const struct dsi_reg idx, int bitnum,
@@ -3000,8 +3001,6 @@ static int dsi_update_thread(void *data)
 	u16 x, y, w, h;
 
 	while (1) {
-		bool sched;
-
 		wait_event_interruptible(dsi.waitqueue,
 				dsi.update_mode == OMAP_DSS_UPDATE_AUTO ||
 				(dsi.update_mode == OMAP_DSS_UPDATE_MANUAL &&
@@ -3087,16 +3086,9 @@ static int dsi_update_thread(void *data)
 			dsi_perf_show("L4");
 		}
 
-		sched = atomic_read(&dsi.bus_lock.count) < 0;
-
 		complete_all(&dsi.update_completion);
 
 		dsi_bus_unlock();
-
-		/* XXX We need to give others chance to get the bus lock. Is
-		 * there a better way for this? */
-		if (dsi.update_mode == OMAP_DSS_UPDATE_AUTO && sched)
-			schedule_timeout_interruptible(1);
 	}
 
 	DSSDBG("update thread exiting\n");
@@ -3796,7 +3788,7 @@ int dsi_init(struct platform_device *pdev)
 	spin_lock_init(&dsi.update_lock);
 
 	mutex_init(&dsi.lock);
-	mutex_init(&dsi.bus_lock);
+	sema_init(&dsi.bus_lock, 1);
 
 #ifdef DSI_CATCH_MISSING_TE
 	init_timer(&dsi.te_timer);
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 02/17] OMAP: DSS2: DSI: remove auto-update perf measurement
  2010-02-08 15:57 ` [PATCH 01/17] OMAP: DSS2: DSI: change DSI bus_lock to semaphore Tomi Valkeinen
@ 2010-02-08 15:57   ` Tomi Valkeinen
  2010-02-08 15:57     ` [PATCH 03/17] OMAP: DSS2: move run_test() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Remove performance measurement for auto-update. Auto-update and thus
performance measurement cannot be supported after the driver change where
the control is moved to display drivers.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 drivers/video/omap2/dss/dsi.c |   81 +++++------------------------------------
 1 files changed, 9 insertions(+), 72 deletions(-)

diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index 74df72b..a6ea8c8 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -261,8 +261,6 @@ static struct
 #ifdef DEBUG
 	ktime_t perf_setup_time;
 	ktime_t perf_start_time;
-	ktime_t perf_start_time_auto;
-	int perf_measure_frames;
 #endif
 	int debug_read;
 	int debug_write;
@@ -338,12 +336,6 @@ static void dsi_perf_mark_start(void)
 	dsi.perf_start_time = ktime_get();
 }
 
-static void dsi_perf_mark_start_auto(void)
-{
-	dsi.perf_measure_frames = 0;
-	dsi.perf_start_time_auto = ktime_get();
-}
-
 static void dsi_perf_show(const char *name)
 {
 	ktime_t t, setup_time, trans_time;
@@ -374,72 +366,19 @@ static void dsi_perf_show(const char *name)
 		dsi.active_update_region.h *
 		dsi.active_update_region.device->ctrl.pixel_size / 8;
 
-	if (dsi.update_mode == OMAP_DSS_UPDATE_AUTO) {
-		static u32 s_total_trans_us, s_total_setup_us;
-		static u32 s_min_trans_us = 0xffffffff, s_min_setup_us;
-		static u32 s_max_trans_us, s_max_setup_us;
-		const int numframes = 100;
-		ktime_t total_time_auto;
-		u32 total_time_auto_us;
-
-		dsi.perf_measure_frames++;
-
-		if (setup_us < s_min_setup_us)
-			s_min_setup_us = setup_us;
-
-		if (setup_us > s_max_setup_us)
-			s_max_setup_us = setup_us;
-
-		s_total_setup_us += setup_us;
-
-		if (trans_us < s_min_trans_us)
-			s_min_trans_us = trans_us;
-
-		if (trans_us > s_max_trans_us)
-			s_max_trans_us = trans_us;
-
-		s_total_trans_us += trans_us;
-
-		if (dsi.perf_measure_frames < numframes)
-			return;
-
-		total_time_auto = ktime_sub(t, dsi.perf_start_time_auto);
-		total_time_auto_us = (u32)ktime_to_us(total_time_auto);
-
-		printk(KERN_INFO "DSI(%s): %u fps, setup %u/%u/%u, "
-				"trans %u/%u/%u\n",
-				name,
-				1000 * 1000 * numframes / total_time_auto_us,
-				s_min_setup_us,
-				s_max_setup_us,
-				s_total_setup_us / numframes,
-				s_min_trans_us,
-				s_max_trans_us,
-				s_total_trans_us / numframes);
-
-		s_total_setup_us = 0;
-		s_min_setup_us = 0xffffffff;
-		s_max_setup_us = 0;
-		s_total_trans_us = 0;
-		s_min_trans_us = 0xffffffff;
-		s_max_trans_us = 0;
-		dsi_perf_mark_start_auto();
-	} else {
-		printk(KERN_INFO "DSI(%s): %u us + %u us = %u us (%uHz), "
-				"%u bytes, %u kbytes/sec\n",
-				name,
-				setup_us,
-				trans_us,
-				total_us,
-				1000*1000 / total_us,
-				total_bytes,
-				total_bytes * 1000 / total_us);
-	}
+	printk(KERN_INFO "DSI(%s): %u us + %u us = %u us (%uHz), "
+			"%u bytes, %u kbytes/sec\n",
+			name,
+			setup_us,
+			trans_us,
+			total_us,
+			1000*1000 / total_us,
+			total_bytes,
+			total_bytes * 1000 / total_us);
 }
 #else
 #define dsi_perf_mark_setup()
 #define dsi_perf_mark_start()
-#define dsi_perf_mark_start_auto()
 #define dsi_perf_show(x)
 #endif
 
@@ -2931,8 +2870,6 @@ static int dsi_set_update_mode(struct omap_dss_device *dssdev,
 
 			dsi_set_update_region(dssdev, 0, 0, w, h);
 
-			dsi_perf_mark_start_auto();
-
 			wake_up(&dsi.waitqueue);
 		}
 	}
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 03/17] OMAP: DSS2: move run_test()
  2010-02-08 15:57   ` [PATCH 02/17] OMAP: DSS2: DSI: remove auto-update perf measurement Tomi Valkeinen
@ 2010-02-08 15:57     ` Tomi Valkeinen
  2010-02-08 15:57       ` [PATCH 04/17] OMAP: DSS2: move memory_read() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move run_test() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    1 -
 drivers/video/omap2/displays/panel-taal.c |   12 +++++++--
 drivers/video/omap2/dss/dsi.c             |   38 -----------------------------
 drivers/video/omap2/omapfb/omapfb-ioctl.c |    8 +++---
 4 files changed, 13 insertions(+), 46 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 8c3688b..7c6413a 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -498,7 +498,6 @@ struct omap_dss_device {
 	bool (*get_mirror)(struct omap_dss_device *dssdev);
 	int (*set_mirror)(struct omap_dss_device *dssdev, bool enable);
 
-	int (*run_test)(struct omap_dss_device *dssdev, int test);
 	int (*memory_read)(struct omap_dss_device *dssdev,
 			void *buf, size_t size,
 			u16 x, u16 y, u16 w, u16 h);
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index 0aaaa8a..e6d0954 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -820,17 +820,23 @@ static int taal_run_test(struct omap_dss_device *dssdev, int test_num)
 	u8 id1, id2, id3;
 	int r;
 
+	dsi_bus_lock();
+
 	r = taal_dcs_read_1(DCS_GET_ID1, &id1);
 	if (r)
-		return r;
+		goto err;
 	r = taal_dcs_read_1(DCS_GET_ID2, &id2);
 	if (r)
-		return r;
+		goto err;
 	r = taal_dcs_read_1(DCS_GET_ID3, &id3);
 	if (r)
-		return r;
+		goto err;
 
+	dsi_bus_unlock();
 	return 0;
+err:
+	dsi_bus_unlock();
+	return r;
 }
 
 static int taal_memory_read(struct omap_dss_device *dssdev,
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index a6ea8c8..f7d494e 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -3582,43 +3582,6 @@ static bool dsi_display_get_mirror(struct omap_dss_device *dssdev)
 	return dssdev->driver->get_mirror(dssdev);
 }
 
-static int dsi_display_run_test(struct omap_dss_device *dssdev, int test_num)
-{
-	int r;
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
-		return -EIO;
-
-	DSSDBGF("%d", test_num);
-
-	dsi_bus_lock();
-
-	/* run test first in low speed mode */
-	omapdss_dsi_vc_enable_hs(0, 0);
-
-	if (dssdev->driver->run_test) {
-		r = dssdev->driver->run_test(dssdev, test_num);
-		if (r)
-			goto end;
-	}
-
-	/* then in high speed */
-	omapdss_dsi_vc_enable_hs(0, 1);
-
-	if (dssdev->driver->run_test) {
-		r = dssdev->driver->run_test(dssdev, test_num);
-		if (r)
-			goto end;
-	}
-
-end:
-	omapdss_dsi_vc_enable_hs(0, 1);
-
-	dsi_bus_unlock();
-
-	return r;
-}
-
 static int dsi_display_memory_read(struct omap_dss_device *dssdev,
 		void *buf, size_t size,
 		u16 x, u16 y, u16 w, u16 h)
@@ -3681,7 +3644,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 	dssdev->get_mirror = dsi_display_get_mirror;
 	dssdev->set_mirror = dsi_display_set_mirror;
 
-	dssdev->run_test = dsi_display_run_test;
 	dssdev->memory_read = dsi_display_memory_read;
 
 	/* XXX these should be figured out dynamically */
diff --git a/drivers/video/omap2/omapfb/omapfb-ioctl.c b/drivers/video/omap2/omapfb/omapfb-ioctl.c
index 56e3ec2..b5657be 100644
--- a/drivers/video/omap2/omapfb/omapfb-ioctl.c
+++ b/drivers/video/omap2/omapfb/omapfb-ioctl.c
@@ -721,12 +721,12 @@ int omapfb_ioctl(struct fb_info *fbi, unsigned int cmd, unsigned long arg)
 			r = -EFAULT;
 			break;
 		}
-		if (!display || !display->run_test) {
+		if (!display || !display->driver->run_test) {
 			r = -EINVAL;
 			break;
 		}
 
-		r = display->run_test(display, p.test_num);
+		r = display->driver->run_test(display, p.test_num);
 
 		break;
 
@@ -736,12 +736,12 @@ int omapfb_ioctl(struct fb_info *fbi, unsigned int cmd, unsigned long arg)
 			r = -EFAULT;
 			break;
 		}
-		if (!display || !display->run_test) {
+		if (!display || !display->driver->run_test) {
 			r = -EINVAL;
 			break;
 		}
 
-		r = display->run_test(display, p.test_num);
+		r = display->driver->run_test(display, p.test_num);
 
 		break;
 
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 04/17] OMAP: DSS2: move memory_read()
  2010-02-08 15:57     ` [PATCH 03/17] OMAP: DSS2: move run_test() Tomi Valkeinen
@ 2010-02-08 15:57       ` Tomi Valkeinen
  2010-02-08 15:57         ` [PATCH 05/17] OMAP: DSS2: move set/get_mirror() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move memory_read() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    4 ---
 drivers/video/omap2/displays/panel-taal.c |   13 +++++++++--
 drivers/video/omap2/dss/dsi.c             |   30 -----------------------------
 drivers/video/omap2/omapfb/omapfb-ioctl.c |    4 +-
 4 files changed, 12 insertions(+), 39 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 7c6413a..37be8bc 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -498,10 +498,6 @@ struct omap_dss_device {
 	bool (*get_mirror)(struct omap_dss_device *dssdev);
 	int (*set_mirror)(struct omap_dss_device *dssdev, bool enable);
 
-	int (*memory_read)(struct omap_dss_device *dssdev,
-			void *buf, size_t size,
-			u16 x, u16 y, u16 w, u16 h);
-
 	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
 	u32 (*get_wss)(struct omap_dss_device *dssdev);
 
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index e6d0954..5f78d38 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -847,6 +847,10 @@ static int taal_memory_read(struct omap_dss_device *dssdev,
 	int first = 1;
 	int plen;
 	unsigned buf_used = 0;
+	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
+
+	if (!td->enabled)
+		return -ENODEV;
 
 	if (size < w * h * 3)
 		return -ENOMEM;
@@ -855,6 +859,8 @@ static int taal_memory_read(struct omap_dss_device *dssdev,
 			dssdev->panel.timings.x_res *
 			dssdev->panel.timings.y_res * 3);
 
+	dsi_bus_lock();
+
 	/* plen 1 or 2 goes into short packet. until checksum error is fixed,
 	 * use short packets. plen 32 works, but bigger packets seem to cause
 	 * an error. */
@@ -863,11 +869,11 @@ static int taal_memory_read(struct omap_dss_device *dssdev,
 	else
 		plen = 2;
 
-	taal_setup_update(dssdev, x, y, w, h);
+	taal_set_update_window(x, y, w, h);
 
 	r = dsi_vc_set_max_rx_packet_size(TCH, plen);
 	if (r)
-		return r;
+		goto err0;
 
 	while (buf_used < size) {
 		u8 dcs_cmd = first ? 0x2e : 0x3e;
@@ -900,7 +906,8 @@ static int taal_memory_read(struct omap_dss_device *dssdev,
 
 err:
 	dsi_vc_set_max_rx_packet_size(TCH, 1);
-
+err0:
+	dsi_bus_unlock();
 	return r;
 }
 
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index f7d494e..ecb15d6 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -3582,34 +3582,6 @@ static bool dsi_display_get_mirror(struct omap_dss_device *dssdev)
 	return dssdev->driver->get_mirror(dssdev);
 }
 
-static int dsi_display_memory_read(struct omap_dss_device *dssdev,
-		void *buf, size_t size,
-		u16 x, u16 y, u16 w, u16 h)
-{
-	int r;
-
-	DSSDBGF("");
-
-	if (!dssdev->driver->memory_read)
-		return -EINVAL;
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
-		return -EIO;
-
-	dsi_bus_lock();
-
-	r = dssdev->driver->memory_read(dssdev, buf, size,
-			x, y, w, h);
-
-	/* Memory read usually changes the update area. This will
-	 * force the next update to re-set the update area */
-	dsi.active_update_region.dirty = true;
-
-	dsi_bus_unlock();
-
-	return r;
-}
-
 void dsi_get_overlay_fifo_thresholds(enum omap_plane plane,
 		u32 fifo_size, enum omap_burst_size *burst_size,
 		u32 *fifo_low, u32 *fifo_high)
@@ -3644,8 +3616,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 	dssdev->get_mirror = dsi_display_get_mirror;
 	dssdev->set_mirror = dsi_display_set_mirror;
 
-	dssdev->memory_read = dsi_display_memory_read;
-
 	/* XXX these should be figured out dynamically */
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
 		OMAP_DSS_DISPLAY_CAP_TEAR_ELIM;
diff --git a/drivers/video/omap2/omapfb/omapfb-ioctl.c b/drivers/video/omap2/omapfb/omapfb-ioctl.c
index b5657be..f3c9c80 100644
--- a/drivers/video/omap2/omapfb/omapfb-ioctl.c
+++ b/drivers/video/omap2/omapfb/omapfb-ioctl.c
@@ -415,7 +415,7 @@ static int omapfb_memory_read(struct fb_info *fbi,
 	void *buf;
 	int r;
 
-	if (!display || !display->memory_read)
+	if (!display || !display->driver->memory_read)
 		return -ENOENT;
 
 	if (!access_ok(VERIFY_WRITE, mr->buffer, mr->buffer_size))
@@ -430,7 +430,7 @@ static int omapfb_memory_read(struct fb_info *fbi,
 		return -ENOMEM;
 	}
 
-	r = display->memory_read(display, buf, mr->buffer_size,
+	r = display->driver->memory_read(display, buf, mr->buffer_size,
 			mr->x, mr->y, mr->w, mr->h);
 
 	if (r > 0) {
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 05/17] OMAP: DSS2: move set/get_mirror()
  2010-02-08 15:57       ` [PATCH 04/17] OMAP: DSS2: move memory_read() Tomi Valkeinen
@ 2010-02-08 15:57         ` Tomi Valkeinen
  2010-02-08 15:57           ` [PATCH 06/17] OMAP: DSS2: move get/set_rotate() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move set/get_mirror() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    3 ---
 drivers/video/omap2/displays/panel-taal.c |    8 ++++++--
 drivers/video/omap2/dss/display.c         |    8 ++++----
 drivers/video/omap2/dss/dsi.c             |   25 -------------------------
 4 files changed, 10 insertions(+), 34 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 37be8bc..4730e71 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -495,9 +495,6 @@ struct omap_dss_device {
 	u8 (*get_rotate)(struct omap_dss_device *dssdev);
 	int (*set_rotate)(struct omap_dss_device *dssdev, u8 rotate);
 
-	bool (*get_mirror)(struct omap_dss_device *dssdev);
-	int (*set_mirror)(struct omap_dss_device *dssdev, bool enable);
-
 	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
 	u32 (*get_wss)(struct omap_dss_device *dssdev);
 
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index 5f78d38..4d64449 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -797,16 +797,20 @@ static int taal_mirror(struct omap_dss_device *dssdev, bool enable)
 
 	dev_dbg(&dssdev->dev, "mirror %d\n", enable);
 
+	dsi_bus_lock();
 	if (td->enabled) {
 		r = taal_set_addr_mode(td->rotate, enable);
-
 		if (r)
-			return r;
+			goto err;
 	}
 
 	td->mirror = enable;
 
+	dsi_bus_unlock();
 	return 0;
+err:
+	dsi_bus_unlock();
+	return r;
 }
 
 static bool taal_get_mirror(struct omap_dss_device *dssdev)
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index 3b92b84..ec82f5a 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -215,9 +215,9 @@ static ssize_t display_mirror_show(struct device *dev,
 {
 	struct omap_dss_device *dssdev = to_dss_device(dev);
 	int mirror;
-	if (!dssdev->get_mirror)
+	if (!dssdev->driver->get_mirror)
 		return -ENOENT;
-	mirror = dssdev->get_mirror(dssdev);
+	mirror = dssdev->driver->get_mirror(dssdev);
 	return snprintf(buf, PAGE_SIZE, "%u\n", mirror);
 }
 
@@ -228,12 +228,12 @@ static ssize_t display_mirror_store(struct device *dev,
 	unsigned long mirror;
 	int r;
 
-	if (!dssdev->set_mirror || !dssdev->get_mirror)
+	if (!dssdev->driver->set_mirror || !dssdev->driver->get_mirror)
 		return -ENOENT;
 
 	mirror = simple_strtoul(buf, NULL, 0);
 
-	r = dssdev->set_mirror(dssdev, mirror);
+	r = dssdev->driver->set_mirror(dssdev, mirror);
 	if (r)
 		return r;
 
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index ecb15d6..8f4f28d 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -3560,28 +3560,6 @@ static u8 dsi_display_get_rotate(struct omap_dss_device *dssdev)
 	return dssdev->driver->get_rotate(dssdev);
 }
 
-static int dsi_display_set_mirror(struct omap_dss_device *dssdev, bool mirror)
-{
-	DSSDBGF("%d", mirror);
-
-	if (!dssdev->driver->set_mirror || !dssdev->driver->get_mirror)
-		return -EINVAL;
-
-	dsi_bus_lock();
-	dssdev->driver->set_mirror(dssdev, mirror);
-	dsi_bus_unlock();
-
-	return 0;
-}
-
-static bool dsi_display_get_mirror(struct omap_dss_device *dssdev)
-{
-	if (!dssdev->driver->set_mirror || !dssdev->driver->get_mirror)
-		return 0;
-
-	return dssdev->driver->get_mirror(dssdev);
-}
-
 void dsi_get_overlay_fifo_thresholds(enum omap_plane plane,
 		u32 fifo_size, enum omap_burst_size *burst_size,
 		u32 *fifo_low, u32 *fifo_high)
@@ -3613,9 +3591,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 	dssdev->get_rotate = dsi_display_get_rotate;
 	dssdev->set_rotate = dsi_display_set_rotate;
 
-	dssdev->get_mirror = dsi_display_get_mirror;
-	dssdev->set_mirror = dsi_display_set_mirror;
-
 	/* XXX these should be figured out dynamically */
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
 		OMAP_DSS_DISPLAY_CAP_TEAR_ELIM;
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 06/17] OMAP: DSS2: move get/set_rotate()
  2010-02-08 15:57         ` [PATCH 05/17] OMAP: DSS2: move set/get_mirror() Tomi Valkeinen
@ 2010-02-08 15:57           ` Tomi Valkeinen
  2010-02-08 15:57             ` [PATCH 07/17] OMAP: DSS2: move wait_vsync() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move get/set_rotate() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    3 --
 drivers/video/omap2/displays/panel-taal.c |    9 ++++++-
 drivers/video/omap2/dss/display.c         |    8 +++---
 drivers/video/omap2/dss/dsi.c             |   33 -----------------------------
 4 files changed, 11 insertions(+), 42 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 4730e71..2fd3c10 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -492,9 +492,6 @@ struct omap_dss_device {
 	int (*enable_te)(struct omap_dss_device *dssdev, bool enable);
 	int (*get_te)(struct omap_dss_device *dssdev);
 
-	u8 (*get_rotate)(struct omap_dss_device *dssdev);
-	int (*set_rotate)(struct omap_dss_device *dssdev, u8 rotate);
-
 	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
 	u32 (*get_wss)(struct omap_dss_device *dssdev);
 
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index 4d64449..8f90de0 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -772,16 +772,21 @@ static int taal_rotate(struct omap_dss_device *dssdev, u8 rotate)
 
 	dev_dbg(&dssdev->dev, "rotate %d\n", rotate);
 
+	dsi_bus_lock();
+
 	if (td->enabled) {
 		r = taal_set_addr_mode(rotate, td->mirror);
-
 		if (r)
-			return r;
+			goto err;
 	}
 
 	td->rotate = rotate;
 
+	dsi_bus_unlock();
 	return 0;
+err:
+	dsi_bus_unlock();
+	return r;
 }
 
 static u8 taal_get_rotate(struct omap_dss_device *dssdev)
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index ec82f5a..5989afb 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -185,9 +185,9 @@ static ssize_t display_rotate_show(struct device *dev,
 {
 	struct omap_dss_device *dssdev = to_dss_device(dev);
 	int rotate;
-	if (!dssdev->get_rotate)
+	if (!dssdev->driver->get_rotate)
 		return -ENOENT;
-	rotate = dssdev->get_rotate(dssdev);
+	rotate = dssdev->driver->get_rotate(dssdev);
 	return snprintf(buf, PAGE_SIZE, "%u\n", rotate);
 }
 
@@ -198,12 +198,12 @@ static ssize_t display_rotate_store(struct device *dev,
 	unsigned long rot;
 	int r;
 
-	if (!dssdev->set_rotate || !dssdev->get_rotate)
+	if (!dssdev->driver->set_rotate || !dssdev->driver->get_rotate)
 		return -ENOENT;
 
 	rot = simple_strtoul(buf, NULL, 0);
 
-	r = dssdev->set_rotate(dssdev, rot);
+	r = dssdev->driver->set_rotate(dssdev, rot);
 	if (r)
 		return r;
 
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index 8f4f28d..8d6a436 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -3530,36 +3530,6 @@ static int dsi_display_get_te(struct omap_dss_device *dssdev)
 	return dsi.te_enabled;
 }
 
-static int dsi_display_set_rotate(struct omap_dss_device *dssdev, u8 rotate)
-{
-
-	DSSDBGF("%d", rotate);
-
-	if (!dssdev->driver->set_rotate || !dssdev->driver->get_rotate)
-		return -EINVAL;
-
-	dsi_bus_lock();
-	dssdev->driver->set_rotate(dssdev, rotate);
-	if (dsi.update_mode == OMAP_DSS_UPDATE_AUTO) {
-		u16 w, h;
-		/* the display dimensions may have changed, so set a new
-		 * update region */
-		dssdev->get_resolution(dssdev, &w, &h);
-		dsi_set_update_region(dssdev, 0, 0, w, h);
-	}
-	dsi_bus_unlock();
-
-	return 0;
-}
-
-static u8 dsi_display_get_rotate(struct omap_dss_device *dssdev)
-{
-	if (!dssdev->driver->set_rotate || !dssdev->driver->get_rotate)
-		return 0;
-
-	return dssdev->driver->get_rotate(dssdev);
-}
-
 void dsi_get_overlay_fifo_thresholds(enum omap_plane plane,
 		u32 fifo_size, enum omap_burst_size *burst_size,
 		u32 *fifo_low, u32 *fifo_high)
@@ -3588,9 +3558,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 	dssdev->enable_te = dsi_display_enable_te;
 	dssdev->get_te = dsi_display_get_te;
 
-	dssdev->get_rotate = dsi_display_get_rotate;
-	dssdev->set_rotate = dsi_display_set_rotate;
-
 	/* XXX these should be figured out dynamically */
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
 		OMAP_DSS_DISPLAY_CAP_TEAR_ELIM;
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 07/17] OMAP: DSS2: move wait_vsync()
  2010-02-08 15:57           ` [PATCH 06/17] OMAP: DSS2: move get/set_rotate() Tomi Valkeinen
@ 2010-02-08 15:57             ` Tomi Valkeinen
  2010-02-08 15:57               ` [PATCH 08/17] OMAP: DSS2: move enable/disable_channel to overlay manager Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move wait_vsync() from omap_dss_device to overlay manager.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    2 +-
 drivers/video/omap2/dss/display.c         |   14 --------------
 drivers/video/omap2/dss/manager.c         |   14 ++++++++++++++
 drivers/video/omap2/omapfb/omapfb-ioctl.c |    2 +-
 4 files changed, 16 insertions(+), 16 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 2fd3c10..2308912 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -370,6 +370,7 @@ struct omap_overlay_manager {
 
 	int (*apply)(struct omap_overlay_manager *mgr);
 	int (*wait_for_go)(struct omap_overlay_manager *mgr);
+	int (*wait_for_vsync)(struct omap_overlay_manager *mgr);
 };
 
 struct omap_dss_device {
@@ -482,7 +483,6 @@ struct omap_dss_device {
 	int (*update)(struct omap_dss_device *dssdev,
 			       u16 x, u16 y, u16 w, u16 h);
 	int (*sync)(struct omap_dss_device *dssdev);
-	int (*wait_vsync)(struct omap_dss_device *dssdev);
 
 	int (*set_update_mode)(struct omap_dss_device *dssdev,
 			enum omap_dss_update_mode);
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index 5989afb..987a8ae 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -323,19 +323,6 @@ void default_get_overlay_fifo_thresholds(enum omap_plane plane,
 	*fifo_low = fifo_size - burst_size_bytes;
 }
 
-static int default_wait_vsync(struct omap_dss_device *dssdev)
-{
-	unsigned long timeout = msecs_to_jiffies(500);
-	u32 irq;
-
-	if (dssdev->type == OMAP_DISPLAY_TYPE_VENC)
-		irq = DISPC_IRQ_EVSYNC_ODD;
-	else
-		irq = DISPC_IRQ_VSYNC;
-
-	return omap_dispc_wait_for_irq_interruptible_timeout(irq, timeout);
-}
-
 static int default_get_recommended_bpp(struct omap_dss_device *dssdev)
 {
 	if (dssdev->panel.recommended_bpp)
@@ -427,7 +414,6 @@ void dss_init_device(struct platform_device *pdev,
 
 	dssdev->get_resolution = default_get_resolution;
 	dssdev->get_recommended_bpp = default_get_recommended_bpp;
-	dssdev->wait_vsync = default_wait_vsync;
 
 	switch (dssdev->type) {
 	case OMAP_DISPLAY_TYPE_DPI:
diff --git a/drivers/video/omap2/dss/manager.c b/drivers/video/omap2/dss/manager.c
index 27d9c46..486cd4a 100644
--- a/drivers/video/omap2/dss/manager.c
+++ b/drivers/video/omap2/dss/manager.c
@@ -501,6 +501,19 @@ static int omap_dss_unset_device(struct omap_overlay_manager *mgr)
 	return 0;
 }
 
+static int dss_mgr_wait_for_vsync(struct omap_overlay_manager *mgr)
+{
+	unsigned long timeout = msecs_to_jiffies(500);
+	u32 irq;
+
+	if (mgr->device->type == OMAP_DISPLAY_TYPE_VENC)
+		irq = DISPC_IRQ_EVSYNC_ODD;
+	else
+		irq = DISPC_IRQ_VSYNC;
+
+	return omap_dispc_wait_for_irq_interruptible_timeout(irq, timeout);
+}
+
 static int dss_mgr_wait_for_go(struct omap_overlay_manager *mgr)
 {
 	unsigned long timeout = msecs_to_jiffies(500);
@@ -1394,6 +1407,7 @@ int dss_init_overlay_managers(struct platform_device *pdev)
 		mgr->set_manager_info = &omap_dss_mgr_set_info;
 		mgr->get_manager_info = &omap_dss_mgr_get_info;
 		mgr->wait_for_go = &dss_mgr_wait_for_go;
+		mgr->wait_for_vsync = &dss_mgr_wait_for_vsync;
 
 		mgr->caps = OMAP_DSS_OVL_MGR_CAP_DISPC;
 
diff --git a/drivers/video/omap2/omapfb/omapfb-ioctl.c b/drivers/video/omap2/omapfb/omapfb-ioctl.c
index f3c9c80..4e1b0cc 100644
--- a/drivers/video/omap2/omapfb/omapfb-ioctl.c
+++ b/drivers/video/omap2/omapfb/omapfb-ioctl.c
@@ -700,7 +700,7 @@ int omapfb_ioctl(struct fb_info *fbi, unsigned int cmd, unsigned long arg)
 			break;
 		}
 
-		r = display->wait_vsync(display);
+		r = display->manager->wait_for_vsync(display->manager);
 		break;
 
 	case OMAPFB_WAITFORGO:
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 08/17] OMAP: DSS2: move enable/disable_channel to overlay manager
  2010-02-08 15:57             ` [PATCH 07/17] OMAP: DSS2: move wait_vsync() Tomi Valkeinen
@ 2010-02-08 15:57               ` Tomi Valkeinen
  2010-02-08 15:57                 ` [PATCH 09/17] OMAP: DSS2: move get_resolution() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move enable/disable_channel() from omap_dss_device to overlay manager.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    3 +++
 drivers/video/omap2/dss/dispc.c           |   24 ++++++++++++++++++++++--
 drivers/video/omap2/dss/dpi.c             |   14 +++++++-------
 drivers/video/omap2/dss/dsi.c             |    2 +-
 drivers/video/omap2/dss/dss.h             |    4 ++--
 drivers/video/omap2/dss/manager.c         |   17 ++++++++++++++++-
 drivers/video/omap2/dss/rfbi.c            |    2 +-
 drivers/video/omap2/dss/sdi.c             |   14 +++++++-------
 drivers/video/omap2/dss/venc.c            |    4 ++--
 9 files changed, 61 insertions(+), 23 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 2308912..df8277c 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -371,6 +371,9 @@ struct omap_overlay_manager {
 	int (*apply)(struct omap_overlay_manager *mgr);
 	int (*wait_for_go)(struct omap_overlay_manager *mgr);
 	int (*wait_for_vsync)(struct omap_overlay_manager *mgr);
+
+	int (*enable)(struct omap_overlay_manager *mgr);
+	int (*disable)(struct omap_overlay_manager *mgr);
 };
 
 struct omap_dss_device {
diff --git a/drivers/video/omap2/dss/dispc.c b/drivers/video/omap2/dss/dispc.c
index 7781c65..68edc32 100644
--- a/drivers/video/omap2/dss/dispc.c
+++ b/drivers/video/omap2/dss/dispc.c
@@ -1725,7 +1725,7 @@ static void _enable_lcd_out(bool enable)
 	REG_FLD_MOD(DISPC_CONTROL, enable ? 1 : 0, 0, 0);
 }
 
-void dispc_enable_lcd_out(bool enable)
+static void dispc_enable_lcd_out(bool enable)
 {
 	struct completion frame_done_completion;
 	bool is_on;
@@ -1772,7 +1772,7 @@ static void _enable_digit_out(bool enable)
 	REG_FLD_MOD(DISPC_CONTROL, enable ? 1 : 0, 1, 1);
 }
 
-void dispc_enable_digit_out(bool enable)
+static void dispc_enable_digit_out(bool enable)
 {
 	struct completion frame_done_completion;
 	int r;
@@ -1836,6 +1836,26 @@ void dispc_enable_digit_out(bool enable)
 	enable_clocks(0);
 }
 
+bool dispc_is_channel_enabled(enum omap_channel channel)
+{
+	if (channel == OMAP_DSS_CHANNEL_LCD)
+		return !!REG_GET(DISPC_CONTROL, 0, 0);
+	else if (channel == OMAP_DSS_CHANNEL_DIGIT)
+		return !!REG_GET(DISPC_CONTROL, 1, 1);
+	else
+		BUG();
+}
+
+void dispc_enable_channel(enum omap_channel channel, bool enable)
+{
+	if (channel == OMAP_DSS_CHANNEL_LCD)
+		dispc_enable_lcd_out(enable);
+	else if (channel == OMAP_DSS_CHANNEL_DIGIT)
+		dispc_enable_digit_out(enable);
+	else
+		BUG();
+}
+
 void dispc_lcd_enable_signal_polarity(bool act_high)
 {
 	enable_clocks(1);
diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c
index c5091ed..77b9557 100644
--- a/drivers/video/omap2/dss/dpi.c
+++ b/drivers/video/omap2/dss/dpi.c
@@ -194,7 +194,7 @@ static int dpi_display_enable(struct omap_dss_device *dssdev)
 
 	mdelay(2);
 
-	dispc_enable_lcd_out(1);
+	dssdev->manager->enable(dssdev->manager);
 
 	r = dssdev->driver->enable(dssdev);
 	if (r)
@@ -205,7 +205,7 @@ static int dpi_display_enable(struct omap_dss_device *dssdev)
 	return 0;
 
 err6:
-	dispc_enable_lcd_out(0);
+	dssdev->manager->disable(dssdev->manager);
 err5:
 #ifdef CONFIG_OMAP2_DSS_USE_DSI_PLL
 	dsi_pll_uninit();
@@ -235,7 +235,7 @@ static void dpi_display_disable(struct omap_dss_device *dssdev)
 
 	dssdev->driver->disable(dssdev);
 
-	dispc_enable_lcd_out(0);
+	dssdev->manager->disable(dssdev->manager);
 
 #ifdef CONFIG_OMAP2_DSS_USE_DSI_PLL
 	dss_select_dispc_clk_source(DSS_SRC_DSS1_ALWON_FCLK);
@@ -263,7 +263,7 @@ static int dpi_display_suspend(struct omap_dss_device *dssdev)
 	if (dssdev->driver->suspend)
 		dssdev->driver->suspend(dssdev);
 
-	dispc_enable_lcd_out(0);
+	dssdev->manager->disable(dssdev->manager);
 
 	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
 
@@ -292,7 +292,7 @@ static int dpi_display_resume(struct omap_dss_device *dssdev)
 
 	dss_clk_enable(DSS_CLK_ICK | DSS_CLK_FCK1);
 
-	dispc_enable_lcd_out(1);
+	dssdev->manager->enable(dssdev->manager);
 
 	if (dssdev->driver->resume)
 		dssdev->driver->resume(dssdev);
@@ -383,10 +383,10 @@ static int dpi_display_set_update_mode(struct omap_dss_device *dssdev,
 		return -EINVAL;
 
 	if (mode == OMAP_DSS_UPDATE_DISABLED) {
-		dispc_enable_lcd_out(0);
+		dssdev->manager->disable(dssdev->manager);
 		dpi.update_enabled = 0;
 	} else {
-		dispc_enable_lcd_out(1);
+		dssdev->manager->enable(dssdev->manager);
 		dpi.update_enabled = 1;
 	}
 
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index 8d6a436..e355517 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -3011,7 +3011,7 @@ static int dsi_update_thread(void *data)
 						x, y, w, h);
 
 				dispc_enable_sidle();
-				dispc_enable_lcd_out(0);
+				device->manager->disable(device->manager);
 
 				dsi_reset_tx_fifo(0);
 			} else {
diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h
index 3713dc6..24326a5 100644
--- a/drivers/video/omap2/dss/dss.h
+++ b/drivers/video/omap2/dss/dss.h
@@ -324,8 +324,8 @@ int dispc_setup_plane(enum omap_plane plane,
 
 bool dispc_go_busy(enum omap_channel channel);
 void dispc_go(enum omap_channel channel);
-void dispc_enable_lcd_out(bool enable);
-void dispc_enable_digit_out(bool enable);
+void dispc_enable_channel(enum omap_channel channel, bool enable);
+bool dispc_is_channel_enabled(enum omap_channel channel);
 int dispc_enable_plane(enum omap_plane plane, bool enable);
 void dispc_enable_replication(enum omap_plane plane, bool enable);
 
diff --git a/drivers/video/omap2/dss/manager.c b/drivers/video/omap2/dss/manager.c
index 486cd4a..4ede519 100644
--- a/drivers/video/omap2/dss/manager.c
+++ b/drivers/video/omap2/dss/manager.c
@@ -1077,7 +1077,7 @@ void dss_start_update(struct omap_dss_device *dssdev)
 		mc->shadow_dirty = false;
 	}
 
-	dispc_enable_lcd_out(1);
+	dssdev->manager->enable(dssdev->manager);
 }
 
 static void dss_apply_irq_handler(void *data, u32 mask)
@@ -1364,6 +1364,18 @@ static void omap_dss_mgr_get_info(struct omap_overlay_manager *mgr,
 	*info = mgr->info;
 }
 
+static int dss_mgr_enable(struct omap_overlay_manager *mgr)
+{
+	dispc_enable_channel(mgr->id, 1);
+	return 0;
+}
+
+static int dss_mgr_disable(struct omap_overlay_manager *mgr)
+{
+	dispc_enable_channel(mgr->id, 0);
+	return 0;
+}
+
 static void omap_dss_add_overlay_manager(struct omap_overlay_manager *manager)
 {
 	++num_managers;
@@ -1409,6 +1421,9 @@ int dss_init_overlay_managers(struct platform_device *pdev)
 		mgr->wait_for_go = &dss_mgr_wait_for_go;
 		mgr->wait_for_vsync = &dss_mgr_wait_for_vsync;
 
+		mgr->enable = &dss_mgr_enable;
+		mgr->disable = &dss_mgr_disable;
+
 		mgr->caps = OMAP_DSS_OVL_MGR_CAP_DISPC;
 
 		dss_overlay_setup_dispc_manager(mgr);
diff --git a/drivers/video/omap2/dss/rfbi.c b/drivers/video/omap2/dss/rfbi.c
index b936495..6b9cd76 100644
--- a/drivers/video/omap2/dss/rfbi.c
+++ b/drivers/video/omap2/dss/rfbi.c
@@ -382,7 +382,7 @@ void rfbi_transfer_area(u16 width, u16 height,
 
 	dispc_set_lcd_size(width, height);
 
-	dispc_enable_lcd_out(1);
+	dispc_enable_channel(OMAP_DSS_CHANNEL_LCD, true);
 
 	rfbi.framedone_callback = callback;
 	rfbi.framedone_callback_data = data;
diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c
index c24f307..5f852ed 100644
--- a/drivers/video/omap2/dss/sdi.c
+++ b/drivers/video/omap2/dss/sdi.c
@@ -119,7 +119,7 @@ static int sdi_display_enable(struct omap_dss_device *dssdev)
 		mdelay(2);
 	}
 
-	dispc_enable_lcd_out(1);
+	dssdev->manager->enable(dssdev->manager);
 
 	if (dssdev->driver->enable) {
 		r = dssdev->driver->enable(dssdev);
@@ -133,7 +133,7 @@ static int sdi_display_enable(struct omap_dss_device *dssdev)
 
 	return 0;
 err3:
-	dispc_enable_lcd_out(0);
+	dssdev->manager->disable(dssdev->manager);
 err2:
 	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
 err1:
@@ -156,7 +156,7 @@ static void sdi_display_disable(struct omap_dss_device *dssdev)
 	if (dssdev->driver->disable)
 		dssdev->driver->disable(dssdev);
 
-	dispc_enable_lcd_out(0);
+	dssdev->manager->disable(dssdev->manager);
 
 	dss_sdi_disable();
 
@@ -175,7 +175,7 @@ static int sdi_display_suspend(struct omap_dss_device *dssdev)
 	if (dssdev->driver->suspend)
 		dssdev->driver->suspend(dssdev);
 
-	dispc_enable_lcd_out(0);
+	dssdev->manager->disable(dssdev->manager);
 
 	dss_sdi_disable();
 
@@ -200,7 +200,7 @@ static int sdi_display_resume(struct omap_dss_device *dssdev)
 		goto err;
 	mdelay(2);
 
-	dispc_enable_lcd_out(1);
+	dssdev->manager->enable(dssdev->manager);
 
 	if (dssdev->driver->resume)
 		dssdev->driver->resume(dssdev);
@@ -220,10 +220,10 @@ static int sdi_display_set_update_mode(struct omap_dss_device *dssdev,
 		return -EINVAL;
 
 	if (mode == OMAP_DSS_UPDATE_DISABLED) {
-		dispc_enable_lcd_out(0);
+		dssdev->manager->disable(dssdev->manager);
 		sdi.update_enabled = 0;
 	} else {
-		dispc_enable_lcd_out(1);
+		dssdev->manager->enable(dssdev->manager);
 		sdi.update_enabled = 1;
 	}
 
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index 44b4998..4e6bd1d 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -538,7 +538,7 @@ static void venc_power_on(struct omap_dss_device *dssdev)
 	if (dssdev->platform_enable)
 		dssdev->platform_enable(dssdev);
 
-	dispc_enable_digit_out(1);
+	dssdev->manager->enable(dssdev->manager);
 }
 
 static void venc_power_off(struct omap_dss_device *dssdev)
@@ -546,7 +546,7 @@ static void venc_power_off(struct omap_dss_device *dssdev)
 	venc_write_reg(VENC_OUTPUT_CONTROL, 0);
 	dss_set_dac_pwrdn_bgz(0);
 
-	dispc_enable_digit_out(0);
+	dssdev->manager->disable(dssdev->manager);
 
 	if (dssdev->platform_disable)
 		dssdev->platform_disable(dssdev);
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 09/17] OMAP: DSS2: move get_resolution()
  2010-02-08 15:57               ` [PATCH 08/17] OMAP: DSS2: move enable/disable_channel to overlay manager Tomi Valkeinen
@ 2010-02-08 15:57                 ` Tomi Valkeinen
  2010-02-08 15:57                   ` [PATCH 10/17] OMAP: DSS2: move get_recommended_bpp() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move get_resolution() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    7 +++++--
 drivers/video/omap2/displays/panel-taal.c |    2 +-
 drivers/video/omap2/dss/core.c            |    4 ++++
 drivers/video/omap2/dss/display.c         |    4 ++--
 drivers/video/omap2/dss/dsi.c             |    4 ++--
 drivers/video/omap2/dss/overlay.c         |    2 +-
 drivers/video/omap2/dss/venc.c            |    2 ++
 drivers/video/omap2/omapfb/omapfb-ioctl.c |    2 +-
 drivers/video/omap2/omapfb/omapfb-main.c  |    9 +++++----
 9 files changed, 23 insertions(+), 13 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index df8277c..c66397f 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -473,8 +473,6 @@ struct omap_dss_device {
 	int (*suspend)(struct omap_dss_device *dssdev);
 	int (*resume)(struct omap_dss_device *dssdev);
 
-	void (*get_resolution)(struct omap_dss_device *dssdev,
-			u16 *xres, u16 *yres);
 	int (*get_recommended_bpp)(struct omap_dss_device *dssdev);
 
 	int (*check_timings)(struct omap_dss_device *dssdev,
@@ -532,6 +530,9 @@ struct omap_dss_driver {
 	int (*memory_read)(struct omap_dss_device *dssdev,
 			void *buf, size_t size,
 			u16 x, u16 y, u16 w, u16 h);
+
+	void (*get_resolution)(struct omap_dss_device *dssdev,
+			u16 *xres, u16 *yres);
 };
 
 int omap_dss_register_driver(struct omap_dss_driver *);
@@ -556,6 +557,8 @@ struct omap_overlay_manager *omap_dss_get_overlay_manager(int num);
 int omap_dss_get_num_overlays(void);
 struct omap_overlay *omap_dss_get_overlay(int num);
 
+void omapdss_default_get_resolution(struct omap_dss_device *dssdev,
+		u16 *xres, u16 *yres);
 typedef void (*omap_dispc_isr_t) (void *arg, u32 mask);
 int omap_dispc_register_isr(omap_dispc_isr_t isr, void *arg, u32 mask);
 int omap_dispc_unregister_isr(omap_dispc_isr_t isr, void *arg, u32 mask);
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index 8f90de0..11d69b6 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -517,7 +517,6 @@ static int taal_probe(struct omap_dss_device *dssdev)
 	dev_set_drvdata(&dssdev->dev, td);
 
 	dssdev->get_timings = taal_get_timings;
-	dssdev->get_resolution = taal_get_resolution;
 
 	/* if no platform set_backlight() defined, presume DSI backlight
 	 * control */
@@ -990,6 +989,7 @@ static struct omap_dss_driver taal_driver = {
 	.resume		= taal_resume,
 
 	.setup_update	= taal_setup_update,
+	.get_resolution	= taal_get_resolution,
 	.enable_te	= taal_enable_te,
 	.wait_for_te	= taal_wait_te,
 	.set_rotate	= taal_rotate,
diff --git a/drivers/video/omap2/dss/core.c b/drivers/video/omap2/dss/core.c
index 5939da9..67ea00d 100644
--- a/drivers/video/omap2/dss/core.c
+++ b/drivers/video/omap2/dss/core.c
@@ -811,6 +811,10 @@ int omap_dss_register_driver(struct omap_dss_driver *dssdriver)
 	dssdriver->driver.bus = &dss_bus_type;
 	dssdriver->driver.probe = dss_driver_probe;
 	dssdriver->driver.remove = dss_driver_remove;
+
+	if (dssdriver->get_resolution == NULL)
+		dssdriver->get_resolution = omapdss_default_get_resolution;
+
 	return driver_register(&dssdriver->driver);
 }
 EXPORT_SYMBOL(omap_dss_register_driver);
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index 987a8ae..6c34233 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -303,12 +303,13 @@ static struct device_attribute *display_sysfs_attrs[] = {
 	NULL
 };
 
-static void default_get_resolution(struct omap_dss_device *dssdev,
+void omapdss_default_get_resolution(struct omap_dss_device *dssdev,
 			u16 *xres, u16 *yres)
 {
 	*xres = dssdev->panel.timings.x_res;
 	*yres = dssdev->panel.timings.y_res;
 }
+EXPORT_SYMBOL(omapdss_default_get_resolution);
 
 void default_get_overlay_fifo_thresholds(enum omap_plane plane,
 		u32 fifo_size, enum omap_burst_size *burst_size,
@@ -412,7 +413,6 @@ void dss_init_device(struct platform_device *pdev,
 		return;
 	}
 
-	dssdev->get_resolution = default_get_resolution;
 	dssdev->get_recommended_bpp = default_get_recommended_bpp;
 
 	switch (dssdev->type) {
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index e355517..eab45b8 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -2866,7 +2866,7 @@ static int dsi_set_update_mode(struct omap_dss_device *dssdev,
 
 			DSSDBG("starting auto update\n");
 
-			dssdev->get_resolution(dssdev, &w, &h);
+			dssdev->driver->get_resolution(dssdev, &w, &h);
 
 			dsi_set_update_region(dssdev, 0, 0, w, h);
 
@@ -3420,7 +3420,7 @@ static int dsi_display_update(struct omap_dss_device *dssdev,
 	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
 		goto end;
 
-	dssdev->get_resolution(dssdev, &dw, &dh);
+	dssdev->driver->get_resolution(dssdev, &dw, &dh);
 
 	if  (x > dw || y > dh)
 		goto end;
diff --git a/drivers/video/omap2/dss/overlay.c b/drivers/video/omap2/dss/overlay.c
index b7f9a73..0c5bea2 100644
--- a/drivers/video/omap2/dss/overlay.c
+++ b/drivers/video/omap2/dss/overlay.c
@@ -350,7 +350,7 @@ int dss_check_overlay(struct omap_overlay *ovl, struct omap_dss_device *dssdev)
 		return -EINVAL;
 	}
 
-	dssdev->get_resolution(dssdev, &dw, &dh);
+	dssdev->driver->get_resolution(dssdev, &dw, &dh);
 
 	DSSDBG("check_overlay %d: (%d,%d %dx%d -> %dx%d) disp (%dx%d)\n",
 			ovl->id,
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index 4e6bd1d..65514f0 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -459,6 +459,8 @@ static struct omap_dss_driver venc_driver = {
 	.suspend	= venc_panel_suspend,
 	.resume		= venc_panel_resume,
 
+	.get_resolution	= omapdss_default_get_resolution,
+
 	.driver         = {
 		.name   = "venc",
 		.owner  = THIS_MODULE,
diff --git a/drivers/video/omap2/omapfb/omapfb-ioctl.c b/drivers/video/omap2/omapfb/omapfb-ioctl.c
index 4e1b0cc..e18a723 100644
--- a/drivers/video/omap2/omapfb/omapfb-ioctl.c
+++ b/drivers/video/omap2/omapfb/omapfb-ioctl.c
@@ -208,7 +208,7 @@ static int omapfb_update_window_nolock(struct fb_info *fbi,
 	if (w == 0 || h == 0)
 		return 0;
 
-	display->get_resolution(display, &dw, &dh);
+	display->driver->get_resolution(display, &dw, &dh);
 
 	if (x + w > dw || y + h > dh)
 		return -EINVAL;
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index d17caef..75d517e 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -1254,7 +1254,7 @@ exit:
 
 	if (r == 0 && do_update && display->update) {
 		u16 w, h;
-		display->get_resolution(display, &w, &h);
+		display->driver->get_resolution(display, &w, &h);
 
 		r = display->update(display, 0, 0, w, h);
 	}
@@ -1427,7 +1427,7 @@ static int omapfb_alloc_fbmem_display(struct fb_info *fbi, unsigned long size,
 	if (!size) {
 		u16 w, h;
 
-		display->get_resolution(display, &w, &h);
+		display->driver->get_resolution(display, &w, &h);
 
 		if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) {
 			size = max(omap_vrfb_min_phys_size(w, h, bytespp),
@@ -1745,7 +1745,7 @@ static int omapfb_fb_init(struct omapfb2_device *fbdev, struct fb_info *fbi)
 		u16 w, h;
 		int rotation = (var->rotate + ofbi->rotation[0]) % 4;
 
-		display->get_resolution(display, &w, &h);
+		display->driver->get_resolution(display, &w, &h);
 
 		if (rotation == FB_ROTATE_CW ||
 				rotation == FB_ROTATE_CCW) {
@@ -2190,7 +2190,8 @@ static int omapfb_probe(struct platform_device *pdev)
 				def_display->set_update_mode(def_display,
 						OMAP_DSS_UPDATE_MANUAL);
 
-			def_display->get_resolution(def_display, &w, &h);
+			def_display->driver->get_resolution(def_display,
+					&w, &h);
 			def_display->update(def_display, 0, 0, w, h);
 #endif
 		} else {
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 10/17] OMAP: DSS2: move get_recommended_bpp()
  2010-02-08 15:57                 ` [PATCH 09/17] OMAP: DSS2: move get_resolution() Tomi Valkeinen
@ 2010-02-08 15:57                   ` Tomi Valkeinen
  2010-02-08 15:57                     ` [PATCH 11/17] OMAP: DSS2: move enable/get_te() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move get_recommended_bpp() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    7 ++---
 drivers/video/omap2/displays/panel-taal.c |    2 +
 drivers/video/omap2/dss/core.c            |    3 ++
 drivers/video/omap2/dss/display.c         |    8 +-----
 drivers/video/omap2/dss/venc.c            |    1 +
 drivers/video/omap2/omapfb/omapfb-main.c  |   31 ++++++++++++++++++++++++----
 drivers/video/omap2/omapfb/omapfb.h       |    6 +++++
 7 files changed, 43 insertions(+), 15 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index c66397f..950d781 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -434,8 +434,6 @@ struct omap_dss_device {
 
 		enum omap_panel_config config;
 
-		u8 recommended_bpp;
-
 		struct omap_dss_device *ctrl;
 	} panel;
 
@@ -473,8 +471,6 @@ struct omap_dss_device {
 	int (*suspend)(struct omap_dss_device *dssdev);
 	int (*resume)(struct omap_dss_device *dssdev);
 
-	int (*get_recommended_bpp)(struct omap_dss_device *dssdev);
-
 	int (*check_timings)(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings);
 	void (*set_timings)(struct omap_dss_device *dssdev,
@@ -533,6 +529,7 @@ struct omap_dss_driver {
 
 	void (*get_resolution)(struct omap_dss_device *dssdev,
 			u16 *xres, u16 *yres);
+	int (*get_recommended_bpp)(struct omap_dss_device *dssdev);
 };
 
 int omap_dss_register_driver(struct omap_dss_driver *);
@@ -559,6 +556,8 @@ struct omap_overlay *omap_dss_get_overlay(int num);
 
 void omapdss_default_get_resolution(struct omap_dss_device *dssdev,
 		u16 *xres, u16 *yres);
+int omapdss_default_get_recommended_bpp(struct omap_dss_device *dssdev);
+
 typedef void (*omap_dispc_isr_t) (void *arg, u32 mask);
 int omap_dispc_register_isr(omap_dispc_isr_t isr, void *arg, u32 mask);
 int omap_dispc_unregister_isr(omap_dispc_isr_t isr, void *arg, u32 mask);
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index 11d69b6..e00502e 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -990,6 +990,8 @@ static struct omap_dss_driver taal_driver = {
 
 	.setup_update	= taal_setup_update,
 	.get_resolution	= taal_get_resolution,
+	.get_recommended_bpp = omapdss_default_get_recommended_bpp,
+
 	.enable_te	= taal_enable_te,
 	.wait_for_te	= taal_wait_te,
 	.set_rotate	= taal_rotate,
diff --git a/drivers/video/omap2/dss/core.c b/drivers/video/omap2/dss/core.c
index 67ea00d..991dd29 100644
--- a/drivers/video/omap2/dss/core.c
+++ b/drivers/video/omap2/dss/core.c
@@ -814,6 +814,9 @@ int omap_dss_register_driver(struct omap_dss_driver *dssdriver)
 
 	if (dssdriver->get_resolution == NULL)
 		dssdriver->get_resolution = omapdss_default_get_resolution;
+	if (dssdriver->get_recommended_bpp == NULL)
+		dssdriver->get_recommended_bpp =
+			omapdss_default_get_recommended_bpp;
 
 	return driver_register(&dssdriver->driver);
 }
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index 6c34233..c5fecee 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -324,11 +324,8 @@ void default_get_overlay_fifo_thresholds(enum omap_plane plane,
 	*fifo_low = fifo_size - burst_size_bytes;
 }
 
-static int default_get_recommended_bpp(struct omap_dss_device *dssdev)
+int omapdss_default_get_recommended_bpp(struct omap_dss_device *dssdev)
 {
-	if (dssdev->panel.recommended_bpp)
-		return dssdev->panel.recommended_bpp;
-
 	switch (dssdev->type) {
 	case OMAP_DISPLAY_TYPE_DPI:
 		if (dssdev->phy.dpi.data_lines == 24)
@@ -350,6 +347,7 @@ static int default_get_recommended_bpp(struct omap_dss_device *dssdev)
 		BUG();
 	}
 }
+EXPORT_SYMBOL(omapdss_default_get_recommended_bpp);
 
 /* Checks if replication logic should be used. Only use for active matrix,
  * when overlay is in RGB12U or RGB16 mode, and LCD interface is
@@ -413,8 +411,6 @@ void dss_init_device(struct platform_device *pdev,
 		return;
 	}
 
-	dssdev->get_recommended_bpp = default_get_recommended_bpp;
-
 	switch (dssdev->type) {
 	case OMAP_DISPLAY_TYPE_DPI:
 		r = dpi_init_display(dssdev);
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index 65514f0..d13071d 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -460,6 +460,7 @@ static struct omap_dss_driver venc_driver = {
 	.resume		= venc_panel_resume,
 
 	.get_resolution	= omapdss_default_get_resolution,
+	.get_recommended_bpp = omapdss_default_get_recommended_bpp,
 
 	.driver         = {
 		.name   = "venc",
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index 75d517e..f77256f 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -54,6 +54,8 @@ module_param_named(test, omapfb_test_pattern, bool, 0644);
 #endif
 
 static int omapfb_fb_init(struct omapfb2_device *fbdev, struct fb_info *fbi);
+static int omapfb_get_recommended_bpp(struct omapfb2_device *fbdev,
+		struct omap_dss_device *dssdev);
 
 #ifdef DEBUG
 static void draw_pixel(struct fb_info *fbi, int x, int y, unsigned color)
@@ -1404,6 +1406,7 @@ static int omapfb_alloc_fbmem_display(struct fb_info *fbi, unsigned long size,
 		unsigned long paddr)
 {
 	struct omapfb_info *ofbi = FB2OFB(fbi);
+	struct omapfb2_device *fbdev = ofbi->fbdev;
 	struct omap_dss_device *display;
 	int bytespp;
 
@@ -1412,7 +1415,7 @@ static int omapfb_alloc_fbmem_display(struct fb_info *fbi, unsigned long size,
 	if (!display)
 		return 0;
 
-	switch (display->get_recommended_bpp(display)) {
+	switch (omapfb_get_recommended_bpp(fbdev, display)) {
 	case 16:
 		bytespp = 2;
 		break;
@@ -1760,7 +1763,7 @@ static int omapfb_fb_init(struct omapfb2_device *fbdev, struct fb_info *fbi)
 		var->yres_virtual = var->yres;
 
 		if (!var->bits_per_pixel) {
-			switch (display->get_recommended_bpp(display)) {
+			switch (omapfb_get_recommended_bpp(fbdev, display)) {
 			case 16:
 				var->bits_per_pixel = 16;
 				break;
@@ -2011,7 +2014,8 @@ static int omapfb_mode_to_timings(const char *mode_str,
 	}
 }
 
-static int omapfb_set_def_mode(struct omap_dss_device *display, char *mode_str)
+static int omapfb_set_def_mode(struct omapfb2_device *fbdev,
+		struct omap_dss_device *display, char *mode_str)
 {
 	int r;
 	u8 bpp;
@@ -2021,7 +2025,9 @@ static int omapfb_set_def_mode(struct omap_dss_device *display, char *mode_str)
 	if (r)
 		return r;
 
-	display->panel.recommended_bpp = bpp;
+	fbdev->bpp_overrides[fbdev->num_bpp_overrides].dssdev = display;
+	fbdev->bpp_overrides[fbdev->num_bpp_overrides].bpp = bpp;
+	++fbdev->num_bpp_overrides;
 
 	if (!display->check_timings || !display->set_timings)
 		return -EINVAL;
@@ -2035,6 +2041,21 @@ static int omapfb_set_def_mode(struct omap_dss_device *display, char *mode_str)
 	return 0;
 }
 
+static int omapfb_get_recommended_bpp(struct omapfb2_device *fbdev,
+		struct omap_dss_device *dssdev)
+{
+	int i;
+
+	BUG_ON(dssdev->driver->get_recommended_bpp == NULL);
+
+	for (i = 0; i < fbdev->num_bpp_overrides; ++i) {
+		if (dssdev == fbdev->bpp_overrides[i].dssdev)
+			return fbdev->bpp_overrides[i].bpp;
+	}
+
+	return dssdev->driver->get_recommended_bpp(dssdev);
+}
+
 static int omapfb_parse_def_modes(struct omapfb2_device *fbdev)
 {
 	char *str, *options, *this_opt;
@@ -2073,7 +2094,7 @@ static int omapfb_parse_def_modes(struct omapfb2_device *fbdev)
 			break;
 		}
 
-		r = omapfb_set_def_mode(display, mode_str);
+		r = omapfb_set_def_mode(fbdev, display, mode_str);
 		if (r)
 			break;
 	}
diff --git a/drivers/video/omap2/omapfb/omapfb.h b/drivers/video/omap2/omapfb/omapfb.h
index 4ae0b64..cd54fdb 100644
--- a/drivers/video/omap2/omapfb/omapfb.h
+++ b/drivers/video/omap2/omapfb/omapfb.h
@@ -83,6 +83,12 @@ struct omapfb2_device {
 	struct omap_overlay *overlays[10];
 	unsigned num_managers;
 	struct omap_overlay_manager *managers[10];
+
+	unsigned num_bpp_overrides;
+	struct {
+		struct omap_dss_device *dssdev;
+		u8 bpp;
+	} bpp_overrides[10];
 };
 
 struct omapfb_colormode {
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 11/17] OMAP: DSS2: move enable/get_te()
  2010-02-08 15:57                   ` [PATCH 10/17] OMAP: DSS2: move get_recommended_bpp() Tomi Valkeinen
@ 2010-02-08 15:57                     ` Tomi Valkeinen
  2010-02-08 15:57                       ` [PATCH 12/17] OMAP: DSS2: move set/get_update_mode() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move enable/get_te() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    5 +--
 drivers/video/omap2/displays/panel-taal.c |   18 ++++++++++
 drivers/video/omap2/dss/display.c         |    7 ++--
 drivers/video/omap2/dss/dsi.c             |   53 ++---------------------------
 drivers/video/omap2/dss/rfbi.c            |    7 ----
 drivers/video/omap2/omapfb/omapfb-ioctl.c |    5 ++-
 drivers/video/omap2/omapfb/omapfb-main.c  |    4 +-
 7 files changed, 32 insertions(+), 67 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 950d781..d9829f1 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -486,9 +486,6 @@ struct omap_dss_device {
 	enum omap_dss_update_mode (*get_update_mode)
 		(struct omap_dss_device *dssdev);
 
-	int (*enable_te)(struct omap_dss_device *dssdev, bool enable);
-	int (*get_te)(struct omap_dss_device *dssdev);
-
 	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
 	u32 (*get_wss)(struct omap_dss_device *dssdev);
 
@@ -516,6 +513,7 @@ struct omap_dss_driver {
 
 	int (*enable_te)(struct omap_dss_device *dssdev, bool enable);
 	int (*wait_for_te)(struct omap_dss_device *dssdev);
+	int (*get_te)(struct omap_dss_device *dssdev);
 
 	u8 (*get_rotate)(struct omap_dss_device *dssdev);
 	int (*set_rotate)(struct omap_dss_device *dssdev, u8 rotate);
@@ -570,5 +568,6 @@ int omap_dispc_wait_for_irq_interruptible_timeout(u32 irqmask,
 #define to_dss_device(x) container_of((x), struct omap_dss_device, dev)
 
 void omapdss_dsi_vc_enable_hs(int channel, bool enable);
+int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable);
 
 #endif
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index e00502e..af4b0b0 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -736,6 +736,8 @@ static int taal_enable_te(struct omap_dss_device *dssdev, bool enable)
 	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
 	int r;
 
+	dsi_bus_lock();
+
 	td->te_enabled = enable;
 
 	if (enable)
@@ -743,9 +745,23 @@ static int taal_enable_te(struct omap_dss_device *dssdev, bool enable)
 	else
 		r = taal_dcs_write_0(DCS_TEAR_OFF);
 
+	omapdss_dsi_enable_te(dssdev, enable);
+
+	/* XXX for some reason, DSI TE breaks if we don't wait here.
+	 * Panel bug? Needs more studying */
+	msleep(100);
+
+	dsi_bus_unlock();
+
 	return r;
 }
 
+static int taal_get_te(struct omap_dss_device *dssdev)
+{
+	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
+	return td->te_enabled;
+}
+
 static int taal_wait_te(struct omap_dss_device *dssdev)
 {
 	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
@@ -993,7 +1009,9 @@ static struct omap_dss_driver taal_driver = {
 	.get_recommended_bpp = omapdss_default_get_recommended_bpp,
 
 	.enable_te	= taal_enable_te,
+	.get_te		= taal_get_te,
 	.wait_for_te	= taal_wait_te,
+
 	.set_rotate	= taal_rotate,
 	.get_rotate	= taal_get_rotate,
 	.set_mirror	= taal_mirror,
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index c5fecee..4c40300 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -106,7 +106,8 @@ static ssize_t display_tear_show(struct device *dev,
 {
 	struct omap_dss_device *dssdev = to_dss_device(dev);
 	return snprintf(buf, PAGE_SIZE, "%d\n",
-			dssdev->get_te ? dssdev->get_te(dssdev) : 0);
+			dssdev->driver->get_te ?
+			dssdev->driver->get_te(dssdev) : 0);
 }
 
 static ssize_t display_tear_store(struct device *dev,
@@ -116,12 +117,12 @@ static ssize_t display_tear_store(struct device *dev,
 	unsigned long te;
 	int r;
 
-	if (!dssdev->enable_te || !dssdev->get_te)
+	if (!dssdev->driver->enable_te || !dssdev->driver->get_te)
 		return -ENOENT;
 
 	te = simple_strtoul(buf, NULL, 0);
 
-	r = dssdev->enable_te(dssdev, te);
+	r = dssdev->driver->enable_te(dssdev, te);
 	if (r)
 		return r;
 
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index eab45b8..4b885a4 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -2877,20 +2877,6 @@ static int dsi_set_update_mode(struct omap_dss_device *dssdev,
 	return r;
 }
 
-static int dsi_set_te(struct omap_dss_device *dssdev, bool enable)
-{
-	int r = 0;
-
-	if (dssdev->driver->enable_te) {
-		r = dssdev->driver->enable_te(dssdev, enable);
-		/* XXX for some reason, DSI TE breaks if we don't wait here.
-		 * Panel bug? Needs more studying */
-		msleep(100);
-	}
-
-	return r;
-}
-
 static void dsi_handle_framedone(void)
 {
 	int r;
@@ -3265,9 +3251,6 @@ static int dsi_display_enable(struct omap_dss_device *dssdev)
 	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
 
 	dsi.use_ext_te = dssdev->phy.dsi.ext_te;
-	r = dsi_set_te(dssdev, dsi.te_enabled);
-	if (r)
-		goto err4;
 
 	dsi_set_update_mode(dssdev, dsi.user_update_mode);
 
@@ -3276,9 +3259,6 @@ static int dsi_display_enable(struct omap_dss_device *dssdev)
 
 	return 0;
 
-err4:
-
-	dsi_display_uninit_dsi(dssdev);
 err3:
 	dsi_display_uninit_dispc(dssdev);
 err2:
@@ -3381,10 +3361,6 @@ static int dsi_display_resume(struct omap_dss_device *dssdev)
 
 	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
 
-	r = dsi_set_te(dssdev, dsi.te_enabled);
-	if (r)
-		goto err2;
-
 	dsi_set_update_mode(dssdev, dsi.user_update_mode);
 
 	dsi_bus_unlock();
@@ -3502,33 +3478,12 @@ static enum omap_dss_update_mode dsi_display_get_update_mode(
 }
 
 
-static int dsi_display_enable_te(struct omap_dss_device *dssdev, bool enable)
+int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable)
 {
-	int r = 0;
-
-	DSSDBGF("%d", enable);
-
-	if (!dssdev->driver->enable_te)
-		return -ENOENT;
-
-	dsi_bus_lock();
-
 	dsi.te_enabled = enable;
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
-		goto end;
-
-	r = dsi_set_te(dssdev, enable);
-end:
-	dsi_bus_unlock();
-
-	return r;
-}
-
-static int dsi_display_get_te(struct omap_dss_device *dssdev)
-{
-	return dsi.te_enabled;
+	return 0;
 }
+EXPORT_SYMBOL(omapdss_dsi_enable_te);
 
 void dsi_get_overlay_fifo_thresholds(enum omap_plane plane,
 		u32 fifo_size, enum omap_burst_size *burst_size,
@@ -3555,8 +3510,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 	dssdev->sync = dsi_display_sync;
 	dssdev->set_update_mode = dsi_display_set_update_mode;
 	dssdev->get_update_mode = dsi_display_get_update_mode;
-	dssdev->enable_te = dsi_display_enable_te;
-	dssdev->get_te = dsi_display_get_te;
 
 	/* XXX these should be figured out dynamically */
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
diff --git a/drivers/video/omap2/dss/rfbi.c b/drivers/video/omap2/dss/rfbi.c
index 6b9cd76..7129387 100644
--- a/drivers/video/omap2/dss/rfbi.c
+++ b/drivers/video/omap2/dss/rfbi.c
@@ -1232,12 +1232,6 @@ static int rfbi_display_sync(struct omap_dss_device *dssdev)
 	return 0;
 }
 
-static int rfbi_display_enable_te(struct omap_dss_device *dssdev, bool enable)
-{
-	dssdev->driver->enable_te(dssdev, enable);
-	return 0;
-}
-
 static int rfbi_display_enable(struct omap_dss_device *dssdev)
 {
 	int r;
@@ -1299,7 +1293,6 @@ int rfbi_init_display(struct omap_dss_device *dssdev)
 	dssdev->disable = rfbi_display_disable;
 	dssdev->update = rfbi_display_update;
 	dssdev->sync = rfbi_display_sync;
-	dssdev->enable_te = rfbi_display_enable_te;
 
 	rfbi.dssdev[dssdev->phy.rfbi.channel] = dssdev;
 
diff --git a/drivers/video/omap2/omapfb/omapfb-ioctl.c b/drivers/video/omap2/omapfb/omapfb-ioctl.c
index e18a723..86467f8 100644
--- a/drivers/video/omap2/omapfb/omapfb-ioctl.c
+++ b/drivers/video/omap2/omapfb/omapfb-ioctl.c
@@ -783,12 +783,13 @@ int omapfb_ioctl(struct fb_info *fbi, unsigned int cmd, unsigned long arg)
 			break;
 		}
 
-		if (!display->enable_te) {
+		if (!display->driver->enable_te) {
 			r = -ENODEV;
 			break;
 		}
 
-		r = display->enable_te(display, !!p.tearsync_info.enabled);
+		r = display->driver->enable_te(display,
+				!!p.tearsync_info.enabled);
 
 		break;
 	}
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index f77256f..fff687b 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -2205,8 +2205,8 @@ static int omapfb_probe(struct platform_device *pdev)
 				def_display->set_update_mode(def_display,
 						OMAP_DSS_UPDATE_AUTO);
 #else /* MANUAL_UPDATE */
-			if (def_display->enable_te)
-				def_display->enable_te(def_display, 0);
+			if (def_display->driver->enable_te)
+				def_display->driver->enable_te(def_display, 0);
 			if (def_display->set_update_mode)
 				def_display->set_update_mode(def_display,
 						OMAP_DSS_UPDATE_MANUAL);
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 12/17] OMAP: DSS2: move set/get_update_mode()
  2010-02-08 15:57                     ` [PATCH 11/17] OMAP: DSS2: move enable/get_te() Tomi Valkeinen
@ 2010-02-08 15:57                       ` Tomi Valkeinen
  2010-02-08 15:57                         ` [PATCH 13/17] OMAP: DSS2: move update() and sync() Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move set/get_update_mode() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    9 +-
 drivers/video/omap2/displays/panel-taal.c |   16 ++++
 drivers/video/omap2/dss/display.c         |    6 +-
 drivers/video/omap2/dss/dpi.c             |   27 -------
 drivers/video/omap2/dss/dsi.c             |  115 +++--------------------------
 drivers/video/omap2/dss/manager.c         |   17 +++--
 drivers/video/omap2/dss/sdi.c             |   26 -------
 drivers/video/omap2/dss/venc.c            |   27 ++++---
 drivers/video/omap2/omapfb/omapfb-ioctl.c |   13 ++-
 drivers/video/omap2/omapfb/omapfb-main.c  |   19 +++--
 10 files changed, 80 insertions(+), 195 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index d9829f1..7e46a5d 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -481,11 +481,6 @@ struct omap_dss_device {
 			       u16 x, u16 y, u16 w, u16 h);
 	int (*sync)(struct omap_dss_device *dssdev);
 
-	int (*set_update_mode)(struct omap_dss_device *dssdev,
-			enum omap_dss_update_mode);
-	enum omap_dss_update_mode (*get_update_mode)
-		(struct omap_dss_device *dssdev);
-
 	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
 	u32 (*get_wss)(struct omap_dss_device *dssdev);
 
@@ -510,6 +505,10 @@ struct omap_dss_driver {
 
 	void (*setup_update)(struct omap_dss_device *dssdev,
 			u16 x, u16 y, u16 w, u16 h);
+	int (*set_update_mode)(struct omap_dss_device *dssdev,
+			enum omap_dss_update_mode);
+	enum omap_dss_update_mode (*get_update_mode)(
+			struct omap_dss_device *dssdev);
 
 	int (*enable_te)(struct omap_dss_device *dssdev, bool enable);
 	int (*wait_for_te)(struct omap_dss_device *dssdev);
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index af4b0b0..4ccb583 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -995,6 +995,20 @@ err:
 	queue_delayed_work(td->esd_wq, &td->esd_work, TAAL_ESD_CHECK_PERIOD);
 }
 
+static int taal_set_update_mode(struct omap_dss_device *dssdev,
+		enum omap_dss_update_mode mode)
+{
+	if (mode != OMAP_DSS_UPDATE_MANUAL)
+		return -EINVAL;
+	return 0;
+}
+
+static enum omap_dss_update_mode taal_get_update_mode(
+		struct omap_dss_device *dssdev)
+{
+	return OMAP_DSS_UPDATE_MANUAL;
+}
+
 static struct omap_dss_driver taal_driver = {
 	.probe		= taal_probe,
 	.remove		= taal_remove,
@@ -1005,6 +1019,8 @@ static struct omap_dss_driver taal_driver = {
 	.resume		= taal_resume,
 
 	.setup_update	= taal_setup_update,
+	.set_update_mode = taal_set_update_mode,
+	.get_update_mode = taal_get_update_mode,
 	.get_resolution	= taal_get_resolution,
 	.get_recommended_bpp = omapdss_default_get_recommended_bpp,
 
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index 4c40300..dba33cd 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -69,8 +69,8 @@ static ssize_t display_upd_mode_show(struct device *dev,
 {
 	struct omap_dss_device *dssdev = to_dss_device(dev);
 	enum omap_dss_update_mode mode = OMAP_DSS_UPDATE_AUTO;
-	if (dssdev->get_update_mode)
-		mode = dssdev->get_update_mode(dssdev);
+	if (dssdev->driver->get_update_mode)
+		mode = dssdev->driver->get_update_mode(dssdev);
 	return snprintf(buf, PAGE_SIZE, "%d\n", mode);
 }
 
@@ -94,7 +94,7 @@ static ssize_t display_upd_mode_store(struct device *dev,
 		return -EINVAL;
 	}
 
-	r = dssdev->set_update_mode(dssdev, mode);
+	r = dssdev->driver->set_update_mode(dssdev, mode);
 	if (r)
 		return r;
 
diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c
index 77b9557..48ff7ea 100644
--- a/drivers/video/omap2/dss/dpi.c
+++ b/drivers/video/omap2/dss/dpi.c
@@ -36,7 +36,6 @@
 #include "dss.h"
 
 static struct {
-	int update_enabled;
 	struct regulator *vdds_dsi_reg;
 } dpi;
 
@@ -376,30 +375,6 @@ static void dpi_get_timings(struct omap_dss_device *dssdev,
 	*timings = dssdev->panel.timings;
 }
 
-static int dpi_display_set_update_mode(struct omap_dss_device *dssdev,
-		enum omap_dss_update_mode mode)
-{
-	if (mode == OMAP_DSS_UPDATE_MANUAL)
-		return -EINVAL;
-
-	if (mode == OMAP_DSS_UPDATE_DISABLED) {
-		dssdev->manager->disable(dssdev->manager);
-		dpi.update_enabled = 0;
-	} else {
-		dssdev->manager->enable(dssdev->manager);
-		dpi.update_enabled = 1;
-	}
-
-	return 0;
-}
-
-static enum omap_dss_update_mode dpi_display_get_update_mode(
-		struct omap_dss_device *dssdev)
-{
-	return dpi.update_enabled ? OMAP_DSS_UPDATE_AUTO :
-		OMAP_DSS_UPDATE_DISABLED;
-}
-
 int dpi_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("init_display\n");
@@ -411,8 +386,6 @@ int dpi_init_display(struct omap_dss_device *dssdev)
 	dssdev->set_timings = dpi_set_timings;
 	dssdev->check_timings = dpi_check_timings;
 	dssdev->get_timings = dpi_get_timings;
-	dssdev->set_update_mode = dpi_display_set_update_mode;
-	dssdev->get_update_mode = dpi_display_get_update_mode;
 
 	return 0;
 }
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index 4b885a4..aa5d0fd 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -243,8 +243,6 @@ static struct
 	struct dsi_update_region active_update_region;
 	struct completion update_completion;
 
-	enum omap_dss_update_mode user_update_mode;
-	enum omap_dss_update_mode update_mode;
 	bool te_enabled;
 	bool use_ext_te;
 
@@ -345,9 +343,6 @@ static void dsi_perf_show(const char *name)
 	if (!dsi_perf)
 		return;
 
-	if (dsi.update_mode == OMAP_DSS_UPDATE_DISABLED)
-		return;
-
 	t = ktime_get();
 
 	setup_time = ktime_sub(dsi.perf_start_time, dsi.perf_setup_time);
@@ -1702,9 +1697,8 @@ static int dsi_force_tx_stop_mode_io(void)
 
 static int dsi_vc_enable(int channel, bool enable)
 {
-	if (dsi.update_mode != OMAP_DSS_UPDATE_AUTO)
-		DSSDBG("dsi_vc_enable channel %d, enable %d\n",
-				channel, enable);
+	DSSDBG("dsi_vc_enable channel %d, enable %d\n",
+			channel, enable);
 
 	enable = enable ? 1 : 0;
 
@@ -1884,8 +1878,7 @@ static u16 dsi_vc_flush_receive_data(int channel)
 
 static int dsi_vc_send_bta(int channel)
 {
-	if (dsi.update_mode != OMAP_DSS_UPDATE_AUTO &&
-			(dsi.debug_write || dsi.debug_read))
+	if (dsi.debug_write || dsi.debug_read)
 		DSSDBG("dsi_vc_send_bta %d\n", channel);
 
 	WARN_ON(!dsi_bus_is_locked());
@@ -2738,9 +2731,8 @@ static void dsi_update_screen_dispc(struct omap_dss_device *dssdev,
 
 	use_te_trigger = dsi.te_enabled && !dsi.use_ext_te;
 
-	if (dsi.update_mode != OMAP_DSS_UPDATE_AUTO)
-		DSSDBG("dsi_update_screen_dispc(%d,%d %dx%d)\n",
-				x, y, w, h);
+	DSSDBG("dsi_update_screen_dispc(%d,%d %dx%d)\n",
+			x, y, w, h);
 
 	bytespp	= dssdev->ctrl.pixel_size / 8;
 	bytespl = w * bytespp;
@@ -2838,45 +2830,6 @@ static void dsi_set_update_region(struct omap_dss_device *dssdev,
 
 }
 
-static int dsi_set_update_mode(struct omap_dss_device *dssdev,
-		enum omap_dss_update_mode mode)
-{
-	int r = 0;
-	int i;
-
-	WARN_ON(!dsi_bus_is_locked());
-
-	if (dsi.update_mode != mode) {
-		dsi.update_mode = mode;
-
-		/* Mark the overlays dirty, and do apply(), so that we get the
-		 * overlays configured properly after update mode change. */
-		for (i = 0; i < omap_dss_get_num_overlays(); ++i) {
-			struct omap_overlay *ovl;
-			ovl = omap_dss_get_overlay(i);
-			if (ovl->manager == dssdev->manager)
-				ovl->info_dirty = true;
-		}
-
-		r = dssdev->manager->apply(dssdev->manager);
-
-		if (dssdev->state == OMAP_DSS_DISPLAY_ACTIVE &&
-				mode == OMAP_DSS_UPDATE_AUTO) {
-			u16 w, h;
-
-			DSSDBG("starting auto update\n");
-
-			dssdev->driver->get_resolution(dssdev, &w, &h);
-
-			dsi_set_update_region(dssdev, 0, 0, w, h);
-
-			wake_up(&dsi.waitqueue);
-		}
-	}
-
-	return r;
-}
-
 static void dsi_handle_framedone(void)
 {
 	int r;
@@ -2885,8 +2838,7 @@ static void dsi_handle_framedone(void)
 
 	use_te_trigger = dsi.te_enabled && !dsi.use_ext_te;
 
-	if (dsi.update_mode != OMAP_DSS_UPDATE_AUTO)
-		DSSDBG("FRAMEDONE\n");
+	DSSDBG("FRAMEDONE\n");
 
 	if (use_te_trigger) {
 		/* enable LP_RX_TO again after the TE */
@@ -2925,9 +2877,7 @@ static int dsi_update_thread(void *data)
 
 	while (1) {
 		wait_event_interruptible(dsi.waitqueue,
-				dsi.update_mode == OMAP_DSS_UPDATE_AUTO ||
-				(dsi.update_mode == OMAP_DSS_UPDATE_MANUAL &&
-				 dsi.update_region.dirty == true) ||
+				dsi.update_region.dirty == true ||
 				kthread_should_stop());
 
 		if (kthread_should_stop())
@@ -2935,8 +2885,7 @@ static int dsi_update_thread(void *data)
 
 		dsi_bus_lock();
 
-		if (dsi.update_mode == OMAP_DSS_UPDATE_DISABLED ||
-				kthread_should_stop()) {
+		if (kthread_should_stop()) {
 			dsi_bus_unlock();
 			break;
 		}
@@ -2958,9 +2907,8 @@ static int dsi_update_thread(void *data)
 
 		if (device->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
 
-			if (dsi.update_mode == OMAP_DSS_UPDATE_MANUAL)
-				dss_setup_partial_planes(device,
-						&x, &y, &w, &h);
+			dss_setup_partial_planes(device,
+					&x, &y, &w, &h);
 
 			dispc_set_lcd_size(w, h);
 		}
@@ -3252,8 +3200,6 @@ static int dsi_display_enable(struct omap_dss_device *dssdev)
 
 	dsi.use_ext_te = dssdev->phy.dsi.ext_te;
 
-	dsi_set_update_mode(dssdev, dsi.user_update_mode);
-
 	dsi_bus_unlock();
 	mutex_unlock(&dsi.lock);
 
@@ -3284,7 +3230,6 @@ static void dsi_display_disable(struct omap_dss_device *dssdev)
 			dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED)
 		goto end;
 
-	dsi.update_mode = OMAP_DSS_UPDATE_DISABLED;
 	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
 
 	dsi_display_uninit_dispc(dssdev);
@@ -3311,7 +3256,6 @@ static int dsi_display_suspend(struct omap_dss_device *dssdev)
 			dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED)
 		goto end;
 
-	dsi.update_mode = OMAP_DSS_UPDATE_DISABLED;
 	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 
 	dsi_display_uninit_dispc(dssdev);
@@ -3361,8 +3305,6 @@ static int dsi_display_resume(struct omap_dss_device *dssdev)
 
 	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
 
-	dsi_set_update_mode(dssdev, dsi.user_update_mode);
-
 	dsi_bus_unlock();
 	mutex_unlock(&dsi.lock);
 
@@ -3390,9 +3332,6 @@ static int dsi_display_update(struct omap_dss_device *dssdev,
 
 	mutex_lock(&dsi.lock);
 
-	if (dsi.update_mode != OMAP_DSS_UPDATE_MANUAL)
-		goto end;
-
 	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
 		goto end;
 
@@ -3434,8 +3373,7 @@ static int dsi_display_sync(struct omap_dss_device *dssdev)
 	mutex_lock(&dsi.lock);
 	dsi_bus_lock();
 
-	if (dsi.update_mode == OMAP_DSS_UPDATE_MANUAL &&
-			dsi.update_region.dirty) {
+	if (dsi.update_region.dirty) {
 		INIT_COMPLETION(dsi.update_completion);
 		wait = true;
 	} else {
@@ -3452,32 +3390,6 @@ static int dsi_display_sync(struct omap_dss_device *dssdev)
 	return 0;
 }
 
-static int dsi_display_set_update_mode(struct omap_dss_device *dssdev,
-		enum omap_dss_update_mode mode)
-{
-	int r = 0;
-
-	DSSDBGF("%d", mode);
-
-	mutex_lock(&dsi.lock);
-	dsi_bus_lock();
-
-	dsi.user_update_mode = mode;
-	r = dsi_set_update_mode(dssdev, mode);
-
-	dsi_bus_unlock();
-	mutex_unlock(&dsi.lock);
-
-	return r;
-}
-
-static enum omap_dss_update_mode dsi_display_get_update_mode(
-		struct omap_dss_device *dssdev)
-{
-	return dsi.update_mode;
-}
-
-
 int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable)
 {
 	dsi.te_enabled = enable;
@@ -3508,8 +3420,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 	dssdev->resume = dsi_display_resume;
 	dssdev->update = dsi_display_update;
 	dssdev->sync = dsi_display_sync;
-	dssdev->set_update_mode = dsi_display_set_update_mode;
-	dssdev->get_update_mode = dsi_display_get_update_mode;
 
 	/* XXX these should be figured out dynamically */
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
@@ -3560,9 +3470,6 @@ int dsi_init(struct platform_device *pdev)
 	dsi.te_timer.data = 0;
 #endif
 
-	dsi.update_mode = OMAP_DSS_UPDATE_DISABLED;
-	dsi.user_update_mode = OMAP_DSS_UPDATE_DISABLED;
-
 	dsi.base = ioremap(DSI_BASE, DSI_SZ_REGS);
 	if (!dsi.base) {
 		DSSERR("can't ioremap DSI\n");
diff --git a/drivers/video/omap2/dss/manager.c b/drivers/video/omap2/dss/manager.c
index 4ede519..913142d 100644
--- a/drivers/video/omap2/dss/manager.c
+++ b/drivers/video/omap2/dss/manager.c
@@ -522,17 +522,18 @@ static int dss_mgr_wait_for_go(struct omap_overlay_manager *mgr)
 	u32 irq;
 	int r;
 	int i;
+	struct omap_dss_device *dssdev = mgr->device;
 
-	if (!mgr->device)
+	if (!dssdev)
 		return 0;
 
-	if (mgr->device->type == OMAP_DISPLAY_TYPE_VENC) {
+	if (dssdev->type == OMAP_DISPLAY_TYPE_VENC) {
 		irq = DISPC_IRQ_EVSYNC_ODD | DISPC_IRQ_EVSYNC_EVEN;
 		channel = OMAP_DSS_CHANNEL_DIGIT;
 	} else {
-		if (mgr->device->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE) {
+		if (dssdev->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE) {
 			enum omap_dss_update_mode mode;
-			mode = mgr->device->get_update_mode(mgr->device);
+			mode = dssdev->driver->get_update_mode(dssdev);
 			if (mode != OMAP_DSS_UPDATE_AUTO)
 				return 0;
 
@@ -605,7 +606,7 @@ int dss_mgr_wait_for_go_ovl(struct omap_overlay *ovl)
 	} else {
 		if (dssdev->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE) {
 			enum omap_dss_update_mode mode;
-			mode = dssdev->get_update_mode(dssdev);
+			mode = dssdev->driver->get_update_mode(dssdev);
 			if (mode != OMAP_DSS_UPDATE_AUTO)
 				return 0;
 
@@ -1209,7 +1210,8 @@ static int omap_dss_mgr_apply(struct omap_overlay_manager *mgr)
 
 		oc->manual_update =
 			dssdev->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE &&
-			dssdev->get_update_mode(dssdev) != OMAP_DSS_UPDATE_AUTO;
+			dssdev->driver->get_update_mode(dssdev) !=
+				OMAP_DSS_UPDATE_AUTO;
 
 		++num_planes_enabled;
 	}
@@ -1250,7 +1252,8 @@ static int omap_dss_mgr_apply(struct omap_overlay_manager *mgr)
 
 		mc->manual_update =
 			dssdev->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE &&
-			dssdev->get_update_mode(dssdev) != OMAP_DSS_UPDATE_AUTO;
+			dssdev->driver->get_update_mode(dssdev) !=
+				OMAP_DSS_UPDATE_AUTO;
 	}
 
 	/* XXX TODO: Try to get fifomerge working. The problem is that it
diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c
index 5f852ed..6bd9b0c 100644
--- a/drivers/video/omap2/dss/sdi.c
+++ b/drivers/video/omap2/dss/sdi.c
@@ -213,30 +213,6 @@ err:
 	return r;
 }
 
-static int sdi_display_set_update_mode(struct omap_dss_device *dssdev,
-		enum omap_dss_update_mode mode)
-{
-	if (mode == OMAP_DSS_UPDATE_MANUAL)
-		return -EINVAL;
-
-	if (mode == OMAP_DSS_UPDATE_DISABLED) {
-		dssdev->manager->disable(dssdev->manager);
-		sdi.update_enabled = 0;
-	} else {
-		dssdev->manager->enable(dssdev->manager);
-		sdi.update_enabled = 1;
-	}
-
-	return 0;
-}
-
-static enum omap_dss_update_mode sdi_display_get_update_mode(
-		struct omap_dss_device *dssdev)
-{
-	return sdi.update_enabled ? OMAP_DSS_UPDATE_AUTO :
-		OMAP_DSS_UPDATE_DISABLED;
-}
-
 static void sdi_get_timings(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings)
 {
@@ -251,8 +227,6 @@ int sdi_init_display(struct omap_dss_device *dssdev)
 	dssdev->disable = sdi_display_disable;
 	dssdev->suspend = sdi_display_suspend;
 	dssdev->resume = sdi_display_resume;
-	dssdev->set_update_mode = sdi_display_set_update_mode;
-	dssdev->get_update_mode = sdi_display_get_update_mode;
 	dssdev->get_timings = sdi_get_timings;
 
 	return 0;
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index d13071d..0d0dc94 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -450,6 +450,20 @@ static int venc_panel_resume(struct omap_dss_device *dssdev)
 	return venc_panel_enable(dssdev);
 }
 
+static enum omap_dss_update_mode venc_get_update_mode(
+		struct omap_dss_device *dssdev)
+{
+	return OMAP_DSS_UPDATE_AUTO;
+}
+
+static int venc_set_update_mode(struct omap_dss_device *dssdev,
+		enum omap_dss_update_mode mode)
+{
+	if (mode != OMAP_DSS_UPDATE_AUTO)
+		return -EINVAL;
+	return 0;
+}
+
 static struct omap_dss_driver venc_driver = {
 	.probe		= venc_panel_probe,
 	.remove		= venc_panel_remove,
@@ -462,6 +476,9 @@ static struct omap_dss_driver venc_driver = {
 	.get_resolution	= omapdss_default_get_resolution,
 	.get_recommended_bpp = omapdss_default_get_recommended_bpp,
 
+	.set_update_mode = venc_set_update_mode,
+	.get_update_mode = venc_get_update_mode,
+
 	.driver         = {
 		.name   = "venc",
 		.owner  = THIS_MODULE,
@@ -717,15 +734,6 @@ static int venc_set_wss(struct omap_dss_device *dssdev,	u32 wss)
 	return 0;
 }
 
-static enum omap_dss_update_mode venc_display_get_update_mode(
-		struct omap_dss_device *dssdev)
-{
-	if (dssdev->state == OMAP_DSS_DISPLAY_ACTIVE)
-		return OMAP_DSS_UPDATE_AUTO;
-	else
-		return OMAP_DSS_UPDATE_DISABLED;
-}
-
 int venc_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("init_display\n");
@@ -739,7 +747,6 @@ int venc_init_display(struct omap_dss_device *dssdev)
 	dssdev->check_timings = venc_check_timings;
 	dssdev->get_wss = venc_get_wss;
 	dssdev->set_wss = venc_set_wss;
-	dssdev->get_update_mode = venc_display_get_update_mode;
 
 	return 0;
 }
diff --git a/drivers/video/omap2/omapfb/omapfb-ioctl.c b/drivers/video/omap2/omapfb/omapfb-ioctl.c
index 86467f8..75fe1e7 100644
--- a/drivers/video/omap2/omapfb/omapfb-ioctl.c
+++ b/drivers/video/omap2/omapfb/omapfb-ioctl.c
@@ -243,7 +243,7 @@ static int omapfb_set_update_mode(struct fb_info *fbi,
 	enum omap_dss_update_mode um;
 	int r;
 
-	if (!display || !display->set_update_mode)
+	if (!display || !display->driver->set_update_mode)
 		return -EINVAL;
 
 	switch (mode) {
@@ -263,7 +263,7 @@ static int omapfb_set_update_mode(struct fb_info *fbi,
 		return -EINVAL;
 	}
 
-	r = display->set_update_mode(display, um);
+	r = display->driver->set_update_mode(display, um);
 
 	return r;
 }
@@ -274,10 +274,15 @@ static int omapfb_get_update_mode(struct fb_info *fbi,
 	struct omap_dss_device *display = fb2display(fbi);
 	enum omap_dss_update_mode m;
 
-	if (!display || !display->get_update_mode)
+	if (!display)
 		return -EINVAL;
 
-	m = display->get_update_mode(display);
+	if (!display->driver->get_update_mode) {
+		*mode = OMAPFB_AUTO_UPDATE;
+		return 0;
+	}
+
+	m = display->driver->get_update_mode(display);
 
 	switch (m) {
 	case OMAP_DSS_UPDATE_DISABLED:
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index fff687b..7686e86 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -1226,8 +1226,8 @@ static int omapfb_blank(int blank, struct fb_info *fbi)
 		if (display->resume)
 			r = display->resume(display);
 
-		if (r == 0 && display->get_update_mode &&
-				display->get_update_mode(display) ==
+		if (r == 0 && display->driver->get_update_mode &&
+				display->driver->get_update_mode(display) ==
 				OMAP_DSS_UPDATE_MANUAL)
 			do_update = 1;
 
@@ -2188,6 +2188,7 @@ static int omapfb_probe(struct platform_device *pdev)
 	}
 
 	if (def_display) {
+		struct omap_dss_driver *dssdrv = def_display->driver;
 #ifndef CONFIG_FB_OMAP2_FORCE_AUTO_UPDATE
 		u16 w, h;
 #endif
@@ -2205,19 +2206,19 @@ static int omapfb_probe(struct platform_device *pdev)
 				def_display->set_update_mode(def_display,
 						OMAP_DSS_UPDATE_AUTO);
 #else /* MANUAL_UPDATE */
-			if (def_display->driver->enable_te)
-				def_display->driver->enable_te(def_display, 0);
-			if (def_display->set_update_mode)
-				def_display->set_update_mode(def_display,
+			if (dssdrv->enable_te)
+				dssdrv->enable_te(def_display, 0);
+			if (dssdrv->set_update_mode)
+				dssdrv->set_update_mode(def_display,
 						OMAP_DSS_UPDATE_MANUAL);
 
-			def_display->driver->get_resolution(def_display,
+			dssdrv->get_resolution(def_display,
 					&w, &h);
 			def_display->update(def_display, 0, 0, w, h);
 #endif
 		} else {
-			if (def_display->set_update_mode)
-				def_display->set_update_mode(def_display,
+			if (dssdrv->set_update_mode)
+				dssdrv->set_update_mode(def_display,
 						OMAP_DSS_UPDATE_AUTO);
 		}
 	}
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 13/17] OMAP: DSS2: move update() and sync()
  2010-02-08 15:57                       ` [PATCH 12/17] OMAP: DSS2: move set/get_update_mode() Tomi Valkeinen
@ 2010-02-08 15:57                         ` Tomi Valkeinen
  2010-02-08 15:57                           ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move update() and sync() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |   23 ++-
 drivers/video/omap2/displays/panel-taal.c |   69 +++++--
 drivers/video/omap2/dss/dsi.c             |  315 ++++++++++-------------------
 drivers/video/omap2/dss/rfbi.c            |  290 +++------------------------
 drivers/video/omap2/omapfb/omapfb-ioctl.c |   10 +-
 drivers/video/omap2/omapfb/omapfb-main.c  |   10 +-
 6 files changed, 212 insertions(+), 505 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 7e46a5d..46b3ff0 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -477,9 +477,6 @@ struct omap_dss_device {
 			struct omap_video_timings *timings);
 	void (*get_timings)(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings);
-	int (*update)(struct omap_dss_device *dssdev,
-			       u16 x, u16 y, u16 w, u16 h);
-	int (*sync)(struct omap_dss_device *dssdev);
 
 	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
 	u32 (*get_wss)(struct omap_dss_device *dssdev);
@@ -503,15 +500,16 @@ struct omap_dss_driver {
 	int (*resume)(struct omap_dss_device *display);
 	int (*run_test)(struct omap_dss_device *display, int test);
 
-	void (*setup_update)(struct omap_dss_device *dssdev,
-			u16 x, u16 y, u16 w, u16 h);
 	int (*set_update_mode)(struct omap_dss_device *dssdev,
 			enum omap_dss_update_mode);
 	enum omap_dss_update_mode (*get_update_mode)(
 			struct omap_dss_device *dssdev);
 
+	int (*update)(struct omap_dss_device *dssdev,
+			       u16 x, u16 y, u16 w, u16 h);
+	int (*sync)(struct omap_dss_device *dssdev);
+
 	int (*enable_te)(struct omap_dss_device *dssdev, bool enable);
-	int (*wait_for_te)(struct omap_dss_device *dssdev);
 	int (*get_te)(struct omap_dss_device *dssdev);
 
 	u8 (*get_rotate)(struct omap_dss_device *dssdev);
@@ -569,4 +567,17 @@ int omap_dispc_wait_for_irq_interruptible_timeout(u32 irqmask,
 void omapdss_dsi_vc_enable_hs(int channel, bool enable);
 int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable);
 
+int omap_dsi_prepare_update(struct omap_dss_device *dssdev,
+				    u16 *x, u16 *y, u16 *w, u16 *h);
+int omap_dsi_update(struct omap_dss_device *dssdev,
+		u16 x, u16 y, u16 w, u16 h,
+		void (*callback)(int, void *), void *data);
+
+int omap_rfbi_prepare_update(struct omap_dss_device *dssdev,
+		u16 *x, u16 *y, u16 *w, u16 *h);
+int omap_rfbi_update(struct omap_dss_device *dssdev,
+		u16 x, u16 y, u16 w, u16 h,
+		void (*callback)(void *), void *data);
+
+
 #endif
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index 4ccb583..cb94596 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -725,10 +725,51 @@ static int taal_resume(struct omap_dss_device *dssdev)
 	return 0;
 }
 
-static void taal_setup_update(struct omap_dss_device *dssdev,
+static void taal_framedone_cb(int err, void *data)
+{
+	struct omap_dss_device *dssdev = data;
+	dev_dbg(&dssdev->dev, "framedone, err %d\n", err);
+	dsi_bus_unlock();
+}
+
+static int taal_update(struct omap_dss_device *dssdev,
 				    u16 x, u16 y, u16 w, u16 h)
 {
-	taal_set_update_window(x, y, w, h);
+	int r;
+
+	dev_dbg(&dssdev->dev, "update %d, %d, %d x %d\n", x, y, w, h);
+
+	dsi_bus_lock();
+
+	r = omap_dsi_prepare_update(dssdev, &x, &y, &w, &h);
+	if (r)
+		goto err;
+
+	r = taal_set_update_window(x, y, w, h);
+	if (r)
+		goto err;
+
+	r = omap_dsi_update(dssdev, x, y, w, h, taal_framedone_cb, dssdev);
+	if (r)
+		goto err;
+
+	/* note: no bus_unlock here. unlock is in framedone_cb */
+	return 0;
+err:
+	dsi_bus_unlock();
+	return r;
+}
+
+static int taal_sync(struct omap_dss_device *dssdev)
+{
+	dev_dbg(&dssdev->dev, "sync\n");
+
+	dsi_bus_lock();
+	dsi_bus_unlock();
+
+	dev_dbg(&dssdev->dev, "sync done\n");
+
+	return 0;
 }
 
 static int taal_enable_te(struct omap_dss_device *dssdev, bool enable)
@@ -762,24 +803,6 @@ static int taal_get_te(struct omap_dss_device *dssdev)
 	return td->te_enabled;
 }
 
-static int taal_wait_te(struct omap_dss_device *dssdev)
-{
-	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
-	long wait = msecs_to_jiffies(500);
-
-	if (!td->use_ext_te || !td->te_enabled)
-		return 0;
-
-	INIT_COMPLETION(td->te_completion);
-	wait = wait_for_completion_timeout(&td->te_completion, wait);
-	if (wait == 0) {
-		dev_err(&dssdev->dev, "timeout waiting TE\n");
-		return -ETIME;
-	}
-
-	return 0;
-}
-
 static int taal_rotate(struct omap_dss_device *dssdev, u8 rotate)
 {
 	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
@@ -1018,15 +1041,17 @@ static struct omap_dss_driver taal_driver = {
 	.suspend	= taal_suspend,
 	.resume		= taal_resume,
 
-	.setup_update	= taal_setup_update,
 	.set_update_mode = taal_set_update_mode,
 	.get_update_mode = taal_get_update_mode,
+
+	.update		= taal_update,
+	.sync		= taal_sync,
+
 	.get_resolution	= taal_get_resolution,
 	.get_recommended_bpp = omapdss_default_get_recommended_bpp,
 
 	.enable_te	= taal_enable_te,
 	.get_te		= taal_get_te,
-	.wait_for_te	= taal_wait_te,
 
 	.set_rotate	= taal_rotate,
 	.get_rotate	= taal_get_rotate,
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index aa5d0fd..a29ca43 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -31,8 +31,8 @@
 #include <linux/seq_file.h>
 #include <linux/platform_device.h>
 #include <linux/regulator/consumer.h>
-#include <linux/kthread.h>
 #include <linux/wait.h>
+#include <linux/workqueue.h>
 
 #include <plat/display.h>
 #include <plat/clock.h>
@@ -200,7 +200,6 @@ enum dsi_vc_mode {
 };
 
 struct dsi_update_region {
-	bool dirty;
 	u16 x, y, w, h;
 	struct omap_dss_device *device;
 };
@@ -234,18 +233,17 @@ static struct
 
 	struct completion bta_completion;
 
-	struct task_struct *thread;
-	wait_queue_head_t waitqueue;
-
-	spinlock_t update_lock;
-	bool framedone_received;
 	struct dsi_update_region update_region;
-	struct dsi_update_region active_update_region;
-	struct completion update_completion;
 
 	bool te_enabled;
 	bool use_ext_te;
 
+	struct work_struct framedone_work;
+	void (*framedone_callback)(int, void *);
+	void *framedone_data;
+
+	struct delayed_work framedone_timeout_work;
+
 #ifdef DSI_CATCH_MISSING_TE
 	struct timer_list te_timer;
 #endif
@@ -357,9 +355,9 @@ static void dsi_perf_show(const char *name)
 
 	total_us = setup_us + trans_us;
 
-	total_bytes = dsi.active_update_region.w *
-		dsi.active_update_region.h *
-		dsi.active_update_region.device->ctrl.pixel_size / 8;
+	total_bytes = dsi.update_region.w *
+		dsi.update_region.h *
+		dsi.update_region.device->ctrl.pixel_size / 8;
 
 	printk(KERN_INFO "DSI(%s): %u us + %u us = %u us (%uHz), "
 			"%u bytes, %u kbytes/sec\n",
@@ -2771,6 +2769,11 @@ static void dsi_update_screen_dispc(struct omap_dss_device *dssdev,
 	 */
 	dispc_disable_sidle();
 
+	dsi_perf_mark_start();
+
+	schedule_delayed_work(&dsi.framedone_timeout_work,
+			msecs_to_jiffies(250));
+
 	dss_start_update(dssdev);
 
 	if (use_te_trigger) {
@@ -2793,41 +2796,57 @@ static void dsi_te_timeout(unsigned long arg)
 }
 #endif
 
-static void dsi_framedone_irq_callback(void *data, u32 mask)
+static void dsi_framedone_timeout_work_callback(struct work_struct *work)
 {
-	/* Note: We get FRAMEDONE when DISPC has finished sending pixels and
-	 * turns itself off. However, DSI still has the pixels in its buffers,
-	 * and is sending the data.
-	 */
+	int r;
+	const int channel = 0;
+	bool use_te_trigger;
+
+	DSSERR("Framedone not received for 250ms!\n");
 
 	/* SIDLEMODE back to smart-idle */
 	dispc_enable_sidle();
 
-	dsi.framedone_received = true;
-	wake_up(&dsi.waitqueue);
-}
+	use_te_trigger = dsi.te_enabled && !dsi.use_ext_te;
 
-static void dsi_set_update_region(struct omap_dss_device *dssdev,
-		u16 x, u16 y, u16 w, u16 h)
-{
-	spin_lock(&dsi.update_lock);
-	if (dsi.update_region.dirty) {
-		dsi.update_region.x = min(x, dsi.update_region.x);
-		dsi.update_region.y = min(y, dsi.update_region.y);
-		dsi.update_region.w = max(w, dsi.update_region.w);
-		dsi.update_region.h = max(h, dsi.update_region.h);
-	} else {
-		dsi.update_region.x = x;
-		dsi.update_region.y = y;
-		dsi.update_region.w = w;
-		dsi.update_region.h = h;
+	if (use_te_trigger) {
+		/* enable LP_RX_TO again after the TE */
+		REG_FLD_MOD(DSI_TIMING2, 1, 15, 15); /* LP_RX_TO */
+	}
+
+	/* Send BTA after the frame. We need this for the TE to work, as TE
+	 * trigger is only sent for BTAs without preceding packet. Thus we need
+	 * to BTA after the pixel packets so that next BTA will cause TE
+	 * trigger.
+	 *
+	 * This is not needed when TE is not in use, but we do it anyway to
+	 * make sure that the transfer has been completed. It would be more
+	 * optimal, but more complex, to wait only just before starting next
+	 * transfer. */
+	r = dsi_vc_send_bta_sync(channel);
+	if (r)
+		DSSERR("BTA after framedone failed\n");
+
+	/* RX_FIFO_NOT_EMPTY */
+	if (REG_GET(DSI_VC_CTRL(channel), 20, 20)) {
+		DSSERR("Received error during frame transfer:\n");
+		dsi_vc_flush_receive_data(channel);
 	}
 
-	dsi.update_region.device = dssdev;
-	dsi.update_region.dirty = true;
+	dsi.framedone_callback(-ETIMEDOUT, dsi.framedone_data);
+}
 
-	spin_unlock(&dsi.update_lock);
+static void dsi_framedone_irq_callback(void *data, u32 mask)
+{
+	/* Note: We get FRAMEDONE when DISPC has finished sending pixels and
+	 * turns itself off. However, DSI still has the pixels in its buffers,
+	 * and is sending the data.
+	 */
 
+	/* SIDLEMODE back to smart-idle */
+	dispc_enable_sidle();
+
+	schedule_work(&dsi.framedone_work);
 }
 
 static void dsi_handle_framedone(void)
@@ -2869,105 +2888,77 @@ static void dsi_handle_framedone(void)
 #endif
 }
 
-static int dsi_update_thread(void *data)
+static void dsi_framedone_work_callback(struct work_struct *work)
 {
-	unsigned long timeout;
-	struct omap_dss_device *device;
-	u16 x, y, w, h;
-
-	while (1) {
-		wait_event_interruptible(dsi.waitqueue,
-				dsi.update_region.dirty == true ||
-				kthread_should_stop());
-
-		if (kthread_should_stop())
-			break;
-
-		dsi_bus_lock();
-
-		if (kthread_should_stop()) {
-			dsi_bus_unlock();
-			break;
-		}
-
-		dsi_perf_mark_setup();
+	DSSDBGF();
 
-		if (dsi.update_region.dirty) {
-			spin_lock(&dsi.update_lock);
-			dsi.active_update_region = dsi.update_region;
-			dsi.update_region.dirty = false;
-			spin_unlock(&dsi.update_lock);
-		}
+	cancel_delayed_work_sync(&dsi.framedone_timeout_work);
 
-		device = dsi.active_update_region.device;
-		x = dsi.active_update_region.x;
-		y = dsi.active_update_region.y;
-		w = dsi.active_update_region.w;
-		h = dsi.active_update_region.h;
+	dsi_handle_framedone();
 
-		if (device->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
+	dsi_perf_show("DISPC");
 
-			dss_setup_partial_planes(device,
-					&x, &y, &w, &h);
+	dsi.framedone_callback(0, dsi.framedone_data);
+}
 
-			dispc_set_lcd_size(w, h);
-		}
+int omap_dsi_prepare_update(struct omap_dss_device *dssdev,
+				    u16 *x, u16 *y, u16 *w, u16 *h)
+{
+	u16 dw, dh;
 
-		if (dsi.active_update_region.dirty) {
-			dsi.active_update_region.dirty = false;
-			/* XXX TODO we don't need to send the coords, if they
-			 * are the same that are already programmed to the
-			 * panel. That should speed up manual update a bit */
-			device->driver->setup_update(device, x, y, w, h);
-		}
+	dssdev->driver->get_resolution(dssdev, &dw, &dh);
 
-		dsi_perf_mark_start();
+	if  (*x > dw || *y > dh)
+		return -EINVAL;
 
-		if (device->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
-			dsi_vc_config_vp(0);
+	if (*x + *w > dw)
+		return -EINVAL;
 
-			if (dsi.te_enabled && dsi.use_ext_te)
-				device->driver->wait_for_te(device);
+	if (*y + *h > dh)
+		return -EINVAL;
 
-			dsi.framedone_received = false;
+	if (*w == 1)
+		return -EINVAL;
 
-			dsi_update_screen_dispc(device, x, y, w, h);
+	if (*w == 0 || *h == 0)
+		return -EINVAL;
 
-			/* wait for framedone */
-			timeout = msecs_to_jiffies(1000);
-			wait_event_timeout(dsi.waitqueue,
-					dsi.framedone_received == true,
-					timeout);
+	dsi_perf_mark_setup();
 
-			if (!dsi.framedone_received) {
-				DSSERR("framedone timeout\n");
-				DSSERR("failed update %d,%d %dx%d\n",
-						x, y, w, h);
+	if (dssdev->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
+		dss_setup_partial_planes(dssdev, x, y, w, h);
+		dispc_set_lcd_size(*w, *h);
+	}
 
-				dispc_enable_sidle();
-				device->manager->disable(device->manager);
+	return 0;
+}
+EXPORT_SYMBOL(omap_dsi_prepare_update);
 
-				dsi_reset_tx_fifo(0);
-			} else {
-				dsi_handle_framedone();
-				dsi_perf_show("DISPC");
-			}
-		} else {
-			dsi_update_screen_l4(device, x, y, w, h);
-			dsi_perf_show("L4");
-		}
+int omap_dsi_update(struct omap_dss_device *dssdev,
+		u16 x, u16 y, u16 w, u16 h,
+		void (*callback)(int, void *), void *data)
+{
+	if (dssdev->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
+		dsi.framedone_callback = callback;
+		dsi.framedone_data = data;
+		dsi_vc_config_vp(0);
 
-		complete_all(&dsi.update_completion);
+		dsi.update_region.x = x;
+		dsi.update_region.y = y;
+		dsi.update_region.w = w;
+		dsi.update_region.h = h;
+		dsi.update_region.device = dssdev;
 
-		dsi_bus_unlock();
+		dsi_update_screen_dispc(dssdev, x, y, w, h);
+	} else {
+		dsi_update_screen_l4(dssdev, x, y, w, h);
+		dsi_perf_show("L4");
+		callback(0, data);
 	}
 
-	DSSDBG("update thread exiting\n");
-
 	return 0;
 }
-
-
+EXPORT_SYMBOL(omap_dsi_update);
 
 /* Display funcs */
 
@@ -3322,74 +3313,6 @@ err0:
 	return r;
 }
 
-static int dsi_display_update(struct omap_dss_device *dssdev,
-			u16 x, u16 y, u16 w, u16 h)
-{
-	int r = 0;
-	u16 dw, dh;
-
-	DSSDBG("dsi_display_update(%d,%d %dx%d)\n", x, y, w, h);
-
-	mutex_lock(&dsi.lock);
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
-		goto end;
-
-	dssdev->driver->get_resolution(dssdev, &dw, &dh);
-
-	if  (x > dw || y > dh)
-		goto end;
-
-	if (x + w > dw)
-		w = dw - x;
-
-	if (y + h > dh)
-		h = dh - y;
-
-	if (w == 0 || h == 0)
-		goto end;
-
-	if (w == 1) {
-		r = -EINVAL;
-		goto end;
-	}
-
-	dsi_set_update_region(dssdev, x, y, w, h);
-
-	wake_up(&dsi.waitqueue);
-
-end:
-	mutex_unlock(&dsi.lock);
-
-	return r;
-}
-
-static int dsi_display_sync(struct omap_dss_device *dssdev)
-{
-	bool wait;
-
-	DSSDBG("dsi_display_sync()\n");
-
-	mutex_lock(&dsi.lock);
-	dsi_bus_lock();
-
-	if (dsi.update_region.dirty) {
-		INIT_COMPLETION(dsi.update_completion);
-		wait = true;
-	} else {
-		wait = false;
-	}
-
-	dsi_bus_unlock();
-	mutex_unlock(&dsi.lock);
-
-	if (wait)
-		wait_for_completion_interruptible(&dsi.update_completion);
-
-	DSSDBG("dsi_display_sync() done\n");
-	return 0;
-}
-
 int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable)
 {
 	dsi.te_enabled = enable;
@@ -3418,8 +3341,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 	dssdev->disable = dsi_display_disable;
 	dssdev->suspend = dsi_display_suspend;
 	dssdev->resume = dsi_display_resume;
-	dssdev->update = dsi_display_update;
-	dssdev->sync = dsi_display_sync;
 
 	/* XXX these should be figured out dynamically */
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
@@ -3435,9 +3356,6 @@ int dsi_init(struct platform_device *pdev)
 {
 	u32 rev;
 	int r;
-	struct sched_param param = {
-		.sched_priority = MAX_USER_RT_PRIO-1
-	};
 
 	spin_lock_init(&dsi.errors_lock);
 	dsi.errors = 0;
@@ -3448,28 +3366,19 @@ int dsi_init(struct platform_device *pdev)
 #endif
 
 	init_completion(&dsi.bta_completion);
-	init_completion(&dsi.update_completion);
-
-	dsi.thread = kthread_create(dsi_update_thread, NULL, "dsi");
-	if (IS_ERR(dsi.thread)) {
-		DSSERR("cannot create kthread\n");
-		r = PTR_ERR(dsi.thread);
-		goto err0;
-	}
-	sched_setscheduler(dsi.thread, SCHED_FIFO, &param);
-
-	init_waitqueue_head(&dsi.waitqueue);
-	spin_lock_init(&dsi.update_lock);
 
 	mutex_init(&dsi.lock);
 	sema_init(&dsi.bus_lock, 1);
 
+	INIT_WORK(&dsi.framedone_work, dsi_framedone_work_callback);
+	INIT_DELAYED_WORK_DEFERRABLE(&dsi.framedone_timeout_work,
+			dsi_framedone_timeout_work_callback);
+
 #ifdef DSI_CATCH_MISSING_TE
 	init_timer(&dsi.te_timer);
 	dsi.te_timer.function = dsi_te_timeout;
 	dsi.te_timer.data = 0;
 #endif
-
 	dsi.base = ioremap(DSI_BASE, DSI_SZ_REGS);
 	if (!dsi.base) {
 		DSSERR("can't ioremap DSI\n");
@@ -3493,21 +3402,15 @@ int dsi_init(struct platform_device *pdev)
 
 	enable_clocks(0);
 
-	wake_up_process(dsi.thread);
-
 	return 0;
 err2:
 	iounmap(dsi.base);
 err1:
-	kthread_stop(dsi.thread);
-err0:
 	return r;
 }
 
 void dsi_exit(void)
 {
-	kthread_stop(dsi.thread);
-
 	iounmap(dsi.base);
 
 	DSSDBG("omap_dsi_exit\n");
diff --git a/drivers/video/omap2/dss/rfbi.c b/drivers/video/omap2/dss/rfbi.c
index 7129387..a6b3316 100644
--- a/drivers/video/omap2/dss/rfbi.c
+++ b/drivers/video/omap2/dss/rfbi.c
@@ -36,8 +36,6 @@
 #include <plat/display.h>
 #include "dss.h"
 
-/*#define MEASURE_PERF*/
-
 #define RFBI_BASE               0x48050800
 
 struct rfbi_reg { u16 idx; };
@@ -66,8 +64,6 @@ struct rfbi_reg { u16 idx; };
 #define RFBI_VSYNC_WIDTH	RFBI_REG(0x0090)
 #define RFBI_HSYNC_WIDTH	RFBI_REG(0x0094)
 
-#define RFBI_CMD_FIFO_LEN_BYTES (16 * sizeof(struct update_param))
-
 #define REG_FLD_MOD(idx, val, start, end) \
 	rfbi_write_reg(idx, FLD_MOD(rfbi_read_reg(idx), val, start, end))
 
@@ -102,7 +98,6 @@ enum update_cmd {
 
 static int rfbi_convert_timings(struct rfbi_timings *t);
 static void rfbi_get_clk_info(u32 *clk_period, u32 *max_clk_div);
-static void process_cmd_fifo(void);
 
 static struct {
 	void __iomem	*base;
@@ -125,11 +120,6 @@ static struct {
 	struct completion cmd_done;
 	atomic_t          cmd_fifo_full;
 	atomic_t          cmd_pending;
-#ifdef MEASURE_PERF
-	unsigned perf_bytes;
-	ktime_t perf_setup_time;
-	ktime_t perf_start_time;
-#endif
 } rfbi;
 
 struct update_region {
@@ -139,16 +129,6 @@ struct update_region {
 	u16     h;
 };
 
-struct update_param {
-	u8 rfbi_module;
-	u8 cmd;
-
-	union {
-		struct update_region r;
-		struct completion *sync;
-	} par;
-};
-
 static inline void rfbi_write_reg(const struct rfbi_reg idx, u32 val)
 {
 	__raw_writel(val, rfbi.base + idx.idx);
@@ -321,55 +301,6 @@ void omap_rfbi_write_pixels(const void __iomem *buf, int scr_width,
 }
 EXPORT_SYMBOL(omap_rfbi_write_pixels);
 
-#ifdef MEASURE_PERF
-static void perf_mark_setup(void)
-{
-	rfbi.perf_setup_time = ktime_get();
-}
-
-static void perf_mark_start(void)
-{
-	rfbi.perf_start_time = ktime_get();
-}
-
-static void perf_show(const char *name)
-{
-	ktime_t t, setup_time, trans_time;
-	u32 total_bytes;
-	u32 setup_us, trans_us, total_us;
-
-	t = ktime_get();
-
-	setup_time = ktime_sub(rfbi.perf_start_time, rfbi.perf_setup_time);
-	setup_us = (u32)ktime_to_us(setup_time);
-	if (setup_us == 0)
-		setup_us = 1;
-
-	trans_time = ktime_sub(t, rfbi.perf_start_time);
-	trans_us = (u32)ktime_to_us(trans_time);
-	if (trans_us == 0)
-		trans_us = 1;
-
-	total_us = setup_us + trans_us;
-
-	total_bytes = rfbi.perf_bytes;
-
-	DSSINFO("%s update %u us + %u us = %u us (%uHz), %u bytes, "
-			"%u kbytes/sec\n",
-			name,
-			setup_us,
-			trans_us,
-			total_us,
-			1000*1000 / total_us,
-			total_bytes,
-			total_bytes * 1000 / total_us);
-}
-#else
-#define perf_mark_setup()
-#define perf_mark_start()
-#define perf_show(x)
-#endif
-
 void rfbi_transfer_area(u16 width, u16 height,
 			     void (callback)(void *data), void *data)
 {
@@ -396,8 +327,6 @@ void rfbi_transfer_area(u16 width, u16 height,
 	if (!rfbi.te_enabled)
 		l = FLD_MOD(l, 1, 4, 4); /* ITE */
 
-	perf_mark_start();
-
 	rfbi_write_reg(RFBI_CONTROL, l);
 }
 
@@ -407,8 +336,6 @@ static void framedone_callback(void *data, u32 mask)
 
 	DSSDBG("FRAMEDONE\n");
 
-	perf_show("DISPC");
-
 	REG_FLD_MOD(RFBI_CONTROL, 0, 0, 0);
 
 	rfbi_enable_clocks(0);
@@ -416,11 +343,10 @@ static void framedone_callback(void *data, u32 mask)
 	callback = rfbi.framedone_callback;
 	rfbi.framedone_callback = NULL;
 
-	/*callback(rfbi.framedone_callback_data);*/
+	if (callback != NULL)
+		callback(rfbi.framedone_callback_data);
 
 	atomic_set(&rfbi.cmd_pending, 0);
-
-	process_cmd_fifo();
 }
 
 #if 1 /* VERBOSE */
@@ -937,52 +863,43 @@ int rfbi_configure(int rfbi_module, int bpp, int lines)
 }
 EXPORT_SYMBOL(rfbi_configure);
 
-static int rfbi_find_display(struct omap_dss_device *dssdev)
+int omap_rfbi_prepare_update(struct omap_dss_device *dssdev,
+		u16 *x, u16 *y, u16 *w, u16 *h)
 {
-	if (dssdev == rfbi.dssdev[0])
-		return 0;
+	u16 dw, dh;
 
-	if (dssdev == rfbi.dssdev[1])
-		return 1;
+	dssdev->driver->get_resolution(dssdev, &dw, &dh);
 
-	BUG();
-	return -1;
-}
+	if  (*x > dw || *y > dh)
+		return -EINVAL;
 
+	if (*x + *w > dw)
+		return -EINVAL;
 
-static void signal_fifo_waiters(void)
-{
-	if (atomic_read(&rfbi.cmd_fifo_full) > 0) {
-		/* DSSDBG("SIGNALING: Fifo not full for waiter!\n"); */
-		complete(&rfbi.cmd_done);
-		atomic_dec(&rfbi.cmd_fifo_full);
-	}
-}
+	if (*y + *h > dh)
+		return -EINVAL;
 
-/* returns 1 for async op, and 0 for sync op */
-static int do_update(struct omap_dss_device *dssdev, struct update_region *upd)
-{
-	u16 x = upd->x;
-	u16 y = upd->y;
-	u16 w = upd->w;
-	u16 h = upd->h;
+	if (*w == 1)
+		return -EINVAL;
 
-	perf_mark_setup();
+	if (*w == 0 || *h == 0)
+		return -EINVAL;
 
 	if (dssdev->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
-		/*dssdev->driver->enable_te(dssdev, 1); */
-		dss_setup_partial_planes(dssdev, &x, &y, &w, &h);
+		dss_setup_partial_planes(dssdev, x, y, w, h);
+		dispc_set_lcd_size(*w, *h);
 	}
 
-#ifdef MEASURE_PERF
-	rfbi.perf_bytes = w * h * 2; /* XXX always 16bit */
-#endif
-
-	dssdev->driver->setup_update(dssdev, x, y, w, h);
+	return 0;
+}
+EXPORT_SYMBOL(omap_rfbi_prepare_update);
 
+int omap_rfbi_update(struct omap_dss_device *dssdev,
+		u16 x, u16 y, u16 w, u16 h,
+		void (*callback)(void *), void *data)
+{
 	if (dssdev->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
-		rfbi_transfer_area(w, h, NULL, NULL);
-		return 1;
+		rfbi_transfer_area(w, h, callback, data);
 	} else {
 		struct omap_overlay *ovl;
 		void __iomem *addr;
@@ -994,123 +911,12 @@ static int do_update(struct omap_dss_device *dssdev, struct update_region *upd)
 
 		omap_rfbi_write_pixels(addr, scr_width, x, y, w, h);
 
-		perf_show("L4");
-
-		return 0;
-	}
-}
-
-static void process_cmd_fifo(void)
-{
-	int len;
-	struct update_param p;
-	struct omap_dss_device *dssdev;
-	unsigned long flags;
-
-	if (atomic_inc_return(&rfbi.cmd_pending) != 1)
-		return;
-
-	while (true) {
-		spin_lock_irqsave(&rfbi.cmd_lock, flags);
-
-		len = kfifo_out(&rfbi.cmd_fifo, (unsigned char *)&p,
-				  sizeof(struct update_param));
-		if (len == 0) {
-			DSSDBG("nothing more in fifo\n");
-			atomic_set(&rfbi.cmd_pending, 0);
-			spin_unlock_irqrestore(&rfbi.cmd_lock, flags);
-			break;
-		}
-
-		/* DSSDBG("fifo full %d\n", rfbi.cmd_fifo_full.counter);*/
-
-		spin_unlock_irqrestore(&rfbi.cmd_lock, flags);
-
-		BUG_ON(len != sizeof(struct update_param));
-		BUG_ON(p.rfbi_module > 1);
-
-		dssdev = rfbi.dssdev[p.rfbi_module];
-
-		if (p.cmd == RFBI_CMD_UPDATE) {
-			if (do_update(dssdev, &p.par.r))
-				break; /* async op */
-		} else if (p.cmd == RFBI_CMD_SYNC) {
-			DSSDBG("Signaling SYNC done!\n");
-			complete(p.par.sync);
-		} else
-			BUG();
+		callback(data);
 	}
 
-	signal_fifo_waiters();
-}
-
-static void rfbi_push_cmd(struct update_param *p)
-{
-	int ret;
-
-	while (1) {
-		unsigned long flags;
-		int available;
-
-		spin_lock_irqsave(&rfbi.cmd_lock, flags);
-		available = RFBI_CMD_FIFO_LEN_BYTES -
-			kfifo_len(&rfbi.cmd_fifo);
-
-/*		DSSDBG("%d bytes left in fifo\n", available); */
-		if (available < sizeof(struct update_param)) {
-			DSSDBG("Going to wait because FIFO FULL..\n");
-			spin_unlock_irqrestore(&rfbi.cmd_lock, flags);
-			atomic_inc(&rfbi.cmd_fifo_full);
-			wait_for_completion(&rfbi.cmd_done);
-			/*DSSDBG("Woke up because fifo not full anymore\n");*/
-			continue;
-		}
-
-		ret = kfifo_in(&rfbi.cmd_fifo, (unsigned char *)p,
-				  sizeof(struct update_param));
-/*		DSSDBG("pushed %d bytes\n", ret);*/
-
-		spin_unlock_irqrestore(&rfbi.cmd_lock, flags);
-
-		BUG_ON(ret != sizeof(struct update_param));
-
-		break;
-	}
-}
-
-static void rfbi_push_update(int rfbi_module, int x, int y, int w, int h)
-{
-	struct update_param p;
-
-	p.rfbi_module = rfbi_module;
-	p.cmd = RFBI_CMD_UPDATE;
-
-	p.par.r.x = x;
-	p.par.r.y = y;
-	p.par.r.w = w;
-	p.par.r.h = h;
-
-	DSSDBG("RFBI pushed %d,%d %dx%d\n", x, y, w, h);
-
-	rfbi_push_cmd(&p);
-
-	process_cmd_fifo();
-}
-
-static void rfbi_push_sync(int rfbi_module, struct completion *sync_comp)
-{
-	struct update_param p;
-
-	p.rfbi_module = rfbi_module;
-	p.cmd = RFBI_CMD_SYNC;
-	p.par.sync = sync_comp;
-
-	rfbi_push_cmd(&p);
-
-	DSSDBG("RFBI sync pushed to cmd fifo\n");
-
-	process_cmd_fifo();
+	return 0;
 }
+EXPORT_SYMBOL(omap_rfbi_update);
 
 void rfbi_dump_regs(struct seq_file *s)
 {
@@ -1155,12 +961,8 @@ int rfbi_init(void)
 {
 	u32 rev;
 	u32 l;
-	int r;
 
 	spin_lock_init(&rfbi.cmd_lock);
-	r = kfifo_alloc(&rfbi.cmd_fifo, RFBI_CMD_FIFO_LEN_BYTES, GFP_KERNEL);
-	if (r)
-		return r;
 
 	init_completion(&rfbi.cmd_done);
 	atomic_set(&rfbi.cmd_fifo_full, 0);
@@ -1196,42 +998,10 @@ void rfbi_exit(void)
 {
 	DSSDBG("rfbi_exit\n");
 
-	kfifo_free(&rfbi.cmd_fifo);
-
 	iounmap(rfbi.base);
 }
 
 /* struct omap_display support */
-static int rfbi_display_update(struct omap_dss_device *dssdev,
-			u16 x, u16 y, u16 w, u16 h)
-{
-	int rfbi_module;
-
-	if (w == 0 || h == 0)
-		return 0;
-
-	rfbi_module = rfbi_find_display(dssdev);
-
-	rfbi_push_update(rfbi_module, x, y, w, h);
-
-	return 0;
-}
-
-static int rfbi_display_sync(struct omap_dss_device *dssdev)
-{
-	struct completion sync_comp;
-	int rfbi_module;
-
-	rfbi_module = rfbi_find_display(dssdev);
-
-	init_completion(&sync_comp);
-	rfbi_push_sync(rfbi_module, &sync_comp);
-	DSSDBG("Waiting for SYNC to happen...\n");
-	wait_for_completion(&sync_comp);
-	DSSDBG("Released from SYNC\n");
-	return 0;
-}
-
 static int rfbi_display_enable(struct omap_dss_device *dssdev)
 {
 	int r;
@@ -1291,8 +1061,6 @@ int rfbi_init_display(struct omap_dss_device *dssdev)
 {
 	dssdev->enable = rfbi_display_enable;
 	dssdev->disable = rfbi_display_disable;
-	dssdev->update = rfbi_display_update;
-	dssdev->sync = rfbi_display_sync;
 
 	rfbi.dssdev[dssdev->phy.rfbi.channel] = dssdev;
 
diff --git a/drivers/video/omap2/omapfb/omapfb-ioctl.c b/drivers/video/omap2/omapfb/omapfb-ioctl.c
index 75fe1e7..b145cae 100644
--- a/drivers/video/omap2/omapfb/omapfb-ioctl.c
+++ b/drivers/video/omap2/omapfb/omapfb-ioctl.c
@@ -213,7 +213,7 @@ static int omapfb_update_window_nolock(struct fb_info *fbi,
 	if (x + w > dw || y + h > dh)
 		return -EINVAL;
 
-	return display->update(display, x, y, w, h);
+	return display->driver->update(display, x, y, w, h);
 }
 
 /* This function is exported for SGX driver use */
@@ -538,18 +538,18 @@ int omapfb_ioctl(struct fb_info *fbi, unsigned int cmd, unsigned long arg)
 	switch (cmd) {
 	case OMAPFB_SYNC_GFX:
 		DBG("ioctl SYNC_GFX\n");
-		if (!display || !display->sync) {
+		if (!display || !display->driver->sync) {
 			/* DSS1 never returns an error here, so we neither */
 			/*r = -EINVAL;*/
 			break;
 		}
 
-		r = display->sync(display);
+		r = display->driver->sync(display);
 		break;
 
 	case OMAPFB_UPDATE_WINDOW_OLD:
 		DBG("ioctl UPDATE_WINDOW_OLD\n");
-		if (!display || !display->update) {
+		if (!display || !display->driver->update) {
 			r = -EINVAL;
 			break;
 		}
@@ -567,7 +567,7 @@ int omapfb_ioctl(struct fb_info *fbi, unsigned int cmd, unsigned long arg)
 
 	case OMAPFB_UPDATE_WINDOW:
 		DBG("ioctl UPDATE_WINDOW\n");
-		if (!display || !display->update) {
+		if (!display || !display->driver->update) {
 			r = -EINVAL;
 			break;
 		}
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index 7686e86..310d573 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -1254,11 +1254,11 @@ static int omapfb_blank(int blank, struct fb_info *fbi)
 exit:
 	omapfb_unlock(fbdev);
 
-	if (r == 0 && do_update && display->update) {
+	if (r == 0 && do_update && display->driver->update) {
 		u16 w, h;
 		display->driver->get_resolution(display, &w, &h);
 
-		r = display->update(display, 0, 0, w, h);
+		r = display->driver->update(display, 0, 0, w, h);
 	}
 
 	return r;
@@ -1639,8 +1639,8 @@ int omapfb_realloc_fbmem(struct fb_info *fbi, unsigned long size, int type)
 	if (old_size == size && old_type == type)
 		return 0;
 
-	if (display && display->sync)
-			display->sync(display);
+	if (display && display->driver->sync)
+			display->driver->sync(display);
 
 	omapfb_free_fbmem(fbi);
 
@@ -2214,7 +2214,7 @@ static int omapfb_probe(struct platform_device *pdev)
 
 			dssdrv->get_resolution(def_display,
 					&w, &h);
-			def_display->update(def_display, 0, 0, w, h);
+			def_display->driver->update(def_display, 0, 0, w, h);
 #endif
 		} else {
 			if (dssdrv->set_update_mode)
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume
  2010-02-08 15:57                         ` [PATCH 13/17] OMAP: DSS2: move update() and sync() Tomi Valkeinen
@ 2010-02-08 15:57                           ` Tomi Valkeinen
  2010-02-08 15:57                             ` [PATCH 15/17] OMAP: DSS2: move set/get_wss() Tomi Valkeinen
  2010-02-09 10:15                             ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Grazvydas Ignotas
  0 siblings, 2 replies; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move enable/disable/suspend/resume from omap_dss_device to
omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h          |   18 +-
 drivers/video/omap2/displays/panel-generic.c       |   56 ++++-
 .../video/omap2/displays/panel-sharp-lq043t1dg01.c |   67 ++++-
 .../video/omap2/displays/panel-sharp-ls037v7dw01.c |   42 +++-
 drivers/video/omap2/displays/panel-taal.c          |   76 +++++-
 .../video/omap2/displays/panel-toppoly-tdo35s.c    |   56 ++++-
 .../video/omap2/displays/panel-tpo-td043mtea1.c    |   61 ++++-
 drivers/video/omap2/dss/dispc.c                    |   12 +-
 drivers/video/omap2/dss/display.c                  |   14 +-
 drivers/video/omap2/dss/dpi.c                      |  102 +-------
 drivers/video/omap2/dss/dsi.c                      |  136 +----------
 drivers/video/omap2/dss/rfbi.c                     |   22 +--
 drivers/video/omap2/dss/sdi.c                      |   75 +------
 drivers/video/omap2/dss/venc.c                     |  251 ++++++++------------
 drivers/video/omap2/omapfb/omapfb-main.c           |   12 +-
 15 files changed, 462 insertions(+), 538 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index 46b3ff0..cc2b4e3 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -465,12 +465,6 @@ struct omap_dss_device {
 
 	enum omap_dss_display_state state;
 
-	int (*enable)(struct omap_dss_device *dssdev);
-	void (*disable)(struct omap_dss_device *dssdev);
-
-	int (*suspend)(struct omap_dss_device *dssdev);
-	int (*resume)(struct omap_dss_device *dssdev);
-
 	int (*check_timings)(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings);
 	void (*set_timings)(struct omap_dss_device *dssdev,
@@ -573,11 +567,21 @@ int omap_dsi_update(struct omap_dss_device *dssdev,
 		u16 x, u16 y, u16 w, u16 h,
 		void (*callback)(int, void *), void *data);
 
+int omapdss_dsi_display_enable(struct omap_dss_device *dssdev);
+void omapdss_dsi_display_disable(struct omap_dss_device *dssdev);
+
+int omapdss_dpi_display_enable(struct omap_dss_device *dssdev);
+void omapdss_dpi_display_disable(struct omap_dss_device *dssdev);
+
+int omapdss_sdi_display_enable(struct omap_dss_device *dssdev);
+void omapdss_sdi_display_disable(struct omap_dss_device *dssdev);
+
+int omapdss_rfbi_display_enable(struct omap_dss_device *dssdev);
+void omapdss_rfbi_display_disable(struct omap_dss_device *dssdev);
 int omap_rfbi_prepare_update(struct omap_dss_device *dssdev,
 		u16 *x, u16 *y, u16 *w, u16 *h);
 int omap_rfbi_update(struct omap_dss_device *dssdev,
 		u16 x, u16 y, u16 w, u16 h,
 		void (*callback)(void *), void *data);
 
-
 #endif
diff --git a/drivers/video/omap2/displays/panel-generic.c b/drivers/video/omap2/displays/panel-generic.c
index eb48d1a..c59e4ba 100644
--- a/drivers/video/omap2/displays/panel-generic.c
+++ b/drivers/video/omap2/displays/panel-generic.c
@@ -35,6 +35,35 @@ static struct omap_video_timings generic_panel_timings = {
 	.vbp		= 7,
 };
 
+static int generic_panel_power_on(struct omap_dss_device *dssdev)
+{
+	int r;
+
+	r = omapdss_dpi_display_enable(dssdev);
+	if (r)
+		goto err0;
+
+	if (dssdev->platform_enable) {
+		r = dssdev->platform_enable(dssdev);
+		if (r)
+			goto err1;
+	}
+
+	return 0;
+err1:
+	omapdss_dpi_display_disable(dssdev);
+err0:
+	return r;
+}
+
+static void generic_panel_power_off(struct omap_dss_device *dssdev)
+{
+	if (dssdev->platform_disable)
+		dssdev->platform_disable(dssdev);
+
+	omapdss_dpi_display_disable(dssdev);
+}
+
 static int generic_panel_probe(struct omap_dss_device *dssdev)
 {
 	dssdev->panel.config = OMAP_DSS_LCD_TFT;
@@ -51,27 +80,40 @@ static int generic_panel_enable(struct omap_dss_device *dssdev)
 {
 	int r = 0;
 
-	if (dssdev->platform_enable)
-		r = dssdev->platform_enable(dssdev);
+	r = generic_panel_power_on(dssdev);
+	if (r)
+		return r;
 
-	return r;
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return 0;
 }
 
 static void generic_panel_disable(struct omap_dss_device *dssdev)
 {
-	if (dssdev->platform_disable)
-		dssdev->platform_disable(dssdev);
+	generic_panel_power_off(dssdev);
+
+	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
 }
 
 static int generic_panel_suspend(struct omap_dss_device *dssdev)
 {
-	generic_panel_disable(dssdev);
+	generic_panel_power_off(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 	return 0;
 }
 
 static int generic_panel_resume(struct omap_dss_device *dssdev)
 {
-	return generic_panel_enable(dssdev);
+	int r = 0;
+
+	r = generic_panel_power_on(dssdev);
+	if (r)
+		return r;
+
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return 0;
 }
 
 static struct omap_dss_driver generic_driver = {
diff --git a/drivers/video/omap2/displays/panel-sharp-lq043t1dg01.c b/drivers/video/omap2/displays/panel-sharp-lq043t1dg01.c
index e75798e..1026746 100644
--- a/drivers/video/omap2/displays/panel-sharp-lq043t1dg01.c
+++ b/drivers/video/omap2/displays/panel-sharp-lq043t1dg01.c
@@ -39,6 +39,41 @@ static struct omap_video_timings sharp_lq_timings = {
 	.vbp		= 2,
 };
 
+static int sharp_lq_panel_power_on(struct omap_dss_device *dssdev)
+{
+	int r;
+
+	r = omapdss_dpi_display_enable(dssdev);
+	if (r)
+		goto err0;
+
+	/* wait couple of vsyncs until enabling the LCD */
+	msleep(50);
+
+	if (dssdev->platform_enable) {
+		r = dssdev->platform_enable(dssdev);
+		if (r)
+			goto err1;
+	}
+
+	return 0;
+err1:
+	omapdss_dpi_display_disable(dssdev);
+err0:
+	return r;
+}
+
+static void sharp_lq_panel_power_off(struct omap_dss_device *dssdev)
+{
+	if (dssdev->platform_disable)
+		dssdev->platform_disable(dssdev);
+
+	/* wait at least 5 vsyncs after disabling the LCD */
+	msleep(100);
+
+	omapdss_dpi_display_disable(dssdev);
+}
+
 static int sharp_lq_panel_probe(struct omap_dss_device *dssdev)
 {
 
@@ -58,36 +93,40 @@ static int sharp_lq_panel_enable(struct omap_dss_device *dssdev)
 {
 	int r = 0;
 
+	r = sharp_lq_panel_power_on(dssdev);
+	if (r)
+		return r;
 
-	/* wait couple of vsyncs until enabling the LCD */
-	msleep(50);
-
-	if (dssdev->platform_enable)
-		r = dssdev->platform_enable(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
 
-	return r;
+	return 0;
 }
 
 static void sharp_lq_panel_disable(struct omap_dss_device *dssdev)
 {
+	sharp_lq_panel_power_off(dssdev);
 
-	if (dssdev->platform_disable)
-		dssdev->platform_disable(dssdev);
-
-	/* wait at least 5 vsyncs after disabling the LCD */
-
-	msleep(100);
+	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
 }
 
 static int sharp_lq_panel_suspend(struct omap_dss_device *dssdev)
 {
-	sharp_lq_panel_disable(dssdev);
+	sharp_lq_panel_power_off(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 	return 0;
 }
 
 static int sharp_lq_panel_resume(struct omap_dss_device *dssdev)
 {
-	return sharp_lq_panel_enable(dssdev);
+	int r = 0;
+
+	r = sharp_lq_panel_power_on(dssdev);
+	if (r)
+		return r;
+
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return 0;
 }
 
 static struct omap_dss_driver sharp_lq_driver = {
diff --git a/drivers/video/omap2/displays/panel-sharp-ls037v7dw01.c b/drivers/video/omap2/displays/panel-sharp-ls037v7dw01.c
index e207d66..8d51a5e 100644
--- a/drivers/video/omap2/displays/panel-sharp-ls037v7dw01.c
+++ b/drivers/video/omap2/displays/panel-sharp-ls037v7dw01.c
@@ -20,7 +20,6 @@
 #include <linux/module.h>
 #include <linux/delay.h>
 #include <linux/device.h>
-#include <linux/regulator/consumer.h>
 #include <linux/err.h>
 
 #include <plat/display.h>
@@ -54,20 +53,31 @@ static void sharp_ls_panel_remove(struct omap_dss_device *dssdev)
 {
 }
 
-static int sharp_ls_panel_enable(struct omap_dss_device *dssdev)
+static int sharp_ls_power_on(struct omap_dss_device *dssdev)
 {
 	int r = 0;
 
+	r = omapdss_dpi_display_enable(dssdev);
+	if (r)
+		goto err0;
+
 	/* wait couple of vsyncs until enabling the LCD */
 	msleep(50);
 
-	if (dssdev->platform_enable)
+	if (dssdev->platform_enable) {
 		r = dssdev->platform_enable(dssdev);
+		if (r)
+			goto err1;
+	}
 
+	return 0;
+err1:
+	omapdss_dpi_display_disable(dssdev);
+err0:
 	return r;
 }
 
-static void sharp_ls_panel_disable(struct omap_dss_device *dssdev)
+static void sharp_ls_power_off(struct omap_dss_device *dssdev)
 {
 	if (dssdev->platform_disable)
 		dssdev->platform_disable(dssdev);
@@ -75,17 +85,37 @@ static void sharp_ls_panel_disable(struct omap_dss_device *dssdev)
 	/* wait at least 5 vsyncs after disabling the LCD */
 
 	msleep(100);
+
+	omapdss_dpi_display_disable(dssdev);
+}
+
+static int sharp_ls_panel_enable(struct omap_dss_device *dssdev)
+{
+	int r;
+	r = sharp_ls_power_on(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+	return r;
+}
+
+static void sharp_ls_panel_disable(struct omap_dss_device *dssdev)
+{
+	sharp_ls_power_off(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
 }
 
 static int sharp_ls_panel_suspend(struct omap_dss_device *dssdev)
 {
-	sharp_ls_panel_disable(dssdev);
+	sharp_ls_power_off(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 	return 0;
 }
 
 static int sharp_ls_panel_resume(struct omap_dss_device *dssdev)
 {
-	return sharp_ls_panel_enable(dssdev);
+	int r;
+	r = sharp_ls_power_on(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+	return r;
 }
 
 static struct omap_dss_driver sharp_ls_driver = {
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index cb94596..cdb7617 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -620,14 +620,12 @@ static void taal_remove(struct omap_dss_device *dssdev)
 	kfree(td);
 }
 
-static int taal_enable(struct omap_dss_device *dssdev)
+static int taal_power_on(struct omap_dss_device *dssdev)
 {
 	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
 	u8 id1, id2, id3;
 	int r;
 
-	dev_dbg(&dssdev->dev, "enable\n");
-
 	if (dssdev->platform_enable) {
 		r = dssdev->platform_enable(dssdev);
 		if (r)
@@ -637,6 +635,16 @@ static int taal_enable(struct omap_dss_device *dssdev)
 	/* it seems we have to wait a bit until taal is ready */
 	msleep(5);
 
+	dsi_bus_lock();
+
+	r = omapdss_dsi_display_enable(dssdev);
+	if (r) {
+		dev_err(&dssdev->dev, "failed to enable DSI\n");
+		goto err0;
+	}
+
+	omapdss_dsi_vc_enable_hs(TCH, false);
+
 	r = taal_sleep_out(td);
 	if (r)
 		goto err;
@@ -675,19 +683,27 @@ static int taal_enable(struct omap_dss_device *dssdev)
 		td->intro_printed = true;
 	}
 
+	omapdss_dsi_vc_enable_hs(TCH, true);
+
+	dsi_bus_unlock();
+
 	return 0;
 err:
+	dsi_bus_unlock();
+
+	omapdss_dsi_display_disable(dssdev);
+err0:
 	if (dssdev->platform_disable)
 		dssdev->platform_disable(dssdev);
 
 	return r;
 }
 
-static void taal_disable(struct omap_dss_device *dssdev)
+static void taal_power_off(struct omap_dss_device *dssdev)
 {
 	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
 
-	dev_dbg(&dssdev->dev, "disable\n");
+	dsi_bus_lock();
 
 	cancel_delayed_work(&td->esd_work);
 
@@ -697,32 +713,64 @@ static void taal_disable(struct omap_dss_device *dssdev)
 	/* wait a bit so that the message goes through */
 	msleep(10);
 
+	omapdss_dsi_display_disable(dssdev);
+
 	if (dssdev->platform_disable)
 		dssdev->platform_disable(dssdev);
 
 	td->enabled = 0;
+
+	dsi_bus_unlock();
+}
+
+static int taal_enable(struct omap_dss_device *dssdev)
+{
+	int r;
+	dev_dbg(&dssdev->dev, "enable\n");
+
+	if (dssdev->state != OMAP_DSS_DISPLAY_DISABLED)
+		return -EINVAL;
+
+	r = taal_power_on(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return r;
+}
+
+static void taal_disable(struct omap_dss_device *dssdev)
+{
+	dev_dbg(&dssdev->dev, "disable\n");
+
+	if (dssdev->state == OMAP_DSS_DISPLAY_ACTIVE)
+		taal_power_off(dssdev);
+
+	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
 }
 
 static int taal_suspend(struct omap_dss_device *dssdev)
 {
-	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
-	struct backlight_device *bldev = td->bldev;
+	dev_dbg(&dssdev->dev, "suspend\n");
 
-	bldev->props.power = FB_BLANK_POWERDOWN;
-	taal_bl_update_status(bldev);
+	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
+		return -EINVAL;
+
+	taal_power_off(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 
 	return 0;
 }
 
 static int taal_resume(struct omap_dss_device *dssdev)
 {
-	struct taal_data *td = dev_get_drvdata(&dssdev->dev);
-	struct backlight_device *bldev = td->bldev;
+	int r;
+	dev_dbg(&dssdev->dev, "resume\n");
 
-	bldev->props.power = FB_BLANK_UNBLANK;
-	taal_bl_update_status(bldev);
+	if (dssdev->state != OMAP_DSS_DISPLAY_SUSPENDED)
+		return -EINVAL;
 
-	return 0;
+	r = taal_power_on(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+	return r;
 }
 
 static void taal_framedone_cb(int err, void *data)
diff --git a/drivers/video/omap2/displays/panel-toppoly-tdo35s.c b/drivers/video/omap2/displays/panel-toppoly-tdo35s.c
index e744b8c..fa434ca 100644
--- a/drivers/video/omap2/displays/panel-toppoly-tdo35s.c
+++ b/drivers/video/omap2/displays/panel-toppoly-tdo35s.c
@@ -42,6 +42,35 @@ static struct omap_video_timings toppoly_tdo_panel_timings = {
 	.vbp		= 2,
 };
 
+static int toppoly_tdo_panel_power_on(struct omap_dss_device *dssdev)
+{
+	int r;
+
+	r = omapdss_dpi_display_enable(dssdev);
+	if (r)
+		goto err0;
+
+	if (dssdev->platform_enable) {
+		r = dssdev->platform_enable(dssdev);
+		if (r)
+			goto err1;
+	}
+
+	return 0;
+err1:
+	omapdss_dpi_display_disable(dssdev);
+err0:
+	return r;
+}
+
+static void toppoly_tdo_panel_power_off(struct omap_dss_device *dssdev)
+{
+	if (dssdev->platform_disable)
+		dssdev->platform_disable(dssdev);
+
+	omapdss_dpi_display_disable(dssdev);
+}
+
 static int toppoly_tdo_panel_probe(struct omap_dss_device *dssdev)
 {
 	dssdev->panel.config = OMAP_DSS_LCD_TFT | OMAP_DSS_LCD_IVS |
@@ -59,27 +88,40 @@ static int toppoly_tdo_panel_enable(struct omap_dss_device *dssdev)
 {
 	int r = 0;
 
-	if (dssdev->platform_enable)
-		r = dssdev->platform_enable(dssdev);
+	r = toppoly_tdo_panel_power_on(dssdev);
+	if (r)
+		return r;
 
-	return r;
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return 0;
 }
 
 static void toppoly_tdo_panel_disable(struct omap_dss_device *dssdev)
 {
-	if (dssdev->platform_disable)
-		dssdev->platform_disable(dssdev);
+	toppoly_tdo_panel_power_off(dssdev);
+
+	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
 }
 
 static int toppoly_tdo_panel_suspend(struct omap_dss_device *dssdev)
 {
-	toppoly_tdo_panel_disable(dssdev);
+	toppoly_tdo_panel_power_off(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 	return 0;
 }
 
 static int toppoly_tdo_panel_resume(struct omap_dss_device *dssdev)
 {
-	return toppoly_tdo_panel_enable(dssdev);
+	int r = 0;
+
+	r = toppoly_tdo_panel_power_on(dssdev);
+	if (r)
+		return r;
+
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return 0;
 }
 
 static struct omap_dss_driver generic_driver = {
diff --git a/drivers/video/omap2/displays/panel-tpo-td043mtea1.c b/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
index f297a46..c6e4a7e 100644
--- a/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
+++ b/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
@@ -262,18 +262,20 @@ static const struct omap_video_timings tpo_td043_timings = {
 	.vbp		= 34,
 };
 
-static int tpo_td043_enable(struct omap_dss_device *dssdev)
+static int generic_panel_power_on(struct omap_dss_device *dssdev)
 {
 	struct tpo_td043_device *tpo_td043 = dev_get_drvdata(&dssdev->dev);
 	int nreset_gpio = dssdev->reset_gpio;
-	int ret;
+	int r;
 
-	dev_dbg(&dssdev->dev, "enable\n");
+	r = omapdss_dpi_display_enable(dssdev);
+	if (r)
+		goto err0;
 
 	if (dssdev->platform_enable) {
-		ret = dssdev->platform_enable(dssdev);
-		if (ret)
-			return ret;
+		r = dssdev->platform_enable(dssdev);
+		if (r)
+			goto err1;
 	}
 
 	regulator_enable(tpo_td043->vcc_reg);
@@ -294,15 +296,17 @@ static int tpo_td043_enable(struct omap_dss_device *dssdev)
 	tpo_td043_write_gamma(tpo_td043->spi, tpo_td043->gamma);
 
 	return 0;
+err1:
+	omapdss_dpi_display_disable(dssdev);
+err0:
+	return r;
 }
 
-static void tpo_td043_disable(struct omap_dss_device *dssdev)
+static void generic_panel_power_off(struct omap_dss_device *dssdev)
 {
 	struct tpo_td043_device *tpo_td043 = dev_get_drvdata(&dssdev->dev);
 	int nreset_gpio = dssdev->reset_gpio;
 
-	dev_dbg(&dssdev->dev, "disable\n");
-
 	tpo_td043_write(tpo_td043->spi, 3,
 			TPO_R03_VAL_STANDBY | TPO_R03_EN_PWM);
 
@@ -318,17 +322,52 @@ static void tpo_td043_disable(struct omap_dss_device *dssdev)
 
 	if (dssdev->platform_disable)
 		dssdev->platform_disable(dssdev);
+
+	omapdss_dpi_display_disable(dssdev);
+}
+
+static int tpo_td043_enable(struct omap_dss_device *dssdev)
+{
+	int ret;
+
+	dev_dbg(&dssdev->dev, "enable\n");
+
+	ret = generic_panel_power_on(dssdev);
+	if (ret)
+		return ret;
+
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return 0;
+}
+
+static void tpo_td043_disable(struct omap_dss_device *dssdev)
+{
+	dev_dbg(&dssdev->dev, "disable\n");
+
+	generic_panel_power_off(dssdev);
+
+	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
 }
 
 static int tpo_td043_suspend(struct omap_dss_device *dssdev)
 {
-	tpo_td043_disable(dssdev);
+	generic_panel_power_off(dssdev);
+	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 	return 0;
 }
 
 static int tpo_td043_resume(struct omap_dss_device *dssdev)
 {
-	return tpo_td043_enable(dssdev);
+	int r = 0;
+
+	r = generic_panel_power_on(dssdev);
+	if (r)
+		return r;
+
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
+	return 0;
 }
 
 static int tpo_td043_probe(struct omap_dss_device *dssdev)
diff --git a/drivers/video/omap2/dss/dispc.c b/drivers/video/omap2/dss/dispc.c
index 68edc32..63636aa 100644
--- a/drivers/video/omap2/dss/dispc.c
+++ b/drivers/video/omap2/dss/dispc.c
@@ -2872,12 +2872,13 @@ static void dispc_error_worker(struct work_struct *work)
 				manager = mgr;
 				enable = mgr->device->state ==
 						OMAP_DSS_DISPLAY_ACTIVE;
-				mgr->device->disable(mgr->device);
+				mgr->device->driver->disable(mgr->device);
 				break;
 			}
 		}
 
 		if (manager) {
+			struct omap_dss_device *dssdev = manager->device;
 			for (i = 0; i < omap_dss_get_num_overlays(); ++i) {
 				struct omap_overlay *ovl;
 				ovl = omap_dss_get_overlay(i);
@@ -2892,7 +2893,7 @@ static void dispc_error_worker(struct work_struct *work)
 			dispc_go(manager->id);
 			mdelay(50);
 			if (enable)
-				manager->device->enable(manager->device);
+				dssdev->driver->enable(dssdev);
 		}
 	}
 
@@ -2910,12 +2911,13 @@ static void dispc_error_worker(struct work_struct *work)
 				manager = mgr;
 				enable = mgr->device->state ==
 						OMAP_DSS_DISPLAY_ACTIVE;
-				mgr->device->disable(mgr->device);
+				mgr->device->driver->disable(mgr->device);
 				break;
 			}
 		}
 
 		if (manager) {
+			struct omap_dss_device *dssdev = manager->device;
 			for (i = 0; i < omap_dss_get_num_overlays(); ++i) {
 				struct omap_overlay *ovl;
 				ovl = omap_dss_get_overlay(i);
@@ -2930,7 +2932,7 @@ static void dispc_error_worker(struct work_struct *work)
 			dispc_go(manager->id);
 			mdelay(50);
 			if (enable)
-				manager->device->enable(manager->device);
+				dssdev->driver->enable(dssdev);
 		}
 	}
 
@@ -2941,7 +2943,7 @@ static void dispc_error_worker(struct work_struct *work)
 			mgr = omap_dss_get_overlay_manager(i);
 
 			if (mgr->caps & OMAP_DSS_OVL_CAP_DISPC)
-				mgr->device->disable(mgr->device);
+				mgr->device->driver->disable(mgr->device);
 		}
 	}
 
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index dba33cd..bc8ae35 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -53,11 +53,11 @@ static ssize_t display_enabled_store(struct device *dev,
 
 	if (enabled != (dssdev->state != OMAP_DSS_DISPLAY_DISABLED)) {
 		if (enabled) {
-			r = dssdev->enable(dssdev);
+			r = dssdev->driver->enable(dssdev);
 			if (r)
 				return r;
 		} else {
-			dssdev->disable(dssdev);
+			dssdev->driver->disable(dssdev);
 		}
 	}
 
@@ -485,13 +485,13 @@ static int dss_suspend_device(struct device *dev, void *data)
 		return 0;
 	}
 
-	if (!dssdev->suspend) {
+	if (!dssdev->driver->suspend) {
 		DSSERR("display '%s' doesn't implement suspend\n",
 				dssdev->name);
 		return -ENOSYS;
 	}
 
-	r = dssdev->suspend(dssdev);
+	r = dssdev->driver->suspend(dssdev);
 	if (r)
 		return r;
 
@@ -520,8 +520,8 @@ static int dss_resume_device(struct device *dev, void *data)
 	int r;
 	struct omap_dss_device *dssdev = to_dss_device(dev);
 
-	if (dssdev->activate_after_resume && dssdev->resume) {
-		r = dssdev->resume(dssdev);
+	if (dssdev->activate_after_resume && dssdev->driver->resume) {
+		r = dssdev->driver->resume(dssdev);
 		if (r)
 			return r;
 	}
@@ -541,7 +541,7 @@ int dss_resume_all_devices(void)
 static int dss_disable_device(struct device *dev, void *data)
 {
 	struct omap_dss_device *dssdev = to_dss_device(dev);
-	dssdev->disable(dssdev);
+	dssdev->driver->disable(dssdev);
 	return 0;
 }
 
diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c
index 48ff7ea..1eef8b7 100644
--- a/drivers/video/omap2/dss/dpi.c
+++ b/drivers/video/omap2/dss/dpi.c
@@ -153,7 +153,7 @@ static int dpi_basic_init(struct omap_dss_device *dssdev)
 	return 0;
 }
 
-static int dpi_display_enable(struct omap_dss_device *dssdev)
+int omapdss_dpi_display_enable(struct omap_dss_device *dssdev)
 {
 	int r;
 
@@ -163,57 +163,42 @@ static int dpi_display_enable(struct omap_dss_device *dssdev)
 		goto err0;
 	}
 
-	if (dssdev->state != OMAP_DSS_DISPLAY_DISABLED) {
-		DSSERR("display already enabled\n");
-		r = -EINVAL;
-		goto err1;
-	}
-
 	if (cpu_is_omap34xx()) {
 		r = regulator_enable(dpi.vdds_dsi_reg);
 		if (r)
-			goto err2;
+			goto err1;
 	}
 
 	dss_clk_enable(DSS_CLK_ICK | DSS_CLK_FCK1);
 
 	r = dpi_basic_init(dssdev);
 	if (r)
-		goto err3;
+		goto err2;
 
 #ifdef CONFIG_OMAP2_DSS_USE_DSI_PLL
 	dss_clk_enable(DSS_CLK_FCK2);
 	r = dsi_pll_init(dssdev, 0, 1);
 	if (r)
-		goto err4;
+		goto err3;
 #endif
 	r = dpi_set_mode(dssdev);
 	if (r)
-		goto err5;
+		goto err4;
 
 	mdelay(2);
 
 	dssdev->manager->enable(dssdev->manager);
 
-	r = dssdev->driver->enable(dssdev);
-	if (r)
-		goto err6;
-
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
-
 	return 0;
 
-err6:
-	dssdev->manager->disable(dssdev->manager);
-err5:
+err4:
 #ifdef CONFIG_OMAP2_DSS_USE_DSI_PLL
 	dsi_pll_uninit();
-err4:
+err3:
 	dss_clk_disable(DSS_CLK_FCK2);
 #endif
-err3:
-	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
 err2:
+	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
 	if (cpu_is_omap34xx())
 		regulator_disable(dpi.vdds_dsi_reg);
 err1:
@@ -221,19 +206,10 @@ err1:
 err0:
 	return r;
 }
+EXPORT_SYMBOL(omapdss_dpi_display_enable);
 
-static int dpi_display_resume(struct omap_dss_device *dssdev);
-
-static void dpi_display_disable(struct omap_dss_device *dssdev)
+void omapdss_dpi_display_disable(struct omap_dss_device *dssdev)
 {
-	if (dssdev->state == OMAP_DSS_DISPLAY_DISABLED)
-		return;
-
-	if (dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED)
-		dpi_display_resume(dssdev);
-
-	dssdev->driver->disable(dssdev);
-
 	dssdev->manager->disable(dssdev->manager);
 
 #ifdef CONFIG_OMAP2_DSS_USE_DSI_PLL
@@ -247,61 +223,9 @@ static void dpi_display_disable(struct omap_dss_device *dssdev)
 	if (cpu_is_omap34xx())
 		regulator_disable(dpi.vdds_dsi_reg);
 
-	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
-
 	omap_dss_stop_device(dssdev);
 }
-
-static int dpi_display_suspend(struct omap_dss_device *dssdev)
-{
-	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
-		return -EINVAL;
-
-	DSSDBG("dpi_display_suspend\n");
-
-	if (dssdev->driver->suspend)
-		dssdev->driver->suspend(dssdev);
-
-	dssdev->manager->disable(dssdev->manager);
-
-	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
-
-	if (cpu_is_omap34xx())
-		regulator_disable(dpi.vdds_dsi_reg);
-
-	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
-
-	return 0;
-}
-
-static int dpi_display_resume(struct omap_dss_device *dssdev)
-{
-	int r;
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_SUSPENDED)
-		return -EINVAL;
-
-	DSSDBG("dpi_display_resume\n");
-
-	if (cpu_is_omap34xx()) {
-		r = regulator_enable(dpi.vdds_dsi_reg);
-		if (r)
-			goto err0;
-	}
-
-	dss_clk_enable(DSS_CLK_ICK | DSS_CLK_FCK1);
-
-	dssdev->manager->enable(dssdev->manager);
-
-	if (dssdev->driver->resume)
-		dssdev->driver->resume(dssdev);
-
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
-
-	return 0;
-err0:
-	return r;
-}
+EXPORT_SYMBOL(omapdss_dpi_display_disable);
 
 static void dpi_set_timings(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings)
@@ -379,10 +303,6 @@ int dpi_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("init_display\n");
 
-	dssdev->enable = dpi_display_enable;
-	dssdev->disable = dpi_display_disable;
-	dssdev->suspend = dpi_display_suspend;
-	dssdev->resume = dpi_display_resume;
 	dssdev->set_timings = dpi_set_timings;
 	dssdev->check_timings = dpi_check_timings;
 	dssdev->get_timings = dpi_get_timings;
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index a29ca43..79d27de 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -3099,18 +3099,7 @@ static int dsi_display_init_dsi(struct omap_dss_device *dssdev)
 	dsi_if_enable(1);
 	dsi_force_tx_stop_mode_io();
 
-	if (dssdev->driver->enable) {
-		r = dssdev->driver->enable(dssdev);
-		if (r)
-			goto err4;
-	}
-
-	/* enable high-speed after initial config */
-	omapdss_dsi_vc_enable_hs(0, 1);
-
 	return 0;
-err4:
-	dsi_if_enable(0);
 err3:
 	dsi_complexio_uninit();
 err2:
@@ -3124,9 +3113,6 @@ err0:
 
 static void dsi_display_uninit_dsi(struct omap_dss_device *dssdev)
 {
-	if (dssdev->driver->disable)
-		dssdev->driver->disable(dssdev);
-
 	dss_select_dispc_clk_source(DSS_SRC_DSS1_ALWON_FCLK);
 	dss_select_dsi_clk_source(DSS_SRC_DSS1_ALWON_FCLK);
 	dsi_complexio_uninit();
@@ -3149,14 +3135,15 @@ static int dsi_core_init(void)
 	return 0;
 }
 
-static int dsi_display_enable(struct omap_dss_device *dssdev)
+int omapdss_dsi_display_enable(struct omap_dss_device *dssdev)
 {
 	int r = 0;
 
 	DSSDBG("dsi_display_enable\n");
 
+	WARN_ON(!dsi_bus_is_locked());
+
 	mutex_lock(&dsi.lock);
-	dsi_bus_lock();
 
 	r = omap_dss_start_device(dssdev);
 	if (r) {
@@ -3164,90 +3151,49 @@ static int dsi_display_enable(struct omap_dss_device *dssdev)
 		goto err0;
 	}
 
-	if (dssdev->state != OMAP_DSS_DISPLAY_DISABLED) {
-		DSSERR("dssdev already enabled\n");
-		r = -EINVAL;
-		goto err1;
-	}
-
 	enable_clocks(1);
 	dsi_enable_pll_clock(1);
 
 	r = _dsi_reset();
 	if (r)
-		goto err2;
+		goto err1;
 
 	dsi_core_init();
 
 	r = dsi_display_init_dispc(dssdev);
 	if (r)
-		goto err2;
+		goto err1;
 
 	r = dsi_display_init_dsi(dssdev);
 	if (r)
-		goto err3;
-
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+		goto err2;
 
 	dsi.use_ext_te = dssdev->phy.dsi.ext_te;
 
-	dsi_bus_unlock();
 	mutex_unlock(&dsi.lock);
 
 	return 0;
 
-err3:
-	dsi_display_uninit_dispc(dssdev);
 err2:
+	dsi_display_uninit_dispc(dssdev);
+err1:
 	enable_clocks(0);
 	dsi_enable_pll_clock(0);
-err1:
 	omap_dss_stop_device(dssdev);
 err0:
-	dsi_bus_unlock();
 	mutex_unlock(&dsi.lock);
 	DSSDBG("dsi_display_enable FAILED\n");
 	return r;
 }
+EXPORT_SYMBOL(omapdss_dsi_display_enable);
 
-static void dsi_display_disable(struct omap_dss_device *dssdev)
+void omapdss_dsi_display_disable(struct omap_dss_device *dssdev)
 {
 	DSSDBG("dsi_display_disable\n");
 
-	mutex_lock(&dsi.lock);
-	dsi_bus_lock();
-
-	if (dssdev->state == OMAP_DSS_DISPLAY_DISABLED ||
-			dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED)
-		goto end;
-
-	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
-
-	dsi_display_uninit_dispc(dssdev);
-
-	dsi_display_uninit_dsi(dssdev);
-
-	enable_clocks(0);
-	dsi_enable_pll_clock(0);
-
-	omap_dss_stop_device(dssdev);
-end:
-	dsi_bus_unlock();
-	mutex_unlock(&dsi.lock);
-}
-
-static int dsi_display_suspend(struct omap_dss_device *dssdev)
-{
-	DSSDBG("dsi_display_suspend\n");
+	WARN_ON(!dsi_bus_is_locked());
 
 	mutex_lock(&dsi.lock);
-	dsi_bus_lock();
-
-	if (dssdev->state == OMAP_DSS_DISPLAY_DISABLED ||
-			dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED)
-		goto end;
-
-	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
 
 	dsi_display_uninit_dispc(dssdev);
 
@@ -3255,63 +3201,12 @@ static int dsi_display_suspend(struct omap_dss_device *dssdev)
 
 	enable_clocks(0);
 	dsi_enable_pll_clock(0);
-end:
-	dsi_bus_unlock();
-	mutex_unlock(&dsi.lock);
 
-	return 0;
-}
-
-static int dsi_display_resume(struct omap_dss_device *dssdev)
-{
-	int r;
-
-	DSSDBG("dsi_display_resume\n");
-
-	mutex_lock(&dsi.lock);
-	dsi_bus_lock();
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_SUSPENDED) {
-		DSSERR("dssdev not suspended\n");
-		r = -EINVAL;
-		goto err0;
-	}
-
-	enable_clocks(1);
-	dsi_enable_pll_clock(1);
-
-	r = _dsi_reset();
-	if (r)
-		goto err1;
-
-	dsi_core_init();
-
-	r = dsi_display_init_dispc(dssdev);
-	if (r)
-		goto err1;
-
-	r = dsi_display_init_dsi(dssdev);
-	if (r)
-		goto err2;
-
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
-
-	dsi_bus_unlock();
-	mutex_unlock(&dsi.lock);
-
-	return 0;
+	omap_dss_stop_device(dssdev);
 
-err2:
-	dsi_display_uninit_dispc(dssdev);
-err1:
-	enable_clocks(0);
-	dsi_enable_pll_clock(0);
-err0:
-	dsi_bus_unlock();
 	mutex_unlock(&dsi.lock);
-	DSSDBG("dsi_display_resume FAILED\n");
-	return r;
 }
+EXPORT_SYMBOL(omapdss_dsi_display_disable);
 
 int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable)
 {
@@ -3337,11 +3232,6 @@ int dsi_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("DSI init\n");
 
-	dssdev->enable = dsi_display_enable;
-	dssdev->disable = dsi_display_disable;
-	dssdev->suspend = dsi_display_suspend;
-	dssdev->resume = dsi_display_resume;
-
 	/* XXX these should be figured out dynamically */
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
 		OMAP_DSS_DISPLAY_CAP_TEAR_ELIM;
diff --git a/drivers/video/omap2/dss/rfbi.c b/drivers/video/omap2/dss/rfbi.c
index a6b3316..cc23f53 100644
--- a/drivers/video/omap2/dss/rfbi.c
+++ b/drivers/video/omap2/dss/rfbi.c
@@ -1001,8 +1001,7 @@ void rfbi_exit(void)
 	iounmap(rfbi.base);
 }
 
-/* struct omap_display support */
-static int rfbi_display_enable(struct omap_dss_device *dssdev)
+int omapdss_rfbi_display_enable(struct omap_dss_device *dssdev)
 {
 	int r;
 
@@ -1033,38 +1032,25 @@ static int rfbi_display_enable(struct omap_dss_device *dssdev)
 			 &dssdev->ctrl.rfbi_timings);
 
 
-	if (dssdev->driver->enable) {
-		r = dssdev->driver->enable(dssdev);
-		if (r)
-			goto err2;
-	}
-
 	return 0;
-err2:
-	omap_dispc_unregister_isr(framedone_callback, NULL,
-			DISPC_IRQ_FRAMEDONE);
 err1:
 	omap_dss_stop_device(dssdev);
 err0:
 	return r;
 }
+EXPORT_SYMBOL(omapdss_rfbi_display_enable);
 
-static void rfbi_display_disable(struct omap_dss_device *dssdev)
+void omapdss_rfbi_display_disable(struct omap_dss_device *dssdev)
 {
-	dssdev->driver->disable(dssdev);
 	omap_dispc_unregister_isr(framedone_callback, NULL,
 			DISPC_IRQ_FRAMEDONE);
 	omap_dss_stop_device(dssdev);
 }
+EXPORT_SYMBOL(omapdss_rfbi_display_disable);
 
 int rfbi_init_display(struct omap_dss_device *dssdev)
 {
-	dssdev->enable = rfbi_display_enable;
-	dssdev->disable = rfbi_display_disable;
-
 	rfbi.dssdev[dssdev->phy.rfbi.channel] = dssdev;
-
 	dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE;
-
 	return 0;
 }
diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c
index 6bd9b0c..929ceb3 100644
--- a/drivers/video/omap2/dss/sdi.c
+++ b/drivers/video/omap2/dss/sdi.c
@@ -41,7 +41,7 @@ static void sdi_basic_init(void)
 	dispc_lcd_enable_signal_polarity(1);
 }
 
-static int sdi_display_enable(struct omap_dss_device *dssdev)
+int omapdss_sdi_display_enable(struct omap_dss_device *dssdev)
 {
 	struct omap_video_timings *t = &dssdev->panel.timings;
 	struct dss_clock_info dss_cinfo;
@@ -57,12 +57,6 @@ static int sdi_display_enable(struct omap_dss_device *dssdev)
 		goto err0;
 	}
 
-	if (dssdev->state != OMAP_DSS_DISPLAY_DISABLED) {
-		DSSERR("dssdev already enabled\n");
-		r = -EINVAL;
-		goto err1;
-	}
-
 	/* In case of skip_init sdi_init has already enabled the clocks */
 	if (!sdi.skip_init)
 		dss_clk_enable(DSS_CLK_ICK | DSS_CLK_FCK1);
@@ -127,8 +121,6 @@ static int sdi_display_enable(struct omap_dss_device *dssdev)
 			goto err3;
 	}
 
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
-
 	sdi.skip_init = 0;
 
 	return 0;
@@ -141,18 +133,10 @@ err1:
 err0:
 	return r;
 }
+EXPORT_SYMBOL(omapdss_sdi_display_enable);
 
-static int sdi_display_resume(struct omap_dss_device *dssdev);
-
-static void sdi_display_disable(struct omap_dss_device *dssdev)
+void omapdss_sdi_display_disable(struct omap_dss_device *dssdev)
 {
-	if (dssdev->state == OMAP_DSS_DISPLAY_DISABLED)
-		return;
-
-	if (dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED)
-		if (sdi_display_resume(dssdev))
-			return;
-
 	if (dssdev->driver->disable)
 		dssdev->driver->disable(dssdev);
 
@@ -162,56 +146,9 @@ static void sdi_display_disable(struct omap_dss_device *dssdev)
 
 	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
 
-	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
-
 	omap_dss_stop_device(dssdev);
 }
-
-static int sdi_display_suspend(struct omap_dss_device *dssdev)
-{
-	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE)
-		return -EINVAL;
-
-	if (dssdev->driver->suspend)
-		dssdev->driver->suspend(dssdev);
-
-	dssdev->manager->disable(dssdev->manager);
-
-	dss_sdi_disable();
-
-	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
-
-	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
-
-	return 0;
-}
-
-static int sdi_display_resume(struct omap_dss_device *dssdev)
-{
-	int r;
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_SUSPENDED)
-		return -EINVAL;
-
-	dss_clk_enable(DSS_CLK_ICK | DSS_CLK_FCK1);
-
-	r = dss_sdi_enable();
-	if (r)
-		goto err;
-	mdelay(2);
-
-	dssdev->manager->enable(dssdev->manager);
-
-	if (dssdev->driver->resume)
-		dssdev->driver->resume(dssdev);
-
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
-
-	return 0;
-err:
-	dss_clk_disable(DSS_CLK_ICK | DSS_CLK_FCK1);
-	return r;
-}
+EXPORT_SYMBOL(omapdss_sdi_display_disable);
 
 static void sdi_get_timings(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings)
@@ -223,10 +160,6 @@ int sdi_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("SDI init\n");
 
-	dssdev->enable = sdi_display_enable;
-	dssdev->disable = sdi_display_disable;
-	dssdev->suspend = sdi_display_suspend;
-	dssdev->resume = sdi_display_resume;
 	dssdev->get_timings = sdi_get_timings;
 
 	return 0;
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index 0d0dc94..a0ab52c 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -400,6 +400,56 @@ static const struct venc_config *venc_timings_to_config(
 	BUG();
 }
 
+static void venc_power_on(struct omap_dss_device *dssdev)
+{
+	u32 l;
+
+	venc_enable_clocks(1);
+
+	venc_reset();
+	venc_write_config(venc_timings_to_config(&dssdev->panel.timings));
+
+	dss_set_venc_output(dssdev->phy.venc.type);
+	dss_set_dac_pwrdn_bgz(1);
+
+	l = 0;
+
+	if (dssdev->phy.venc.type == OMAP_DSS_VENC_TYPE_COMPOSITE)
+		l |= 1 << 1;
+	else /* S-Video */
+		l |= (1 << 0) | (1 << 2);
+
+	if (dssdev->phy.venc.invert_polarity == false)
+		l |= 1 << 3;
+
+	venc_write_reg(VENC_OUTPUT_CONTROL, l);
+
+	dispc_set_digit_size(dssdev->panel.timings.x_res,
+			dssdev->panel.timings.y_res/2);
+
+	regulator_enable(venc.vdda_dac_reg);
+
+	if (dssdev->platform_enable)
+		dssdev->platform_enable(dssdev);
+
+	dssdev->manager->enable(dssdev->manager);
+}
+
+static void venc_power_off(struct omap_dss_device *dssdev)
+{
+	venc_write_reg(VENC_OUTPUT_CONTROL, 0);
+	dss_set_dac_pwrdn_bgz(0);
+
+	dssdev->manager->disable(dssdev->manager);
+
+	if (dssdev->platform_disable)
+		dssdev->platform_disable(dssdev);
+
+	regulator_disable(venc.vdda_dac_reg);
+
+	venc_enable_clocks(0);
+}
+
 
 
 
@@ -420,23 +470,66 @@ static int venc_panel_enable(struct omap_dss_device *dssdev)
 {
 	int r = 0;
 
+	DSSDBG("venc_enable_display\n");
+
+	mutex_lock(&venc.venc_lock);
+
+	if (dssdev->state != OMAP_DSS_DISPLAY_DISABLED) {
+		r = -EINVAL;
+		goto err1;
+	}
+
+	if (dssdev->platform_enable) {
+		r = dssdev->platform_enable(dssdev);
+		if (r)
+			goto err2;
+	}
+
+	venc_power_on(dssdev);
+
+	venc.wss_data = 0;
+
+	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
+
 	/* wait couple of vsyncs until enabling the LCD */
 	msleep(50);
 
-	if (dssdev->platform_enable)
-		r = dssdev->platform_enable(dssdev);
+	mutex_unlock(&venc.venc_lock);
 
 	return r;
+err2:
+	venc_power_off(dssdev);
+err1:
+	mutex_unlock(&venc.venc_lock);
+	return r;
 }
 
 static void venc_panel_disable(struct omap_dss_device *dssdev)
 {
-	if (dssdev->platform_disable)
-		dssdev->platform_disable(dssdev);
+	DSSDBG("venc_disable_display\n");
 
-	/* wait at least 5 vsyncs after disabling the LCD */
+	mutex_lock(&venc.venc_lock);
+
+	if (dssdev->state == OMAP_DSS_DISPLAY_DISABLED)
+		goto end;
 
+	if (dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED) {
+		/* suspended is the same as disabled with venc */
+		dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
+		goto end;
+	}
+
+	venc_power_off(dssdev);
+
+	/* wait at least 5 vsyncs after disabling the LCD */
 	msleep(100);
+
+	if (dssdev->platform_disable)
+		dssdev->platform_disable(dssdev);
+
+	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
+end:
+	mutex_unlock(&venc.venc_lock);
 }
 
 static int venc_panel_suspend(struct omap_dss_device *dssdev)
@@ -526,146 +619,6 @@ void venc_exit(void)
 	iounmap(venc.base);
 }
 
-static void venc_power_on(struct omap_dss_device *dssdev)
-{
-	u32 l;
-
-	venc_enable_clocks(1);
-
-	venc_reset();
-	venc_write_config(venc_timings_to_config(&dssdev->panel.timings));
-
-	dss_set_venc_output(dssdev->phy.venc.type);
-	dss_set_dac_pwrdn_bgz(1);
-
-	l = 0;
-
-	if (dssdev->phy.venc.type == OMAP_DSS_VENC_TYPE_COMPOSITE)
-		l |= 1 << 1;
-	else /* S-Video */
-		l |= (1 << 0) | (1 << 2);
-
-	if (dssdev->phy.venc.invert_polarity == false)
-		l |= 1 << 3;
-
-	venc_write_reg(VENC_OUTPUT_CONTROL, l);
-
-	dispc_set_digit_size(dssdev->panel.timings.x_res,
-			dssdev->panel.timings.y_res/2);
-
-	regulator_enable(venc.vdda_dac_reg);
-
-	if (dssdev->platform_enable)
-		dssdev->platform_enable(dssdev);
-
-	dssdev->manager->enable(dssdev->manager);
-}
-
-static void venc_power_off(struct omap_dss_device *dssdev)
-{
-	venc_write_reg(VENC_OUTPUT_CONTROL, 0);
-	dss_set_dac_pwrdn_bgz(0);
-
-	dssdev->manager->disable(dssdev->manager);
-
-	if (dssdev->platform_disable)
-		dssdev->platform_disable(dssdev);
-
-	regulator_disable(venc.vdda_dac_reg);
-
-	venc_enable_clocks(0);
-}
-
-static int venc_enable_display(struct omap_dss_device *dssdev)
-{
-	int r = 0;
-
-	DSSDBG("venc_enable_display\n");
-
-	mutex_lock(&venc.venc_lock);
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_DISABLED) {
-		r = -EINVAL;
-		goto err;
-	}
-
-	venc_power_on(dssdev);
-
-	venc.wss_data = 0;
-
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
-err:
-	mutex_unlock(&venc.venc_lock);
-
-	return r;
-}
-
-static void venc_disable_display(struct omap_dss_device *dssdev)
-{
-	DSSDBG("venc_disable_display\n");
-
-	mutex_lock(&venc.venc_lock);
-
-	if (dssdev->state == OMAP_DSS_DISPLAY_DISABLED)
-		goto end;
-
-	if (dssdev->state == OMAP_DSS_DISPLAY_SUSPENDED) {
-		/* suspended is the same as disabled with venc */
-		dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
-		goto end;
-	}
-
-	venc_power_off(dssdev);
-
-	dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
-end:
-	mutex_unlock(&venc.venc_lock);
-}
-
-static int venc_display_suspend(struct omap_dss_device *dssdev)
-{
-	int r = 0;
-
-	DSSDBG("venc_display_suspend\n");
-
-	mutex_lock(&venc.venc_lock);
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE) {
-		r = -EINVAL;
-		goto err;
-	}
-
-	venc_power_off(dssdev);
-
-	dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
-err:
-	mutex_unlock(&venc.venc_lock);
-
-	return r;
-}
-
-static int venc_display_resume(struct omap_dss_device *dssdev)
-{
-	int r = 0;
-
-	DSSDBG("venc_display_resume\n");
-
-	mutex_lock(&venc.venc_lock);
-
-	if (dssdev->state != OMAP_DSS_DISPLAY_SUSPENDED) {
-		r = -EINVAL;
-		goto err;
-	}
-
-	venc_power_on(dssdev);
-
-	dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
-err:
-	mutex_unlock(&venc.venc_lock);
-
-	return r;
-}
-
 static void venc_get_timings(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings)
 {
@@ -684,8 +637,8 @@ static void venc_set_timings(struct omap_dss_device *dssdev,
 	dssdev->panel.timings = *timings;
 	if (dssdev->state == OMAP_DSS_DISPLAY_ACTIVE) {
 		/* turn the venc off and on to get new timings to use */
-		venc_disable_display(dssdev);
-		venc_enable_display(dssdev);
+		venc_panel_disable(dssdev);
+		venc_panel_enable(dssdev);
 	}
 }
 
@@ -738,10 +691,6 @@ int venc_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("init_display\n");
 
-	dssdev->enable = venc_enable_display;
-	dssdev->disable = venc_disable_display;
-	dssdev->suspend = venc_display_suspend;
-	dssdev->resume = venc_display_resume;
 	dssdev->get_timings = venc_get_timings;
 	dssdev->set_timings = venc_set_timings;
 	dssdev->check_timings = venc_check_timings;
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index 310d573..f0b304d 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -1223,8 +1223,8 @@ static int omapfb_blank(int blank, struct fb_info *fbi)
 		if (display->state != OMAP_DSS_DISPLAY_SUSPENDED)
 			goto exit;
 
-		if (display->resume)
-			r = display->resume(display);
+		if (display->driver->resume)
+			r = display->driver->resume(display);
 
 		if (r == 0 && display->driver->get_update_mode &&
 				display->driver->get_update_mode(display) ==
@@ -1242,8 +1242,8 @@ static int omapfb_blank(int blank, struct fb_info *fbi)
 		if (display->state != OMAP_DSS_DISPLAY_ACTIVE)
 			goto exit;
 
-		if (display->suspend)
-			r = display->suspend(display);
+		if (display->driver->suspend)
+			r = display->driver->suspend(display);
 
 		break;
 
@@ -1831,7 +1831,7 @@ static void omapfb_free_resources(struct omapfb2_device *fbdev)
 
 	for (i = 0; i < fbdev->num_displays; i++) {
 		if (fbdev->displays[i]->state != OMAP_DSS_DISPLAY_DISABLED)
-			fbdev->displays[i]->disable(fbdev->displays[i]);
+			fbdev->displays[i]->driver->disable(fbdev->displays[i]);
 
 		omap_dss_put_device(fbdev->displays[i]);
 	}
@@ -2192,7 +2192,7 @@ static int omapfb_probe(struct platform_device *pdev)
 #ifndef CONFIG_FB_OMAP2_FORCE_AUTO_UPDATE
 		u16 w, h;
 #endif
-		r = def_display->enable(def_display);
+		r = def_display->driver->enable(def_display);
 		if (r)
 			dev_warn(fbdev->dev, "Failed to enable display '%s'\n",
 					def_display->name);
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 15/17] OMAP: DSS2: move set/get_wss()
  2010-02-08 15:57                           ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Tomi Valkeinen
@ 2010-02-08 15:57                             ` Tomi Valkeinen
  2010-02-08 15:57                               ` [PATCH 16/17] OMAP: DSS2: move timing functions Tomi Valkeinen
  2010-02-09 10:15                             ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Grazvydas Ignotas
  1 sibling, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move set/get_wss() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    6 +-
 drivers/video/omap2/dss/display.c         |    8 ++--
 drivers/video/omap2/dss/venc.c            |   67 +++++++++++++++--------------
 3 files changed, 41 insertions(+), 40 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index cc2b4e3..e2d785c 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -472,9 +472,6 @@ struct omap_dss_device {
 	void (*get_timings)(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings);
 
-	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
-	u32 (*get_wss)(struct omap_dss_device *dssdev);
-
 	/* platform specific  */
 	int (*platform_enable)(struct omap_dss_device *dssdev);
 	void (*platform_disable)(struct omap_dss_device *dssdev);
@@ -519,6 +516,9 @@ struct omap_dss_driver {
 	void (*get_resolution)(struct omap_dss_device *dssdev,
 			u16 *xres, u16 *yres);
 	int (*get_recommended_bpp)(struct omap_dss_device *dssdev);
+
+	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
+	u32 (*get_wss)(struct omap_dss_device *dssdev);
 };
 
 int omap_dss_register_driver(struct omap_dss_driver *);
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index bc8ae35..3194f21 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -247,10 +247,10 @@ static ssize_t display_wss_show(struct device *dev,
 	struct omap_dss_device *dssdev = to_dss_device(dev);
 	unsigned int wss;
 
-	if (!dssdev->get_wss)
+	if (!dssdev->driver->get_wss)
 		return -ENOENT;
 
-	wss = dssdev->get_wss(dssdev);
+	wss = dssdev->driver->get_wss(dssdev);
 
 	return snprintf(buf, PAGE_SIZE, "0x%05x\n", wss);
 }
@@ -262,7 +262,7 @@ static ssize_t display_wss_store(struct device *dev,
 	unsigned long wss;
 	int r;
 
-	if (!dssdev->get_wss || !dssdev->set_wss)
+	if (!dssdev->driver->get_wss || !dssdev->driver->set_wss)
 		return -ENOENT;
 
 	if (strict_strtoul(buf, 0, &wss))
@@ -271,7 +271,7 @@ static ssize_t display_wss_store(struct device *dev,
 	if (wss > 0xfffff)
 		return -EINVAL;
 
-	r = dssdev->set_wss(dssdev, wss);
+	r = dssdev->driver->set_wss(dssdev, wss);
 	if (r)
 		return r;
 
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index a0ab52c..5c6e98b 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -557,6 +557,37 @@ static int venc_set_update_mode(struct omap_dss_device *dssdev,
 	return 0;
 }
 
+static u32 venc_get_wss(struct omap_dss_device *dssdev)
+{
+	/* Invert due to VENC_L21_WC_CTL:INV=1 */
+	return (venc.wss_data >> 8) ^ 0xfffff;
+}
+
+static int venc_set_wss(struct omap_dss_device *dssdev,	u32 wss)
+{
+	const struct venc_config *config;
+
+	DSSDBG("venc_set_wss\n");
+
+	mutex_lock(&venc.venc_lock);
+
+	config = venc_timings_to_config(&dssdev->panel.timings);
+
+	/* Invert due to VENC_L21_WC_CTL:INV=1 */
+	venc.wss_data = (wss ^ 0xfffff) << 8;
+
+	venc_enable_clocks(1);
+
+	venc_write_reg(VENC_BSTAMP_WSS_DATA, config->bstamp_wss_data |
+			venc.wss_data);
+
+	venc_enable_clocks(0);
+
+	mutex_unlock(&venc.venc_lock);
+
+	return 0;
+}
+
 static struct omap_dss_driver venc_driver = {
 	.probe		= venc_panel_probe,
 	.remove		= venc_panel_remove,
@@ -572,6 +603,9 @@ static struct omap_dss_driver venc_driver = {
 	.set_update_mode = venc_set_update_mode,
 	.get_update_mode = venc_get_update_mode,
 
+	.get_wss	= venc_get_wss,
+	.set_wss	= venc_set_wss,
+
 	.driver         = {
 		.name   = "venc",
 		.owner  = THIS_MODULE,
@@ -656,37 +690,6 @@ static int venc_check_timings(struct omap_dss_device *dssdev,
 	return -EINVAL;
 }
 
-static u32 venc_get_wss(struct omap_dss_device *dssdev)
-{
-	/* Invert due to VENC_L21_WC_CTL:INV=1 */
-	return (venc.wss_data >> 8) ^ 0xfffff;
-}
-
-static int venc_set_wss(struct omap_dss_device *dssdev,	u32 wss)
-{
-	const struct venc_config *config;
-
-	DSSDBG("venc_set_wss\n");
-
-	mutex_lock(&venc.venc_lock);
-
-	config = venc_timings_to_config(&dssdev->panel.timings);
-
-	/* Invert due to VENC_L21_WC_CTL:INV=1 */
-	venc.wss_data = (wss ^ 0xfffff) << 8;
-
-	venc_enable_clocks(1);
-
-	venc_write_reg(VENC_BSTAMP_WSS_DATA, config->bstamp_wss_data |
-			venc.wss_data);
-
-	venc_enable_clocks(0);
-
-	mutex_unlock(&venc.venc_lock);
-
-	return 0;
-}
-
 int venc_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("init_display\n");
@@ -694,8 +697,6 @@ int venc_init_display(struct omap_dss_device *dssdev)
 	dssdev->get_timings = venc_get_timings;
 	dssdev->set_timings = venc_set_timings;
 	dssdev->check_timings = venc_check_timings;
-	dssdev->get_wss = venc_get_wss;
-	dssdev->set_wss = venc_set_wss;
 
 	return 0;
 }
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 16/17] OMAP: DSS2: move timing functions
  2010-02-08 15:57                             ` [PATCH 15/17] OMAP: DSS2: move set/get_wss() Tomi Valkeinen
@ 2010-02-08 15:57                               ` Tomi Valkeinen
  2010-02-08 15:57                                 ` [PATCH 17/17] OMAP: DSS2: DSI: Add VC support for update Tomi Valkeinen
  0 siblings, 1 reply; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Move check/set/get_timings() from omap_dss_device to omap_dss_driver.

This is part of a larger patch-set, which moves the control from omapdss
driver to the display driver.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |   18 ++++---
 drivers/video/omap2/displays/panel-taal.c |    4 +-
 drivers/video/omap2/dss/display.c         |   10 ++--
 drivers/video/omap2/dss/dpi.c             |   16 ++----
 drivers/video/omap2/dss/sdi.c             |    8 ---
 drivers/video/omap2/dss/venc.c            |   82 ++++++++++++++--------------
 drivers/video/omap2/omapfb/omapfb-main.c  |   10 ++--
 7 files changed, 68 insertions(+), 80 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index e2d785c..ccf35a8 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -465,13 +465,6 @@ struct omap_dss_device {
 
 	enum omap_dss_display_state state;
 
-	int (*check_timings)(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings);
-	void (*set_timings)(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings);
-	void (*get_timings)(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings);
-
 	/* platform specific  */
 	int (*platform_enable)(struct omap_dss_device *dssdev);
 	void (*platform_disable)(struct omap_dss_device *dssdev);
@@ -517,6 +510,13 @@ struct omap_dss_driver {
 			u16 *xres, u16 *yres);
 	int (*get_recommended_bpp)(struct omap_dss_device *dssdev);
 
+	int (*check_timings)(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings);
+	void (*set_timings)(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings);
+	void (*get_timings)(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings);
+
 	int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
 	u32 (*get_wss)(struct omap_dss_device *dssdev);
 };
@@ -572,6 +572,10 @@ void omapdss_dsi_display_disable(struct omap_dss_device *dssdev);
 
 int omapdss_dpi_display_enable(struct omap_dss_device *dssdev);
 void omapdss_dpi_display_disable(struct omap_dss_device *dssdev);
+void dpi_set_timings(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings);
+int dpi_check_timings(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings);
 
 int omapdss_sdi_display_enable(struct omap_dss_device *dssdev);
 void omapdss_sdi_display_disable(struct omap_dss_device *dssdev);
diff --git a/drivers/video/omap2/displays/panel-taal.c b/drivers/video/omap2/displays/panel-taal.c
index cdb7617..e0f1c9e 100644
--- a/drivers/video/omap2/displays/panel-taal.c
+++ b/drivers/video/omap2/displays/panel-taal.c
@@ -516,8 +516,6 @@ static int taal_probe(struct omap_dss_device *dssdev)
 
 	dev_set_drvdata(&dssdev->dev, td);
 
-	dssdev->get_timings = taal_get_timings;
-
 	/* if no platform set_backlight() defined, presume DSI backlight
 	 * control */
 	if (!dssdev->set_backlight)
@@ -1108,6 +1106,8 @@ static struct omap_dss_driver taal_driver = {
 	.run_test	= taal_run_test,
 	.memory_read	= taal_memory_read,
 
+	.get_timings	= taal_get_timings,
+
 	.driver         = {
 		.name   = "taal",
 		.owner  = THIS_MODULE,
diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c
index 3194f21..74b923a 100644
--- a/drivers/video/omap2/dss/display.c
+++ b/drivers/video/omap2/dss/display.c
@@ -135,10 +135,10 @@ static ssize_t display_timings_show(struct device *dev,
 	struct omap_dss_device *dssdev = to_dss_device(dev);
 	struct omap_video_timings t;
 
-	if (!dssdev->get_timings)
+	if (!dssdev->driver->get_timings)
 		return -ENOENT;
 
-	dssdev->get_timings(dssdev, &t);
+	dssdev->driver->get_timings(dssdev, &t);
 
 	return snprintf(buf, PAGE_SIZE, "%u,%u/%u/%u/%u,%u/%u/%u/%u\n",
 			t.pixel_clock,
@@ -153,7 +153,7 @@ static ssize_t display_timings_store(struct device *dev,
 	struct omap_video_timings t;
 	int r, found;
 
-	if (!dssdev->set_timings || !dssdev->check_timings)
+	if (!dssdev->driver->set_timings || !dssdev->driver->check_timings)
 		return -ENOENT;
 
 	found = 0;
@@ -172,11 +172,11 @@ static ssize_t display_timings_store(struct device *dev,
 				&t.y_res, &t.vfp, &t.vbp, &t.vsw) != 9)
 		return -EINVAL;
 
-	r = dssdev->check_timings(dssdev, &t);
+	r = dssdev->driver->check_timings(dssdev, &t);
 	if (r)
 		return r;
 
-	dssdev->set_timings(dssdev, &t);
+	dssdev->driver->set_timings(dssdev, &t);
 
 	return size;
 }
diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c
index 1eef8b7..960e977 100644
--- a/drivers/video/omap2/dss/dpi.c
+++ b/drivers/video/omap2/dss/dpi.c
@@ -227,7 +227,7 @@ void omapdss_dpi_display_disable(struct omap_dss_device *dssdev)
 }
 EXPORT_SYMBOL(omapdss_dpi_display_disable);
 
-static void dpi_set_timings(struct omap_dss_device *dssdev,
+void dpi_set_timings(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings)
 {
 	DSSDBG("dpi_set_timings\n");
@@ -237,8 +237,9 @@ static void dpi_set_timings(struct omap_dss_device *dssdev,
 		dispc_go(OMAP_DSS_CHANNEL_LCD);
 	}
 }
+EXPORT_SYMBOL(dpi_set_timings);
 
-static int dpi_check_timings(struct omap_dss_device *dssdev,
+int dpi_check_timings(struct omap_dss_device *dssdev,
 			struct omap_video_timings *timings)
 {
 	bool is_tft;
@@ -292,21 +293,12 @@ static int dpi_check_timings(struct omap_dss_device *dssdev,
 
 	return 0;
 }
-
-static void dpi_get_timings(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings)
-{
-	*timings = dssdev->panel.timings;
-}
+EXPORT_SYMBOL(dpi_check_timings);
 
 int dpi_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("init_display\n");
 
-	dssdev->set_timings = dpi_set_timings;
-	dssdev->check_timings = dpi_check_timings;
-	dssdev->get_timings = dpi_get_timings;
-
 	return 0;
 }
 
diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c
index 929ceb3..12eb404 100644
--- a/drivers/video/omap2/dss/sdi.c
+++ b/drivers/video/omap2/dss/sdi.c
@@ -150,18 +150,10 @@ void omapdss_sdi_display_disable(struct omap_dss_device *dssdev)
 }
 EXPORT_SYMBOL(omapdss_sdi_display_disable);
 
-static void sdi_get_timings(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings)
-{
-	*timings = dssdev->panel.timings;
-}
-
 int sdi_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("SDI init\n");
 
-	dssdev->get_timings = sdi_get_timings;
-
 	return 0;
 }
 
diff --git a/drivers/video/omap2/dss/venc.c b/drivers/video/omap2/dss/venc.c
index 5c6e98b..f0ba573 100644
--- a/drivers/video/omap2/dss/venc.c
+++ b/drivers/video/omap2/dss/venc.c
@@ -557,6 +557,43 @@ static int venc_set_update_mode(struct omap_dss_device *dssdev,
 	return 0;
 }
 
+static void venc_get_timings(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings)
+{
+	*timings = dssdev->panel.timings;
+}
+
+static void venc_set_timings(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings)
+{
+	DSSDBG("venc_set_timings\n");
+
+	/* Reset WSS data when the TV standard changes. */
+	if (memcmp(&dssdev->panel.timings, timings, sizeof(*timings)))
+		venc.wss_data = 0;
+
+	dssdev->panel.timings = *timings;
+	if (dssdev->state == OMAP_DSS_DISPLAY_ACTIVE) {
+		/* turn the venc off and on to get new timings to use */
+		venc_panel_disable(dssdev);
+		venc_panel_enable(dssdev);
+	}
+}
+
+static int venc_check_timings(struct omap_dss_device *dssdev,
+			struct omap_video_timings *timings)
+{
+	DSSDBG("venc_check_timings\n");
+
+	if (memcmp(&omap_dss_pal_timings, timings, sizeof(*timings)) == 0)
+		return 0;
+
+	if (memcmp(&omap_dss_ntsc_timings, timings, sizeof(*timings)) == 0)
+		return 0;
+
+	return -EINVAL;
+}
+
 static u32 venc_get_wss(struct omap_dss_device *dssdev)
 {
 	/* Invert due to VENC_L21_WC_CTL:INV=1 */
@@ -603,6 +640,10 @@ static struct omap_dss_driver venc_driver = {
 	.set_update_mode = venc_set_update_mode,
 	.get_update_mode = venc_get_update_mode,
 
+	.get_timings	= venc_get_timings,
+	.set_timings	= venc_set_timings,
+	.check_timings	= venc_check_timings,
+
 	.get_wss	= venc_get_wss,
 	.set_wss	= venc_set_wss,
 
@@ -653,51 +694,10 @@ void venc_exit(void)
 	iounmap(venc.base);
 }
 
-static void venc_get_timings(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings)
-{
-	*timings = dssdev->panel.timings;
-}
-
-static void venc_set_timings(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings)
-{
-	DSSDBG("venc_set_timings\n");
-
-	/* Reset WSS data when the TV standard changes. */
-	if (memcmp(&dssdev->panel.timings, timings, sizeof(*timings)))
-		venc.wss_data = 0;
-
-	dssdev->panel.timings = *timings;
-	if (dssdev->state == OMAP_DSS_DISPLAY_ACTIVE) {
-		/* turn the venc off and on to get new timings to use */
-		venc_panel_disable(dssdev);
-		venc_panel_enable(dssdev);
-	}
-}
-
-static int venc_check_timings(struct omap_dss_device *dssdev,
-			struct omap_video_timings *timings)
-{
-	DSSDBG("venc_check_timings\n");
-
-	if (memcmp(&omap_dss_pal_timings, timings, sizeof(*timings)) == 0)
-		return 0;
-
-	if (memcmp(&omap_dss_ntsc_timings, timings, sizeof(*timings)) == 0)
-		return 0;
-
-	return -EINVAL;
-}
-
 int venc_init_display(struct omap_dss_device *dssdev)
 {
 	DSSDBG("init_display\n");
 
-	dssdev->get_timings = venc_get_timings;
-	dssdev->set_timings = venc_set_timings;
-	dssdev->check_timings = venc_check_timings;
-
 	return 0;
 }
 
diff --git a/drivers/video/omap2/omapfb/omapfb-main.c b/drivers/video/omap2/omapfb/omapfb-main.c
index f0b304d..5b2e269 100644
--- a/drivers/video/omap2/omapfb/omapfb-main.c
+++ b/drivers/video/omap2/omapfb/omapfb-main.c
@@ -705,9 +705,9 @@ int check_fb_var(struct fb_info *fbi, struct fb_var_screeninfo *var)
 	var->width              = -1;
 	var->grayscale          = 0;
 
-	if (display && display->get_timings) {
+	if (display && display->driver->get_timings) {
 		struct omap_video_timings timings;
-		display->get_timings(display, &timings);
+		display->driver->get_timings(display, &timings);
 
 		/* pixclock in ps, the rest in pixclock */
 		var->pixclock = timings.pixel_clock != 0 ?
@@ -2029,14 +2029,14 @@ static int omapfb_set_def_mode(struct omapfb2_device *fbdev,
 	fbdev->bpp_overrides[fbdev->num_bpp_overrides].bpp = bpp;
 	++fbdev->num_bpp_overrides;
 
-	if (!display->check_timings || !display->set_timings)
+	if (!display->driver->check_timings || !display->driver->set_timings)
 		return -EINVAL;
 
-	r = display->check_timings(display, &timings);
+	r = display->driver->check_timings(display, &timings);
 	if (r)
 		return r;
 
-	display->set_timings(display, &timings);
+	display->driver->set_timings(display, &timings);
 
 	return 0;
 }
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 17/17] OMAP: DSS2: DSI: Add VC support for update
  2010-02-08 15:57                               ` [PATCH 16/17] OMAP: DSS2: move timing functions Tomi Valkeinen
@ 2010-02-08 15:57                                 ` Tomi Valkeinen
  0 siblings, 0 replies; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-08 15:57 UTC (permalink / raw)
  To: linux-omap, linux-fbdev; +Cc: Tomi Valkeinen

Update was hardcoded to use virtual channel 0. This patch adds a parameter
that specifies the VC.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
---
 arch/arm/plat-omap/include/plat/display.h |    1 +
 drivers/video/omap2/dss/dsi.c             |   13 +++++++++----
 2 files changed, 10 insertions(+), 4 deletions(-)

diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
index ccf35a8..cd7b769 100644
--- a/arch/arm/plat-omap/include/plat/display.h
+++ b/arch/arm/plat-omap/include/plat/display.h
@@ -564,6 +564,7 @@ int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable);
 int omap_dsi_prepare_update(struct omap_dss_device *dssdev,
 				    u16 *x, u16 *y, u16 *w, u16 *h);
 int omap_dsi_update(struct omap_dss_device *dssdev,
+		int channel,
 		u16 x, u16 y, u16 w, u16 h,
 		void (*callback)(int, void *), void *data);
 
diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c
index 79d27de..624d53e 100644
--- a/drivers/video/omap2/dss/dsi.c
+++ b/drivers/video/omap2/dss/dsi.c
@@ -233,6 +233,7 @@ static struct
 
 	struct completion bta_completion;
 
+	int update_channel;
 	struct dsi_update_region update_region;
 
 	bool te_enabled;
@@ -2721,7 +2722,7 @@ static void dsi_update_screen_dispc(struct omap_dss_device *dssdev,
 	unsigned packet_len;
 	u32 l;
 	bool use_te_trigger;
-	const unsigned channel = 0;
+	const unsigned channel = dsi.update_channel;
 	/* line buffer is 1024 x 24bits */
 	/* XXX: for some reason using full buffer size causes considerable TX
 	 * slowdown with update sizes that fill the whole buffer */
@@ -2732,6 +2733,8 @@ static void dsi_update_screen_dispc(struct omap_dss_device *dssdev,
 	DSSDBG("dsi_update_screen_dispc(%d,%d %dx%d)\n",
 			x, y, w, h);
 
+	dsi_vc_config_vp(channel);
+
 	bytespp	= dssdev->ctrl.pixel_size / 8;
 	bytespl = w * bytespp;
 	bytespf = bytespl * h;
@@ -2799,7 +2802,7 @@ static void dsi_te_timeout(unsigned long arg)
 static void dsi_framedone_timeout_work_callback(struct work_struct *work)
 {
 	int r;
-	const int channel = 0;
+	const int channel = dsi.update_channel;
 	bool use_te_trigger;
 
 	DSSERR("Framedone not received for 250ms!\n");
@@ -2852,7 +2855,7 @@ static void dsi_framedone_irq_callback(void *data, u32 mask)
 static void dsi_handle_framedone(void)
 {
 	int r;
-	const int channel = 0;
+	const int channel = dsi.update_channel;
 	bool use_te_trigger;
 
 	use_te_trigger = dsi.te_enabled && !dsi.use_ext_te;
@@ -2935,13 +2938,15 @@ int omap_dsi_prepare_update(struct omap_dss_device *dssdev,
 EXPORT_SYMBOL(omap_dsi_prepare_update);
 
 int omap_dsi_update(struct omap_dss_device *dssdev,
+		int channel,
 		u16 x, u16 y, u16 w, u16 h,
 		void (*callback)(int, void *), void *data)
 {
+	dsi.update_channel = channel;
+
 	if (dssdev->manager->caps & OMAP_DSS_OVL_MGR_CAP_DISPC) {
 		dsi.framedone_callback = callback;
 		dsi.framedone_data = data;
-		dsi_vc_config_vp(0);
 
 		dsi.update_region.x = x;
 		dsi.update_region.y = y;
-- 
1.6.5


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* Re: [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume
  2010-02-08 15:57                           ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Tomi Valkeinen
  2010-02-08 15:57                             ` [PATCH 15/17] OMAP: DSS2: move set/get_wss() Tomi Valkeinen
@ 2010-02-09 10:15                             ` Grazvydas Ignotas
  2010-02-09 12:12                               ` Tomi Valkeinen
  1 sibling, 1 reply; 22+ messages in thread
From: Grazvydas Ignotas @ 2010-02-09 10:15 UTC (permalink / raw)
  To: Tomi Valkeinen; +Cc: linux-omap, linux-fbdev

On Mon, Feb 8, 2010 at 5:57 PM, Tomi Valkeinen <tomi.valkeinen@nokia.com> wrote:
> Move enable/disable/suspend/resume from omap_dss_device to
> omap_dss_driver.
>
> This is part of a larger patch-set, which moves the control from omapdss
> driver to the display driver.
>
> Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
> ---

<snip>

> diff --git a/drivers/video/omap2/displays/panel-tpo-td043mtea1.c b/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
> index f297a46..c6e4a7e 100644
> --- a/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
> +++ b/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
> @@ -262,18 +262,20 @@ static const struct omap_video_timings tpo_td043_timings = {
>        .vbp            = 34,
>  };
>
> -static int tpo_td043_enable(struct omap_dss_device *dssdev)
> +static int generic_panel_power_on(struct omap_dss_device *dssdev)

I guess you meant tpo_td043_power_on/tpo_td043_power_off?

I'll try to test your both series later this week.
--
To unsubscribe from this list: send the line "unsubscribe linux-omap" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume
  2010-02-09 10:15                             ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Grazvydas Ignotas
@ 2010-02-09 12:12                               ` Tomi Valkeinen
  0 siblings, 0 replies; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-09 12:12 UTC (permalink / raw)
  To: ext Grazvydas Ignotas; +Cc: linux-omap, linux-fbdev

On Tue, 2010-02-09 at 11:15 +0100, ext Grazvydas Ignotas wrote:
> On Mon, Feb 8, 2010 at 5:57 PM, Tomi Valkeinen <tomi.valkeinen@nokia.com> wrote:
> > Move enable/disable/suspend/resume from omap_dss_device to
> > omap_dss_driver.
> >
> > This is part of a larger patch-set, which moves the control from omapdss
> > driver to the display driver.
> >
> > Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
> > ---
> 
> <snip>
> 
> > diff --git a/drivers/video/omap2/displays/panel-tpo-td043mtea1.c b/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
> > index f297a46..c6e4a7e 100644
> > --- a/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
> > +++ b/drivers/video/omap2/displays/panel-tpo-td043mtea1.c
> > @@ -262,18 +262,20 @@ static const struct omap_video_timings tpo_td043_timings = {
> >        .vbp            = 34,
> >  };
> >
> > -static int tpo_td043_enable(struct omap_dss_device *dssdev)
> > +static int generic_panel_power_on(struct omap_dss_device *dssdev)
> 
> I guess you meant tpo_td043_power_on/tpo_td043_power_off?

Yes, copy paste error =)

> I'll try to test your both series later this week.

Thanks.

 Tomi



^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 00/17] OMAP DSS2 model restructuring
  2010-02-08 15:57 [PATCH 00/17] OMAP DSS2 model restructuring Tomi Valkeinen
  2010-02-08 15:57 ` [PATCH 01/17] OMAP: DSS2: DSI: change DSI bus_lock to semaphore Tomi Valkeinen
@ 2010-02-13 15:34 ` Grazvydas Ignotas
  2010-02-15  7:45   ` Tomi Valkeinen
  1 sibling, 1 reply; 22+ messages in thread
From: Grazvydas Ignotas @ 2010-02-13 15:34 UTC (permalink / raw)
  To: Tomi Valkeinen; +Cc: linux-omap, linux-fbdev

On Mon, Feb 8, 2010 at 5:57 PM, Tomi Valkeinen <tomi.valkeinen@nokia.com> wrote:
> Here are a bunch of patches that change the DSS2 driver's driver model a bit.
> This change was triggered by trying to support new hardware, and realizing that
> the current model just won't work.
>
> Currently the omapdss driver is in control of most aspects of the DSS, and
> omapdss calls necessary functions in display drivers. I made it that way to
> keep the display drivers simple, and I, naively, thought that it will work
> because the display panels are using standard bus interfaces and thus will be
> very similar. I was so wrong =).
>
> This patch set moves the control to the display driver. The display driver then
> calls omapdss functions to perform whatever deed is needed at that time. This
> will make display drivers slightly more complex, but it will be easier to
> control the hardware properly with strange or complex display devices.
>
> As a simple example, let's look at the update function.
>
> Currently user space app issues OMAPFB_UPDATE_WINDOW ioctl, and omapfb driver
> then calls update() in corresponding dss device struct, which goes to omapdss.
> omapdss will configure the update, calling the panel driver if needed.
>
> After these patches, omapfb will call update() in the panel driver. The panel
> driver will then call functions in omapdss to setup the update, start the
> update, and the panel driver will eventually get a callback informing that the
> update is done.
>
> These patches are still under work, but my basic tests on 3430SDP board seems
> to work ok.
>
> The patches can also be found from
> http://gitorious.org/linux-omap-dss2/linux work branch

Tested those along with the other series, seems to work fine on
pandora too. Panel callbacks like set_mirror
also work now, thanks.

Tested-by: Grazvydas Ignotas <notasas@gmail.com>

>
> Tomi Valkeinen (17):
>  OMAP: DSS2: DSI: change DSI bus_lock to semaphore
>  OMAP: DSS2: DSI: remove auto-update perf measurement
>  OMAP: DSS2: move run_test()
>  OMAP: DSS2: move memory_read()
>  OMAP: DSS2: move set/get_mirror()
>  OMAP: DSS2: move get/set_rotate()
>  OMAP: DSS2: move wait_vsync()
>  OMAP: DSS2: move enable/disable_channel to overlay manager
>  OMAP: DSS2: move get_resolution()
>  OMAP: DSS2: move get_recommended_bpp()
>  OMAP: DSS2: move enable/get_te()
>  OMAP: DSS2: move set/get_update_mode()
>  OMAP: DSS2: move update() and sync()
>  OMAP: DSS2: move enable/disable/suspend/resume
>  OMAP: DSS2: move set/get_wss()
>  OMAP: DSS2: move timing functions
>  OMAP: DSS2: DSI: Add VC support for update
>
>  arch/arm/plat-omap/include/plat/display.h          |  108 ++--
>  drivers/video/omap2/displays/panel-generic.c       |   56 ++-
>  .../video/omap2/displays/panel-sharp-lq043t1dg01.c |   67 ++-
>  .../video/omap2/displays/panel-sharp-ls037v7dw01.c |   42 +-
>  drivers/video/omap2/displays/panel-taal.c          |  221 +++++--
>  .../video/omap2/displays/panel-toppoly-tdo35s.c    |   56 ++-
>  .../video/omap2/displays/panel-tpo-td043mtea1.c    |   61 ++-
>  drivers/video/omap2/dss/core.c                     |    7 +
>  drivers/video/omap2/dss/dispc.c                    |   36 +-
>  drivers/video/omap2/dss/display.c                  |   87 +--
>  drivers/video/omap2/dss/dpi.c                      |  149 +----
>  drivers/video/omap2/dss/dsi.c                      |  829 ++++----------------
>  drivers/video/omap2/dss/dss.h                      |    4 +-
>  drivers/video/omap2/dss/manager.c                  |   48 +-
>  drivers/video/omap2/dss/overlay.c                  |    2 +-
>  drivers/video/omap2/dss/rfbi.c                     |  321 +-------
>  drivers/video/omap2/dss/sdi.c                      |  115 +---
>  drivers/video/omap2/dss/venc.c                     |  294 +++----
>  drivers/video/omap2/omapfb/omapfb-ioctl.c          |   44 +-
>  drivers/video/omap2/omapfb/omapfb-main.c           |   89 ++-
>  drivers/video/omap2/omapfb/omapfb.h                |    6 +
>  21 files changed, 1004 insertions(+), 1638 deletions(-)
>
> --
> To unsubscribe from this list: send the line "unsubscribe linux-omap" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
>
--
To unsubscribe from this list: send the line "unsubscribe linux-omap" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 00/17] OMAP DSS2 model restructuring
  2010-02-13 15:34 ` [PATCH 00/17] OMAP DSS2 model restructuring Grazvydas Ignotas
@ 2010-02-15  7:45   ` Tomi Valkeinen
  0 siblings, 0 replies; 22+ messages in thread
From: Tomi Valkeinen @ 2010-02-15  7:45 UTC (permalink / raw)
  To: ext Grazvydas Ignotas; +Cc: linux-omap, linux-fbdev

On Sat, 2010-02-13 at 16:34 +0100, ext Grazvydas Ignotas wrote:
> On Mon, Feb 8, 2010 at 5:57 PM, Tomi Valkeinen <tomi.valkeinen@nokia.com> wrote:
> > Here are a bunch of patches that change the DSS2 driver's driver model a bit.
> > This change was triggered by trying to support new hardware, and realizing that
> > the current model just won't work.
> >
> > Currently the omapdss driver is in control of most aspects of the DSS, and
> > omapdss calls necessary functions in display drivers. I made it that way to
> > keep the display drivers simple, and I, naively, thought that it will work
> > because the display panels are using standard bus interfaces and thus will be
> > very similar. I was so wrong =).
> >
> > This patch set moves the control to the display driver. The display driver then
> > calls omapdss functions to perform whatever deed is needed at that time. This
> > will make display drivers slightly more complex, but it will be easier to
> > control the hardware properly with strange or complex display devices.
> >
> > As a simple example, let's look at the update function.
> >
> > Currently user space app issues OMAPFB_UPDATE_WINDOW ioctl, and omapfb driver
> > then calls update() in corresponding dss device struct, which goes to omapdss.
> > omapdss will configure the update, calling the panel driver if needed.
> >
> > After these patches, omapfb will call update() in the panel driver. The panel
> > driver will then call functions in omapdss to setup the update, start the
> > update, and the panel driver will eventually get a callback informing that the
> > update is done.
> >
> > These patches are still under work, but my basic tests on 3430SDP board seems
> > to work ok.
> >
> > The patches can also be found from
> > http://gitorious.org/linux-omap-dss2/linux work branch
> 
> Tested those along with the other series, seems to work fine on
> pandora too. Panel callbacks like set_mirror
> also work now, thanks.
> 
> Tested-by: Grazvydas Ignotas <notasas@gmail.com>

Ok, thanks!

 Tomi



^ permalink raw reply	[flat|nested] 22+ messages in thread

end of thread, other threads:[~2010-02-15  7:42 UTC | newest]

Thread overview: 22+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2010-02-08 15:57 [PATCH 00/17] OMAP DSS2 model restructuring Tomi Valkeinen
2010-02-08 15:57 ` [PATCH 01/17] OMAP: DSS2: DSI: change DSI bus_lock to semaphore Tomi Valkeinen
2010-02-08 15:57   ` [PATCH 02/17] OMAP: DSS2: DSI: remove auto-update perf measurement Tomi Valkeinen
2010-02-08 15:57     ` [PATCH 03/17] OMAP: DSS2: move run_test() Tomi Valkeinen
2010-02-08 15:57       ` [PATCH 04/17] OMAP: DSS2: move memory_read() Tomi Valkeinen
2010-02-08 15:57         ` [PATCH 05/17] OMAP: DSS2: move set/get_mirror() Tomi Valkeinen
2010-02-08 15:57           ` [PATCH 06/17] OMAP: DSS2: move get/set_rotate() Tomi Valkeinen
2010-02-08 15:57             ` [PATCH 07/17] OMAP: DSS2: move wait_vsync() Tomi Valkeinen
2010-02-08 15:57               ` [PATCH 08/17] OMAP: DSS2: move enable/disable_channel to overlay manager Tomi Valkeinen
2010-02-08 15:57                 ` [PATCH 09/17] OMAP: DSS2: move get_resolution() Tomi Valkeinen
2010-02-08 15:57                   ` [PATCH 10/17] OMAP: DSS2: move get_recommended_bpp() Tomi Valkeinen
2010-02-08 15:57                     ` [PATCH 11/17] OMAP: DSS2: move enable/get_te() Tomi Valkeinen
2010-02-08 15:57                       ` [PATCH 12/17] OMAP: DSS2: move set/get_update_mode() Tomi Valkeinen
2010-02-08 15:57                         ` [PATCH 13/17] OMAP: DSS2: move update() and sync() Tomi Valkeinen
2010-02-08 15:57                           ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Tomi Valkeinen
2010-02-08 15:57                             ` [PATCH 15/17] OMAP: DSS2: move set/get_wss() Tomi Valkeinen
2010-02-08 15:57                               ` [PATCH 16/17] OMAP: DSS2: move timing functions Tomi Valkeinen
2010-02-08 15:57                                 ` [PATCH 17/17] OMAP: DSS2: DSI: Add VC support for update Tomi Valkeinen
2010-02-09 10:15                             ` [PATCH 14/17] OMAP: DSS2: move enable/disable/suspend/resume Grazvydas Ignotas
2010-02-09 12:12                               ` Tomi Valkeinen
2010-02-13 15:34 ` [PATCH 00/17] OMAP DSS2 model restructuring Grazvydas Ignotas
2010-02-15  7:45   ` Tomi Valkeinen

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).