~mmach/netext73/mesa-haswell

« back to all changes in this revision

Viewing changes to src/gallium/winsys/i915/drm/i915_drm_buffer.c

  • Committer: mmach
  • Date: 2022-09-22 19:56:13 UTC
  • Revision ID: netbit73@gmail.com-20220922195613-wtik9mmy20tmor0i
2022-09-22 21:17:09

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
#include "frontend/drm_driver.h"
2
 
#include "i915_drm_winsys.h"
3
 
#include "util/u_memory.h"
4
 
 
5
 
#include "drm-uapi/i915_drm.h"
6
 
 
7
 
static char *i915_drm_type_to_name(enum i915_winsys_buffer_type type)
8
 
{
9
 
   char *name;
10
 
 
11
 
   if (type == I915_NEW_TEXTURE) {
12
 
      name = "gallium3d_texture";
13
 
   } else if (type == I915_NEW_VERTEX) {
14
 
      name = "gallium3d_vertex";
15
 
   } else if (type == I915_NEW_SCANOUT) {
16
 
      name = "gallium3d_scanout";
17
 
   } else {
18
 
      assert(0);
19
 
      name = "gallium3d_unknown";
20
 
   }
21
 
 
22
 
   return name;
23
 
}
24
 
 
25
 
static struct i915_winsys_buffer *
26
 
i915_drm_buffer_create(struct i915_winsys *iws,
27
 
                        unsigned size,
28
 
                        enum i915_winsys_buffer_type type)
29
 
{
30
 
   struct i915_drm_buffer *buf = CALLOC_STRUCT(i915_drm_buffer);
31
 
   struct i915_drm_winsys *idws = i915_drm_winsys(iws);
32
 
 
33
 
   if (!buf)
34
 
      return NULL;
35
 
 
36
 
   buf->magic = 0xDEAD1337;
37
 
   buf->flinked = false;
38
 
   buf->flink = 0;
39
 
 
40
 
   buf->bo = drm_intel_bo_alloc(idws->gem_manager,
41
 
                                i915_drm_type_to_name(type), size, 0);
42
 
 
43
 
   if (!buf->bo)
44
 
      goto err;
45
 
 
46
 
   return (struct i915_winsys_buffer *)buf;
47
 
 
48
 
err:
49
 
   assert(0);
50
 
   FREE(buf);
51
 
   return NULL;
52
 
}
53
 
 
54
 
static struct i915_winsys_buffer *
55
 
i915_drm_buffer_create_tiled(struct i915_winsys *iws,
56
 
                             unsigned *stride, unsigned height, 
57
 
                             enum i915_winsys_buffer_tile *tiling,
58
 
                             enum i915_winsys_buffer_type type)
59
 
{
60
 
   struct i915_drm_buffer *buf = CALLOC_STRUCT(i915_drm_buffer);
61
 
   struct i915_drm_winsys *idws = i915_drm_winsys(iws);
62
 
   unsigned long pitch = 0;
63
 
   uint32_t tiling_mode = *tiling;
64
 
 
65
 
   if (!buf)
66
 
      return NULL;
67
 
 
68
 
   buf->magic = 0xDEAD1337;
69
 
   buf->flinked = false;
70
 
   buf->flink = 0;
71
 
 
72
 
   buf->bo = drm_intel_bo_alloc_tiled(idws->gem_manager,
73
 
                                      i915_drm_type_to_name(type),
74
 
                                      *stride, height, 1,
75
 
                                      &tiling_mode, &pitch, 0);
76
 
 
77
 
   if (!buf->bo)
78
 
      goto err;
79
 
 
80
 
   *stride = pitch;
81
 
   *tiling = tiling_mode;
82
 
   return (struct i915_winsys_buffer *)buf;
83
 
 
84
 
err:
85
 
   assert(0);
86
 
   FREE(buf);
87
 
   return NULL;
88
 
}
89
 
 
90
 
static struct i915_winsys_buffer *
91
 
i915_drm_buffer_from_handle(struct i915_winsys *iws,
92
 
                            struct winsys_handle *whandle,
93
 
                            unsigned height,
94
 
                            enum i915_winsys_buffer_tile *tiling,
95
 
                            unsigned *stride)
96
 
{
97
 
   struct i915_drm_winsys *idws = i915_drm_winsys(iws);
98
 
   struct i915_drm_buffer *buf;
99
 
   uint32_t tile = 0, swizzle = 0;
100
 
 
101
 
   if ((whandle->type != WINSYS_HANDLE_TYPE_SHARED) && (whandle->type != WINSYS_HANDLE_TYPE_FD))
102
 
      return NULL;
103
 
 
104
 
   if (whandle->offset != 0)
105
 
      return NULL;
106
 
 
107
 
   buf = CALLOC_STRUCT(i915_drm_buffer);
108
 
   if (!buf)
109
 
      return NULL;
110
 
 
111
 
   buf->magic = 0xDEAD1337;
112
 
 
113
 
   if (whandle->type == WINSYS_HANDLE_TYPE_SHARED)
114
 
       buf->bo = drm_intel_bo_gem_create_from_name(idws->gem_manager, "gallium3d_from_handle", whandle->handle);
115
 
   else if (whandle->type == WINSYS_HANDLE_TYPE_FD) {
116
 
       int fd = (int) whandle->handle;
117
 
       buf->bo = drm_intel_bo_gem_create_from_prime(idws->gem_manager, fd, height * whandle->stride);
118
 
   }
119
 
 
120
 
   buf->flinked = true;
121
 
   buf->flink = whandle->handle;
122
 
 
123
 
   if (!buf->bo)
124
 
      goto err;
125
 
 
126
 
   drm_intel_bo_get_tiling(buf->bo, &tile, &swizzle);
127
 
 
128
 
   *stride = whandle->stride;
129
 
   *tiling = tile;
130
 
 
131
 
   return (struct i915_winsys_buffer *)buf;
132
 
 
133
 
err:
134
 
   FREE(buf);
135
 
   return NULL;
136
 
}
137
 
 
138
 
