2 #include "state_tracker/drm_driver.h"
3 #include "i965_drm_winsys.h"
4 #include "util/u_memory.h"
5 #include "util/u_inlines.h"
8 #include "intel_bufmgr.h"
12 const char *names[BRW_BUFFER_TYPE_MAX] = {
27 const char *usages[BRW_USAGE_MAX] = {
40 const char *data_types[BRW_DATA_MAX] =
45 "GS: SAMPLER_DEFAULT_COLOR",
65 static enum pipe_error
66 i965_libdrm_bo_alloc(struct brw_winsys_screen *sws,
67 enum brw_buffer_type type,
70 struct brw_winsys_buffer **bo_out)
72 struct i965_libdrm_winsys *idws = i965_libdrm_winsys(sws);
73 struct i965_libdrm_buffer *buf;
76 debug_printf("%s type %s sz %d align %d\n",
77 __FUNCTION__, names[type], size, alignment );
79 buf = CALLOC_STRUCT(i965_libdrm_buffer);
81 return PIPE_ERROR_OUT_OF_MEMORY;
84 case BRW_BUFFER_TYPE_TEXTURE:
85 /* case BRW_BUFFER_TYPE_SCANOUT:*/
86 case BRW_BUFFER_TYPE_VERTEX:
87 case BRW_BUFFER_TYPE_CURBE:
88 case BRW_BUFFER_TYPE_QUERY:
89 case BRW_BUFFER_TYPE_SHADER_CONSTANTS:
90 case BRW_BUFFER_TYPE_SHADER_SCRATCH:
91 case BRW_BUFFER_TYPE_BATCH:
92 case BRW_BUFFER_TYPE_GENERAL_STATE:
93 case BRW_BUFFER_TYPE_SURFACE_STATE:
94 case BRW_BUFFER_TYPE_PIXEL:
95 case BRW_BUFFER_TYPE_GENERIC:
97 case BRW_BUFFER_TYPE_SCANOUT:
105 buf->bo = drm_intel_bo_alloc(idws->gem,
113 pipe_reference_init(&buf->base.reference, 1);
114 buf->base.size = size;
117 *bo_out = &buf->base;
123 return PIPE_ERROR_OUT_OF_MEMORY;
126 static enum pipe_error
127 i965_libdrm_bo_from_handle(struct brw_winsys_screen *sws,
128 struct winsys_handle *whandle,
131 struct brw_winsys_buffer **bo_out)
133 struct i965_libdrm_winsys *idws = i965_libdrm_winsys(sws);
134 struct i965_libdrm_buffer *buf = CALLOC_STRUCT(i965_libdrm_buffer);
135 uint32_t swizzle = 0;
138 debug_printf("%s\n", __FUNCTION__);
141 return PIPE_ERROR_OUT_OF_MEMORY;
143 pipe_reference_init(&buf->base.reference, 1);
144 buf->bo = drm_intel_bo_gem_create_from_name(idws->gem, "FROM_HANDLE", whandle->handle);
145 buf->base.size = buf->bo->size;
146 buf->base.sws = &idws->base;
148 buf->flink = whandle->handle;
154 drm_intel_bo_get_tiling(buf->bo, &buf->tiling, &swizzle);
155 if (buf->tiling != 0)
159 *stride = whandle->stride;
161 *bo_out = &buf->base;
166 return PIPE_ERROR_OUT_OF_MEMORY;
169 static enum pipe_error
170 i965_libdrm_bo_get_handle(struct brw_winsys_buffer *buffer,
171 struct winsys_handle *whandle,
174 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
177 debug_printf("%s\n", __FUNCTION__);
179 if (whandle->type == DRM_API_HANDLE_TYPE_SHARED) {
181 if (drm_intel_bo_flink(buf->bo, &buf->flink))
182 return PIPE_ERROR_BAD_INPUT;
186 whandle->handle = buf->flink;
187 } else if (whandle->type == DRM_API_HANDLE_TYPE_KMS) {
188 whandle->handle = buf->bo->handle;
190 assert(!"unknown usage");
191 return PIPE_ERROR_BAD_INPUT;
194 whandle->stride = stride;
199 i965_libdrm_bo_destroy(struct brw_winsys_buffer *buffer)
201 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
204 debug_printf("%s\n", __FUNCTION__);
206 drm_intel_bo_unreference(buf->bo);
210 static enum pipe_error
211 i965_libdrm_bo_emit_reloc(struct brw_winsys_buffer *buffer,
212 enum brw_buffer_usage usage,
215 struct brw_winsys_buffer *buffer2)
217 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
218 struct i965_libdrm_buffer *buf2 = i965_libdrm_buffer(buffer2);
223 debug_printf("%s buf %p offset %x delta %x buf2 %p/%s/%s\n",
224 __FUNCTION__, (void *)buffer,
226 (void *)buffer2, names[buf2->data_type], usages[usage]);
229 case BRW_USAGE_STATE:
230 read = I915_GEM_DOMAIN_INSTRUCTION;
233 case BRW_USAGE_QUERY_RESULT:
234 read = I915_GEM_DOMAIN_INSTRUCTION;
235 write = I915_GEM_DOMAIN_INSTRUCTION;
237 case BRW_USAGE_RENDER_TARGET:
238 read = I915_GEM_DOMAIN_RENDER;
241 case BRW_USAGE_DEPTH_BUFFER:
242 read = I915_GEM_DOMAIN_RENDER;
243 write = I915_GEM_DOMAIN_RENDER;
245 case BRW_USAGE_BLIT_SOURCE:
247 write = I915_GEM_DOMAIN_RENDER;
249 case BRW_USAGE_BLIT_DEST:
250 read = I915_GEM_DOMAIN_RENDER;
251 write = I915_GEM_DOMAIN_RENDER;
253 case BRW_USAGE_SAMPLER:
254 read = I915_GEM_DOMAIN_SAMPLER;
257 case BRW_USAGE_VERTEX:
258 read = I915_GEM_DOMAIN_VERTEX;
261 case BRW_USAGE_SCRATCH:
271 ((uint32_t *)buf->bo->virtual)[offset/4] = (delta +
275 ret = dri_bo_emit_reloc( buf->bo, read, write, delta, offset, buf2->bo );
282 static enum pipe_error
283 i965_libdrm_bo_exec(struct brw_winsys_buffer *buffer,
286 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
287 struct i965_libdrm_winsys *idws = i965_libdrm_winsys(buffer->sws);
291 debug_printf("execute buffer %p, bytes %d\n", (void *)buffer, bytes_used);
293 if (idws->send_cmd) {
294 ret = dri_bo_exec(buf->bo, bytes_used, NULL, 0, 0);
302 static enum pipe_error
303 i965_libdrm_bo_subdata(struct brw_winsys_buffer *buffer,
304 enum brw_buffer_data_type data_type,
308 const struct brw_winsys_reloc *reloc,
311 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
312 struct i965_libdrm_winsys *idws = i965_libdrm_winsys(buffer->sws);
318 debug_printf("%s buf %p off %d sz %d %s relocs: %d\n",
320 (void *)buffer, offset, size,
321 data_types[data_type],
325 brw_dump_data( idws->base.pci_id,
327 buf->bo->offset + offset,
328 data, size, buffer->sws->gen );
330 /* XXX: use bo_map_gtt/memcpy/unmap_gtt under some circumstances???
332 ret = drm_intel_bo_subdata(buf->bo, offset, size, (void*)data);
336 for (i = 0; i < nr_reloc; i++) {
337 i965_libdrm_bo_emit_reloc(buffer, reloc[i].usage, reloc[i].delta,
338 reloc[i].offset, reloc[i].bo);
345 i965_libdrm_bo_is_busy(struct brw_winsys_buffer *buffer)
347 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
351 debug_printf("%s %p\n", __FUNCTION__, (void *)buffer);
353 ret = drm_intel_bo_busy(buf->bo);
356 debug_printf(" --> %d\n", ret);
362 i965_libdrm_bo_references(struct brw_winsys_buffer *a,
363 struct brw_winsys_buffer *b)
365 struct i965_libdrm_buffer *bufa = i965_libdrm_buffer(a);
366 struct i965_libdrm_buffer *bufb = i965_libdrm_buffer(b);
370 debug_printf("%s %p %p\n", __FUNCTION__, (void *)a, (void *)b);
372 ret = drm_intel_bo_references(bufa->bo, bufb->bo);
375 debug_printf(" --> %d\n", ret);
380 /* XXX: couldn't this be handled by returning true/false on
383 static enum pipe_error
384 i965_libdrm_check_aperture_space(struct brw_winsys_screen *iws,
385 struct brw_winsys_buffer **buffers,
388 static drm_intel_bo *bos[128];
393 debug_printf("%s\n", __FUNCTION__);
395 if (count > Elements(bos)) {
400 for (i = 0; i < count; i++)
401 bos[i] = i965_libdrm_buffer(buffers[i])->bo;
403 /* XXX: converting from ??? to pipe_error:
405 ret = dri_bufmgr_check_aperture_space(bos, count);
408 debug_printf(" --> %d (ok == %d)\n", ret, PIPE_OK);
414 i965_libdrm_bo_map(struct brw_winsys_buffer *buffer,
415 enum brw_buffer_data_type data_type,
420 boolean flush_explicit)
422 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
427 debug_printf("%s %p %s %s\n", __FUNCTION__, (void *)buffer,
428 write ? "read/write" : "read",
429 write ? data_types[data_type] : "");
431 if (!buf->map_count) {
433 ret = drm_intel_gem_bo_map_gtt(buf->bo);
438 ret = drm_intel_bo_map(buf->bo, write);
444 buf->data_type = data_type;
446 return buf->bo->virtual;
450 i965_libdrm_bo_flush_range(struct brw_winsys_buffer *buffer,
454 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
455 struct i965_libdrm_winsys *idws = i965_libdrm_winsys(buffer->sws);
458 debug_printf("%s %s offset %d len %d\n", __FUNCTION__,
459 data_types[buf->data_type],
463 brw_dump_data( idws->base.pci_id,
465 buf->bo->offset + offset,
466 (char*)buf->bo->virtual + offset,
467 length, buffer->sws->gen );
471 i965_libdrm_bo_unmap(struct brw_winsys_buffer *buffer)
473 struct i965_libdrm_buffer *buf = i965_libdrm_buffer(buffer);
476 debug_printf("%s\n", __FUNCTION__);
478 if (--buf->map_count > 0)
482 drm_intel_gem_bo_unmap_gtt(buf->bo);
484 drm_intel_bo_unmap(buf->bo);
488 i965_libdrm_winsys_init_buffer_functions(struct i965_libdrm_winsys *idws)
490 idws->base.bo_alloc = i965_libdrm_bo_alloc;
491 idws->base.bo_from_handle = i965_libdrm_bo_from_handle;
492 idws->base.bo_get_handle = i965_libdrm_bo_get_handle;
493 idws->base.bo_destroy = i965_libdrm_bo_destroy;
494 idws->base.bo_emit_reloc = i965_libdrm_bo_emit_reloc;
495 idws->base.bo_exec = i965_libdrm_bo_exec;
496 idws->base.bo_subdata = i965_libdrm_bo_subdata;
497 idws->base.bo_is_busy = i965_libdrm_bo_is_busy;
498 idws->base.bo_references = i965_libdrm_bo_references;
499 idws->base.check_aperture_space = i965_libdrm_check_aperture_space;
500 idws->base.bo_map = i965_libdrm_bo_map;
501 idws->base.bo_flush_range = i965_libdrm_bo_flush_range;
502 idws->base.bo_unmap = i965_libdrm_bo_unmap;