-
Notifications
You must be signed in to change notification settings - Fork 1
/
0018-gbm-add-gbm_bo_blit.patch
213 lines (196 loc) · 7.25 KB
/
0018-gbm-add-gbm_bo_blit.patch
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
From 3cd9a9c294a177303a71f0babfe9e91366ef34fb Mon Sep 17 00:00:00 2001
From: Brendan King <Brendan.King@imgtec.com>
Date: Tue, 28 Nov 2017 16:27:38 +0000
Subject: [PATCH] gbm: add gbm_bo_blit
For the GBM DRI backend, gbm_bo_blit is a wrapper around blitImage in
the DRI Image extension.
---
src/gbm/backends/dri/gbm_dri.c | 33 +++++++++++++++++++++++++++++++++
src/gbm/main/gbm.c | 31 +++++++++++++++++++++++++++++++
src/gbm/main/gbm.h | 21 +++++++++++++++++++++
src/gbm/main/gbm_abi_check.c | 20 +++++++++++++++++++-
src/gbm/main/gbm_backend_abi.h | 8 ++++++++
5 files changed, 112 insertions(+), 1 deletion(-)
diff --git a/src/gbm/backends/dri/gbm_dri.c b/src/gbm/backends/dri/gbm_dri.c
index 644ea3c..00fcc57 100644
--- a/src/gbm/backends/dri/gbm_dri.c
+++ b/src/gbm/backends/dri/gbm_dri.c
@@ -1400,6 +1400,37 @@ gbm_dri_surface_destroy(struct gbm_surface *_surf)
free(surf);
}
+static int
+gbm_dri_bo_blit(struct gbm_bo *_dst_bo, struct gbm_bo *_src_bo,
+ int dst_x0, int dst_y0, int dst_width, int dst_height,
+ int src_x0, int src_y0, int src_width, int src_height,
+ enum gbm_blit_flags flags)
+{
+ struct gbm_dri_device *dri = gbm_dri_device(_dst_bo->gbm);
+ struct gbm_dri_bo *dst_bo = gbm_dri_bo(_dst_bo);
+ struct gbm_dri_bo *src_bo = gbm_dri_bo(_src_bo);
+
+ if (!dri->image || dri->image->base.version < 9 || !dri->image->blitImage) {
+ errno = ENOSYS;
+ return 0;
+ }
+
+ mtx_lock(&dri->mutex);
+ if (!dri->context)
+ dri->context = dri->dri2->createNewContext(dri->screen, NULL,
+ NULL, NULL);
+ assert(dri->context);
+ mtx_unlock(&dri->mutex);
+
+ /* GBM flags and DRI flags are the same, so just pass them on */
+ dri->image->blitImage(dri->context, dst_bo->image, src_bo->image,
+ dst_x0, dst_y0, dst_width, dst_height,
+ src_x0, src_y0, src_width, src_height,
+ flags);
+
+ return 1;
+}
+
static void
dri_destroy(struct gbm_device *gbm)
{
@@ -1461,6 +1492,8 @@ dri_device_create(int fd, uint32_t gbm_backend_version)
dri->base.v0.name = "drm";
+ dri->base.v1.bo_blit = gbm_dri_bo_blit;
+
dri->visual_table = gbm_dri_visuals_table;
dri->num_visuals = ARRAY_SIZE(gbm_dri_visuals_table);
diff --git a/src/gbm/main/gbm.c b/src/gbm/main/gbm.c
index ab685b8..3ce816f 100644
--- a/src/gbm/main/gbm.c
+++ b/src/gbm/main/gbm.c
@@ -825,6 +825,37 @@ gbm_format_get_name(uint32_t gbm_format, struct gbm_format_name_desc *desc)
return desc->name;
}
+/**
+ * Blit from one buffer object to another
+ *
+ * \param dst_bo The destination buffer object
+ * \param src_bo The source buffer object
+ * \param dst_x0 The X coordinate (top left origin) of the destination rectangle
+ * \param dst_y0 The Y coordinate (top left origin) of the destination rectangle
+ * \param dst_width The width of the destination rectangle
+ * \param dst_height The height of the destination rectangle
+ * \param src_x0 The X coordinate (top left origin) of the source rectangle
+ * \param src_y0 The Y coordinate (top left origin) of the source rectangle
+ * \param src_width The width of the source rectangle
+ * \param src_height The height of the source rectangle
+ * \param flags The flags for the blit
+ * \return 1 on success, 0 otherwise
+ */
+GBM_EXPORT int
+gbm_bo_blit(struct gbm_bo *dst_bo, struct gbm_bo *src_bo,
+ int dst_x0, int dst_y0, int dst_width, int dst_height,
+ int src_x0, int src_y0, int src_width, int src_height,
+ enum gbm_blit_flags flags)
+{
+ if (dst_bo->gbm->v0.backend_version >= 1)
+ return dst_bo->gbm->v1.bo_blit(dst_bo, src_bo,
+ dst_x0, dst_y0, dst_width, dst_height,
+ src_x0, src_y0, src_width, src_height,
+ flags);
+ else
+ return 0;
+}
+
/**
* A global table of functions and global variables defined in the core GBM
* code that need to be accessed directly by GBM backends.
diff --git a/src/gbm/main/gbm.h b/src/gbm/main/gbm.h
index ea3cc1b..57fd1b9 100644
--- a/src/gbm/main/gbm.h
+++ b/src/gbm/main/gbm.h
@@ -253,6 +253,21 @@ enum gbm_bo_flags {
GBM_BO_USE_PROTECTED = (1 << 5),
};
+/**
+ * Flags to control the behaviour of a blit - these are passed to
+ * gbm_bo_blit().
+ */
+enum gbm_blit_flags {
+ /**
+ * Force blit execution in finite time
+ */
+ GBM_BLIT_FLAG_FLUSH = 0x0001,
+ /**
+ * Flush, and wait for the blit to complete
+ */
+ GBM_BLIT_FLAG_FINISH = 0x0002
+};
+
int
gbm_device_get_fd(struct gbm_device *gbm);
@@ -449,6 +464,12 @@ gbm_surface_destroy(struct gbm_surface *surface);
char *
gbm_format_get_name(uint32_t gbm_format, struct gbm_format_name_desc *desc);
+int
+gbm_bo_blit(struct gbm_bo *dst_bo, struct gbm_bo *src_bo,
+ int dst_x0, int dst_y0, int dst_width, int dst_height,
+ int src_x0, int src_y0, int src_width, int src_height,
+ enum gbm_blit_flags flags);
+
#ifdef __cplusplus
}
#endif
diff --git a/src/gbm/main/gbm_abi_check.c b/src/gbm/main/gbm_abi_check.c
index feca099..0153b5a 100644
--- a/src/gbm/main/gbm_abi_check.c
+++ b/src/gbm/main/gbm_abi_check.c
@@ -106,6 +106,21 @@ struct gbm_device_abi0 {
struct gbm_device_v0_abi0 v0;
};
+#define GBM_BACKEND_ABI_VERSION_abi1 1
+struct gbm_device_v1_abi1 {
+ int (*bo_blit)(struct gbm_bo *dst_bo, struct gbm_bo *src_bo,
+ int dst_x0, int dst_y0, int dst_width, int dst_height,
+ int src_x0, int src_y0, int src_width, int src_height,
+ enum gbm_blit_flags flags);
+};
+
+struct gbm_device_abi1 {
+ /* Hack to make a gbm_device detectable by its first element. */
+ struct gbm_device *(*dummy)(int);
+ struct gbm_device_v0_abi0 v0;
+ struct gbm_device_v1_abi1 v1;
+};
+
/**
* GBM buffer object interface corresponding to GBM_BACKEND_ABI_VERSION = 0
*
@@ -364,8 +379,11 @@ int main(int argc, char **argv)
CHECK_MEMBER_CURRENT(gbm_device_v0, _abi0, surface_has_free_buffers);
CHECK_MEMBER_CURRENT(gbm_device_v0, _abi0, surface_destroy);
+ CHECK_MEMBER_CURRENT(gbm_device_v1, _abi1, bo_blit);
+
/* Size of ABI-versioned substructures verified by above member checks */
- CHECK_SIZE_CURRENT (gbm_device, _abi0);
+ CHECK_SIZE (gbm_device, _abi0, _abi1);
+ CHECK_SIZE_CURRENT (gbm_device, _abi1);
/* Check current gbm_bo ABI against gbm_bo_abi0*/
diff --git a/src/gbm/main/gbm_backend_abi.h b/src/gbm/main/gbm_backend_abi.h
index 222ce34..17f5e0c 100644
--- a/src/gbm/main/gbm_backend_abi.h
+++ b/src/gbm/main/gbm_backend_abi.h
@@ -157,6 +157,13 @@ struct gbm_device_v0 {
void (*surface_destroy)(struct gbm_surface *surface);
};
+struct gbm_device_v1 {
+ int (*bo_blit)(struct gbm_bo *dst_bo, struct gbm_bo *src_bo,
+ int dst_x0, int dst_y0, int dst_width, int dst_height,
+ int src_x0, int src_y0, int src_width, int src_height,
+ enum gbm_blit_flags flags);
+};
+
/**
* The device used for the memory allocation.
*
@@ -169,6 +176,7 @@ struct gbm_device {
/* Hack to make a gbm_device detectable by its first element. */
struct gbm_device *(*dummy)(int);
struct gbm_device_v0 v0;
+ struct gbm_device_v1 v1;
};
/**