gpu: pvr: Use DSS notifier to signal flip complete events
authorVille Syrjälä <ville.syrjala@nokia.com>
Tue, 25 May 2010 20:30:41 +0000 (23:30 +0300)
committerGrazvydas Ignotas <notasas@gmail.com>
Sun, 20 May 2012 18:09:41 +0000 (21:09 +0300)
Utilize to the DSS GO notifier to get callbacks when the flip
has completed.

Signed-off-by: Ville Syrjälä <ville.syrjala@nokia.com>
pvr/module.c
pvr/pvr_events.c
pvr/pvr_events.h

index 64ef368..da24ed9 100644 (file)
@@ -276,6 +276,8 @@ static void __exit pvr_cleanup(void)
 
        SysAcquireData(&sysdata);
 
+       pvr_exit_events();
+
        platform_driver_unregister(&pvr_driver);
 
        PVRMMapCleanup();
index a26506b..bb851cb 100644 (file)
@@ -8,10 +8,14 @@
 #include <linux/time.h>
 #include <linux/uaccess.h>
 #include <linux/fs.h>
+#include <linux/notifier.h>
+
+#include <plat/display.h>
 
 static spinlock_t event_lock;
 static struct list_head sync_wait_list;
 static struct list_head flip_wait_list;
+static struct notifier_block dss_nb;
 
 static inline bool is_render_complete(const struct PVRSRV_SYNC_DATA *sync)
 {
@@ -112,11 +116,10 @@ int pvr_flip_event_req(struct PVRSRV_FILE_PRIVATE_DATA *priv,
        priv->event_space -= sizeof(e->event);
 
        list_add_tail(&e->base.link, &flip_wait_list);
-       pvr_signal_flip_event(e, &now);
 
        spin_unlock_irqrestore(&event_lock, flags);
 
-       return 0;
+       return omap_dss_request_notify(OMAP_DSS_NOTIFY_GO_OVL, overlay);
 }
 
 static bool pvr_dequeue_event(struct PVRSRV_FILE_PRIVATE_DATA *priv,
@@ -208,6 +211,34 @@ void pvr_handle_sync_events(void)
        spin_unlock_irqrestore(&event_lock, flags);
 }
 
+static int dss_notifier_callback(struct notifier_block *nb,
+                                unsigned long event, void *data)
+{
+       struct pvr_pending_flip_event *e;
+       struct pvr_pending_flip_event *t;
+       struct timeval now;
+       unsigned long flags;
+       long overlay = (long) data;
+
+       if (event != OMAP_DSS_NOTIFY_GO_OVL)
+               return 0;
+
+       do_gettimeofday(&now);
+
+       spin_lock_irqsave(&event_lock, flags);
+
+       list_for_each_entry_safe(e, t, &flip_wait_list, base.link) {
+               if (e->event.overlay != overlay)
+                       continue;
+
+               pvr_signal_flip_event(e, &now);
+       }
+
+       spin_unlock_irqrestore(&event_lock, flags);
+
+       return 0;
+}
+
 void pvr_release_events(struct PVRSRV_FILE_PRIVATE_DATA *priv)
 {
        struct pvr_pending_event *w;
@@ -245,4 +276,12 @@ void pvr_init_events(void)
        spin_lock_init(&event_lock);
        INIT_LIST_HEAD(&sync_wait_list);
        INIT_LIST_HEAD(&flip_wait_list);
+
+       dss_nb.notifier_call = dss_notifier_callback;
+       omap_dss_register_notifier(&dss_nb);
+}
+
+void pvr_exit_events(void)
+{
+       omap_dss_unregister_notifier(&dss_nb);
 }
index b90074d..5183ed3 100644 (file)
@@ -76,6 +76,7 @@ struct pvr_pending_flip_event {
 };
 
 void pvr_init_events(void);
+void pvr_exit_events(void);
 
 int pvr_sync_event_req(struct PVRSRV_FILE_PRIVATE_DATA *priv,
                        const struct PVRSRV_KERNEL_SYNC_INFO *sync_info,