vk/cmd_buffer: Track descriptor set dirtying per-stage
[mesa.git] / src / vulkan / device.c
1 /*
2 * Copyright © 2015 Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
21 * IN THE SOFTWARE.
22 */
23
24 #include <assert.h>
25 #include <stdbool.h>
26 #include <string.h>
27 #include <unistd.h>
28 #include <fcntl.h>
29
30 #include "private.h"
31
32 static int
33 anv_env_get_int(const char *name)
34 {
35 const char *val = getenv(name);
36
37 if (!val)
38 return 0;
39
40 return strtol(val, NULL, 0);
41 }
42
43 static VkResult
44 fill_physical_device(struct anv_physical_device *device,
45 struct anv_instance *instance,
46 const char *path)
47 {
48 int fd;
49
50 fd = open("/dev/dri/renderD128", O_RDWR | O_CLOEXEC);
51 if (fd < 0)
52 return vk_error(VK_ERROR_UNAVAILABLE);
53
54 device->instance = instance;
55 device->path = path;
56
57 device->chipset_id = anv_env_get_int("INTEL_DEVID_OVERRIDE");
58 device->no_hw = false;
59 if (device->chipset_id) {
60 /* INTEL_DEVID_OVERRIDE implies INTEL_NO_HW. */
61 device->no_hw = true;
62 } else {
63 device->chipset_id = anv_gem_get_param(fd, I915_PARAM_CHIPSET_ID);
64 }
65 if (!device->chipset_id)
66 goto fail;
67
68 device->name = brw_get_device_name(device->chipset_id);
69 device->info = brw_get_device_info(device->chipset_id, -1);
70 if (!device->info)
71 goto fail;
72
73 if (!anv_gem_get_param(fd, I915_PARAM_HAS_WAIT_TIMEOUT))
74 goto fail;
75
76 if (!anv_gem_get_param(fd, I915_PARAM_HAS_EXECBUF2))
77 goto fail;
78
79 if (!anv_gem_get_param(fd, I915_PARAM_HAS_LLC))
80 goto fail;
81
82 if (!anv_gem_get_param(fd, I915_PARAM_HAS_EXEC_CONSTANTS))
83 goto fail;
84
85 close(fd);
86
87 return VK_SUCCESS;
88
89 fail:
90 close(fd);
91
92 return vk_error(VK_ERROR_UNAVAILABLE);
93 }
94
95 static void *default_alloc(
96 void* pUserData,
97 size_t size,
98 size_t alignment,
99 VkSystemAllocType allocType)
100 {
101 return malloc(size);
102 }
103
104 static void default_free(
105 void* pUserData,
106 void* pMem)
107 {
108 free(pMem);
109 }
110
111 static const VkAllocCallbacks default_alloc_callbacks = {
112 .pUserData = NULL,
113 .pfnAlloc = default_alloc,
114 .pfnFree = default_free
115 };
116
117 VkResult anv_CreateInstance(
118 const VkInstanceCreateInfo* pCreateInfo,
119 VkInstance* pInstance)
120 {
121 struct anv_instance *instance;
122 const VkAllocCallbacks *alloc_callbacks = &default_alloc_callbacks;
123 void *user_data = NULL;
124 VkResult result;
125
126 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO);
127
128 if (pCreateInfo->pAllocCb) {
129 alloc_callbacks = pCreateInfo->pAllocCb;
130 user_data = pCreateInfo->pAllocCb->pUserData;
131 }
132 instance = alloc_callbacks->pfnAlloc(user_data, sizeof(*instance), 8,
133 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
134 if (!instance)
135 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
136
137 instance->pAllocUserData = alloc_callbacks->pUserData;
138 instance->pfnAlloc = alloc_callbacks->pfnAlloc;
139 instance->pfnFree = alloc_callbacks->pfnFree;
140 instance->apiVersion = pCreateInfo->pAppInfo->apiVersion;
141
142 instance->physicalDeviceCount = 0;
143 result = fill_physical_device(&instance->physicalDevice,
144 instance, "/dev/dri/renderD128");
145
146 if (result != VK_SUCCESS)
147 return result;
148
149 instance->physicalDeviceCount++;
150 *pInstance = (VkInstance) instance;
151
152 return VK_SUCCESS;
153 }
154
155 VkResult anv_DestroyInstance(
156 VkInstance _instance)
157 {
158 struct anv_instance *instance = (struct anv_instance *) _instance;
159
160 instance->pfnFree(instance->pAllocUserData, instance);
161
162 return VK_SUCCESS;
163 }
164
165 VkResult anv_EnumeratePhysicalDevices(
166 VkInstance _instance,
167 uint32_t* pPhysicalDeviceCount,
168 VkPhysicalDevice* pPhysicalDevices)
169 {
170 struct anv_instance *instance = (struct anv_instance *) _instance;
171
172 if (*pPhysicalDeviceCount >= 1)
173 pPhysicalDevices[0] = (VkPhysicalDevice) &instance->physicalDevice;
174 *pPhysicalDeviceCount = instance->physicalDeviceCount;
175
176 return VK_SUCCESS;
177 }
178
179 VkResult anv_GetPhysicalDeviceInfo(
180 VkPhysicalDevice physicalDevice,
181 VkPhysicalDeviceInfoType infoType,
182 size_t* pDataSize,
183 void* pData)
184 {
185 struct anv_physical_device *device = (struct anv_physical_device *) physicalDevice;
186 VkPhysicalDeviceProperties *properties;
187 VkPhysicalDevicePerformance *performance;
188 VkPhysicalDeviceQueueProperties *queue_properties;
189 VkPhysicalDeviceMemoryProperties *memory_properties;
190 VkDisplayPropertiesWSI *display_properties;
191 uint64_t ns_per_tick = 80;
192
193 switch ((uint32_t) infoType) {
194 case VK_PHYSICAL_DEVICE_INFO_TYPE_PROPERTIES:
195 properties = pData;
196
197 *pDataSize = sizeof(*properties);
198 if (pData == NULL)
199 return VK_SUCCESS;
200
201 properties->apiVersion = 1;
202 properties->driverVersion = 1;
203 properties->vendorId = 0x8086;
204 properties->deviceId = device->chipset_id;
205 properties->deviceType = VK_PHYSICAL_DEVICE_TYPE_INTEGRATED_GPU;
206 strcpy(properties->deviceName, device->name);
207 properties->maxInlineMemoryUpdateSize = 0;
208 properties->maxBoundDescriptorSets = MAX_SETS;
209 properties->maxThreadGroupSize = 512;
210 properties->timestampFrequency = 1000 * 1000 * 1000 / ns_per_tick;
211 properties->multiColorAttachmentClears = true;
212 properties->maxDescriptorSets = 8;
213 properties->maxViewports = 16;
214 properties->maxColorAttachments = 8;
215 return VK_SUCCESS;
216
217 case VK_PHYSICAL_DEVICE_INFO_TYPE_PERFORMANCE:
218 performance = pData;
219
220 *pDataSize = sizeof(*performance);
221 if (pData == NULL)
222 return VK_SUCCESS;
223
224 performance->maxDeviceClock = 1.0;
225 performance->aluPerClock = 1.0;
226 performance->texPerClock = 1.0;
227 performance->primsPerClock = 1.0;
228 performance->pixelsPerClock = 1.0;
229 return VK_SUCCESS;
230
231 case VK_PHYSICAL_DEVICE_INFO_TYPE_QUEUE_PROPERTIES:
232 queue_properties = pData;
233
234 *pDataSize = sizeof(*queue_properties);
235 if (pData == NULL)
236 return VK_SUCCESS;
237
238 queue_properties->queueFlags = 0;
239 queue_properties->queueCount = 1;
240 queue_properties->maxAtomicCounters = 0;
241 queue_properties->supportsTimestamps = true;
242 queue_properties->maxMemReferences = 256;
243 return VK_SUCCESS;
244
245 case VK_PHYSICAL_DEVICE_INFO_TYPE_MEMORY_PROPERTIES:
246 memory_properties = pData;
247
248 *pDataSize = sizeof(*memory_properties);
249 if (pData == NULL)
250 return VK_SUCCESS;
251
252 memory_properties->supportsMigration = false;
253 memory_properties->supportsPinning = false;
254 return VK_SUCCESS;
255
256 case VK_PHYSICAL_DEVICE_INFO_TYPE_DISPLAY_PROPERTIES_WSI:
257 anv_finishme("VK_PHYSICAL_DEVICE_INFO_TYPE_DISPLAY_PROPERTIES_WSI");
258
259 *pDataSize = sizeof(*display_properties);
260 if (pData == NULL)
261 return VK_SUCCESS;
262
263 display_properties = pData;
264 display_properties->display = 0;
265 display_properties->physicalResolution = (VkExtent2D) { 0, 0 };
266 return VK_SUCCESS;
267
268 case VK_PHYSICAL_DEVICE_INFO_TYPE_QUEUE_PRESENT_PROPERTIES_WSI:
269 anv_finishme("VK_PHYSICAL_DEVICE_INFO_TYPE_QUEUE_PRESENT_PROPERTIES_WSI");
270 return VK_SUCCESS;
271
272
273 default:
274 return VK_UNSUPPORTED;
275 }
276
277 }
278
279 void * vkGetProcAddr(
280 VkPhysicalDevice physicalDevice,
281 const char* pName)
282 {
283 return anv_lookup_entrypoint(pName);
284 }
285
286 static void
287 parse_debug_flags(struct anv_device *device)
288 {
289 const char *debug, *p, *end;
290
291 debug = getenv("INTEL_DEBUG");
292 device->dump_aub = false;
293 if (debug) {
294 for (p = debug; *p; p = end + 1) {
295 end = strchrnul(p, ',');
296 if (end - p == 3 && memcmp(p, "aub", 3) == 0)
297 device->dump_aub = true;
298 if (end - p == 5 && memcmp(p, "no_hw", 5) == 0)
299 device->no_hw = true;
300 if (*end == '\0')
301 break;
302 }
303 }
304 }
305
306 static const uint32_t BATCH_SIZE = 8192;
307
308 VkResult anv_CreateDevice(
309 VkPhysicalDevice _physicalDevice,
310 const VkDeviceCreateInfo* pCreateInfo,
311 VkDevice* pDevice)
312 {
313 struct anv_physical_device *physicalDevice =
314 (struct anv_physical_device *) _physicalDevice;
315 struct anv_instance *instance = physicalDevice->instance;
316 struct anv_device *device;
317
318 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO);
319
320 device = instance->pfnAlloc(instance->pAllocUserData,
321 sizeof(*device), 8,
322 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
323 if (!device)
324 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
325
326 device->no_hw = physicalDevice->no_hw;
327 parse_debug_flags(device);
328
329 device->instance = physicalDevice->instance;
330 device->fd = open("/dev/dri/renderD128", O_RDWR | O_CLOEXEC);
331 if (device->fd == -1)
332 goto fail_device;
333
334 device->context_id = anv_gem_create_context(device);
335 if (device->context_id == -1)
336 goto fail_fd;
337
338 anv_bo_pool_init(&device->batch_bo_pool, device, BATCH_SIZE);
339
340 anv_block_pool_init(&device->dynamic_state_block_pool, device, 2048);
341
342 anv_state_pool_init(&device->dynamic_state_pool,
343 &device->dynamic_state_block_pool);
344
345 anv_block_pool_init(&device->instruction_block_pool, device, 2048);
346 anv_block_pool_init(&device->surface_state_block_pool, device, 2048);
347
348
349 /* Binding table pointers are only 16 bits so we have to make sure that
350 * they get allocated at the beginning of the surface state BO. To
351 * handle this, we create a separate block pool that works out of the
352 * first 64 KB of the surface state BO.
353 */
354 anv_block_pool_init_slave(&device->binding_table_block_pool,
355 &device->surface_state_block_pool, 32);
356
357 anv_state_pool_init(&device->surface_state_pool,
358 &device->surface_state_block_pool);
359
360 device->compiler = anv_compiler_create(device->fd);
361 device->aub_writer = NULL;
362
363 device->info = *physicalDevice->info;
364
365 pthread_mutex_init(&device->mutex, NULL);
366
367 anv_device_init_meta(device);
368
369 *pDevice = (VkDevice) device;
370
371 return VK_SUCCESS;
372
373 fail_fd:
374 close(device->fd);
375 fail_device:
376 anv_device_free(device, device);
377
378 return vk_error(VK_ERROR_UNAVAILABLE);
379 }
380
381 VkResult anv_DestroyDevice(
382 VkDevice _device)
383 {
384 struct anv_device *device = (struct anv_device *) _device;
385
386 anv_compiler_destroy(device->compiler);
387
388
389 anv_bo_pool_finish(&device->batch_bo_pool);
390 anv_block_pool_finish(&device->dynamic_state_block_pool);
391 anv_block_pool_finish(&device->instruction_block_pool);
392 anv_block_pool_finish(&device->surface_state_block_pool);
393
394 close(device->fd);
395
396 if (device->aub_writer)
397 anv_aub_writer_destroy(device->aub_writer);
398
399 anv_device_free(device, device);
400
401 return VK_SUCCESS;
402 }
403
404 VkResult anv_GetGlobalExtensionInfo(
405 VkExtensionInfoType infoType,
406 uint32_t extensionIndex,
407 size_t* pDataSize,
408 void* pData)
409 {
410 static const VkExtensionProperties extensions[] = {
411 {
412 .extName = "VK_WSI_LunarG",
413 .version = 3
414 }
415 };
416 uint32_t count = ARRAY_SIZE(extensions);
417
418 switch (infoType) {
419 case VK_EXTENSION_INFO_TYPE_COUNT:
420 memcpy(pData, &count, sizeof(count));
421 *pDataSize = sizeof(count);
422 return VK_SUCCESS;
423
424 case VK_EXTENSION_INFO_TYPE_PROPERTIES:
425 if (extensionIndex >= count)
426 return vk_error(VK_ERROR_INVALID_EXTENSION);
427
428 memcpy(pData, &extensions[extensionIndex], sizeof(extensions[0]));
429 *pDataSize = sizeof(extensions[0]);
430 return VK_SUCCESS;
431
432 default:
433 return VK_UNSUPPORTED;
434 }
435 }
436
437 VkResult anv_GetPhysicalDeviceExtensionInfo(
438 VkPhysicalDevice physicalDevice,
439 VkExtensionInfoType infoType,
440 uint32_t extensionIndex,
441 size_t* pDataSize,
442 void* pData)
443 {
444 uint32_t *count;
445
446 switch (infoType) {
447 case VK_EXTENSION_INFO_TYPE_COUNT:
448 *pDataSize = 4;
449 if (pData == NULL)
450 return VK_SUCCESS;
451
452 count = pData;
453 *count = 0;
454 return VK_SUCCESS;
455
456 case VK_EXTENSION_INFO_TYPE_PROPERTIES:
457 return vk_error(VK_ERROR_INVALID_EXTENSION);
458
459 default:
460 return VK_UNSUPPORTED;
461 }
462 }
463
464 VkResult anv_EnumerateLayers(
465 VkPhysicalDevice physicalDevice,
466 size_t maxStringSize,
467 size_t* pLayerCount,
468 char* const* pOutLayers,
469 void* pReserved)
470 {
471 *pLayerCount = 0;
472
473 return VK_SUCCESS;
474 }
475
476 VkResult anv_GetDeviceQueue(
477 VkDevice _device,
478 uint32_t queueNodeIndex,
479 uint32_t queueIndex,
480 VkQueue* pQueue)
481 {
482 struct anv_device *device = (struct anv_device *) _device;
483 struct anv_queue *queue;
484
485 /* FIXME: Should allocate these at device create time. */
486
487 queue = anv_device_alloc(device, sizeof(*queue), 8,
488 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
489 if (queue == NULL)
490 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
491
492 queue->device = device;
493 queue->pool = &device->surface_state_pool;
494
495 queue->completed_serial = anv_state_pool_alloc(queue->pool, 4, 4);
496 *(uint32_t *)queue->completed_serial.map = 0;
497 queue->next_serial = 1;
498
499 *pQueue = (VkQueue) queue;
500
501 return VK_SUCCESS;
502 }
503
504 VkResult
505 anv_reloc_list_init(struct anv_reloc_list *list, struct anv_device *device)
506 {
507 list->num_relocs = 0;
508 list->array_length = 256;
509 list->relocs =
510 anv_device_alloc(device, list->array_length * sizeof(*list->relocs), 8,
511 VK_SYSTEM_ALLOC_TYPE_INTERNAL);
512
513 if (list->relocs == NULL)
514 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
515
516 list->reloc_bos =
517 anv_device_alloc(device, list->array_length * sizeof(*list->reloc_bos), 8,
518 VK_SYSTEM_ALLOC_TYPE_INTERNAL);
519
520 if (list->relocs == NULL) {
521 anv_device_free(device, list->relocs);
522 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
523 }
524
525 return VK_SUCCESS;
526 }
527
528 void
529 anv_reloc_list_finish(struct anv_reloc_list *list, struct anv_device *device)
530 {
531 anv_device_free(device, list->relocs);
532 anv_device_free(device, list->reloc_bos);
533 }
534
535 static VkResult
536 anv_reloc_list_grow(struct anv_reloc_list *list, struct anv_device *device,
537 size_t num_additional_relocs)
538 {
539 if (list->num_relocs + num_additional_relocs <= list->array_length)
540 return VK_SUCCESS;
541
542 size_t new_length = list->array_length * 2;
543 while (new_length < list->num_relocs + num_additional_relocs)
544 new_length *= 2;
545
546 struct drm_i915_gem_relocation_entry *new_relocs =
547 anv_device_alloc(device, new_length * sizeof(*list->relocs), 8,
548 VK_SYSTEM_ALLOC_TYPE_INTERNAL);
549 if (new_relocs == NULL)
550 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
551
552 struct anv_bo **new_reloc_bos =
553 anv_device_alloc(device, new_length * sizeof(*list->reloc_bos), 8,
554 VK_SYSTEM_ALLOC_TYPE_INTERNAL);
555 if (new_relocs == NULL) {
556 anv_device_free(device, new_relocs);
557 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
558 }
559
560 memcpy(new_relocs, list->relocs, list->num_relocs * sizeof(*list->relocs));
561 memcpy(new_reloc_bos, list->reloc_bos,
562 list->num_relocs * sizeof(*list->reloc_bos));
563
564 anv_device_free(device, list->relocs);
565 anv_device_free(device, list->reloc_bos);
566
567 list->relocs = new_relocs;
568 list->reloc_bos = new_reloc_bos;
569
570 return VK_SUCCESS;
571 }
572
573 static VkResult
574 anv_batch_bo_create(struct anv_device *device, struct anv_batch_bo **bbo_out)
575 {
576 VkResult result;
577
578 struct anv_batch_bo *bbo =
579 anv_device_alloc(device, sizeof(*bbo), 8, VK_SYSTEM_ALLOC_TYPE_INTERNAL);
580 if (bbo == NULL)
581 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
582
583 bbo->num_relocs = 0;
584 bbo->prev_batch_bo = NULL;
585
586 result = anv_bo_pool_alloc(&device->batch_bo_pool, &bbo->bo);
587 if (result != VK_SUCCESS) {
588 anv_device_free(device, bbo);
589 return result;
590 }
591
592 *bbo_out = bbo;
593
594 return VK_SUCCESS;
595 }
596
597 static void
598 anv_batch_bo_start(struct anv_batch_bo *bbo, struct anv_batch *batch,
599 size_t batch_padding)
600 {
601 batch->next = batch->start = bbo->bo.map;
602 batch->end = bbo->bo.map + bbo->bo.size - batch_padding;
603 bbo->first_reloc = batch->relocs.num_relocs;
604 }
605
606 static void
607 anv_batch_bo_finish(struct anv_batch_bo *bbo, struct anv_batch *batch)
608 {
609 assert(batch->start == bbo->bo.map);
610 bbo->length = batch->next - batch->start;
611 bbo->num_relocs = batch->relocs.num_relocs - bbo->first_reloc;
612 }
613
614 static void
615 anv_batch_bo_destroy(struct anv_batch_bo *bbo, struct anv_device *device)
616 {
617 anv_bo_pool_free(&device->batch_bo_pool, &bbo->bo);
618 anv_device_free(device, bbo);
619 }
620
621 void *
622 anv_batch_emit_dwords(struct anv_batch *batch, int num_dwords)
623 {
624 if (batch->next + num_dwords * 4 > batch->end)
625 batch->extend_cb(batch, batch->user_data);
626
627 void *p = batch->next;
628
629 batch->next += num_dwords * 4;
630 assert(batch->next <= batch->end);
631
632 return p;
633 }
634
635 static void
636 anv_reloc_list_append(struct anv_reloc_list *list, struct anv_device *device,
637 struct anv_reloc_list *other, uint32_t offset)
638 {
639 anv_reloc_list_grow(list, device, other->num_relocs);
640 /* TODO: Handle failure */
641
642 memcpy(&list->relocs[list->num_relocs], &other->relocs[0],
643 other->num_relocs * sizeof(other->relocs[0]));
644 memcpy(&list->reloc_bos[list->num_relocs], &other->reloc_bos[0],
645 other->num_relocs * sizeof(other->reloc_bos[0]));
646
647 for (uint32_t i = 0; i < other->num_relocs; i++)
648 list->relocs[i + list->num_relocs].offset += offset;
649
650 list->num_relocs += other->num_relocs;
651 }
652
653 static uint64_t
654 anv_reloc_list_add(struct anv_reloc_list *list, struct anv_device *device,
655 uint32_t offset, struct anv_bo *target_bo, uint32_t delta)
656 {
657 struct drm_i915_gem_relocation_entry *entry;
658 int index;
659
660 anv_reloc_list_grow(list, device, 1);
661 /* TODO: Handle failure */
662
663 /* XXX: Can we use I915_EXEC_HANDLE_LUT? */
664 index = list->num_relocs++;
665 list->reloc_bos[index] = target_bo;
666 entry = &list->relocs[index];
667 entry->target_handle = target_bo->gem_handle;
668 entry->delta = delta;
669 entry->offset = offset;
670 entry->presumed_offset = target_bo->offset;
671 entry->read_domains = 0;
672 entry->write_domain = 0;
673
674 return target_bo->offset + delta;
675 }
676
677 void
678 anv_batch_emit_batch(struct anv_batch *batch, struct anv_batch *other)
679 {
680 uint32_t size, offset;
681
682 size = other->next - other->start;
683 assert(size % 4 == 0);
684
685 if (batch->next + size > batch->end)
686 batch->extend_cb(batch, batch->user_data);
687
688 assert(batch->next + size <= batch->end);
689
690 memcpy(batch->next, other->start, size);
691
692 offset = batch->next - batch->start;
693 anv_reloc_list_append(&batch->relocs, batch->device,
694 &other->relocs, offset);
695
696 batch->next += size;
697 }
698
699 uint64_t
700 anv_batch_emit_reloc(struct anv_batch *batch,
701 void *location, struct anv_bo *bo, uint32_t delta)
702 {
703 return anv_reloc_list_add(&batch->relocs, batch->device,
704 location - batch->start, bo, delta);
705 }
706
707 VkResult anv_QueueSubmit(
708 VkQueue _queue,
709 uint32_t cmdBufferCount,
710 const VkCmdBuffer* pCmdBuffers,
711 VkFence _fence)
712 {
713 struct anv_queue *queue = (struct anv_queue *) _queue;
714 struct anv_device *device = queue->device;
715 struct anv_fence *fence = (struct anv_fence *) _fence;
716 int ret;
717
718 for (uint32_t i = 0; i < cmdBufferCount; i++) {
719 struct anv_cmd_buffer *cmd_buffer =
720 (struct anv_cmd_buffer *) pCmdBuffers[i];
721
722 if (device->dump_aub)
723 anv_cmd_buffer_dump(cmd_buffer);
724
725 if (!device->no_hw) {
726 ret = anv_gem_execbuffer(device, &cmd_buffer->execbuf);
727 if (ret != 0)
728 return vk_error(VK_ERROR_UNKNOWN);
729
730 if (fence) {
731 ret = anv_gem_execbuffer(device, &fence->execbuf);
732 if (ret != 0)
733 return vk_error(VK_ERROR_UNKNOWN);
734 }
735
736 for (uint32_t i = 0; i < cmd_buffer->bo_count; i++)
737 cmd_buffer->exec2_bos[i]->offset = cmd_buffer->exec2_objects[i].offset;
738 } else {
739 *(uint32_t *)queue->completed_serial.map = cmd_buffer->serial;
740 }
741 }
742
743 return VK_SUCCESS;
744 }
745
746 VkResult anv_QueueAddMemReferences(
747 VkQueue queue,
748 uint32_t count,
749 const VkDeviceMemory* pMems)
750 {
751 return VK_SUCCESS;
752 }
753
754 VkResult anv_QueueRemoveMemReferences(
755 VkQueue queue,
756 uint32_t count,
757 const VkDeviceMemory* pMems)
758 {
759 return VK_SUCCESS;
760 }
761
762 VkResult anv_QueueWaitIdle(
763 VkQueue _queue)
764 {
765 struct anv_queue *queue = (struct anv_queue *) _queue;
766
767 return vkDeviceWaitIdle((VkDevice) queue->device);
768 }
769
770 VkResult anv_DeviceWaitIdle(
771 VkDevice _device)
772 {
773 struct anv_device *device = (struct anv_device *) _device;
774 struct anv_state state;
775 struct anv_batch batch;
776 struct drm_i915_gem_execbuffer2 execbuf;
777 struct drm_i915_gem_exec_object2 exec2_objects[1];
778 struct anv_bo *bo = NULL;
779 VkResult result;
780 int64_t timeout;
781 int ret;
782
783 state = anv_state_pool_alloc(&device->dynamic_state_pool, 32, 32);
784 bo = &device->dynamic_state_pool.block_pool->bo;
785 batch.start = batch.next = state.map;
786 batch.end = state.map + 32;
787 anv_batch_emit(&batch, GEN8_MI_BATCH_BUFFER_END);
788 anv_batch_emit(&batch, GEN8_MI_NOOP);
789
790 exec2_objects[0].handle = bo->gem_handle;
791 exec2_objects[0].relocation_count = 0;
792 exec2_objects[0].relocs_ptr = 0;
793 exec2_objects[0].alignment = 0;
794 exec2_objects[0].offset = bo->offset;
795 exec2_objects[0].flags = 0;
796 exec2_objects[0].rsvd1 = 0;
797 exec2_objects[0].rsvd2 = 0;
798
799 execbuf.buffers_ptr = (uintptr_t) exec2_objects;
800 execbuf.buffer_count = 1;
801 execbuf.batch_start_offset = state.offset;
802 execbuf.batch_len = batch.next - state.map;
803 execbuf.cliprects_ptr = 0;
804 execbuf.num_cliprects = 0;
805 execbuf.DR1 = 0;
806 execbuf.DR4 = 0;
807
808 execbuf.flags =
809 I915_EXEC_HANDLE_LUT | I915_EXEC_NO_RELOC | I915_EXEC_RENDER;
810 execbuf.rsvd1 = device->context_id;
811 execbuf.rsvd2 = 0;
812
813 if (!device->no_hw) {
814 ret = anv_gem_execbuffer(device, &execbuf);
815 if (ret != 0) {
816 result = vk_error(VK_ERROR_UNKNOWN);
817 goto fail;
818 }
819
820 timeout = INT64_MAX;
821 ret = anv_gem_wait(device, bo->gem_handle, &timeout);
822 if (ret != 0) {
823 result = vk_error(VK_ERROR_UNKNOWN);
824 goto fail;
825 }
826 }
827
828 anv_state_pool_free(&device->dynamic_state_pool, state);
829
830 return VK_SUCCESS;
831
832 fail:
833 anv_state_pool_free(&device->dynamic_state_pool, state);
834
835 return result;
836 }
837
838 void *
839 anv_device_alloc(struct anv_device * device,
840 size_t size,
841 size_t alignment,
842 VkSystemAllocType allocType)
843 {
844 return device->instance->pfnAlloc(device->instance->pAllocUserData,
845 size,
846 alignment,
847 allocType);
848 }
849
850 void
851 anv_device_free(struct anv_device * device,
852 void * mem)
853 {
854 return device->instance->pfnFree(device->instance->pAllocUserData,
855 mem);
856 }
857
858 VkResult
859 anv_bo_init_new(struct anv_bo *bo, struct anv_device *device, uint64_t size)
860 {
861 bo->gem_handle = anv_gem_create(device, size);
862 if (!bo->gem_handle)
863 return vk_error(VK_ERROR_OUT_OF_DEVICE_MEMORY);
864
865 bo->map = NULL;
866 bo->index = 0;
867 bo->offset = 0;
868 bo->size = size;
869
870 return VK_SUCCESS;
871 }
872
873 VkResult anv_AllocMemory(
874 VkDevice _device,
875 const VkMemoryAllocInfo* pAllocInfo,
876 VkDeviceMemory* pMem)
877 {
878 struct anv_device *device = (struct anv_device *) _device;
879 struct anv_device_memory *mem;
880 VkResult result;
881
882 assert(pAllocInfo->sType == VK_STRUCTURE_TYPE_MEMORY_ALLOC_INFO);
883
884 mem = anv_device_alloc(device, sizeof(*mem), 8,
885 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
886 if (mem == NULL)
887 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
888
889 result = anv_bo_init_new(&mem->bo, device, pAllocInfo->allocationSize);
890 if (result != VK_SUCCESS)
891 goto fail;
892
893 *pMem = (VkDeviceMemory) mem;
894
895 return VK_SUCCESS;
896
897 fail:
898 anv_device_free(device, mem);
899
900 return result;
901 }
902
903 VkResult anv_FreeMemory(
904 VkDevice _device,
905 VkDeviceMemory _mem)
906 {
907 struct anv_device *device = (struct anv_device *) _device;
908 struct anv_device_memory *mem = (struct anv_device_memory *) _mem;
909
910 if (mem->bo.map)
911 anv_gem_munmap(mem->bo.map, mem->bo.size);
912
913 if (mem->bo.gem_handle != 0)
914 anv_gem_close(device, mem->bo.gem_handle);
915
916 anv_device_free(device, mem);
917
918 return VK_SUCCESS;
919 }
920
921 VkResult anv_SetMemoryPriority(
922 VkDevice device,
923 VkDeviceMemory mem,
924 VkMemoryPriority priority)
925 {
926 return VK_SUCCESS;
927 }
928
929 VkResult anv_MapMemory(
930 VkDevice _device,
931 VkDeviceMemory _mem,
932 VkDeviceSize offset,
933 VkDeviceSize size,
934 VkMemoryMapFlags flags,
935 void** ppData)
936 {
937 struct anv_device *device = (struct anv_device *) _device;
938 struct anv_device_memory *mem = (struct anv_device_memory *) _mem;
939
940 /* FIXME: Is this supposed to be thread safe? Since vkUnmapMemory() only
941 * takes a VkDeviceMemory pointer, it seems like only one map of the memory
942 * at a time is valid. We could just mmap up front and return an offset
943 * pointer here, but that may exhaust virtual memory on 32 bit
944 * userspace. */
945
946 mem->map = anv_gem_mmap(device, mem->bo.gem_handle, offset, size);
947 mem->map_size = size;
948
949 *ppData = mem->map;
950
951 return VK_SUCCESS;
952 }
953
954 VkResult anv_UnmapMemory(
955 VkDevice _device,
956 VkDeviceMemory _mem)
957 {
958 struct anv_device_memory *mem = (struct anv_device_memory *) _mem;
959
960 anv_gem_munmap(mem->map, mem->map_size);
961
962 return VK_SUCCESS;
963 }
964
965 VkResult anv_FlushMappedMemory(
966 VkDevice device,
967 VkDeviceMemory mem,
968 VkDeviceSize offset,
969 VkDeviceSize size)
970 {
971 /* clflush here for !llc platforms */
972
973 return VK_SUCCESS;
974 }
975
976 VkResult anv_PinSystemMemory(
977 VkDevice device,
978 const void* pSysMem,
979 size_t memSize,
980 VkDeviceMemory* pMem)
981 {
982 return VK_SUCCESS;
983 }
984
985 VkResult anv_GetMultiDeviceCompatibility(
986 VkPhysicalDevice physicalDevice0,
987 VkPhysicalDevice physicalDevice1,
988 VkPhysicalDeviceCompatibilityInfo* pInfo)
989 {
990 return VK_UNSUPPORTED;
991 }
992
993 VkResult anv_OpenSharedMemory(
994 VkDevice device,
995 const VkMemoryOpenInfo* pOpenInfo,
996 VkDeviceMemory* pMem)
997 {
998 return VK_UNSUPPORTED;
999 }
1000
1001 VkResult anv_OpenSharedSemaphore(
1002 VkDevice device,
1003 const VkSemaphoreOpenInfo* pOpenInfo,
1004 VkSemaphore* pSemaphore)
1005 {
1006 return VK_UNSUPPORTED;
1007 }
1008
1009 VkResult anv_OpenPeerMemory(
1010 VkDevice device,
1011 const VkPeerMemoryOpenInfo* pOpenInfo,
1012 VkDeviceMemory* pMem)
1013 {
1014 return VK_UNSUPPORTED;
1015 }
1016
1017 VkResult anv_OpenPeerImage(
1018 VkDevice device,
1019 const VkPeerImageOpenInfo* pOpenInfo,
1020 VkImage* pImage,
1021 VkDeviceMemory* pMem)
1022 {
1023 return VK_UNSUPPORTED;
1024 }
1025
1026 VkResult anv_DestroyObject(
1027 VkDevice _device,
1028 VkObjectType objType,
1029 VkObject _object)
1030 {
1031 struct anv_device *device = (struct anv_device *) _device;
1032 struct anv_object *object = (struct anv_object *) _object;
1033
1034 switch (objType) {
1035 case VK_OBJECT_TYPE_INSTANCE:
1036 return anv_DestroyInstance((VkInstance) _object);
1037
1038 case VK_OBJECT_TYPE_PHYSICAL_DEVICE:
1039 /* We don't want to actually destroy physical devices */
1040 return VK_SUCCESS;
1041
1042 case VK_OBJECT_TYPE_DEVICE:
1043 assert(_device == (VkDevice) _object);
1044 return anv_DestroyDevice((VkDevice) _object);
1045
1046 case VK_OBJECT_TYPE_QUEUE:
1047 /* TODO */
1048 return VK_SUCCESS;
1049
1050 case VK_OBJECT_TYPE_DEVICE_MEMORY:
1051 return anv_FreeMemory(_device, (VkDeviceMemory) _object);
1052
1053 case VK_OBJECT_TYPE_DESCRIPTOR_POOL:
1054 /* These are just dummys anyway, so we don't need to destroy them */
1055 return VK_SUCCESS;
1056
1057 case VK_OBJECT_TYPE_BUFFER:
1058 case VK_OBJECT_TYPE_BUFFER_VIEW:
1059 case VK_OBJECT_TYPE_IMAGE:
1060 case VK_OBJECT_TYPE_IMAGE_VIEW:
1061 case VK_OBJECT_TYPE_COLOR_ATTACHMENT_VIEW:
1062 case VK_OBJECT_TYPE_DEPTH_STENCIL_VIEW:
1063 case VK_OBJECT_TYPE_SHADER:
1064 case VK_OBJECT_TYPE_PIPELINE_LAYOUT:
1065 case VK_OBJECT_TYPE_SAMPLER:
1066 case VK_OBJECT_TYPE_DESCRIPTOR_SET:
1067 case VK_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT:
1068 case VK_OBJECT_TYPE_DYNAMIC_RS_STATE:
1069 case VK_OBJECT_TYPE_DYNAMIC_CB_STATE:
1070 case VK_OBJECT_TYPE_DYNAMIC_DS_STATE:
1071 case VK_OBJECT_TYPE_RENDER_PASS:
1072 /* These are trivially destroyable */
1073 anv_device_free(device, (void *) _object);
1074 return VK_SUCCESS;
1075
1076 case VK_OBJECT_TYPE_COMMAND_BUFFER:
1077 case VK_OBJECT_TYPE_PIPELINE:
1078 case VK_OBJECT_TYPE_DYNAMIC_VP_STATE:
1079 case VK_OBJECT_TYPE_FENCE:
1080 case VK_OBJECT_TYPE_QUERY_POOL:
1081 case VK_OBJECT_TYPE_FRAMEBUFFER:
1082 (object->destructor)(device, object, objType);
1083 return VK_SUCCESS;
1084
1085 case VK_OBJECT_TYPE_SEMAPHORE:
1086 case VK_OBJECT_TYPE_EVENT:
1087 stub_return(VK_UNSUPPORTED);
1088
1089 default:
1090 unreachable("Invalid object type");
1091 }
1092 }
1093
1094 static void
1095 fill_memory_requirements(
1096 VkObjectType objType,
1097 VkObject object,
1098 VkMemoryRequirements * memory_requirements)
1099 {
1100 struct anv_buffer *buffer;
1101 struct anv_image *image;
1102
1103 memory_requirements->memPropsAllowed =
1104 VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT |
1105 VK_MEMORY_PROPERTY_HOST_DEVICE_COHERENT_BIT |
1106 /* VK_MEMORY_PROPERTY_HOST_UNCACHED_BIT | */
1107 VK_MEMORY_PROPERTY_HOST_WRITE_COMBINED_BIT |
1108 VK_MEMORY_PROPERTY_PREFER_HOST_LOCAL |
1109 VK_MEMORY_PROPERTY_SHAREABLE_BIT;
1110
1111 memory_requirements->memPropsRequired = 0;
1112
1113 switch (objType) {
1114 case VK_OBJECT_TYPE_BUFFER:
1115 buffer = (struct anv_buffer *) object;
1116 memory_requirements->size = buffer->size;
1117 memory_requirements->alignment = 16;
1118 break;
1119 case VK_OBJECT_TYPE_IMAGE:
1120 image = (struct anv_image *) object;
1121 memory_requirements->size = image->size;
1122 memory_requirements->alignment = image->alignment;
1123 break;
1124 default:
1125 memory_requirements->size = 0;
1126 break;
1127 }
1128 }
1129
1130 static uint32_t
1131 get_allocation_count(VkObjectType objType)
1132 {
1133 switch (objType) {
1134 case VK_OBJECT_TYPE_BUFFER:
1135 case VK_OBJECT_TYPE_IMAGE:
1136 return 1;
1137 default:
1138 return 0;
1139 }
1140 }
1141
1142 VkResult anv_GetObjectInfo(
1143 VkDevice _device,
1144 VkObjectType objType,
1145 VkObject object,
1146 VkObjectInfoType infoType,
1147 size_t* pDataSize,
1148 void* pData)
1149 {
1150 VkMemoryRequirements memory_requirements;
1151 uint32_t *count;
1152
1153 switch (infoType) {
1154 case VK_OBJECT_INFO_TYPE_MEMORY_REQUIREMENTS:
1155 *pDataSize = sizeof(memory_requirements);
1156 if (pData == NULL)
1157 return VK_SUCCESS;
1158
1159 fill_memory_requirements(objType, object, pData);
1160 return VK_SUCCESS;
1161
1162 case VK_OBJECT_INFO_TYPE_MEMORY_ALLOCATION_COUNT:
1163 *pDataSize = sizeof(count);
1164 if (pData == NULL)
1165 return VK_SUCCESS;
1166
1167 count = pData;
1168 *count = get_allocation_count(objType);
1169 return VK_SUCCESS;
1170
1171 default:
1172 return VK_UNSUPPORTED;
1173 }
1174
1175 }
1176
1177 VkResult anv_QueueBindObjectMemory(
1178 VkQueue queue,
1179 VkObjectType objType,
1180 VkObject object,
1181 uint32_t allocationIdx,
1182 VkDeviceMemory _mem,
1183 VkDeviceSize memOffset)
1184 {
1185 struct anv_buffer *buffer;
1186 struct anv_image *image;
1187 struct anv_device_memory *mem = (struct anv_device_memory *) _mem;
1188
1189 switch (objType) {
1190 case VK_OBJECT_TYPE_BUFFER:
1191 buffer = (struct anv_buffer *) object;
1192 buffer->bo = &mem->bo;
1193 buffer->offset = memOffset;
1194 break;
1195 case VK_OBJECT_TYPE_IMAGE:
1196 image = (struct anv_image *) object;
1197 image->bo = &mem->bo;
1198 image->offset = memOffset;
1199 break;
1200 default:
1201 break;
1202 }
1203
1204 return VK_SUCCESS;
1205 }
1206
1207 VkResult anv_QueueBindObjectMemoryRange(
1208 VkQueue queue,
1209 VkObjectType objType,
1210 VkObject object,
1211 uint32_t allocationIdx,
1212 VkDeviceSize rangeOffset,
1213 VkDeviceSize rangeSize,
1214 VkDeviceMemory mem,
1215 VkDeviceSize memOffset)
1216 {
1217 stub_return(VK_UNSUPPORTED);
1218 }
1219
1220 VkResult anv_QueueBindImageMemoryRange(
1221 VkQueue queue,
1222 VkImage image,
1223 uint32_t allocationIdx,
1224 const VkImageMemoryBindInfo* pBindInfo,
1225 VkDeviceMemory mem,
1226 VkDeviceSize memOffset)
1227 {
1228 stub_return(VK_UNSUPPORTED);
1229 }
1230
1231 static void
1232 anv_fence_destroy(struct anv_device *device,
1233 struct anv_object *object,
1234 VkObjectType obj_type)
1235 {
1236 struct anv_fence *fence = (struct anv_fence *) object;
1237
1238 assert(obj_type == VK_OBJECT_TYPE_FENCE);
1239
1240 anv_gem_munmap(fence->bo.map, fence->bo.size);
1241 anv_gem_close(device, fence->bo.gem_handle);
1242 anv_device_free(device, fence);
1243 }
1244
1245 VkResult anv_CreateFence(
1246 VkDevice _device,
1247 const VkFenceCreateInfo* pCreateInfo,
1248 VkFence* pFence)
1249 {
1250 struct anv_device *device = (struct anv_device *) _device;
1251 struct anv_fence *fence;
1252 struct anv_batch batch;
1253 VkResult result;
1254
1255 const uint32_t fence_size = 128;
1256
1257 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_FENCE_CREATE_INFO);
1258
1259 fence = anv_device_alloc(device, sizeof(*fence), 8,
1260 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
1261 if (fence == NULL)
1262 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1263
1264 result = anv_bo_init_new(&fence->bo, device, fence_size);
1265 if (result != VK_SUCCESS)
1266 goto fail;
1267
1268 fence->base.destructor = anv_fence_destroy;
1269
1270 fence->bo.map =
1271 anv_gem_mmap(device, fence->bo.gem_handle, 0, fence->bo.size);
1272 batch.next = batch.start = fence->bo.map;
1273 batch.end = fence->bo.map + fence->bo.size;
1274 anv_batch_emit(&batch, GEN8_MI_BATCH_BUFFER_END);
1275 anv_batch_emit(&batch, GEN8_MI_NOOP);
1276
1277 fence->exec2_objects[0].handle = fence->bo.gem_handle;
1278 fence->exec2_objects[0].relocation_count = 0;
1279 fence->exec2_objects[0].relocs_ptr = 0;
1280 fence->exec2_objects[0].alignment = 0;
1281 fence->exec2_objects[0].offset = fence->bo.offset;
1282 fence->exec2_objects[0].flags = 0;
1283 fence->exec2_objects[0].rsvd1 = 0;
1284 fence->exec2_objects[0].rsvd2 = 0;
1285
1286 fence->execbuf.buffers_ptr = (uintptr_t) fence->exec2_objects;
1287 fence->execbuf.buffer_count = 1;
1288 fence->execbuf.batch_start_offset = 0;
1289 fence->execbuf.batch_len = batch.next - fence->bo.map;
1290 fence->execbuf.cliprects_ptr = 0;
1291 fence->execbuf.num_cliprects = 0;
1292 fence->execbuf.DR1 = 0;
1293 fence->execbuf.DR4 = 0;
1294
1295 fence->execbuf.flags =
1296 I915_EXEC_HANDLE_LUT | I915_EXEC_NO_RELOC | I915_EXEC_RENDER;
1297 fence->execbuf.rsvd1 = device->context_id;
1298 fence->execbuf.rsvd2 = 0;
1299
1300 *pFence = (VkQueryPool) fence;
1301
1302 return VK_SUCCESS;
1303
1304 fail:
1305 anv_device_free(device, fence);
1306
1307 return result;
1308 }
1309
1310 VkResult anv_ResetFences(
1311 VkDevice _device,
1312 uint32_t fenceCount,
1313 VkFence* pFences)
1314 {
1315 struct anv_fence **fences = (struct anv_fence **) pFences;
1316
1317 for (uint32_t i; i < fenceCount; i++)
1318 fences[i]->ready = false;
1319
1320 return VK_SUCCESS;
1321 }
1322
1323 VkResult anv_GetFenceStatus(
1324 VkDevice _device,
1325 VkFence _fence)
1326 {
1327 struct anv_device *device = (struct anv_device *) _device;
1328 struct anv_fence *fence = (struct anv_fence *) _fence;
1329 int64_t t = 0;
1330 int ret;
1331
1332 if (fence->ready)
1333 return VK_SUCCESS;
1334
1335 ret = anv_gem_wait(device, fence->bo.gem_handle, &t);
1336 if (ret == 0) {
1337 fence->ready = true;
1338 return VK_SUCCESS;
1339 }
1340
1341 return VK_NOT_READY;
1342 }
1343
1344 VkResult anv_WaitForFences(
1345 VkDevice _device,
1346 uint32_t fenceCount,
1347 const VkFence* pFences,
1348 bool32_t waitAll,
1349 uint64_t timeout)
1350 {
1351 struct anv_device *device = (struct anv_device *) _device;
1352 struct anv_fence **fences = (struct anv_fence **) pFences;
1353 int64_t t = timeout;
1354 int ret;
1355
1356 /* FIXME: handle !waitAll */
1357
1358 for (uint32_t i = 0; i < fenceCount; i++) {
1359 ret = anv_gem_wait(device, fences[i]->bo.gem_handle, &t);
1360 if (ret == -1 && errno == ETIME)
1361 return VK_TIMEOUT;
1362 else if (ret == -1)
1363 return vk_error(VK_ERROR_UNKNOWN);
1364 }
1365
1366 return VK_SUCCESS;
1367 }
1368
1369 // Queue semaphore functions
1370
1371 VkResult anv_CreateSemaphore(
1372 VkDevice device,
1373 const VkSemaphoreCreateInfo* pCreateInfo,
1374 VkSemaphore* pSemaphore)
1375 {
1376 stub_return(VK_UNSUPPORTED);
1377 }
1378
1379 VkResult anv_QueueSignalSemaphore(
1380 VkQueue queue,
1381 VkSemaphore semaphore)
1382 {
1383 stub_return(VK_UNSUPPORTED);
1384 }
1385
1386 VkResult anv_QueueWaitSemaphore(
1387 VkQueue queue,
1388 VkSemaphore semaphore)
1389 {
1390 stub_return(VK_UNSUPPORTED);
1391 }
1392
1393 // Event functions
1394
1395 VkResult anv_CreateEvent(
1396 VkDevice device,
1397 const VkEventCreateInfo* pCreateInfo,
1398 VkEvent* pEvent)
1399 {
1400 stub_return(VK_UNSUPPORTED);
1401 }
1402
1403 VkResult anv_GetEventStatus(
1404 VkDevice device,
1405 VkEvent event)
1406 {
1407 stub_return(VK_UNSUPPORTED);
1408 }
1409
1410 VkResult anv_SetEvent(
1411 VkDevice device,
1412 VkEvent event)
1413 {
1414 stub_return(VK_UNSUPPORTED);
1415 }
1416
1417 VkResult anv_ResetEvent(
1418 VkDevice device,
1419 VkEvent event)
1420 {
1421 stub_return(VK_UNSUPPORTED);
1422 }
1423
1424 // Query functions
1425
1426 static void
1427 anv_query_pool_destroy(struct anv_device *device,
1428 struct anv_object *object,
1429 VkObjectType obj_type)
1430 {
1431 struct anv_query_pool *pool = (struct anv_query_pool *) object;
1432
1433 assert(obj_type == VK_OBJECT_TYPE_QUERY_POOL);
1434
1435 anv_gem_munmap(pool->bo.map, pool->bo.size);
1436 anv_gem_close(device, pool->bo.gem_handle);
1437 anv_device_free(device, pool);
1438 }
1439
1440 VkResult anv_CreateQueryPool(
1441 VkDevice _device,
1442 const VkQueryPoolCreateInfo* pCreateInfo,
1443 VkQueryPool* pQueryPool)
1444 {
1445 struct anv_device *device = (struct anv_device *) _device;
1446 struct anv_query_pool *pool;
1447 VkResult result;
1448 size_t size;
1449
1450 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_QUERY_POOL_CREATE_INFO);
1451
1452 switch (pCreateInfo->queryType) {
1453 case VK_QUERY_TYPE_OCCLUSION:
1454 break;
1455 case VK_QUERY_TYPE_PIPELINE_STATISTICS:
1456 return VK_UNSUPPORTED;
1457 default:
1458 unreachable("");
1459 }
1460
1461 pool = anv_device_alloc(device, sizeof(*pool), 8,
1462 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
1463 if (pool == NULL)
1464 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1465
1466 pool->base.destructor = anv_query_pool_destroy;
1467
1468 pool->type = pCreateInfo->queryType;
1469 size = pCreateInfo->slots * sizeof(struct anv_query_pool_slot);
1470 result = anv_bo_init_new(&pool->bo, device, size);
1471 if (result != VK_SUCCESS)
1472 goto fail;
1473
1474 pool->bo.map = anv_gem_mmap(device, pool->bo.gem_handle, 0, size);
1475
1476 *pQueryPool = (VkQueryPool) pool;
1477
1478 return VK_SUCCESS;
1479
1480 fail:
1481 anv_device_free(device, pool);
1482
1483 return result;
1484 }
1485
1486 VkResult anv_GetQueryPoolResults(
1487 VkDevice _device,
1488 VkQueryPool queryPool,
1489 uint32_t startQuery,
1490 uint32_t queryCount,
1491 size_t* pDataSize,
1492 void* pData,
1493 VkQueryResultFlags flags)
1494 {
1495 struct anv_device *device = (struct anv_device *) _device;
1496 struct anv_query_pool *pool = (struct anv_query_pool *) queryPool;
1497 struct anv_query_pool_slot *slot = pool->bo.map;
1498 int64_t timeout = INT64_MAX;
1499 uint32_t *dst32 = pData;
1500 uint64_t *dst64 = pData;
1501 uint64_t result;
1502 int ret;
1503
1504 if (flags & VK_QUERY_RESULT_WITH_AVAILABILITY_BIT) {
1505 /* Where is the availabilty info supposed to go? */
1506 anv_finishme("VK_QUERY_RESULT_WITH_AVAILABILITY_BIT");
1507 return VK_UNSUPPORTED;
1508 }
1509
1510 assert(pool->type == VK_QUERY_TYPE_OCCLUSION);
1511
1512 if (flags & VK_QUERY_RESULT_64_BIT)
1513 *pDataSize = queryCount * sizeof(uint64_t);
1514 else
1515 *pDataSize = queryCount * sizeof(uint32_t);
1516
1517 if (pData == NULL)
1518 return VK_SUCCESS;
1519
1520 if (flags & VK_QUERY_RESULT_WAIT_BIT) {
1521 ret = anv_gem_wait(device, pool->bo.gem_handle, &timeout);
1522 if (ret == -1)
1523 return vk_error(VK_ERROR_UNKNOWN);
1524 }
1525
1526 for (uint32_t i = 0; i < queryCount; i++) {
1527 result = slot[startQuery + i].end - slot[startQuery + i].begin;
1528 if (flags & VK_QUERY_RESULT_64_BIT) {
1529 *dst64++ = result;
1530 } else {
1531 if (result > UINT32_MAX)
1532 result = UINT32_MAX;
1533 *dst32++ = result;
1534 }
1535 }
1536
1537 return VK_SUCCESS;
1538 }
1539
1540 // Buffer functions
1541
1542 VkResult anv_CreateBuffer(
1543 VkDevice _device,
1544 const VkBufferCreateInfo* pCreateInfo,
1545 VkBuffer* pBuffer)
1546 {
1547 struct anv_device *device = (struct anv_device *) _device;
1548 struct anv_buffer *buffer;
1549
1550 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO);
1551
1552 buffer = anv_device_alloc(device, sizeof(*buffer), 8,
1553 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
1554 if (buffer == NULL)
1555 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1556
1557 buffer->size = pCreateInfo->size;
1558 buffer->bo = NULL;
1559 buffer->offset = 0;
1560
1561 *pBuffer = (VkBuffer) buffer;
1562
1563 return VK_SUCCESS;
1564 }
1565
1566 // Buffer view functions
1567
1568 static void
1569 fill_buffer_surface_state(void *state, VkFormat format,
1570 uint32_t offset, uint32_t range)
1571 {
1572 const struct anv_format *info;
1573
1574 info = anv_format_for_vk_format(format);
1575 /* This assumes RGBA float format. */
1576 uint32_t stride = 4;
1577 uint32_t num_elements = range / stride;
1578
1579 struct GEN8_RENDER_SURFACE_STATE surface_state = {
1580 .SurfaceType = SURFTYPE_BUFFER,
1581 .SurfaceArray = false,
1582 .SurfaceFormat = info->format,
1583 .SurfaceVerticalAlignment = VALIGN4,
1584 .SurfaceHorizontalAlignment = HALIGN4,
1585 .TileMode = LINEAR,
1586 .VerticalLineStride = 0,
1587 .VerticalLineStrideOffset = 0,
1588 .SamplerL2BypassModeDisable = true,
1589 .RenderCacheReadWriteMode = WriteOnlyCache,
1590 .MemoryObjectControlState = GEN8_MOCS,
1591 .BaseMipLevel = 0,
1592 .SurfaceQPitch = 0,
1593 .Height = (num_elements >> 7) & 0x3fff,
1594 .Width = num_elements & 0x7f,
1595 .Depth = (num_elements >> 21) & 0x3f,
1596 .SurfacePitch = stride - 1,
1597 .MinimumArrayElement = 0,
1598 .NumberofMultisamples = MULTISAMPLECOUNT_1,
1599 .XOffset = 0,
1600 .YOffset = 0,
1601 .SurfaceMinLOD = 0,
1602 .MIPCountLOD = 0,
1603 .AuxiliarySurfaceMode = AUX_NONE,
1604 .RedClearColor = 0,
1605 .GreenClearColor = 0,
1606 .BlueClearColor = 0,
1607 .AlphaClearColor = 0,
1608 .ShaderChannelSelectRed = SCS_RED,
1609 .ShaderChannelSelectGreen = SCS_GREEN,
1610 .ShaderChannelSelectBlue = SCS_BLUE,
1611 .ShaderChannelSelectAlpha = SCS_ALPHA,
1612 .ResourceMinLOD = 0,
1613 /* FIXME: We assume that the image must be bound at this time. */
1614 .SurfaceBaseAddress = { NULL, offset },
1615 };
1616
1617 GEN8_RENDER_SURFACE_STATE_pack(NULL, state, &surface_state);
1618 }
1619
1620 VkResult anv_CreateBufferView(
1621 VkDevice _device,
1622 const VkBufferViewCreateInfo* pCreateInfo,
1623 VkBufferView* pView)
1624 {
1625 struct anv_device *device = (struct anv_device *) _device;
1626 struct anv_buffer *buffer = (struct anv_buffer *) pCreateInfo->buffer;
1627 struct anv_surface_view *view;
1628
1629 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_BUFFER_VIEW_CREATE_INFO);
1630
1631 view = anv_device_alloc(device, sizeof(*view), 8,
1632 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
1633 if (view == NULL)
1634 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1635
1636 view->bo = buffer->bo;
1637 view->offset = buffer->offset + pCreateInfo->offset;
1638 view->surface_state =
1639 anv_state_pool_alloc(&device->surface_state_pool, 64, 64);
1640 view->format = pCreateInfo->format;
1641 view->range = pCreateInfo->range;
1642
1643 fill_buffer_surface_state(view->surface_state.map,
1644 pCreateInfo->format, view->offset, pCreateInfo->range);
1645
1646 *pView = (VkImageView) view;
1647
1648 return VK_SUCCESS;
1649 }
1650
1651 // Sampler functions
1652
1653 VkResult anv_CreateSampler(
1654 VkDevice _device,
1655 const VkSamplerCreateInfo* pCreateInfo,
1656 VkSampler* pSampler)
1657 {
1658 struct anv_device *device = (struct anv_device *) _device;
1659 struct anv_sampler *sampler;
1660
1661 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO);
1662
1663 sampler = anv_device_alloc(device, sizeof(*sampler), 8,
1664 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
1665 if (!sampler)
1666 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1667
1668 static const uint32_t vk_to_gen_tex_filter[] = {
1669 [VK_TEX_FILTER_NEAREST] = MAPFILTER_NEAREST,
1670 [VK_TEX_FILTER_LINEAR] = MAPFILTER_LINEAR
1671 };
1672
1673 static const uint32_t vk_to_gen_mipmap_mode[] = {
1674 [VK_TEX_MIPMAP_MODE_BASE] = MIPFILTER_NONE,
1675 [VK_TEX_MIPMAP_MODE_NEAREST] = MIPFILTER_NEAREST,
1676 [VK_TEX_MIPMAP_MODE_LINEAR] = MIPFILTER_LINEAR
1677 };
1678
1679 static const uint32_t vk_to_gen_tex_address[] = {
1680 [VK_TEX_ADDRESS_WRAP] = TCM_WRAP,
1681 [VK_TEX_ADDRESS_MIRROR] = TCM_MIRROR,
1682 [VK_TEX_ADDRESS_CLAMP] = TCM_CLAMP,
1683 [VK_TEX_ADDRESS_MIRROR_ONCE] = TCM_MIRROR_ONCE,
1684 [VK_TEX_ADDRESS_CLAMP_BORDER] = TCM_CLAMP_BORDER,
1685 };
1686
1687 static const uint32_t vk_to_gen_compare_op[] = {
1688 [VK_COMPARE_OP_NEVER] = PREFILTEROPNEVER,
1689 [VK_COMPARE_OP_LESS] = PREFILTEROPLESS,
1690 [VK_COMPARE_OP_EQUAL] = PREFILTEROPEQUAL,
1691 [VK_COMPARE_OP_LESS_EQUAL] = PREFILTEROPLEQUAL,
1692 [VK_COMPARE_OP_GREATER] = PREFILTEROPGREATER,
1693 [VK_COMPARE_OP_NOT_EQUAL] = PREFILTEROPNOTEQUAL,
1694 [VK_COMPARE_OP_GREATER_EQUAL] = PREFILTEROPGEQUAL,
1695 [VK_COMPARE_OP_ALWAYS] = PREFILTEROPALWAYS,
1696 };
1697
1698 if (pCreateInfo->maxAnisotropy > 0)
1699 anv_finishme("missing support for anisotropic filtering");
1700
1701 struct GEN8_SAMPLER_STATE sampler_state = {
1702 .SamplerDisable = false,
1703 .TextureBorderColorMode = DX10OGL,
1704 .LODPreClampMode = 0,
1705 .BaseMipLevel = 0,
1706 .MipModeFilter = vk_to_gen_mipmap_mode[pCreateInfo->mipMode],
1707 .MagModeFilter = vk_to_gen_tex_filter[pCreateInfo->magFilter],
1708 .MinModeFilter = vk_to_gen_tex_filter[pCreateInfo->minFilter],
1709 .TextureLODBias = pCreateInfo->mipLodBias * 256,
1710 .AnisotropicAlgorithm = EWAApproximation,
1711 .MinLOD = pCreateInfo->minLod * 256,
1712 .MaxLOD = pCreateInfo->maxLod * 256,
1713 .ChromaKeyEnable = 0,
1714 .ChromaKeyIndex = 0,
1715 .ChromaKeyMode = 0,
1716 .ShadowFunction = vk_to_gen_compare_op[pCreateInfo->compareOp],
1717 .CubeSurfaceControlMode = 0,
1718 .IndirectStatePointer = 0,
1719 .LODClampMagnificationMode = MIPNONE,
1720 .MaximumAnisotropy = 0,
1721 .RAddressMinFilterRoundingEnable = 0,
1722 .RAddressMagFilterRoundingEnable = 0,
1723 .VAddressMinFilterRoundingEnable = 0,
1724 .VAddressMagFilterRoundingEnable = 0,
1725 .UAddressMinFilterRoundingEnable = 0,
1726 .UAddressMagFilterRoundingEnable = 0,
1727 .TrilinearFilterQuality = 0,
1728 .NonnormalizedCoordinateEnable = 0,
1729 .TCXAddressControlMode = vk_to_gen_tex_address[pCreateInfo->addressU],
1730 .TCYAddressControlMode = vk_to_gen_tex_address[pCreateInfo->addressV],
1731 .TCZAddressControlMode = vk_to_gen_tex_address[pCreateInfo->addressW],
1732 };
1733
1734 GEN8_SAMPLER_STATE_pack(NULL, sampler->state, &sampler_state);
1735
1736 *pSampler = (VkSampler) sampler;
1737
1738 return VK_SUCCESS;
1739 }
1740
1741 // Descriptor set functions
1742
1743 VkResult anv_CreateDescriptorSetLayout(
1744 VkDevice _device,
1745 const VkDescriptorSetLayoutCreateInfo* pCreateInfo,
1746 VkDescriptorSetLayout* pSetLayout)
1747 {
1748 struct anv_device *device = (struct anv_device *) _device;
1749 struct anv_descriptor_set_layout *set_layout;
1750
1751 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO);
1752
1753 uint32_t sampler_count[VK_NUM_SHADER_STAGE] = { 0, };
1754 uint32_t surface_count[VK_NUM_SHADER_STAGE] = { 0, };
1755 uint32_t num_dynamic_buffers = 0;
1756 uint32_t count = 0;
1757 uint32_t stages = 0;
1758 uint32_t s;
1759
1760 for (uint32_t i = 0; i < pCreateInfo->count; i++) {
1761 switch (pCreateInfo->pBinding[i].descriptorType) {
1762 case VK_DESCRIPTOR_TYPE_SAMPLER:
1763 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
1764 for_each_bit(s, pCreateInfo->pBinding[i].stageFlags)
1765 sampler_count[s] += pCreateInfo->pBinding[i].count;
1766 break;
1767 default:
1768 break;
1769 }
1770
1771 switch (pCreateInfo->pBinding[i].descriptorType) {
1772 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
1773 case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE:
1774 case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE:
1775 case VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER:
1776 case VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER:
1777 case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER:
1778 case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER:
1779 case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC:
1780 case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC:
1781 for_each_bit(s, pCreateInfo->pBinding[i].stageFlags)
1782 surface_count[s] += pCreateInfo->pBinding[i].count;
1783 break;
1784 default:
1785 break;
1786 }
1787
1788 switch (pCreateInfo->pBinding[i].descriptorType) {
1789 case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC:
1790 case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC:
1791 num_dynamic_buffers += pCreateInfo->pBinding[i].count;
1792 break;
1793 default:
1794 break;
1795 }
1796
1797 stages |= pCreateInfo->pBinding[i].stageFlags;
1798 count += pCreateInfo->pBinding[i].count;
1799 }
1800
1801 uint32_t sampler_total = 0;
1802 uint32_t surface_total = 0;
1803 for (uint32_t s = 0; s < VK_NUM_SHADER_STAGE; s++) {
1804 sampler_total += sampler_count[s];
1805 surface_total += surface_count[s];
1806 }
1807
1808 size_t size = sizeof(*set_layout) +
1809 (sampler_total + surface_total) * sizeof(set_layout->entries[0]);
1810 set_layout = anv_device_alloc(device, size, 8,
1811 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
1812 if (!set_layout)
1813 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1814
1815 set_layout->num_dynamic_buffers = num_dynamic_buffers;
1816 set_layout->count = count;
1817 set_layout->shader_stages = stages;
1818
1819 struct anv_descriptor_slot *p = set_layout->entries;
1820 struct anv_descriptor_slot *sampler[VK_NUM_SHADER_STAGE];
1821 struct anv_descriptor_slot *surface[VK_NUM_SHADER_STAGE];
1822 for (uint32_t s = 0; s < VK_NUM_SHADER_STAGE; s++) {
1823 set_layout->stage[s].surface_count = surface_count[s];
1824 set_layout->stage[s].surface_start = surface[s] = p;
1825 p += surface_count[s];
1826 set_layout->stage[s].sampler_count = sampler_count[s];
1827 set_layout->stage[s].sampler_start = sampler[s] = p;
1828 p += sampler_count[s];
1829 }
1830
1831 uint32_t descriptor = 0;
1832 int8_t dynamic_slot = 0;
1833 bool is_dynamic;
1834 for (uint32_t i = 0; i < pCreateInfo->count; i++) {
1835 switch (pCreateInfo->pBinding[i].descriptorType) {
1836 case VK_DESCRIPTOR_TYPE_SAMPLER:
1837 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
1838 for_each_bit(s, pCreateInfo->pBinding[i].stageFlags)
1839 for (uint32_t j = 0; j < pCreateInfo->pBinding[i].count; j++) {
1840 sampler[s]->index = descriptor + j;
1841 sampler[s]->dynamic_slot = -1;
1842 sampler[s]++;
1843 }
1844 break;
1845 default:
1846 break;
1847 }
1848
1849 switch (pCreateInfo->pBinding[i].descriptorType) {
1850 case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC:
1851 case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC:
1852 is_dynamic = true;
1853 break;
1854 default:
1855 is_dynamic = false;
1856 break;
1857 }
1858
1859 switch (pCreateInfo->pBinding[i].descriptorType) {
1860 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
1861 case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE:
1862 case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE:
1863 case VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER:
1864 case VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER:
1865 case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER:
1866 case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER:
1867 case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC:
1868 case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC:
1869 for_each_bit(s, pCreateInfo->pBinding[i].stageFlags)
1870 for (uint32_t j = 0; j < pCreateInfo->pBinding[i].count; j++) {
1871 surface[s]->index = descriptor + j;
1872 if (is_dynamic)
1873 surface[s]->dynamic_slot = dynamic_slot + j;
1874 else
1875 surface[s]->dynamic_slot = -1;
1876 surface[s]++;
1877 }
1878 break;
1879 default:
1880 break;
1881 }
1882
1883 if (is_dynamic)
1884 dynamic_slot += pCreateInfo->pBinding[i].count;
1885
1886 descriptor += pCreateInfo->pBinding[i].count;
1887 }
1888
1889 *pSetLayout = (VkDescriptorSetLayout) set_layout;
1890
1891 return VK_SUCCESS;
1892 }
1893
1894 VkResult anv_BeginDescriptorPoolUpdate(
1895 VkDevice device,
1896 VkDescriptorUpdateMode updateMode)
1897 {
1898 return VK_SUCCESS;
1899 }
1900
1901 VkResult anv_EndDescriptorPoolUpdate(
1902 VkDevice device,
1903 VkCmdBuffer cmd)
1904 {
1905 return VK_SUCCESS;
1906 }
1907
1908 VkResult anv_CreateDescriptorPool(
1909 VkDevice device,
1910 VkDescriptorPoolUsage poolUsage,
1911 uint32_t maxSets,
1912 const VkDescriptorPoolCreateInfo* pCreateInfo,
1913 VkDescriptorPool* pDescriptorPool)
1914 {
1915 *pDescriptorPool = 1;
1916
1917 return VK_SUCCESS;
1918 }
1919
1920 VkResult anv_ResetDescriptorPool(
1921 VkDevice device,
1922 VkDescriptorPool descriptorPool)
1923 {
1924 return VK_SUCCESS;
1925 }
1926
1927 VkResult anv_AllocDescriptorSets(
1928 VkDevice _device,
1929 VkDescriptorPool descriptorPool,
1930 VkDescriptorSetUsage setUsage,
1931 uint32_t count,
1932 const VkDescriptorSetLayout* pSetLayouts,
1933 VkDescriptorSet* pDescriptorSets,
1934 uint32_t* pCount)
1935 {
1936 struct anv_device *device = (struct anv_device *) _device;
1937 const struct anv_descriptor_set_layout *layout;
1938 struct anv_descriptor_set *set;
1939 size_t size;
1940
1941 for (uint32_t i = 0; i < count; i++) {
1942 layout = (struct anv_descriptor_set_layout *) pSetLayouts[i];
1943 size = sizeof(*set) + layout->count * sizeof(set->descriptors[0]);
1944 set = anv_device_alloc(device, size, 8,
1945 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
1946 if (!set) {
1947 *pCount = i;
1948 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1949 }
1950
1951 /* Descriptor sets may not be 100% filled out so we need to memset to
1952 * ensure that we can properly detect and handle holes.
1953 */
1954 memset(set, 0, size);
1955
1956 pDescriptorSets[i] = (VkDescriptorSet) set;
1957 }
1958
1959 *pCount = count;
1960
1961 return VK_SUCCESS;
1962 }
1963
1964 void anv_ClearDescriptorSets(
1965 VkDevice device,
1966 VkDescriptorPool descriptorPool,
1967 uint32_t count,
1968 const VkDescriptorSet* pDescriptorSets)
1969 {
1970 }
1971
1972 void anv_UpdateDescriptors(
1973 VkDevice _device,
1974 VkDescriptorSet descriptorSet,
1975 uint32_t updateCount,
1976 const void** ppUpdateArray)
1977 {
1978 struct anv_descriptor_set *set = (struct anv_descriptor_set *) descriptorSet;
1979 VkUpdateSamplers *update_samplers;
1980 VkUpdateSamplerTextures *update_sampler_textures;
1981 VkUpdateImages *update_images;
1982 VkUpdateBuffers *update_buffers;
1983 VkUpdateAsCopy *update_as_copy;
1984
1985 for (uint32_t i = 0; i < updateCount; i++) {
1986 const struct anv_common *common = ppUpdateArray[i];
1987
1988 switch (common->sType) {
1989 case VK_STRUCTURE_TYPE_UPDATE_SAMPLERS:
1990 update_samplers = (VkUpdateSamplers *) common;
1991
1992 for (uint32_t j = 0; j < update_samplers->count; j++) {
1993 set->descriptors[update_samplers->binding + j].sampler =
1994 (struct anv_sampler *) update_samplers->pSamplers[j];
1995 }
1996 break;
1997
1998 case VK_STRUCTURE_TYPE_UPDATE_SAMPLER_TEXTURES:
1999 /* FIXME: Shouldn't this be *_UPDATE_SAMPLER_IMAGES? */
2000 update_sampler_textures = (VkUpdateSamplerTextures *) common;
2001
2002 for (uint32_t j = 0; j < update_sampler_textures->count; j++) {
2003 set->descriptors[update_sampler_textures->binding + j].view =
2004 (struct anv_surface_view *)
2005 update_sampler_textures->pSamplerImageViews[j].pImageView->view;
2006 set->descriptors[update_sampler_textures->binding + j].sampler =
2007 (struct anv_sampler *)
2008 update_sampler_textures->pSamplerImageViews[j].sampler;
2009 }
2010 break;
2011
2012 case VK_STRUCTURE_TYPE_UPDATE_IMAGES:
2013 update_images = (VkUpdateImages *) common;
2014
2015 for (uint32_t j = 0; j < update_images->count; j++) {
2016 set->descriptors[update_images->binding + j].view =
2017 (struct anv_surface_view *) update_images->pImageViews[j].view;
2018 }
2019 break;
2020
2021 case VK_STRUCTURE_TYPE_UPDATE_BUFFERS:
2022 update_buffers = (VkUpdateBuffers *) common;
2023
2024 for (uint32_t j = 0; j < update_buffers->count; j++) {
2025 set->descriptors[update_buffers->binding + j].view =
2026 (struct anv_surface_view *) update_buffers->pBufferViews[j].view;
2027 }
2028 /* FIXME: descriptor arrays? */
2029 break;
2030
2031 case VK_STRUCTURE_TYPE_UPDATE_AS_COPY:
2032 update_as_copy = (VkUpdateAsCopy *) common;
2033 (void) update_as_copy;
2034 break;
2035
2036 default:
2037 break;
2038 }
2039 }
2040 }
2041
2042 // State object functions
2043
2044 static inline int64_t
2045 clamp_int64(int64_t x, int64_t min, int64_t max)
2046 {
2047 if (x < min)
2048 return min;
2049 else if (x < max)
2050 return x;
2051 else
2052 return max;
2053 }
2054
2055 static void
2056 anv_dynamic_vp_state_destroy(struct anv_device *device,
2057 struct anv_object *object,
2058 VkObjectType obj_type)
2059 {
2060 struct anv_dynamic_vp_state *state = (void *)object;
2061
2062 assert(obj_type == VK_OBJECT_TYPE_DYNAMIC_VP_STATE);
2063
2064 anv_state_pool_free(&device->dynamic_state_pool, state->sf_clip_vp);
2065 anv_state_pool_free(&device->dynamic_state_pool, state->cc_vp);
2066 anv_state_pool_free(&device->dynamic_state_pool, state->scissor);
2067
2068 anv_device_free(device, state);
2069 }
2070
2071 VkResult anv_CreateDynamicViewportState(
2072 VkDevice _device,
2073 const VkDynamicVpStateCreateInfo* pCreateInfo,
2074 VkDynamicVpState* pState)
2075 {
2076 struct anv_device *device = (struct anv_device *) _device;
2077 struct anv_dynamic_vp_state *state;
2078
2079 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_DYNAMIC_VP_STATE_CREATE_INFO);
2080
2081 state = anv_device_alloc(device, sizeof(*state), 8,
2082 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
2083 if (state == NULL)
2084 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
2085
2086 state->base.destructor = anv_dynamic_vp_state_destroy;
2087
2088 unsigned count = pCreateInfo->viewportAndScissorCount;
2089 state->sf_clip_vp = anv_state_pool_alloc(&device->dynamic_state_pool,
2090 count * 64, 64);
2091 state->cc_vp = anv_state_pool_alloc(&device->dynamic_state_pool,
2092 count * 8, 32);
2093 state->scissor = anv_state_pool_alloc(&device->dynamic_state_pool,
2094 count * 32, 32);
2095
2096 for (uint32_t i = 0; i < pCreateInfo->viewportAndScissorCount; i++) {
2097 const VkViewport *vp = &pCreateInfo->pViewports[i];
2098 const VkRect *s = &pCreateInfo->pScissors[i];
2099
2100 struct GEN8_SF_CLIP_VIEWPORT sf_clip_viewport = {
2101 .ViewportMatrixElementm00 = vp->width / 2,
2102 .ViewportMatrixElementm11 = vp->height / 2,
2103 .ViewportMatrixElementm22 = (vp->maxDepth - vp->minDepth) / 2,
2104 .ViewportMatrixElementm30 = vp->originX + vp->width / 2,
2105 .ViewportMatrixElementm31 = vp->originY + vp->height / 2,
2106 .ViewportMatrixElementm32 = (vp->maxDepth + vp->minDepth) / 2,
2107 .XMinClipGuardband = -1.0f,
2108 .XMaxClipGuardband = 1.0f,
2109 .YMinClipGuardband = -1.0f,
2110 .YMaxClipGuardband = 1.0f,
2111 .XMinViewPort = vp->originX,
2112 .XMaxViewPort = vp->originX + vp->width - 1,
2113 .YMinViewPort = vp->originY,
2114 .YMaxViewPort = vp->originY + vp->height - 1,
2115 };
2116
2117 struct GEN8_CC_VIEWPORT cc_viewport = {
2118 .MinimumDepth = vp->minDepth,
2119 .MaximumDepth = vp->maxDepth
2120 };
2121
2122 /* Since xmax and ymax are inclusive, we have to have xmax < xmin or
2123 * ymax < ymin for empty clips. In case clip x, y, width height are all
2124 * 0, the clamps below produce 0 for xmin, ymin, xmax, ymax, which isn't
2125 * what we want. Just special case empty clips and produce a canonical
2126 * empty clip. */
2127 static const struct GEN8_SCISSOR_RECT empty_scissor = {
2128 .ScissorRectangleYMin = 1,
2129 .ScissorRectangleXMin = 1,
2130 .ScissorRectangleYMax = 0,
2131 .ScissorRectangleXMax = 0
2132 };
2133
2134 const int max = 0xffff;
2135 struct GEN8_SCISSOR_RECT scissor = {
2136 /* Do this math using int64_t so overflow gets clamped correctly. */
2137 .ScissorRectangleYMin = clamp_int64(s->offset.y, 0, max),
2138 .ScissorRectangleXMin = clamp_int64(s->offset.x, 0, max),
2139 .ScissorRectangleYMax = clamp_int64((uint64_t) s->offset.y + s->extent.height - 1, 0, max),
2140 .ScissorRectangleXMax = clamp_int64((uint64_t) s->offset.x + s->extent.width - 1, 0, max)
2141 };
2142
2143 GEN8_SF_CLIP_VIEWPORT_pack(NULL, state->sf_clip_vp.map + i * 64, &sf_clip_viewport);
2144 GEN8_CC_VIEWPORT_pack(NULL, state->cc_vp.map + i * 32, &cc_viewport);
2145
2146 if (s->extent.width <= 0 || s->extent.height <= 0) {
2147 GEN8_SCISSOR_RECT_pack(NULL, state->scissor.map + i * 32, &empty_scissor);
2148 } else {
2149 GEN8_SCISSOR_RECT_pack(NULL, state->scissor.map + i * 32, &scissor);
2150 }
2151 }
2152
2153 *pState = (VkDynamicVpState) state;
2154
2155 return VK_SUCCESS;
2156 }
2157
2158 VkResult anv_CreateDynamicRasterState(
2159 VkDevice _device,
2160 const VkDynamicRsStateCreateInfo* pCreateInfo,
2161 VkDynamicRsState* pState)
2162 {
2163 struct anv_device *device = (struct anv_device *) _device;
2164 struct anv_dynamic_rs_state *state;
2165
2166 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_DYNAMIC_RS_STATE_CREATE_INFO);
2167
2168 state = anv_device_alloc(device, sizeof(*state), 8,
2169 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
2170 if (state == NULL)
2171 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
2172
2173 /* Missing these:
2174 * float pointFadeThreshold;
2175 * // optional (GL45) - Size of point fade threshold
2176 */
2177
2178 struct GEN8_3DSTATE_SF sf = {
2179 GEN8_3DSTATE_SF_header,
2180 .LineWidth = pCreateInfo->lineWidth,
2181 .PointWidth = pCreateInfo->pointSize,
2182 };
2183
2184 GEN8_3DSTATE_SF_pack(NULL, state->state_sf, &sf);
2185
2186 bool enable_bias = pCreateInfo->depthBias != 0.0f ||
2187 pCreateInfo->slopeScaledDepthBias != 0.0f;
2188 struct GEN8_3DSTATE_RASTER raster = {
2189 .GlobalDepthOffsetEnableSolid = enable_bias,
2190 .GlobalDepthOffsetEnableWireframe = enable_bias,
2191 .GlobalDepthOffsetEnablePoint = enable_bias,
2192 .GlobalDepthOffsetConstant = pCreateInfo->depthBias,
2193 .GlobalDepthOffsetScale = pCreateInfo->slopeScaledDepthBias,
2194 .GlobalDepthOffsetClamp = pCreateInfo->depthBiasClamp
2195 };
2196
2197 GEN8_3DSTATE_RASTER_pack(NULL, state->state_raster, &raster);
2198
2199 *pState = (VkDynamicRsState) state;
2200
2201 return VK_SUCCESS;
2202 }
2203
2204 VkResult anv_CreateDynamicColorBlendState(
2205 VkDevice _device,
2206 const VkDynamicCbStateCreateInfo* pCreateInfo,
2207 VkDynamicCbState* pState)
2208 {
2209 struct anv_device *device = (struct anv_device *) _device;
2210 struct anv_dynamic_cb_state *state;
2211
2212 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_DYNAMIC_CB_STATE_CREATE_INFO);
2213
2214 state = anv_device_alloc(device, sizeof(*state), 8,
2215 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
2216 if (state == NULL)
2217 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
2218
2219 struct GEN8_COLOR_CALC_STATE color_calc_state = {
2220 .BlendConstantColorRed = pCreateInfo->blendConst[0],
2221 .BlendConstantColorGreen = pCreateInfo->blendConst[1],
2222 .BlendConstantColorBlue = pCreateInfo->blendConst[2],
2223 .BlendConstantColorAlpha = pCreateInfo->blendConst[3]
2224 };
2225
2226 GEN8_COLOR_CALC_STATE_pack(NULL, state->state_color_calc, &color_calc_state);
2227
2228 *pState = (VkDynamicCbState) state;
2229
2230 return VK_SUCCESS;
2231 }
2232
2233 VkResult anv_CreateDynamicDepthStencilState(
2234 VkDevice _device,
2235 const VkDynamicDsStateCreateInfo* pCreateInfo,
2236 VkDynamicDsState* pState)
2237 {
2238 struct anv_device *device = (struct anv_device *) _device;
2239 struct anv_dynamic_ds_state *state;
2240
2241 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_DYNAMIC_DS_STATE_CREATE_INFO);
2242
2243 state = anv_device_alloc(device, sizeof(*state), 8,
2244 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
2245 if (state == NULL)
2246 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
2247
2248 struct GEN8_3DSTATE_WM_DEPTH_STENCIL wm_depth_stencil = {
2249 GEN8_3DSTATE_WM_DEPTH_STENCIL_header,
2250
2251 /* Is this what we need to do? */
2252 .StencilBufferWriteEnable = pCreateInfo->stencilWriteMask != 0,
2253
2254 .StencilTestMask = pCreateInfo->stencilReadMask,
2255 .StencilWriteMask = pCreateInfo->stencilWriteMask,
2256
2257 .BackfaceStencilTestMask = pCreateInfo->stencilReadMask,
2258 .BackfaceStencilWriteMask = pCreateInfo->stencilWriteMask,
2259 };
2260
2261 GEN8_3DSTATE_WM_DEPTH_STENCIL_pack(NULL, state->state_wm_depth_stencil,
2262 &wm_depth_stencil);
2263
2264 struct GEN8_COLOR_CALC_STATE color_calc_state = {
2265 .StencilReferenceValue = pCreateInfo->stencilFrontRef,
2266 .BackFaceStencilReferenceValue = pCreateInfo->stencilBackRef
2267 };
2268
2269 GEN8_COLOR_CALC_STATE_pack(NULL, state->state_color_calc, &color_calc_state);
2270
2271 *pState = (VkDynamicDsState) state;
2272
2273 return VK_SUCCESS;
2274 }
2275
2276 // Command buffer functions
2277
2278 static void
2279 anv_cmd_buffer_destroy(struct anv_device *device,
2280 struct anv_object *object,
2281 VkObjectType obj_type)
2282 {
2283 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) object;
2284
2285 assert(obj_type == VK_OBJECT_TYPE_COMMAND_BUFFER);
2286
2287 /* Destroy all of the batch buffers */
2288 struct anv_batch_bo *bbo = cmd_buffer->last_batch_bo;
2289 while (bbo->prev_batch_bo) {
2290 struct anv_batch_bo *prev = bbo->prev_batch_bo;
2291 anv_batch_bo_destroy(bbo, device);
2292 bbo = prev;
2293 }
2294 anv_reloc_list_finish(&cmd_buffer->batch.relocs, device);
2295
2296 /* Destroy all of the surface state buffers */
2297 bbo = cmd_buffer->surface_batch_bo;
2298 while (bbo->prev_batch_bo) {
2299 struct anv_batch_bo *prev = bbo->prev_batch_bo;
2300 anv_batch_bo_destroy(bbo, device);
2301 bbo = prev;
2302 }
2303 anv_reloc_list_finish(&cmd_buffer->surface_relocs, device);
2304
2305 anv_state_stream_finish(&cmd_buffer->surface_state_stream);
2306 anv_state_stream_finish(&cmd_buffer->dynamic_state_stream);
2307 anv_state_stream_finish(&cmd_buffer->binding_table_state_stream);
2308 anv_device_free(device, cmd_buffer->exec2_objects);
2309 anv_device_free(device, cmd_buffer->exec2_bos);
2310 anv_device_free(device, cmd_buffer);
2311 }
2312
2313 static VkResult
2314 anv_cmd_buffer_chain_batch(struct anv_batch *batch, void *_data)
2315 {
2316 struct anv_cmd_buffer *cmd_buffer = _data;
2317
2318 struct anv_batch_bo *new_bbo, *old_bbo = cmd_buffer->last_batch_bo;
2319
2320 VkResult result = anv_batch_bo_create(cmd_buffer->device, &new_bbo);
2321 if (result != VK_SUCCESS)
2322 return result;
2323
2324 /* We set the end of the batch a little short so we would be sure we
2325 * have room for the chaining command. Since we're about to emit the
2326 * chaining command, let's set it back where it should go.
2327 */
2328 batch->end += GEN8_MI_BATCH_BUFFER_START_length * 4;
2329 assert(batch->end == old_bbo->bo.map + old_bbo->bo.size);
2330
2331 anv_batch_emit(batch, GEN8_MI_BATCH_BUFFER_START,
2332 GEN8_MI_BATCH_BUFFER_START_header,
2333 ._2ndLevelBatchBuffer = _1stlevelbatch,
2334 .AddressSpaceIndicator = ASI_PPGTT,
2335 .BatchBufferStartAddress = { &new_bbo->bo, 0 },
2336 );
2337
2338 /* Pad out to a 2-dword aligned boundary with zeros */
2339 if ((uintptr_t)batch->next % 8 != 0) {
2340 *(uint32_t *)batch->next = 0;
2341 batch->next += 4;
2342 }
2343
2344 anv_batch_bo_finish(cmd_buffer->last_batch_bo, batch);
2345
2346 new_bbo->prev_batch_bo = old_bbo;
2347 cmd_buffer->last_batch_bo = new_bbo;
2348
2349 anv_batch_bo_start(new_bbo, batch, GEN8_MI_BATCH_BUFFER_START_length * 4);
2350
2351 return VK_SUCCESS;
2352 }
2353
2354 VkResult anv_CreateCommandBuffer(
2355 VkDevice _device,
2356 const VkCmdBufferCreateInfo* pCreateInfo,
2357 VkCmdBuffer* pCmdBuffer)
2358 {
2359 struct anv_device *device = (struct anv_device *) _device;
2360 struct anv_cmd_buffer *cmd_buffer;
2361 VkResult result;
2362
2363 cmd_buffer = anv_device_alloc(device, sizeof(*cmd_buffer), 8,
2364 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
2365 if (cmd_buffer == NULL)
2366 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
2367
2368 cmd_buffer->base.destructor = anv_cmd_buffer_destroy;
2369
2370 cmd_buffer->device = device;
2371 cmd_buffer->rs_state = NULL;
2372 cmd_buffer->vp_state = NULL;
2373 memset(&cmd_buffer->descriptors, 0, sizeof(cmd_buffer->descriptors));
2374
2375 result = anv_batch_bo_create(device, &cmd_buffer->last_batch_bo);
2376 if (result != VK_SUCCESS)
2377 goto fail;
2378
2379 result = anv_reloc_list_init(&cmd_buffer->batch.relocs, device);
2380 if (result != VK_SUCCESS)
2381 goto fail_batch_bo;
2382
2383 cmd_buffer->batch.device = device;
2384 cmd_buffer->batch.extend_cb = anv_cmd_buffer_chain_batch;
2385 cmd_buffer->batch.user_data = cmd_buffer;
2386
2387 anv_batch_bo_start(cmd_buffer->last_batch_bo, &cmd_buffer->batch,
2388 GEN8_MI_BATCH_BUFFER_START_length * 4);
2389
2390 result = anv_batch_bo_create(device, &cmd_buffer->surface_batch_bo);
2391 if (result != VK_SUCCESS)
2392 goto fail_batch_relocs;
2393 cmd_buffer->surface_batch_bo->first_reloc = 0;
2394
2395 result = anv_reloc_list_init(&cmd_buffer->surface_relocs, device);
2396 if (result != VK_SUCCESS)
2397 goto fail_ss_batch_bo;
2398
2399 /* Start surface_next at 1 so surface offset 0 is invalid. */
2400 cmd_buffer->surface_next = 1;
2401
2402 cmd_buffer->exec2_objects = NULL;
2403 cmd_buffer->exec2_bos = NULL;
2404 cmd_buffer->exec2_array_length = 0;
2405
2406 anv_state_stream_init(&cmd_buffer->binding_table_state_stream,
2407 &device->binding_table_block_pool);
2408 anv_state_stream_init(&cmd_buffer->surface_state_stream,
2409 &device->surface_state_block_pool);
2410 anv_state_stream_init(&cmd_buffer->dynamic_state_stream,
2411 &device->dynamic_state_block_pool);
2412
2413 cmd_buffer->dirty = 0;
2414 cmd_buffer->vb_dirty = 0;
2415 cmd_buffer->descriptors_dirty = 0;
2416 cmd_buffer->pipeline = NULL;
2417 cmd_buffer->vp_state = NULL;
2418 cmd_buffer->rs_state = NULL;
2419 cmd_buffer->ds_state = NULL;
2420
2421 *pCmdBuffer = (VkCmdBuffer) cmd_buffer;
2422
2423 return VK_SUCCESS;
2424
2425 fail_ss_batch_bo:
2426 anv_batch_bo_destroy(cmd_buffer->surface_batch_bo, device);
2427 fail_batch_relocs:
2428 anv_reloc_list_finish(&cmd_buffer->batch.relocs, device);
2429 fail_batch_bo:
2430 anv_batch_bo_destroy(cmd_buffer->last_batch_bo, device);
2431 fail:
2432 anv_device_free(device, cmd_buffer);
2433
2434 return result;
2435 }
2436
2437 static void
2438 anv_cmd_buffer_emit_state_base_address(struct anv_cmd_buffer *cmd_buffer)
2439 {
2440 struct anv_device *device = cmd_buffer->device;
2441
2442 anv_batch_emit(&cmd_buffer->batch, GEN8_STATE_BASE_ADDRESS,
2443 .GeneralStateBaseAddress = { NULL, 0 },
2444 .GeneralStateMemoryObjectControlState = GEN8_MOCS,
2445 .GeneralStateBaseAddressModifyEnable = true,
2446 .GeneralStateBufferSize = 0xfffff,
2447 .GeneralStateBufferSizeModifyEnable = true,
2448
2449 .SurfaceStateBaseAddress = { &cmd_buffer->surface_batch_bo->bo, 0 },
2450 .SurfaceStateMemoryObjectControlState = GEN8_MOCS,
2451 .SurfaceStateBaseAddressModifyEnable = true,
2452
2453 .DynamicStateBaseAddress = { &device->dynamic_state_block_pool.bo, 0 },
2454 .DynamicStateMemoryObjectControlState = GEN8_MOCS,
2455 .DynamicStateBaseAddressModifyEnable = true,
2456 .DynamicStateBufferSize = 0xfffff,
2457 .DynamicStateBufferSizeModifyEnable = true,
2458
2459 .IndirectObjectBaseAddress = { NULL, 0 },
2460 .IndirectObjectMemoryObjectControlState = GEN8_MOCS,
2461 .IndirectObjectBaseAddressModifyEnable = true,
2462 .IndirectObjectBufferSize = 0xfffff,
2463 .IndirectObjectBufferSizeModifyEnable = true,
2464
2465 .InstructionBaseAddress = { &device->instruction_block_pool.bo, 0 },
2466 .InstructionMemoryObjectControlState = GEN8_MOCS,
2467 .InstructionBaseAddressModifyEnable = true,
2468 .InstructionBufferSize = 0xfffff,
2469 .InstructionBuffersizeModifyEnable = true);
2470 }
2471
2472 VkResult anv_BeginCommandBuffer(
2473 VkCmdBuffer cmdBuffer,
2474 const VkCmdBufferBeginInfo* pBeginInfo)
2475 {
2476 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2477
2478 anv_batch_emit(&cmd_buffer->batch, GEN8_PIPELINE_SELECT,
2479 .PipelineSelection = _3D);
2480 anv_batch_emit(&cmd_buffer->batch, GEN8_STATE_SIP);
2481
2482 anv_cmd_buffer_emit_state_base_address(cmd_buffer);
2483
2484 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_VF_STATISTICS,
2485 .StatisticsEnable = true);
2486 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_HS, .Enable = false);
2487 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_TE, .TEEnable = false);
2488 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_DS, .FunctionEnable = false);
2489 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_STREAMOUT, .SOFunctionEnable = false);
2490
2491 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_PUSH_CONSTANT_ALLOC_VS,
2492 .ConstantBufferOffset = 0,
2493 .ConstantBufferSize = 4);
2494 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_PUSH_CONSTANT_ALLOC_GS,
2495 .ConstantBufferOffset = 4,
2496 .ConstantBufferSize = 4);
2497 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_PUSH_CONSTANT_ALLOC_PS,
2498 .ConstantBufferOffset = 8,
2499 .ConstantBufferSize = 4);
2500
2501 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_WM_CHROMAKEY,
2502 .ChromaKeyKillEnable = false);
2503 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_SBE_SWIZ);
2504 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_AA_LINE_PARAMETERS);
2505
2506 return VK_SUCCESS;
2507 }
2508
2509 static VkResult
2510 anv_cmd_buffer_add_bo(struct anv_cmd_buffer *cmd_buffer,
2511 struct anv_bo *bo,
2512 struct drm_i915_gem_relocation_entry *relocs,
2513 size_t num_relocs)
2514 {
2515 struct drm_i915_gem_exec_object2 *obj;
2516
2517 if (bo->index < cmd_buffer->bo_count &&
2518 cmd_buffer->exec2_bos[bo->index] == bo)
2519 return VK_SUCCESS;
2520
2521 if (cmd_buffer->bo_count >= cmd_buffer->exec2_array_length) {
2522 uint32_t new_len = cmd_buffer->exec2_objects ?
2523 cmd_buffer->exec2_array_length * 2 : 64;
2524
2525 struct drm_i915_gem_exec_object2 *new_objects =
2526 anv_device_alloc(cmd_buffer->device, new_len * sizeof(*new_objects),
2527 8, VK_SYSTEM_ALLOC_TYPE_INTERNAL);
2528 if (new_objects == NULL)
2529 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
2530
2531 struct anv_bo **new_bos =
2532 anv_device_alloc(cmd_buffer->device, new_len * sizeof(*new_bos),
2533 8, VK_SYSTEM_ALLOC_TYPE_INTERNAL);
2534 if (new_objects == NULL) {
2535 anv_device_free(cmd_buffer->device, new_objects);
2536 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
2537 }
2538
2539 if (cmd_buffer->exec2_objects) {
2540 memcpy(new_objects, cmd_buffer->exec2_objects,
2541 cmd_buffer->bo_count * sizeof(*new_objects));
2542 memcpy(new_bos, cmd_buffer->exec2_bos,
2543 cmd_buffer->bo_count * sizeof(*new_bos));
2544 }
2545
2546 cmd_buffer->exec2_objects = new_objects;
2547 cmd_buffer->exec2_bos = new_bos;
2548 cmd_buffer->exec2_array_length = new_len;
2549 }
2550
2551 assert(cmd_buffer->bo_count < cmd_buffer->exec2_array_length);
2552
2553 bo->index = cmd_buffer->bo_count++;
2554 obj = &cmd_buffer->exec2_objects[bo->index];
2555 cmd_buffer->exec2_bos[bo->index] = bo;
2556
2557 obj->handle = bo->gem_handle;
2558 obj->relocation_count = 0;
2559 obj->relocs_ptr = 0;
2560 obj->alignment = 0;
2561 obj->offset = bo->offset;
2562 obj->flags = 0;
2563 obj->rsvd1 = 0;
2564 obj->rsvd2 = 0;
2565
2566 if (relocs) {
2567 obj->relocation_count = num_relocs;
2568 obj->relocs_ptr = (uintptr_t) relocs;
2569 }
2570
2571 return VK_SUCCESS;
2572 }
2573
2574 static void
2575 anv_cmd_buffer_add_validate_bos(struct anv_cmd_buffer *cmd_buffer,
2576 struct anv_reloc_list *list)
2577 {
2578 for (size_t i = 0; i < list->num_relocs; i++)
2579 anv_cmd_buffer_add_bo(cmd_buffer, list->reloc_bos[i], NULL, 0);
2580 }
2581
2582 static void
2583 anv_cmd_buffer_process_relocs(struct anv_cmd_buffer *cmd_buffer,
2584 struct anv_reloc_list *list)
2585 {
2586 struct anv_bo *bo;
2587
2588 /* If the kernel supports I915_EXEC_NO_RELOC, it will compare offset in
2589 * struct drm_i915_gem_exec_object2 against the bos current offset and if
2590 * all bos haven't moved it will skip relocation processing alltogether.
2591 * If I915_EXEC_NO_RELOC is not supported, the kernel ignores the incoming
2592 * value of offset so we can set it either way. For that to work we need
2593 * to make sure all relocs use the same presumed offset.
2594 */
2595
2596 for (size_t i = 0; i < list->num_relocs; i++) {
2597 bo = list->reloc_bos[i];
2598 if (bo->offset != list->relocs[i].presumed_offset)
2599 cmd_buffer->need_reloc = true;
2600
2601 list->relocs[i].target_handle = bo->index;
2602 }
2603 }
2604
2605 VkResult anv_EndCommandBuffer(
2606 VkCmdBuffer cmdBuffer)
2607 {
2608 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2609 struct anv_device *device = cmd_buffer->device;
2610 struct anv_batch *batch = &cmd_buffer->batch;
2611
2612 anv_batch_emit(batch, GEN8_MI_BATCH_BUFFER_END);
2613
2614 /* Round batch up to an even number of dwords. */
2615 if ((batch->next - batch->start) & 4)
2616 anv_batch_emit(batch, GEN8_MI_NOOP);
2617
2618 anv_batch_bo_finish(cmd_buffer->last_batch_bo, &cmd_buffer->batch);
2619 cmd_buffer->surface_batch_bo->num_relocs =
2620 cmd_buffer->surface_relocs.num_relocs - cmd_buffer->surface_batch_bo->first_reloc;
2621 cmd_buffer->surface_batch_bo->length = cmd_buffer->surface_next;
2622
2623 cmd_buffer->bo_count = 0;
2624 cmd_buffer->need_reloc = false;
2625
2626 /* Lock for access to bo->index. */
2627 pthread_mutex_lock(&device->mutex);
2628
2629 /* Add surface state bos first so we can add them with their relocs. */
2630 for (struct anv_batch_bo *bbo = cmd_buffer->surface_batch_bo;
2631 bbo != NULL; bbo = bbo->prev_batch_bo) {
2632 anv_cmd_buffer_add_bo(cmd_buffer, &bbo->bo,
2633 &cmd_buffer->surface_relocs.relocs[bbo->first_reloc],
2634 bbo->num_relocs);
2635 }
2636
2637 /* Add all of the BOs referenced by surface state */
2638 anv_cmd_buffer_add_validate_bos(cmd_buffer, &cmd_buffer->surface_relocs);
2639
2640 /* Add all but the first batch BO */
2641 struct anv_batch_bo *batch_bo = cmd_buffer->last_batch_bo;
2642 while (batch_bo->prev_batch_bo) {
2643 anv_cmd_buffer_add_bo(cmd_buffer, &batch_bo->bo,
2644 &batch->relocs.relocs[batch_bo->first_reloc],
2645 batch_bo->num_relocs);
2646 batch_bo = batch_bo->prev_batch_bo;
2647 }
2648
2649 /* Add everything referenced by the batches */
2650 anv_cmd_buffer_add_validate_bos(cmd_buffer, &batch->relocs);
2651
2652 /* Add the first batch bo last */
2653 assert(batch_bo->prev_batch_bo == NULL && batch_bo->first_reloc == 0);
2654 anv_cmd_buffer_add_bo(cmd_buffer, &batch_bo->bo,
2655 &batch->relocs.relocs[batch_bo->first_reloc],
2656 batch_bo->num_relocs);
2657 assert(batch_bo->bo.index == cmd_buffer->bo_count - 1);
2658
2659 anv_cmd_buffer_process_relocs(cmd_buffer, &cmd_buffer->surface_relocs);
2660 anv_cmd_buffer_process_relocs(cmd_buffer, &batch->relocs);
2661
2662 cmd_buffer->execbuf.buffers_ptr = (uintptr_t) cmd_buffer->exec2_objects;
2663 cmd_buffer->execbuf.buffer_count = cmd_buffer->bo_count;
2664 cmd_buffer->execbuf.batch_start_offset = 0;
2665 cmd_buffer->execbuf.batch_len = batch->next - batch->start;
2666 cmd_buffer->execbuf.cliprects_ptr = 0;
2667 cmd_buffer->execbuf.num_cliprects = 0;
2668 cmd_buffer->execbuf.DR1 = 0;
2669 cmd_buffer->execbuf.DR4 = 0;
2670
2671 cmd_buffer->execbuf.flags = I915_EXEC_HANDLE_LUT;
2672 if (!cmd_buffer->need_reloc)
2673 cmd_buffer->execbuf.flags |= I915_EXEC_NO_RELOC;
2674 cmd_buffer->execbuf.flags |= I915_EXEC_RENDER;
2675 cmd_buffer->execbuf.rsvd1 = device->context_id;
2676 cmd_buffer->execbuf.rsvd2 = 0;
2677
2678 pthread_mutex_unlock(&device->mutex);
2679
2680 return VK_SUCCESS;
2681 }
2682
2683 VkResult anv_ResetCommandBuffer(
2684 VkCmdBuffer cmdBuffer)
2685 {
2686 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2687
2688 /* Delete all but the first batch bo */
2689 while (cmd_buffer->last_batch_bo->prev_batch_bo) {
2690 struct anv_batch_bo *prev = cmd_buffer->last_batch_bo->prev_batch_bo;
2691 anv_batch_bo_destroy(cmd_buffer->last_batch_bo, cmd_buffer->device);
2692 cmd_buffer->last_batch_bo = prev;
2693 }
2694 assert(cmd_buffer->last_batch_bo->prev_batch_bo == NULL);
2695
2696 cmd_buffer->batch.relocs.num_relocs = 0;
2697 anv_batch_bo_start(cmd_buffer->last_batch_bo, &cmd_buffer->batch,
2698 GEN8_MI_BATCH_BUFFER_START_length * 4);
2699
2700 /* Delete all but the first batch bo */
2701 while (cmd_buffer->surface_batch_bo->prev_batch_bo) {
2702 struct anv_batch_bo *prev = cmd_buffer->surface_batch_bo->prev_batch_bo;
2703 anv_batch_bo_destroy(cmd_buffer->surface_batch_bo, cmd_buffer->device);
2704 cmd_buffer->surface_batch_bo = prev;
2705 }
2706 assert(cmd_buffer->surface_batch_bo->prev_batch_bo == NULL);
2707
2708 cmd_buffer->surface_next = 1;
2709 cmd_buffer->surface_relocs.num_relocs = 0;
2710
2711 return VK_SUCCESS;
2712 }
2713
2714 // Command buffer building functions
2715
2716 void anv_CmdBindPipeline(
2717 VkCmdBuffer cmdBuffer,
2718 VkPipelineBindPoint pipelineBindPoint,
2719 VkPipeline _pipeline)
2720 {
2721 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2722 struct anv_pipeline *pipeline = (struct anv_pipeline *) _pipeline;
2723
2724 cmd_buffer->pipeline = pipeline;
2725 cmd_buffer->vb_dirty |= pipeline->vb_used;
2726 cmd_buffer->dirty |= ANV_CMD_BUFFER_PIPELINE_DIRTY;
2727 }
2728
2729 void anv_CmdBindDynamicStateObject(
2730 VkCmdBuffer cmdBuffer,
2731 VkStateBindPoint stateBindPoint,
2732 VkDynamicStateObject dynamicState)
2733 {
2734 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2735 struct anv_dynamic_vp_state *vp_state;
2736
2737 switch (stateBindPoint) {
2738 case VK_STATE_BIND_POINT_VIEWPORT:
2739 vp_state = (struct anv_dynamic_vp_state *) dynamicState;
2740 /* We emit state immediately, but set cmd_buffer->vp_state to indicate
2741 * that vp state has been set in this command buffer. */
2742 cmd_buffer->vp_state = vp_state;
2743 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_SCISSOR_STATE_POINTERS,
2744 .ScissorRectPointer = vp_state->scissor.offset);
2745 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_VIEWPORT_STATE_POINTERS_CC,
2746 .CCViewportPointer = vp_state->cc_vp.offset);
2747 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_VIEWPORT_STATE_POINTERS_SF_CLIP,
2748 .SFClipViewportPointer = vp_state->sf_clip_vp.offset);
2749 break;
2750 case VK_STATE_BIND_POINT_RASTER:
2751 cmd_buffer->rs_state = (struct anv_dynamic_rs_state *) dynamicState;
2752 cmd_buffer->dirty |= ANV_CMD_BUFFER_RS_DIRTY;
2753 break;
2754 case VK_STATE_BIND_POINT_COLOR_BLEND:
2755 cmd_buffer->cb_state = (struct anv_dynamic_cb_state *) dynamicState;
2756 cmd_buffer->dirty |= ANV_CMD_BUFFER_CB_DIRTY;
2757 break;
2758 case VK_STATE_BIND_POINT_DEPTH_STENCIL:
2759 cmd_buffer->ds_state = (struct anv_dynamic_ds_state *) dynamicState;
2760 cmd_buffer->dirty |= ANV_CMD_BUFFER_DS_DIRTY;
2761 break;
2762 default:
2763 break;
2764 };
2765 }
2766
2767 static struct anv_state
2768 anv_cmd_buffer_alloc_surface_state(struct anv_cmd_buffer *cmd_buffer,
2769 uint32_t size, uint32_t alignment)
2770 {
2771 struct anv_state state;
2772
2773 state.offset = ALIGN_U32(cmd_buffer->surface_next, alignment);
2774 if (state.offset + size > cmd_buffer->surface_batch_bo->bo.size)
2775 return (struct anv_state) { 0 };
2776
2777 state.map = cmd_buffer->surface_batch_bo->bo.map + state.offset;
2778 state.alloc_size = size;
2779 cmd_buffer->surface_next = state.offset + size;
2780
2781 assert(state.offset + size <= cmd_buffer->surface_batch_bo->bo.size);
2782
2783 return state;
2784 }
2785
2786 static VkResult
2787 anv_cmd_buffer_new_surface_state_bo(struct anv_cmd_buffer *cmd_buffer)
2788 {
2789 struct anv_batch_bo *new_bbo, *old_bbo = cmd_buffer->surface_batch_bo;
2790
2791 /* Finish off the old buffer */
2792 old_bbo->num_relocs =
2793 cmd_buffer->surface_relocs.num_relocs - old_bbo->first_reloc;
2794 old_bbo->length = cmd_buffer->surface_next;
2795
2796 VkResult result = anv_batch_bo_create(cmd_buffer->device, &new_bbo);
2797 if (result != VK_SUCCESS)
2798 return result;
2799
2800 new_bbo->first_reloc = cmd_buffer->surface_relocs.num_relocs;
2801 cmd_buffer->surface_next = 1;
2802
2803 new_bbo->prev_batch_bo = old_bbo;
2804 cmd_buffer->surface_batch_bo = new_bbo;
2805
2806 /* Re-emit state base addresses so we get the new surface state base
2807 * address before we start emitting binding tables etc.
2808 */
2809 anv_batch_emit(&cmd_buffer->batch, GEN8_PIPE_CONTROL,
2810 .CommandStreamerStallEnable = true,
2811 .RenderTargetCacheFlushEnable = true);
2812 anv_cmd_buffer_emit_state_base_address(cmd_buffer);
2813
2814 /* It seems like just chainging the state base addresses isn't enough.
2815 * If we don't do another PIPE_CONTROL afterwards to invalidate the
2816 * texture cache, we still don't always get the right results. I have
2817 * no idea if this is actually what we are supposed to do, but it seems
2818 * to work.
2819 *
2820 * FIXME: We should look into this more. Maybe there is something more
2821 * specific we're supposed to be doing.
2822 */
2823 anv_batch_emit(&cmd_buffer->batch, GEN8_PIPE_CONTROL,
2824 .TextureCacheInvalidationEnable = true);
2825
2826 return VK_SUCCESS;
2827 }
2828
2829 void anv_CmdBindDescriptorSets(
2830 VkCmdBuffer cmdBuffer,
2831 VkPipelineBindPoint pipelineBindPoint,
2832 uint32_t firstSet,
2833 uint32_t setCount,
2834 const VkDescriptorSet* pDescriptorSets,
2835 uint32_t dynamicOffsetCount,
2836 const uint32_t* pDynamicOffsets)
2837 {
2838 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2839 struct anv_pipeline_layout *layout = cmd_buffer->pipeline->layout;
2840 struct anv_descriptor_set *set;
2841 struct anv_descriptor_set_layout *set_layout;
2842
2843 assert(firstSet + setCount < MAX_SETS);
2844
2845 uint32_t dynamic_slot = 0;
2846 for (uint32_t i = 0; i < setCount; i++) {
2847 set = (struct anv_descriptor_set *) pDescriptorSets[i];
2848 set_layout = layout->set[firstSet + i].layout;
2849
2850 cmd_buffer->descriptors[firstSet + i].set = set;
2851
2852 assert(set_layout->num_dynamic_buffers <
2853 ARRAY_SIZE(cmd_buffer->descriptors[0].dynamic_offsets));
2854 memcpy(cmd_buffer->descriptors[firstSet + i].dynamic_offsets,
2855 pDynamicOffsets + dynamic_slot,
2856 set_layout->num_dynamic_buffers * sizeof(*pDynamicOffsets));
2857
2858 cmd_buffer->descriptors_dirty |= set_layout->shader_stages;
2859
2860 dynamic_slot += set_layout->num_dynamic_buffers;
2861 }
2862 }
2863
2864 void anv_CmdBindIndexBuffer(
2865 VkCmdBuffer cmdBuffer,
2866 VkBuffer _buffer,
2867 VkDeviceSize offset,
2868 VkIndexType indexType)
2869 {
2870 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2871 struct anv_buffer *buffer = (struct anv_buffer *) _buffer;
2872
2873 static const uint32_t vk_to_gen_index_type[] = {
2874 [VK_INDEX_TYPE_UINT8] = INDEX_BYTE,
2875 [VK_INDEX_TYPE_UINT16] = INDEX_WORD,
2876 [VK_INDEX_TYPE_UINT32] = INDEX_DWORD,
2877 };
2878
2879 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_INDEX_BUFFER,
2880 .IndexFormat = vk_to_gen_index_type[indexType],
2881 .MemoryObjectControlState = GEN8_MOCS,
2882 .BufferStartingAddress = { buffer->bo, buffer->offset + offset },
2883 .BufferSize = buffer->size - offset);
2884 }
2885
2886 void anv_CmdBindVertexBuffers(
2887 VkCmdBuffer cmdBuffer,
2888 uint32_t startBinding,
2889 uint32_t bindingCount,
2890 const VkBuffer* pBuffers,
2891 const VkDeviceSize* pOffsets)
2892 {
2893 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
2894 struct anv_vertex_binding *vb = cmd_buffer->vertex_bindings;
2895
2896 /* We have to defer setting up vertex buffer since we need the buffer
2897 * stride from the pipeline. */
2898
2899 assert(startBinding + bindingCount < MAX_VBS);
2900 for (uint32_t i = 0; i < bindingCount; i++) {
2901 vb[startBinding + i].buffer = (struct anv_buffer *) pBuffers[i];
2902 vb[startBinding + i].offset = pOffsets[i];
2903 cmd_buffer->vb_dirty |= 1 << (startBinding + i);
2904 }
2905 }
2906
2907 static VkResult
2908 cmd_buffer_emit_binding_table(struct anv_cmd_buffer *cmd_buffer,
2909 unsigned stage)
2910 {
2911 struct anv_pipeline_layout *layout = cmd_buffer->pipeline->layout;
2912 uint32_t color_attachments, bias, size;
2913 struct anv_state bt_state;
2914
2915 if (stage == VK_SHADER_STAGE_FRAGMENT) {
2916 bias = MAX_RTS;
2917 color_attachments = cmd_buffer->framebuffer->color_attachment_count;
2918 } else {
2919 bias = 0;
2920 color_attachments = 0;
2921 }
2922
2923 /* This is a little awkward: layout can be NULL but we still have to
2924 * allocate and set a binding table for the PS stage for render
2925 * targets. */
2926 uint32_t surface_count = layout ? layout->stage[stage].surface_count : 0;
2927
2928 if (color_attachments + surface_count == 0)
2929 return VK_SUCCESS;
2930
2931 size = (bias + surface_count) * sizeof(uint32_t);
2932 bt_state = anv_cmd_buffer_alloc_surface_state(cmd_buffer, size, 32);
2933 uint32_t *bt_map = bt_state.map;
2934
2935 if (bt_state.map == NULL)
2936 return VK_ERROR_OUT_OF_DEVICE_MEMORY;
2937
2938 static const uint32_t binding_table_opcodes[] = {
2939 [VK_SHADER_STAGE_VERTEX] = 38,
2940 [VK_SHADER_STAGE_TESS_CONTROL] = 39,
2941 [VK_SHADER_STAGE_TESS_EVALUATION] = 40,
2942 [VK_SHADER_STAGE_GEOMETRY] = 41,
2943 [VK_SHADER_STAGE_FRAGMENT] = 42,
2944 [VK_SHADER_STAGE_COMPUTE] = 0,
2945 };
2946
2947 anv_batch_emit(&cmd_buffer->batch,
2948 GEN8_3DSTATE_BINDING_TABLE_POINTERS_VS,
2949 ._3DCommandSubOpcode = binding_table_opcodes[stage],
2950 .PointertoVSBindingTable = bt_state.offset);
2951
2952 for (uint32_t ca = 0; ca < color_attachments; ca++) {
2953 const struct anv_surface_view *view =
2954 cmd_buffer->framebuffer->color_attachments[ca];
2955
2956 struct anv_state state =
2957 anv_cmd_buffer_alloc_surface_state(cmd_buffer, 64, 64);
2958
2959 if (state.map == NULL)
2960 return VK_ERROR_OUT_OF_DEVICE_MEMORY;
2961
2962 memcpy(state.map, view->surface_state.map, 64);
2963
2964 /* The address goes in dwords 8 and 9 of the SURFACE_STATE */
2965 *(uint64_t *)(state.map + 8 * 4) =
2966 anv_reloc_list_add(&cmd_buffer->surface_relocs,
2967 cmd_buffer->device,
2968 state.offset + 8 * 4,
2969 view->bo, view->offset);
2970
2971 bt_map[ca] = state.offset;
2972 }
2973
2974 if (layout == NULL)
2975 return VK_SUCCESS;
2976
2977 for (uint32_t set = 0; set < layout->num_sets; set++) {
2978 struct anv_descriptor_set_binding *d = &cmd_buffer->descriptors[set];
2979 struct anv_descriptor_set_layout *set_layout = layout->set[set].layout;
2980 struct anv_descriptor_slot *surface_slots =
2981 set_layout->stage[stage].surface_start;
2982
2983 uint32_t start = bias + layout->set[set].surface_start[stage];
2984
2985 for (uint32_t b = 0; b < set_layout->stage[stage].surface_count; b++) {
2986 struct anv_surface_view *view =
2987 d->set->descriptors[surface_slots[b].index].view;
2988
2989 if (!view)
2990 continue;
2991
2992 struct anv_state state =
2993 anv_cmd_buffer_alloc_surface_state(cmd_buffer, 64, 64);
2994
2995 if (state.map == NULL)
2996 return VK_ERROR_OUT_OF_DEVICE_MEMORY;
2997
2998 uint32_t offset;
2999 if (surface_slots[b].dynamic_slot >= 0) {
3000 uint32_t dynamic_offset =
3001 d->dynamic_offsets[surface_slots[b].dynamic_slot];
3002
3003 offset = view->offset + dynamic_offset;
3004 fill_buffer_surface_state(state.map, view->format, offset,
3005 view->range - dynamic_offset);
3006 } else {
3007 offset = view->offset;
3008 memcpy(state.map, view->surface_state.map, 64);
3009 }
3010
3011 /* The address goes in dwords 8 and 9 of the SURFACE_STATE */
3012 *(uint64_t *)(state.map + 8 * 4) =
3013 anv_reloc_list_add(&cmd_buffer->surface_relocs,
3014 cmd_buffer->device,
3015 state.offset + 8 * 4,
3016 view->bo, offset);
3017
3018 bt_map[start + b] = state.offset;
3019 }
3020 }
3021
3022 return VK_SUCCESS;
3023 }
3024
3025 static VkResult
3026 cmd_buffer_emit_samplers(struct anv_cmd_buffer *cmd_buffer, unsigned stage)
3027 {
3028 struct anv_pipeline_layout *layout = cmd_buffer->pipeline->layout;
3029 struct anv_state state;
3030
3031 if (!layout)
3032 return VK_SUCCESS;
3033
3034 uint32_t sampler_count = layout->stage[stage].sampler_count;
3035
3036 if (sampler_count == 0)
3037 return VK_SUCCESS;
3038
3039 uint32_t size = sampler_count * 16;
3040 state = anv_state_stream_alloc(&cmd_buffer->dynamic_state_stream, size, 32);
3041
3042 if (state.map == NULL)
3043 return VK_ERROR_OUT_OF_DEVICE_MEMORY;
3044
3045 static const uint32_t sampler_state_opcodes[] = {
3046 [VK_SHADER_STAGE_VERTEX] = 43,
3047 [VK_SHADER_STAGE_TESS_CONTROL] = 44, /* HS */
3048 [VK_SHADER_STAGE_TESS_EVALUATION] = 45, /* DS */
3049 [VK_SHADER_STAGE_GEOMETRY] = 46,
3050 [VK_SHADER_STAGE_FRAGMENT] = 47,
3051 [VK_SHADER_STAGE_COMPUTE] = 0,
3052 };
3053
3054 anv_batch_emit(&cmd_buffer->batch,
3055 GEN8_3DSTATE_SAMPLER_STATE_POINTERS_VS,
3056 ._3DCommandSubOpcode = sampler_state_opcodes[stage],
3057 .PointertoVSSamplerState = state.offset);
3058
3059 for (uint32_t set = 0; set < layout->num_sets; set++) {
3060 struct anv_descriptor_set_binding *d = &cmd_buffer->descriptors[set];
3061 struct anv_descriptor_set_layout *set_layout = layout->set[set].layout;
3062 struct anv_descriptor_slot *sampler_slots =
3063 set_layout->stage[stage].sampler_start;
3064
3065 uint32_t start = layout->set[set].sampler_start[stage];
3066
3067 for (uint32_t b = 0; b < set_layout->stage[stage].sampler_count; b++) {
3068 struct anv_sampler *sampler =
3069 d->set->descriptors[sampler_slots[b].index].sampler;
3070
3071 if (!sampler)
3072 continue;
3073
3074 memcpy(state.map + (start + b) * 16,
3075 sampler->state, sizeof(sampler->state));
3076 }
3077 }
3078
3079 return VK_SUCCESS;
3080 }
3081
3082 static void
3083 flush_descriptor_sets(struct anv_cmd_buffer *cmd_buffer)
3084 {
3085 uint32_t s, dirty = cmd_buffer->descriptors_dirty &
3086 cmd_buffer->pipeline->active_stages;
3087
3088 VkResult result;
3089 for_each_bit(s, dirty) {
3090 result = cmd_buffer_emit_binding_table(cmd_buffer, s);
3091 if (result != VK_SUCCESS)
3092 break;
3093
3094 result = cmd_buffer_emit_samplers(cmd_buffer, s);
3095 if (result != VK_SUCCESS)
3096 break;
3097 }
3098
3099 if (result != VK_SUCCESS) {
3100 assert(result == VK_ERROR_OUT_OF_DEVICE_MEMORY);
3101
3102 result = anv_cmd_buffer_new_surface_state_bo(cmd_buffer);
3103 assert(result == VK_SUCCESS);
3104
3105 /* Re-emit all active binding tables */
3106 for_each_bit(s, cmd_buffer->pipeline->active_stages) {
3107 result = cmd_buffer_emit_binding_table(cmd_buffer, s);
3108 result = cmd_buffer_emit_samplers(cmd_buffer, s);
3109 }
3110
3111 /* It had better succeed this time */
3112 assert(result == VK_SUCCESS);
3113 }
3114
3115 cmd_buffer->descriptors_dirty &= ~cmd_buffer->pipeline->active_stages;
3116 }
3117
3118 static struct anv_state
3119 anv_cmd_buffer_emit_dynamic(struct anv_cmd_buffer *cmd_buffer,
3120 uint32_t *a, uint32_t dwords, uint32_t alignment)
3121 {
3122 struct anv_device *device = cmd_buffer->device;
3123 struct anv_state state;
3124
3125 state = anv_state_pool_alloc(&device->dynamic_state_pool, dwords * 4, alignment);
3126 memcpy(state.map, a, dwords * 4);
3127
3128 return state;
3129 }
3130
3131 static struct anv_state
3132 anv_cmd_buffer_merge_dynamic(struct anv_cmd_buffer *cmd_buffer,
3133 uint32_t *a, uint32_t *b, uint32_t dwords, uint32_t alignment)
3134 {
3135 struct anv_device *device = cmd_buffer->device;
3136 struct anv_state state;
3137 uint32_t *p;
3138
3139 state = anv_state_pool_alloc(&device->dynamic_state_pool, dwords * 4, alignment);
3140 p = state.map;
3141 for (uint32_t i = 0; i < dwords; i++)
3142 p[i] = a[i] | b[i];
3143
3144 return state;
3145 }
3146
3147 static void
3148 anv_cmd_buffer_flush_state(struct anv_cmd_buffer *cmd_buffer)
3149 {
3150 struct anv_pipeline *pipeline = cmd_buffer->pipeline;
3151 uint32_t *p;
3152
3153 uint32_t vb_emit = cmd_buffer->vb_dirty & pipeline->vb_used;
3154
3155 if (vb_emit) {
3156 const uint32_t num_buffers = __builtin_popcount(vb_emit);
3157 const uint32_t num_dwords = 1 + num_buffers * 4;
3158
3159 p = anv_batch_emitn(&cmd_buffer->batch, num_dwords,
3160 GEN8_3DSTATE_VERTEX_BUFFERS);
3161 uint32_t vb, i = 0;
3162 for_each_bit(vb, vb_emit) {
3163 struct anv_buffer *buffer = cmd_buffer->vertex_bindings[vb].buffer;
3164 uint32_t offset = cmd_buffer->vertex_bindings[vb].offset;
3165
3166 struct GEN8_VERTEX_BUFFER_STATE state = {
3167 .VertexBufferIndex = vb,
3168 .MemoryObjectControlState = GEN8_MOCS,
3169 .AddressModifyEnable = true,
3170 .BufferPitch = pipeline->binding_stride[vb],
3171 .BufferStartingAddress = { buffer->bo, buffer->offset + offset },
3172 .BufferSize = buffer->size - offset
3173 };
3174
3175 GEN8_VERTEX_BUFFER_STATE_pack(&cmd_buffer->batch, &p[1 + i * 4], &state);
3176 i++;
3177 }
3178 }
3179
3180 if (cmd_buffer->dirty & ANV_CMD_BUFFER_PIPELINE_DIRTY)
3181 anv_batch_emit_batch(&cmd_buffer->batch, &pipeline->batch);
3182
3183 if (cmd_buffer->descriptors_dirty)
3184 flush_descriptor_sets(cmd_buffer);
3185
3186 if (cmd_buffer->dirty & (ANV_CMD_BUFFER_PIPELINE_DIRTY | ANV_CMD_BUFFER_RS_DIRTY)) {
3187 anv_batch_emit_merge(&cmd_buffer->batch,
3188 cmd_buffer->rs_state->state_sf, pipeline->state_sf);
3189 anv_batch_emit_merge(&cmd_buffer->batch,
3190 cmd_buffer->rs_state->state_raster, pipeline->state_raster);
3191 }
3192
3193 if (cmd_buffer->ds_state &&
3194 (cmd_buffer->dirty & (ANV_CMD_BUFFER_PIPELINE_DIRTY | ANV_CMD_BUFFER_DS_DIRTY)))
3195 anv_batch_emit_merge(&cmd_buffer->batch,
3196 cmd_buffer->ds_state->state_wm_depth_stencil,
3197 pipeline->state_wm_depth_stencil);
3198
3199 if (cmd_buffer->dirty & (ANV_CMD_BUFFER_CB_DIRTY | ANV_CMD_BUFFER_DS_DIRTY)) {
3200 struct anv_state state;
3201 if (cmd_buffer->ds_state == NULL)
3202 state = anv_cmd_buffer_emit_dynamic(cmd_buffer,
3203 cmd_buffer->cb_state->state_color_calc,
3204 GEN8_COLOR_CALC_STATE_length, 32);
3205 else if (cmd_buffer->cb_state == NULL)
3206 state = anv_cmd_buffer_emit_dynamic(cmd_buffer,
3207 cmd_buffer->ds_state->state_color_calc,
3208 GEN8_COLOR_CALC_STATE_length, 32);
3209 else
3210 state = anv_cmd_buffer_merge_dynamic(cmd_buffer,
3211 cmd_buffer->ds_state->state_color_calc,
3212 cmd_buffer->cb_state->state_color_calc,
3213 GEN8_COLOR_CALC_STATE_length, 32);
3214
3215 anv_batch_emit(&cmd_buffer->batch,
3216 GEN8_3DSTATE_CC_STATE_POINTERS,
3217 .ColorCalcStatePointer = state.offset,
3218 .ColorCalcStatePointerValid = true);
3219 }
3220
3221 cmd_buffer->vb_dirty &= ~vb_emit;
3222 cmd_buffer->dirty = 0;
3223 }
3224
3225 void anv_CmdDraw(
3226 VkCmdBuffer cmdBuffer,
3227 uint32_t firstVertex,
3228 uint32_t vertexCount,
3229 uint32_t firstInstance,
3230 uint32_t instanceCount)
3231 {
3232 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3233
3234 anv_cmd_buffer_flush_state(cmd_buffer);
3235
3236 anv_batch_emit(&cmd_buffer->batch, GEN8_3DPRIMITIVE,
3237 .VertexAccessType = SEQUENTIAL,
3238 .VertexCountPerInstance = vertexCount,
3239 .StartVertexLocation = firstVertex,
3240 .InstanceCount = instanceCount,
3241 .StartInstanceLocation = firstInstance,
3242 .BaseVertexLocation = 0);
3243 }
3244
3245 void anv_CmdDrawIndexed(
3246 VkCmdBuffer cmdBuffer,
3247 uint32_t firstIndex,
3248 uint32_t indexCount,
3249 int32_t vertexOffset,
3250 uint32_t firstInstance,
3251 uint32_t instanceCount)
3252 {
3253 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3254
3255 anv_cmd_buffer_flush_state(cmd_buffer);
3256
3257 anv_batch_emit(&cmd_buffer->batch, GEN8_3DPRIMITIVE,
3258 .VertexAccessType = RANDOM,
3259 .VertexCountPerInstance = indexCount,
3260 .StartVertexLocation = firstIndex,
3261 .InstanceCount = instanceCount,
3262 .StartInstanceLocation = firstInstance,
3263 .BaseVertexLocation = 0);
3264 }
3265
3266 static void
3267 anv_batch_lrm(struct anv_batch *batch,
3268 uint32_t reg, struct anv_bo *bo, uint32_t offset)
3269 {
3270 anv_batch_emit(batch, GEN8_MI_LOAD_REGISTER_MEM,
3271 .RegisterAddress = reg,
3272 .MemoryAddress = { bo, offset });
3273 }
3274
3275 static void
3276 anv_batch_lri(struct anv_batch *batch, uint32_t reg, uint32_t imm)
3277 {
3278 anv_batch_emit(batch, GEN8_MI_LOAD_REGISTER_IMM,
3279 .RegisterOffset = reg,
3280 .DataDWord = imm);
3281 }
3282
3283 /* Auto-Draw / Indirect Registers */
3284 #define GEN7_3DPRIM_END_OFFSET 0x2420
3285 #define GEN7_3DPRIM_START_VERTEX 0x2430
3286 #define GEN7_3DPRIM_VERTEX_COUNT 0x2434
3287 #define GEN7_3DPRIM_INSTANCE_COUNT 0x2438
3288 #define GEN7_3DPRIM_START_INSTANCE 0x243C
3289 #define GEN7_3DPRIM_BASE_VERTEX 0x2440
3290
3291 void anv_CmdDrawIndirect(
3292 VkCmdBuffer cmdBuffer,
3293 VkBuffer _buffer,
3294 VkDeviceSize offset,
3295 uint32_t count,
3296 uint32_t stride)
3297 {
3298 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3299 struct anv_buffer *buffer = (struct anv_buffer *) _buffer;
3300 struct anv_bo *bo = buffer->bo;
3301 uint32_t bo_offset = buffer->offset + offset;
3302
3303 anv_cmd_buffer_flush_state(cmd_buffer);
3304
3305 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_VERTEX_COUNT, bo, bo_offset);
3306 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_INSTANCE_COUNT, bo, bo_offset + 4);
3307 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_START_VERTEX, bo, bo_offset + 8);
3308 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_START_INSTANCE, bo, bo_offset + 12);
3309 anv_batch_lri(&cmd_buffer->batch, GEN7_3DPRIM_BASE_VERTEX, 0);
3310
3311 anv_batch_emit(&cmd_buffer->batch, GEN8_3DPRIMITIVE,
3312 .IndirectParameterEnable = true,
3313 .VertexAccessType = SEQUENTIAL);
3314 }
3315
3316 void anv_CmdDrawIndexedIndirect(
3317 VkCmdBuffer cmdBuffer,
3318 VkBuffer _buffer,
3319 VkDeviceSize offset,
3320 uint32_t count,
3321 uint32_t stride)
3322 {
3323 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3324 struct anv_buffer *buffer = (struct anv_buffer *) _buffer;
3325 struct anv_bo *bo = buffer->bo;
3326 uint32_t bo_offset = buffer->offset + offset;
3327
3328 anv_cmd_buffer_flush_state(cmd_buffer);
3329
3330 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_VERTEX_COUNT, bo, bo_offset);
3331 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_INSTANCE_COUNT, bo, bo_offset + 4);
3332 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_START_VERTEX, bo, bo_offset + 8);
3333 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_BASE_VERTEX, bo, bo_offset + 12);
3334 anv_batch_lrm(&cmd_buffer->batch, GEN7_3DPRIM_START_INSTANCE, bo, bo_offset + 16);
3335
3336 anv_batch_emit(&cmd_buffer->batch, GEN8_3DPRIMITIVE,
3337 .IndirectParameterEnable = true,
3338 .VertexAccessType = RANDOM);
3339 }
3340
3341 void anv_CmdDispatch(
3342 VkCmdBuffer cmdBuffer,
3343 uint32_t x,
3344 uint32_t y,
3345 uint32_t z)
3346 {
3347 stub();
3348 }
3349
3350 void anv_CmdDispatchIndirect(
3351 VkCmdBuffer cmdBuffer,
3352 VkBuffer buffer,
3353 VkDeviceSize offset)
3354 {
3355 stub();
3356 }
3357
3358 void anv_CmdSetEvent(
3359 VkCmdBuffer cmdBuffer,
3360 VkEvent event,
3361 VkPipeEvent pipeEvent)
3362 {
3363 stub();
3364 }
3365
3366 void anv_CmdResetEvent(
3367 VkCmdBuffer cmdBuffer,
3368 VkEvent event,
3369 VkPipeEvent pipeEvent)
3370 {
3371 stub();
3372 }
3373
3374 void anv_CmdWaitEvents(
3375 VkCmdBuffer cmdBuffer,
3376 VkWaitEvent waitEvent,
3377 uint32_t eventCount,
3378 const VkEvent* pEvents,
3379 uint32_t memBarrierCount,
3380 const void** ppMemBarriers)
3381 {
3382 stub();
3383 }
3384
3385 void anv_CmdPipelineBarrier(
3386 VkCmdBuffer cmdBuffer,
3387 VkWaitEvent waitEvent,
3388 uint32_t pipeEventCount,
3389 const VkPipeEvent* pPipeEvents,
3390 uint32_t memBarrierCount,
3391 const void** ppMemBarriers)
3392 {
3393 stub();
3394 }
3395
3396 static void
3397 anv_batch_emit_ps_depth_count(struct anv_batch *batch,
3398 struct anv_bo *bo, uint32_t offset)
3399 {
3400 anv_batch_emit(batch, GEN8_PIPE_CONTROL,
3401 .DestinationAddressType = DAT_PPGTT,
3402 .PostSyncOperation = WritePSDepthCount,
3403 .Address = { bo, offset }); /* FIXME: This is only lower 32 bits */
3404 }
3405
3406 void anv_CmdBeginQuery(
3407 VkCmdBuffer cmdBuffer,
3408 VkQueryPool queryPool,
3409 uint32_t slot,
3410 VkQueryControlFlags flags)
3411 {
3412 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3413 struct anv_query_pool *pool = (struct anv_query_pool *) queryPool;
3414
3415 switch (pool->type) {
3416 case VK_QUERY_TYPE_OCCLUSION:
3417 anv_batch_emit_ps_depth_count(&cmd_buffer->batch, &pool->bo,
3418 slot * sizeof(struct anv_query_pool_slot));
3419 break;
3420
3421 case VK_QUERY_TYPE_PIPELINE_STATISTICS:
3422 default:
3423 unreachable("");
3424 }
3425 }
3426
3427 void anv_CmdEndQuery(
3428 VkCmdBuffer cmdBuffer,
3429 VkQueryPool queryPool,
3430 uint32_t slot)
3431 {
3432 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3433 struct anv_query_pool *pool = (struct anv_query_pool *) queryPool;
3434
3435 switch (pool->type) {
3436 case VK_QUERY_TYPE_OCCLUSION:
3437 anv_batch_emit_ps_depth_count(&cmd_buffer->batch, &pool->bo,
3438 slot * sizeof(struct anv_query_pool_slot) + 8);
3439 break;
3440
3441 case VK_QUERY_TYPE_PIPELINE_STATISTICS:
3442 default:
3443 unreachable("");
3444 }
3445 }
3446
3447 void anv_CmdResetQueryPool(
3448 VkCmdBuffer cmdBuffer,
3449 VkQueryPool queryPool,
3450 uint32_t startQuery,
3451 uint32_t queryCount)
3452 {
3453 stub();
3454 }
3455
3456 #define TIMESTAMP 0x2358
3457
3458 void anv_CmdWriteTimestamp(
3459 VkCmdBuffer cmdBuffer,
3460 VkTimestampType timestampType,
3461 VkBuffer destBuffer,
3462 VkDeviceSize destOffset)
3463 {
3464 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3465 struct anv_buffer *buffer = (struct anv_buffer *) destBuffer;
3466 struct anv_bo *bo = buffer->bo;
3467
3468 switch (timestampType) {
3469 case VK_TIMESTAMP_TYPE_TOP:
3470 anv_batch_emit(&cmd_buffer->batch, GEN8_MI_STORE_REGISTER_MEM,
3471 .RegisterAddress = TIMESTAMP,
3472 .MemoryAddress = { bo, buffer->offset + destOffset });
3473 anv_batch_emit(&cmd_buffer->batch, GEN8_MI_STORE_REGISTER_MEM,
3474 .RegisterAddress = TIMESTAMP + 4,
3475 .MemoryAddress = { bo, buffer->offset + destOffset + 4 });
3476 break;
3477
3478 case VK_TIMESTAMP_TYPE_BOTTOM:
3479 anv_batch_emit(&cmd_buffer->batch, GEN8_PIPE_CONTROL,
3480 .DestinationAddressType = DAT_PPGTT,
3481 .PostSyncOperation = WriteTimestamp,
3482 .Address = /* FIXME: This is only lower 32 bits */
3483 { bo, buffer->offset + destOffset });
3484 break;
3485
3486 default:
3487 break;
3488 }
3489 }
3490
3491 #define alu_opcode(v) __gen_field((v), 20, 31)
3492 #define alu_operand1(v) __gen_field((v), 10, 19)
3493 #define alu_operand2(v) __gen_field((v), 0, 9)
3494 #define alu(opcode, operand1, operand2) \
3495 alu_opcode(opcode) | alu_operand1(operand1) | alu_operand2(operand2)
3496
3497 #define OPCODE_NOOP 0x000
3498 #define OPCODE_LOAD 0x080
3499 #define OPCODE_LOADINV 0x480
3500 #define OPCODE_LOAD0 0x081
3501 #define OPCODE_LOAD1 0x481
3502 #define OPCODE_ADD 0x100
3503 #define OPCODE_SUB 0x101
3504 #define OPCODE_AND 0x102
3505 #define OPCODE_OR 0x103
3506 #define OPCODE_XOR 0x104
3507 #define OPCODE_STORE 0x180
3508 #define OPCODE_STOREINV 0x580
3509
3510 #define OPERAND_R0 0x00
3511 #define OPERAND_R1 0x01
3512 #define OPERAND_R2 0x02
3513 #define OPERAND_R3 0x03
3514 #define OPERAND_R4 0x04
3515 #define OPERAND_SRCA 0x20
3516 #define OPERAND_SRCB 0x21
3517 #define OPERAND_ACCU 0x31
3518 #define OPERAND_ZF 0x32
3519 #define OPERAND_CF 0x33
3520
3521 #define CS_GPR(n) (0x2600 + (n) * 8)
3522
3523 static void
3524 emit_load_alu_reg_u64(struct anv_batch *batch, uint32_t reg,
3525 struct anv_bo *bo, uint32_t offset)
3526 {
3527 anv_batch_emit(batch, GEN8_MI_LOAD_REGISTER_MEM,
3528 .RegisterAddress = reg,
3529 .MemoryAddress = { bo, offset });
3530 anv_batch_emit(batch, GEN8_MI_LOAD_REGISTER_MEM,
3531 .RegisterAddress = reg + 4,
3532 .MemoryAddress = { bo, offset + 4 });
3533 }
3534
3535 void anv_CmdCopyQueryPoolResults(
3536 VkCmdBuffer cmdBuffer,
3537 VkQueryPool queryPool,
3538 uint32_t startQuery,
3539 uint32_t queryCount,
3540 VkBuffer destBuffer,
3541 VkDeviceSize destOffset,
3542 VkDeviceSize destStride,
3543 VkQueryResultFlags flags)
3544 {
3545 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3546 struct anv_query_pool *pool = (struct anv_query_pool *) queryPool;
3547 struct anv_buffer *buffer = (struct anv_buffer *) destBuffer;
3548 uint32_t slot_offset, dst_offset;
3549
3550 if (flags & VK_QUERY_RESULT_WITH_AVAILABILITY_BIT) {
3551 /* Where is the availabilty info supposed to go? */
3552 anv_finishme("VK_QUERY_RESULT_WITH_AVAILABILITY_BIT");
3553 return;
3554 }
3555
3556 assert(pool->type == VK_QUERY_TYPE_OCCLUSION);
3557
3558 /* FIXME: If we're not waiting, should we just do this on the CPU? */
3559 if (flags & VK_QUERY_RESULT_WAIT_BIT)
3560 anv_batch_emit(&cmd_buffer->batch, GEN8_PIPE_CONTROL,
3561 .CommandStreamerStallEnable = true,
3562 .StallAtPixelScoreboard = true);
3563
3564 dst_offset = buffer->offset + destOffset;
3565 for (uint32_t i = 0; i < queryCount; i++) {
3566
3567 slot_offset = (startQuery + i) * sizeof(struct anv_query_pool_slot);
3568
3569 emit_load_alu_reg_u64(&cmd_buffer->batch, CS_GPR(0), &pool->bo, slot_offset);
3570 emit_load_alu_reg_u64(&cmd_buffer->batch, CS_GPR(1), &pool->bo, slot_offset + 8);
3571
3572 /* FIXME: We need to clamp the result for 32 bit. */
3573
3574 uint32_t *dw = anv_batch_emitn(&cmd_buffer->batch, 5, GEN8_MI_MATH);
3575 dw[1] = alu(OPCODE_LOAD, OPERAND_SRCA, OPERAND_R1);
3576 dw[2] = alu(OPCODE_LOAD, OPERAND_SRCB, OPERAND_R0);
3577 dw[3] = alu(OPCODE_SUB, 0, 0);
3578 dw[4] = alu(OPCODE_STORE, OPERAND_R2, OPERAND_ACCU);
3579
3580 anv_batch_emit(&cmd_buffer->batch, GEN8_MI_STORE_REGISTER_MEM,
3581 .RegisterAddress = CS_GPR(2),
3582 /* FIXME: This is only lower 32 bits */
3583 .MemoryAddress = { buffer->bo, dst_offset });
3584
3585 if (flags & VK_QUERY_RESULT_64_BIT)
3586 anv_batch_emit(&cmd_buffer->batch, GEN8_MI_STORE_REGISTER_MEM,
3587 .RegisterAddress = CS_GPR(2) + 4,
3588 /* FIXME: This is only lower 32 bits */
3589 .MemoryAddress = { buffer->bo, dst_offset + 4 });
3590
3591 dst_offset += destStride;
3592 }
3593 }
3594
3595 void anv_CmdInitAtomicCounters(
3596 VkCmdBuffer cmdBuffer,
3597 VkPipelineBindPoint pipelineBindPoint,
3598 uint32_t startCounter,
3599 uint32_t counterCount,
3600 const uint32_t* pData)
3601 {
3602 stub();
3603 }
3604
3605 void anv_CmdLoadAtomicCounters(
3606 VkCmdBuffer cmdBuffer,
3607 VkPipelineBindPoint pipelineBindPoint,
3608 uint32_t startCounter,
3609 uint32_t counterCount,
3610 VkBuffer srcBuffer,
3611 VkDeviceSize srcOffset)
3612 {
3613 stub();
3614 }
3615
3616 void anv_CmdSaveAtomicCounters(
3617 VkCmdBuffer cmdBuffer,
3618 VkPipelineBindPoint pipelineBindPoint,
3619 uint32_t startCounter,
3620 uint32_t counterCount,
3621 VkBuffer destBuffer,
3622 VkDeviceSize destOffset)
3623 {
3624 stub();
3625 }
3626
3627 static void
3628 anv_framebuffer_destroy(struct anv_device *device,
3629 struct anv_object *object,
3630 VkObjectType obj_type)
3631 {
3632 struct anv_framebuffer *fb = (struct anv_framebuffer *)object;
3633
3634 assert(obj_type == VK_OBJECT_TYPE_FRAMEBUFFER);
3635
3636 anv_DestroyObject((VkDevice) device,
3637 VK_OBJECT_TYPE_DYNAMIC_VP_STATE,
3638 fb->vp_state);
3639
3640 anv_device_free(device, fb);
3641 }
3642
3643 VkResult anv_CreateFramebuffer(
3644 VkDevice _device,
3645 const VkFramebufferCreateInfo* pCreateInfo,
3646 VkFramebuffer* pFramebuffer)
3647 {
3648 struct anv_device *device = (struct anv_device *) _device;
3649 struct anv_framebuffer *framebuffer;
3650
3651 static const struct anv_depth_stencil_view null_view =
3652 { .depth_format = D16_UNORM, .depth_stride = 0, .stencil_stride = 0 };
3653
3654 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO);
3655
3656 framebuffer = anv_device_alloc(device, sizeof(*framebuffer), 8,
3657 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
3658 if (framebuffer == NULL)
3659 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
3660
3661 framebuffer->base.destructor = anv_framebuffer_destroy;
3662
3663 framebuffer->color_attachment_count = pCreateInfo->colorAttachmentCount;
3664 for (uint32_t i = 0; i < pCreateInfo->colorAttachmentCount; i++) {
3665 framebuffer->color_attachments[i] =
3666 (struct anv_surface_view *) pCreateInfo->pColorAttachments[i].view;
3667 }
3668
3669 if (pCreateInfo->pDepthStencilAttachment) {
3670 framebuffer->depth_stencil =
3671 (struct anv_depth_stencil_view *) pCreateInfo->pDepthStencilAttachment->view;
3672 } else {
3673 framebuffer->depth_stencil = &null_view;
3674 }
3675
3676 framebuffer->sample_count = pCreateInfo->sampleCount;
3677 framebuffer->width = pCreateInfo->width;
3678 framebuffer->height = pCreateInfo->height;
3679 framebuffer->layers = pCreateInfo->layers;
3680
3681 vkCreateDynamicViewportState((VkDevice) device,
3682 &(VkDynamicVpStateCreateInfo) {
3683 .sType = VK_STRUCTURE_TYPE_DYNAMIC_VP_STATE_CREATE_INFO,
3684 .viewportAndScissorCount = 1,
3685 .pViewports = (VkViewport[]) {
3686 {
3687 .originX = 0,
3688 .originY = 0,
3689 .width = pCreateInfo->width,
3690 .height = pCreateInfo->height,
3691 .minDepth = 0,
3692 .maxDepth = 1
3693 },
3694 },
3695 .pScissors = (VkRect[]) {
3696 { { 0, 0 },
3697 { pCreateInfo->width, pCreateInfo->height } },
3698 }
3699 },
3700 &framebuffer->vp_state);
3701
3702 *pFramebuffer = (VkFramebuffer) framebuffer;
3703
3704 return VK_SUCCESS;
3705 }
3706
3707 VkResult anv_CreateRenderPass(
3708 VkDevice _device,
3709 const VkRenderPassCreateInfo* pCreateInfo,
3710 VkRenderPass* pRenderPass)
3711 {
3712 struct anv_device *device = (struct anv_device *) _device;
3713 struct anv_render_pass *pass;
3714 size_t size;
3715
3716 assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO);
3717
3718 size = sizeof(*pass) +
3719 pCreateInfo->layers * sizeof(struct anv_render_pass_layer);
3720 pass = anv_device_alloc(device, size, 8,
3721 VK_SYSTEM_ALLOC_TYPE_API_OBJECT);
3722 if (pass == NULL)
3723 return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
3724
3725 pass->render_area = pCreateInfo->renderArea;
3726
3727 pass->num_layers = pCreateInfo->layers;
3728
3729 pass->num_clear_layers = 0;
3730 for (uint32_t i = 0; i < pCreateInfo->layers; i++) {
3731 pass->layers[i].color_load_op = pCreateInfo->pColorLoadOps[i];
3732 pass->layers[i].clear_color = pCreateInfo->pColorLoadClearValues[i];
3733 if (pass->layers[i].color_load_op == VK_ATTACHMENT_LOAD_OP_CLEAR)
3734 pass->num_clear_layers++;
3735 }
3736
3737 *pRenderPass = (VkRenderPass) pass;
3738
3739 return VK_SUCCESS;
3740 }
3741
3742 static void
3743 anv_cmd_buffer_emit_depth_stencil(struct anv_cmd_buffer *cmd_buffer,
3744 struct anv_render_pass *pass)
3745 {
3746 const struct anv_depth_stencil_view *view =
3747 cmd_buffer->framebuffer->depth_stencil;
3748
3749 /* FIXME: Implement the PMA stall W/A */
3750
3751 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_DEPTH_BUFFER,
3752 .SurfaceType = SURFTYPE_2D,
3753 .DepthWriteEnable = view->depth_stride > 0,
3754 .StencilWriteEnable = view->stencil_stride > 0,
3755 .HierarchicalDepthBufferEnable = false,
3756 .SurfaceFormat = view->depth_format,
3757 .SurfacePitch = view->depth_stride > 0 ? view->depth_stride - 1 : 0,
3758 .SurfaceBaseAddress = { view->bo, view->depth_offset },
3759 .Height = pass->render_area.extent.height - 1,
3760 .Width = pass->render_area.extent.width - 1,
3761 .LOD = 0,
3762 .Depth = 1 - 1,
3763 .MinimumArrayElement = 0,
3764 .DepthBufferObjectControlState = GEN8_MOCS,
3765 .RenderTargetViewExtent = 1 - 1,
3766 .SurfaceQPitch = 0);
3767
3768 /* Disable hierarchial depth buffers. */
3769 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_HIER_DEPTH_BUFFER);
3770
3771 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_STENCIL_BUFFER,
3772 .StencilBufferEnable = view->stencil_stride > 0,
3773 .StencilBufferObjectControlState = GEN8_MOCS,
3774 .SurfacePitch = view->stencil_stride > 0 ? view->stencil_stride - 1 : 0,
3775 .SurfaceBaseAddress = { view->bo, view->stencil_offset },
3776 .SurfaceQPitch = 0);
3777
3778 /* Clear the clear params. */
3779 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_CLEAR_PARAMS);
3780 }
3781
3782 void anv_CmdBeginRenderPass(
3783 VkCmdBuffer cmdBuffer,
3784 const VkRenderPassBegin* pRenderPassBegin)
3785 {
3786 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *) cmdBuffer;
3787 struct anv_render_pass *pass = (struct anv_render_pass *) pRenderPassBegin->renderPass;
3788 struct anv_framebuffer *framebuffer =
3789 (struct anv_framebuffer *) pRenderPassBegin->framebuffer;
3790
3791 cmd_buffer->framebuffer = framebuffer;
3792
3793 cmd_buffer->descriptors_dirty |= VK_SHADER_STAGE_FRAGMENT_BIT;
3794
3795 anv_batch_emit(&cmd_buffer->batch, GEN8_3DSTATE_DRAWING_RECTANGLE,
3796 .ClippedDrawingRectangleYMin = pass->render_area.offset.y,
3797 .ClippedDrawingRectangleXMin = pass->render_area.offset.x,
3798 .ClippedDrawingRectangleYMax =
3799 pass->render_area.offset.y + pass->render_area.extent.height - 1,
3800 .ClippedDrawingRectangleXMax =
3801 pass->render_area.offset.x + pass->render_area.extent.width - 1,
3802 .DrawingRectangleOriginY = 0,
3803 .DrawingRectangleOriginX = 0);
3804
3805 anv_cmd_buffer_emit_depth_stencil(cmd_buffer, pass);
3806
3807 anv_cmd_buffer_clear(cmd_buffer, pass);
3808 }
3809
3810 void anv_CmdEndRenderPass(
3811 VkCmdBuffer cmdBuffer,
3812 VkRenderPass renderPass)
3813 {
3814 /* Emit a flushing pipe control at the end of a pass. This is kind of a
3815 * hack but it ensures that render targets always actually get written.
3816 * Eventually, we should do flushing based on image format transitions
3817 * or something of that nature.
3818 */
3819 struct anv_cmd_buffer *cmd_buffer = (struct anv_cmd_buffer *)cmdBuffer;
3820 anv_batch_emit(&cmd_buffer->batch, GEN8_PIPE_CONTROL,
3821 .PostSyncOperation = NoWrite,
3822 .RenderTargetCacheFlushEnable = true,
3823 .InstructionCacheInvalidateEnable = true,
3824 .DepthCacheFlushEnable = true,
3825 .VFCacheInvalidationEnable = true,
3826 .TextureCacheInvalidationEnable = true,
3827 .CommandStreamerStallEnable = true);
3828 }
3829
3830 void vkCmdDbgMarkerBegin(
3831 VkCmdBuffer cmdBuffer,
3832 const char* pMarker)
3833 __attribute__ ((visibility ("default")));
3834
3835 void vkCmdDbgMarkerEnd(
3836 VkCmdBuffer cmdBuffer)
3837 __attribute__ ((visibility ("default")));
3838
3839 VkResult vkDbgSetObjectTag(
3840 VkDevice device,
3841 VkObject object,
3842 size_t tagSize,
3843 const void* pTag)
3844 __attribute__ ((visibility ("default")));
3845
3846
3847 void vkCmdDbgMarkerBegin(
3848 VkCmdBuffer cmdBuffer,
3849 const char* pMarker)
3850 {
3851 }
3852
3853 void vkCmdDbgMarkerEnd(
3854 VkCmdBuffer cmdBuffer)
3855 {
3856 }
3857
3858 VkResult vkDbgSetObjectTag(
3859 VkDevice device,
3860 VkObject object,
3861 size_t tagSize,
3862 const void* pTag)
3863 {
3864 return VK_SUCCESS;
3865 }