xref: /openbsd-src/sys/dev/pci/drm/include/linux/dma-fence.h (revision 3374c67d44f9b75b98444cbf63020f777792342e)
1 /* Public domain. */
2 
3 #ifndef _LINUX_DMA_FENCE_H
4 #define _LINUX_DMA_FENCE_H
5 
6 #include <sys/types.h>
7 #include <sys/mutex.h>
8 #include <linux/kref.h>
9 #include <linux/list.h>
10 #include <linux/sched.h>
11 #include <linux/rcupdate.h>
12 
13 #define DMA_FENCE_TRACE(fence, fmt, args...) do {} while(0)
14 
15 struct dma_fence {
16 	struct kref refcount;
17 	const struct dma_fence_ops *ops;
18 	unsigned long flags;
19 	uint64_t context;
20 	uint64_t seqno;
21 	struct mutex *lock;
22 	union {
23 		struct list_head cb_list;
24 		ktime_t timestamp;
25 		struct rcu_head rcu;
26 	};
27 	int error;
28 };
29 
30 enum dma_fence_flag_bits {
31 	DMA_FENCE_FLAG_SIGNALED_BIT,
32 	DMA_FENCE_FLAG_TIMESTAMP_BIT,
33 	DMA_FENCE_FLAG_ENABLE_SIGNAL_BIT,
34 	DMA_FENCE_FLAG_USER_BITS,
35 };
36 
37 struct dma_fence_ops {
38 	const char * (*get_driver_name)(struct dma_fence *);
39 	const char * (*get_timeline_name)(struct dma_fence *);
40 	bool (*enable_signaling)(struct dma_fence *);
41 	bool (*signaled)(struct dma_fence *);
42 	long (*wait)(struct dma_fence *, bool, long);
43 	void (*release)(struct dma_fence *);
44 	bool use_64bit_seqno;
45 };
46 
47 struct dma_fence_cb;
48 typedef void (*dma_fence_func_t)(struct dma_fence *fence, struct dma_fence_cb *cb);
49 
50 struct dma_fence_cb {
51 	struct list_head node;
52 	dma_fence_func_t func;
53 };
54 
55 uint64_t dma_fence_context_alloc(unsigned int);
56 struct dma_fence *dma_fence_get(struct dma_fence *);
57 struct dma_fence *dma_fence_get_rcu(struct dma_fence *);
58 struct dma_fence *dma_fence_get_rcu_safe(struct dma_fence **);
59 void dma_fence_release(struct kref *);
60 void dma_fence_put(struct dma_fence *);
61 int dma_fence_signal(struct dma_fence *);
62 int dma_fence_signal_locked(struct dma_fence *);
63 int dma_fence_signal_timestamp(struct dma_fence *, ktime_t);
64 int dma_fence_signal_timestamp_locked(struct dma_fence *, ktime_t);
65 bool dma_fence_is_signaled(struct dma_fence *);
66 bool dma_fence_is_signaled_locked(struct dma_fence *);
67 long dma_fence_default_wait(struct dma_fence *, bool, long);
68 long dma_fence_wait_any_timeout(struct dma_fence **, uint32_t, bool, long,
69     uint32_t *);
70 long dma_fence_wait_timeout(struct dma_fence *, bool, long);
71 long dma_fence_wait(struct dma_fence *, bool);
72 void dma_fence_enable_sw_signaling(struct dma_fence *);
73 void dma_fence_init(struct dma_fence *, const struct dma_fence_ops *,
74     struct mutex *, uint64_t, uint64_t);
75 int dma_fence_add_callback(struct dma_fence *, struct dma_fence_cb *,
76     dma_fence_func_t);
77 bool dma_fence_remove_callback(struct dma_fence *, struct dma_fence_cb *);
78 bool dma_fence_is_container(struct dma_fence *);
79 
80 struct dma_fence *dma_fence_get_stub(void);
81 struct dma_fence *dma_fence_allocate_private_stub(void);
82 
83 static inline void
84 dma_fence_free(struct dma_fence *fence)
85 {
86 	free(fence, M_DRM, 0);
87 }
88 
89 /*
90  * is a later than b
91  * if a and b are the same, should return false to avoid unwanted work
92  */
93 static inline bool
94 __dma_fence_is_later(uint64_t a, uint64_t b, const struct dma_fence_ops *ops)
95 {
96 	uint32_t al, bl;
97 
98 	if (ops->use_64bit_seqno)
99 		return a > b;
100 
101 	al = a & 0xffffffff;
102 	bl = b & 0xffffffff;
103 
104 	return (int)(al - bl) > 0;
105 }
106 
107 static inline bool
108 dma_fence_is_later(struct dma_fence *a, struct dma_fence *b)
109 {
110 	if (a->context != b->context)
111 		return false;
112 	return __dma_fence_is_later(a->seqno, b->seqno, a->ops);
113 }
114 
115 static inline void
116 dma_fence_set_error(struct dma_fence *fence, int error)
117 {
118 	fence->error = error;
119 }
120 
121 static inline bool
122 dma_fence_begin_signalling(void)
123 {
124 	return true;
125 }
126 
127 static inline void
128 dma_fence_end_signalling(bool x)
129 {
130 }
131 
132 #endif
133