VIA_WAIT_ON() is a direct copy of DRM_WAIT_ON() from
drm_os_linux.h.
The copy is made so we can avoid the dependency on the legacy header.
A more involved approach had been to introduce wait_event_* but for this
legacy driver the simpler and more safe approach with a copy of the
macro was selected.
Added the relevant header files for the functions used in VIA_WAIT_ON.

Users of the macro will come in a follow-up patch.

Signed-off-by: Sam Ravnborg <[email protected]>
Cc: Kevin Brace <[email protected]>
Cc: Thomas Hellstrom <[email protected]>
Cc: "Gustavo A. R. Silva" <[email protected]>
Cc: Mike Marshall <[email protected]>
Cc: Ira Weiny <[email protected]>
Cc: Daniel Vetter <[email protected]>
Cc: Emil Velikov <[email protected]>
Cc: Michel Dänzer <[email protected]>
---
 drivers/gpu/drm/via/via_drv.h | 42 ++++++++++++++++++++++++++++++++++-
 1 file changed, 41 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/via/via_drv.h b/drivers/gpu/drm/via/via_drv.h
index d5a2b1ffd8c1..664b7f8a20c4 100644
--- a/drivers/gpu/drm/via/via_drv.h
+++ b/drivers/gpu/drm/via/via_drv.h
@@ -24,8 +24,13 @@
 #ifndef _VIA_DRV_H_
 #define _VIA_DRV_H_
 
-#include <drm/drm_mm.h>
+#include <linux/jiffies.h>
+#include <linux/sched.h>
+#include <linux/sched/signal.h>
+#include <linux/wait.h>
+
 #include <drm/drm_legacy.h>
+#include <drm/drm_mm.h>
 
 #define DRIVER_AUTHOR  "Various"
 
@@ -127,6 +132,41 @@ enum via_family {
 #define VIA_WRITE8(reg, val) \
        writeb(val, ((void __iomem *)VIA_BASE->handle) + (reg))
 
+/*
+ * Poll in a loop waiting for 'contidition' to be true.
+ * Note: A direct replacement with wait_event_interruptible_timeout()
+ *       will not work unless driver is updated to emit wake_up()
+ *       in relevant places that can impact the 'condition'
+ *
+ * Returns:
+ *   ret keeps current value if 'condition' becomes true
+ *   ret = -BUSY if timeout happens
+ *   ret = -EINTR if a signal interrupted the waiting period
+ */
+#define VIA_WAIT_ON( ret, queue, timeout, condition )          \
+do {                                                           \
+       DECLARE_WAITQUEUE(entry, current);                      \
+       unsigned long end = jiffies + (timeout);                \
+       add_wait_queue(&(queue), &entry);                       \
+                                                               \
+       for (;;) {                                              \
+               __set_current_state(TASK_INTERRUPTIBLE);        \
+               if (condition)                                  \
+                       break;                                  \
+               if (time_after_eq(jiffies, end)) {              \
+                       ret = -EBUSY;                           \
+                       break;                                  \
+               }                                               \
+               schedule_timeout((HZ/100 > 1) ? HZ/100 : 1);    \
+               if (signal_pending(current)) {                  \
+                       ret = -EINTR;                           \
+                       break;                                  \
+               }                                               \
+       }                                                       \
+       __set_current_state(TASK_RUNNING);                      \
+       remove_wait_queue(&(queue), &entry);                    \
+} while (0)
+
 extern const struct drm_ioctl_desc via_ioctls[];
 extern int via_max_ioctl;
 
-- 
2.20.1

_______________________________________________
dri-devel mailing list
[email protected]
https://lists.freedesktop.org/mailman/listinfo/dri-devel

Reply via email to