static bool
139
 
i915_drm_buffer_get_handle(struct i915_winsys *iws,
140
 
                            struct i915_winsys_buffer *buffer,
141
 
                            struct winsys_handle *whandle,
142
 
                            unsigned stride)
143
 
{
144
 
   struct i915_drm_buffer *buf = i915_drm_buffer(buffer);
145
 
 
146
 
   if (whandle->type == WINSYS_HANDLE_TYPE_SHARED) {
147
 
      if (!buf->flinked) {
148
 
         if (drm_intel_bo_flink(buf->bo, &buf->flink))
149
 
            return false;
150
 
         buf->flinked = true;
151
 
      }
152
 
 
153
 
      whandle->handle = buf->flink;
154
 
   } else if (whandle->type == WINSYS_HANDLE_TYPE_KMS) {
155
 
      whandle->handle = buf->bo->handle;
156
 
   } else if (whandle->type == WINSYS_HANDLE_TYPE_FD) {
157
 
      int fd;
158
 
 
159
 
      if (drm_intel_bo_gem_export_to_prime(buf->bo, &fd))
160
 
         return false;
161
 
      whandle->handle = fd;
162
 
   } else {
163
 
      assert(!"unknown usage");
164
 
      return false;
165
 
   }
166
 
 
167
 
   whandle->stride = stride;
168
 
   return true;
169
 
}
170
 
 
171
 
static void *
172
 
i915_drm_buffer_map(struct i915_winsys *iws,
173
 
                     struct i915_winsys_buffer *buffer,
174
 
                     bool write)
175
 
{
176
 
   struct i915_drm_buffer *buf = i915_drm_buffer(buffer);
177
 
   drm_intel_bo *bo = intel_bo(buffer);
178
 
   int ret = 0;
179
 
 
180
 
   assert(bo);
181
 
 
182
 
   if (buf->map_count)
183
 
      goto out;
184
 
 
185
 
   ret = drm_intel_gem_bo_map_gtt(bo);
186
 
 
187
 
   buf->ptr = bo->virtual;
188
 
 
189
 
   assert(ret == 0);
190
 
out:
191
 
   if (ret)
192
 
      return NULL;
193
 
 
194
 
   buf->map_count++;
195
 
   return buf->ptr;
196
 
}
197
 
 
198
 
static void
199
 
i915_drm_buffer_unmap(struct i915_winsys *iws,
200
 
                       struct i915_winsys_buffer *buffer)
201
 
{
202
 
   struct i915_drm_buffer *buf = i915_drm_buffer(buffer);
203
 
 
204
 
   if (--buf->map_count)
205
 
      return;
206
 
 
207
 
   drm_intel_gem_bo_unmap_gtt(intel_bo(buffer));
208
 
}
209
 
 
210
 
static int
211
 
i915_drm_buffer_write(struct i915_winsys *iws,
212
 
                       struct i915_winsys_buffer *buffer,
213
 
                       size_t offset,
214
 
                       size_t size,
215
 
                       const void *data)
216
 
{
217
 
   struct i915_drm_buffer *buf = i915_drm_buffer(buffer);
218
 
 
219
 
   return drm_intel_bo_subdata(buf->bo, offset, size, (void*)data);
220
 
}
221
 
 
222
 
static void
223
 
i915_drm_buffer_destroy(struct i915_winsys *iws,
224
 
                         struct i915_winsys_buffer *buffer)
225
 
{
226
 
   drm_intel_bo_unreference(intel_bo(buffer));
227
 
 
228
 
#ifdef DEBUG
229
 
   i915_drm_buffer(buffer)->magic = 0;
230
 
   i915_drm_buffer(buffer)->bo = NULL;
231
 
#endif
232
 
 
233
 
   FREE(buffer);
234
 
}
235
 
 
236
 
static bool
237
 
i915_drm_buffer_is_busy(struct i915_winsys *iws,
238
 
                        struct i915_winsys_buffer *buffer)
239
 
{
240
 
   struct i915_drm_buffer* i915_buffer = i915_drm_buffer(buffer);
241
 
   if (!i915_buffer)
242
 
      return false;
243
 
   return drm_intel_bo_busy(i915_buffer->bo);
244
 
}
245
 
 
246
 
 
247
 
void
248
 
i915_drm_winsys_init_buffer_functions(struct i915_drm_winsys *idws)
249
 
{
250
 
   idws->base.buffer_create = i915_drm_buffer_create;
251
 
   idws->base.buffer_create_tiled = i915_drm_buffer_create_tiled;
252
 
   idws->base.buffer_from_handle = i915_drm_buffer_from_handle;
253
 
   idws->base.buffer_get_handle = i915_drm_buffer_get_handle;
254
 
   idws->base.buffer_map = i915_drm_buffer_map;
255
 
   idws->base.buffer_unmap = i915_drm_buffer_unmap;
256
 
   idws->base.buffer_write = i915_drm_buffer_write;
257
 
   idws->base.buffer_destroy = i915_drm_buffer_destroy;
258
 
   idws->base.buffer_is_busy = i915_drm_buffer_is_busy;
259
 
}