Monado OpenXR Runtime
Loading...
Searching...
No Matches
vk_helpers.h
Go to the documentation of this file.
1// Copyright 2019-2024, Collabora, Ltd.
2// Copyright 2024-2026, NVIDIA CORPORATION.
3// SPDX-License-Identifier: BSL-1.0
4/*!
5 * @file
6 * @brief Common Vulkan code header.
7 *
8 * Note that some functionality in this file is generated by the script
9 * `src/xrt/auxiliary/vk/vk_generate_inc_files.py`. The generated parts are
10 * included via .h.inc files.
11 *
12 * @author Jakob Bornecrantz <jakob@collabora.com>
13 * @author Lubosz Sarnecki <lubosz.sarnecki@collabora.com>
14 * @author Moshi Turner <moshiturner@protonmail.com>
15 * @author Korcan Hussein <korcan.hussein@collabora.com>
16 * @ingroup aux_vk
17 */
18
19#pragma once
20
21#include "xrt/xrt_compiler.h"
22#include "xrt/xrt_compositor.h"
24#include "xrt/xrt_handles.h"
25
26#include "util/u_logging.h"
28
29#include "vk/vk_print.h"
30
31#include "os/os_threading.h"
32
33
34#ifdef __cplusplus
35extern "C" {
36#endif
37
38
39#define VK_BUNDLE_MAX_QUEUES 3
40
41/*
42 *
43 * Structs
44 *
45 */
46
48{
49 //! The queue family index
50 uint32_t family_index;
51 //! The queue (instance) index
52 uint32_t index;
53};
54
55#define VK_NULL_QUEUE_PAIR \
56 XRT_C11_COMPOUND(struct vk_queue_pair) \
57 { \
58 .family_index = VK_QUEUE_FAMILY_IGNORED, .index = (uint32_t)-1, \
59 }
60
62{
63 //! The Vulkan queue handle
64 VkQueue queue;
65 //! The queue family index
66 uint32_t family_index;
67 //! The queue (instance) index
68 uint32_t index;
69 //! The queue mutex - @see vk_queue_lock, vk_queue_unlock
71};
72
73/*!
74 * A bundle of Vulkan functions and objects, used by both @ref comp and @ref
75 * comp_client. Note that they both have different instances of the object, and
76 * thus different VkInstance, etc.
77 *
78 * @ingroup aux_vk
79 */
81{
82 enum u_logging_level log_level;
83
84 VkInstance instance;
85 uint32_t version;
86 VkPhysicalDevice physical_device;
87 int physical_device_index;
88 VkDevice device;
89
90 /*!
91 * @brief queues - a free list of **unique** queues
92 *
93 * One per uniquely identifiable vk queue (family x instance index),
94 * duplicate entries must not be stored.
95 *
96 * Should not be used directly, @see main_queue, graphics_queue, encode_queue
97 */
98 struct vk_bundle_queue queues[VK_BUNDLE_MAX_QUEUES];
99
100 /*!
101 * @brief Main queue for general work.
102 *
103 * In normal mode, this is a graphics queue.
104 * In compute-only mode, this is a compute queue.
105 *
106 * May alias with graphics_queue.
107 */
109
110 /*!
111 * @brief Graphics queue.
112 *
113 * Always a graphics queue, even in compute-only mode.
114 * In normal mode, aliases with main_queue.
115 * In compute-only mode, this is a separate graphics queue.
116 */
118
119#if defined(VK_KHR_video_encode_queue)
120 /*!
121 * @brief Video encode queue.
122 *
123 * May be NULL if video encoding is not supported.
124 * May alias with other queues.
125 */
126 struct vk_bundle_queue *encode_queue;
127#endif
128
129 struct
130 {
131#if defined(XRT_GRAPHICS_BUFFER_HANDLE_IS_WIN32_HANDLE)
132 bool color_image_import_opaque_win32;
133 bool color_image_export_opaque_win32;
134 bool depth_image_import_opaque_win32;
135 bool depth_image_export_opaque_win32;
136
137 bool color_image_import_d3d11;
138 bool color_image_export_d3d11;
139 bool depth_image_import_d3d11;
140 bool depth_image_export_d3d11;
141
142#elif defined(XRT_GRAPHICS_BUFFER_HANDLE_IS_FD)
143 bool color_image_import_opaque_fd;
144 bool color_image_export_opaque_fd;
145 bool depth_image_import_opaque_fd;
146 bool depth_image_export_opaque_fd;
147
148#elif defined(XRT_GRAPHICS_BUFFER_HANDLE_IS_AHARDWAREBUFFER)
149 bool color_image_import_opaque_fd;
150 bool color_image_export_opaque_fd;
151 bool depth_image_import_opaque_fd;
152 bool depth_image_export_opaque_fd;
153
154 bool color_image_import_ahardwarebuffer;
155 bool color_image_export_ahardwarebuffer;
156 bool depth_image_import_ahardwarebuffer;
157 bool depth_image_export_ahardwarebuffer;
158#endif
159
160#if defined(XRT_GRAPHICS_SYNC_HANDLE_IS_FD)
161 bool fence_sync_fd;
162 bool fence_opaque_fd;
163
164 bool binary_semaphore_sync_fd;
165 bool binary_semaphore_opaque_fd;
166
167 bool timeline_semaphore_sync_fd;
168 bool timeline_semaphore_opaque_fd;
169#elif defined(XRT_GRAPHICS_SYNC_HANDLE_IS_WIN32_HANDLE)
170 bool fence_win32_handle;
171
172 bool binary_semaphore_d3d12_fence;
173 bool binary_semaphore_win32_handle;
174
175 bool timeline_semaphore_d3d12_fence;
176 bool timeline_semaphore_win32_handle;
177#else
178#error "Need port for fence sync handles checkers"
179#endif
180 } external;
181
182 // Include the generated fields for has_KHR_extension.
183#include "vk_helpers_h_ext.h.inc"
184
185 struct
186 {
187 //! Are timestamps available for compute and graphics queues?
189
190 //! Nanoseconds per gpu tick.
192
193 //! Valid bits in the queue selected.
195
196 //! Were timeline semaphore requested, available, and enabled?
198
199 //! Was synchronization2 requested, available, and enabled?
201
202 //! Was KHR_present_id requested, available, and enabled?
204
205 //! Was KHR_present_id2 requested, available, and enabled?
207
208 //! Was KHR_present_wait requested, available, and enabled?
210
211 //! Was KHR_video_maintenance1 requested, available, and enabled?
213 } features;
214
215 struct
216 {
217 //! Maximum number of sampler objects, as created by vkCreateSampler, which can simultaneously exist on
219
220 //! Maximum number of descriptor sets that can be simultaneously used by a pipeline.
222
223 //! Maximum number of samplers that can be included in a pipeline layout.
225
226 //! Maximum number of sampled images that can be included in a pipeline layout.
228
229 //! Maximum number of samplers that can be accessible to a single shader stage in a pipeline layout.
231
232 //! Per stage limit on sampled images (includes combined).
234
235 //! Per stage limit on storage images.
237 } limits;
238
239 //! Is the GPU a tegra device.
241
242
243 VkDebugReportCallbackEXT debug_report_cb;
244
245 VkPhysicalDeviceMemoryProperties device_memory_props;
246
247 // Loader functions
248 PFN_vkGetInstanceProcAddr vkGetInstanceProcAddr;
249 PFN_vkCreateInstance vkCreateInstance;
250 PFN_vkEnumerateInstanceExtensionProperties vkEnumerateInstanceExtensionProperties;
251
252 // Include the generated function pointers fields.
253#include "vk_helpers_h_funcs.h.inc"
254};
255
257{
258 VkBuffer handle;
259 VkDeviceMemory memory;
260 uint32_t size;
261 void *data;
262};
263
264
265/*
266 *
267 * Helper defines.
268 *
269 */
270
271/*!
272 * This define will print if `RET` is not `VK_SUCCESS`, printing out that the
273 * @p FUNC_STR string has failed. The implicit argument @p vk will be used for
274 * the @ref vk_print_result call.
275 *
276 * Use this when you need to do special things after an error,
277 * but still want to pirnt the pretty message about the failure.
278 *
279 * @param RET The @p VkResult to check.
280 * @param FUNC_STR String literal with the function name, used for logging.
281 *
282 * @ingroup aux_vk
283 *
284 * @see VK_CHK_AND_RET
285 * @see VK_CHK_WITH_RET
286 * @see VK_CHK_WITH_GOTO
287 */
288#define VK_CHK_ONLY_PRINT(RET, FUNC_STR) \
289 do { \
290 VkResult _ret = RET; \
291 if (_ret != VK_SUCCESS) { \
292 vk_print_result(vk, __FILE__, __LINE__, __func__, _ret, FUNC_STR); \
293 } \
294 } while (false)
295
296/*!
297 * This define will error if `RET` is not `VK_SUCCESS`, printing out that the
298 * @p FUNC_STR string has failed, then returns @p RET. The implicit argument
299 * @p vk will be used for the @ref vk_print_result call.
300 *
301 * Use this macro when your function returns a `VkResult`.
302 *
303 * @param RET The @p VkResult to check.
304 * @param FUNC_STR String literal with the function name, used for logging.
305 *
306 * @ingroup aux_vk
307 *
308 * @see VK_CHK_ONLY_PRINT
309 * @see VK_CHK_WITH_RET
310 * @see VK_CHK_WITH_GOTO
311 */
312#define VK_CHK_AND_RET(RET, FUNC_STR) \
313 do { \
314 VkResult _ret = RET; \
315 if (_ret != VK_SUCCESS) { \
316 vk_print_result(vk, __FILE__, __LINE__, __func__, _ret, FUNC_STR); \
317 return _ret; \
318 } \
319 } while (false)
320
321/*!
322 * This define will error if @p RET is not @p VK_SUCCESS, printing out that the
323 * @p FUNC_STR string has failed, then returns @p TO_RET. The implicit argument
324 * @p vk will be used for the @ref vk_print_result call.
325 *
326 * Use this macro when your function doesn't return a `VkResult`.
327 *
328 * @param RET The @p VkResult to check.
329 * @param FUNC_STR String literal with the function name, used for logging.
330 * @param TO_RET Value to return, upon error
331 *
332 * @ingroup aux_vk
333 *
334 * @see VK_CHK_ONLY_PRINT
335 * @see VK_CHK_AND_RET
336 * @see VK_CHK_WITH_GOTO
337 */
338#define VK_CHK_WITH_RET(RET, FUNC_STR, TO_RET) \
339 do { \
340 VkResult _ret = RET; \
341 if (_ret != VK_SUCCESS) { \
342 vk_print_result(vk, __FILE__, __LINE__, __func__, _ret, FUNC_STR); \
343 return TO_RET; \
344 } \
345 } while (false)
346
347/*!
348 * This define will error if @p RET is not @p VK_SUCCESS, printing out that the
349 * @p FUNC_STR string has failed, then goto @p GOTO. The implicit argument @p vk
350 * will be used for the @ref vk_print_result call.
351 *
352 * Use this macro when your function needs to `goto` some cleanup code and
353 * return from there.
354 *
355 * @param RET The @p VkResult to check.
356 * @param FUNC_STR String literal with the function name, used for logging.
357 * @param GOTO Label to jump to, upon error
358 *
359 * @ingroup aux_vk
360 *
361 * @see VK_CHK_ONLY_PRINT
362 * @see VK_CHK_AND_RET
363 * @see VK_CHK_WITH_RET
364 */
365#define VK_CHK_WITH_GOTO(RET, FUNC_STR, GOTO) \
366 do { \
367 VkResult _ret = RET; \
368 if (_ret != VK_SUCCESS) { \
369 vk_print_result(vk, __FILE__, __LINE__, __func__, _ret, FUNC_STR); \
370 goto GOTO; \
371 } \
372 } while (false)
373
374//! For xrt_result_t, see @ref VK_CHK_AND_RET.
375#define XVK_CHK_AND_RET(...) U_LOG_CHK_AND_RET(vk->log_level, __VA_ARGS__)
376//! For xrt_result_t, see @ref VK_CHK_WITH_GOTO.
377#define XVK_CHK_WITH_GOTO(...) U_LOG_CHK_WITH_GOTO(vk->log_level, __VA_ARGS__)
378//! For xrt_result_t, see @ref VK_CHK_WITH_RET.
379#define XVK_CHK_WITH_RET(...) U_LOG_CHK_WITH_RET(vk->log_level, __VA_ARGS__)
380//! For xrt_result_t, see @ref VK_CHK_ONLY_PRINT.
381#define XVK_CHK_ONLY_PRINT(...) U_LOG_CHK_ONLY_PRINT(vk->log_level, __VA_ARGS__)
382//! For xrt_result_t, see @ref VK_CHK_ALWAYS_RET.
383#define XVK_CHK_ALWAYS_RET(...) U_LOG_CHK_ALWAYS_RET(vk->log_level, __VA_ARGS__)
384
385static inline void
386vk_append_to_pnext_chain(VkBaseInStructure *head, VkBaseInStructure *new_struct)
387{
388 assert(new_struct->pNext == NULL);
389 // Insert ourselves between head and its previous pNext
390 new_struct->pNext = head->pNext;
391 head->pNext = new_struct;
392}
393
394
395/*
396 *
397 * Flag bits string functions.
398 *
399 */
400
401/*!
402 * Returns the format feature flag if one valid bit is set,
403 * if multiple bits are set, will return 'MULTIPLE BIT SET'.
404 */
405XRT_CHECK_RESULT const char *
406vk_format_feature_flag_string(VkFormatFeatureFlagBits bits, bool null_on_unknown);
407
408/*!
409 * Returns the image usage flag if one valid bit is set,
410 * if multiple bits are set, will return 'MULTIPLE BIT SET'.
411 */
412XRT_CHECK_RESULT const char *
413vk_image_usage_flag_string(VkImageUsageFlagBits bits, bool null_on_unknown);
414
415/*!
416 * Returns the composite alpha flag if one valid bit is set,
417 * if multiple bits are set, will return 'MULTIPLE BIT SET'.
418 */
419XRT_CHECK_RESULT const char *
420vk_composite_alpha_flag_string(VkCompositeAlphaFlagBitsKHR bits, bool null_on_unknown);
421
422/*!
423 * Returns the surface transform flag if one valid bit is set,
424 * if multiple bits are set, will return 'MULTIPLE BIT SET'.
425 */
426XRT_CHECK_RESULT const char *
427vk_surface_transform_flag_string(VkSurfaceTransformFlagBitsKHR bits, bool null_on_unknown);
428
429#ifdef VK_KHR_display
430/*!
431 * Returns the display plane alpha flag if one valid bit is set,
432 * if multiple bits are set, will return 'MULTIPLE BIT SET'.
433 */
434XRT_CHECK_RESULT const char *
435vk_display_plane_alpha_flag_string(VkDisplayPlaneAlphaFlagBitsKHR bits, bool null_on_unknown);
436#endif
437
438
439/*
440 *
441 * Function and helpers.
442 *
443 */
444
445#define VK_TRACE(d, ...) U_LOG_IFL_T(d->log_level, __VA_ARGS__)
446#define VK_DEBUG(d, ...) U_LOG_IFL_D(d->log_level, __VA_ARGS__)
447#define VK_INFO(d, ...) U_LOG_IFL_I(d->log_level, __VA_ARGS__)
448#define VK_WARN(d, ...) U_LOG_IFL_W(d->log_level, __VA_ARGS__)
449#define VK_ERROR(d, ...) U_LOG_IFL_E(d->log_level, __VA_ARGS__)
450
451
452/*
453 *
454 * Debug helper functions, in the vk_debug.c file.
455 *
456 */
457
458#if defined(VK_EXT_debug_utils) || defined(XRT_DOXYGEN)
459
460/*!
461 * Uses VK_EXT_debug_utils to set a name for an object, for easier debugging.
462 *
463 * @ingroup aux_vk
464 */
465void
466vk_name_object(struct vk_bundle *vk, VkObjectType type, uint64_t object, const char *name);
467
468/*!
469 * Small helper for @ref vk_name_object that makes use of pre-process to avoid
470 * writing out long type names.
471 *
472 * @ingroup aux_vk
473 */
474#define VK_NAME_OBJ(VK, TYPE, SUFFIX, OBJ, NAME) \
475 do { \
476 if ((VK)->has_EXT_debug_utils) { \
477 XRT_MAYBE_UNUSED TYPE _thing = (TYPE)(OBJ); \
478 vk_name_object(VK, VK_OBJECT_TYPE_##SUFFIX, (uint64_t)OBJ, NAME); \
479 } \
480 } while (false)
481
482
483#else
484
485#define VK_NAME_OBJ(VK, TYPE, SUFFIX, OBJ, NAME) VK_NAME_OBJ_DISABLED(VK, TYPE, OBJ)
486
487#endif
488
489/*!
490 * Some combinations of Vulkan implementation and types are broken, we still
491 * want type safety so we have this define. Examples of broken combinations:
492 *
493 * 1. Both Mesa and the Vulkan loader didn't support setting names on the
494 * VkInstance, loader got support in 1.3.261 and Mesa hasn't as of writing.
495 * 2. For Mesa drivers we can not name VkSurfaceKHR objects on some systems as
496 * it causes memory corruption, asserts, crashes or functions failing. This
497 * is as of writing broken on the 23.2.1 release, fixed in main and scheduled
498 * for the 23.2.2 release.
499 * 3. Mesa RADV leaks the name strings for VkDescriptorSet objects for pools
500 * that we use the reset function.
501 *
502 * @ingroup aux_vk
503 */
504#define VK_NAME_OBJ_DISABLED(VK, TYPE, OBJ) \
505 do { \
506 XRT_MAYBE_UNUSED TYPE _thing = (TYPE)(OBJ); \
507 } while (false)
508
509
510// clang-format off
511// VK_DEFINE_HANDLE types are always pointers
512#define VK_NAME_INSTANCE(VK, OBJ, NAME) VK_NAME_OBJ_DISABLED(VK, VkInstance, (uintptr_t)OBJ)
513#define VK_NAME_PHYSICAL_DEVICE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkPhysicalDevice, PHYSICAL_DEVICE, (uintptr_t)OBJ, NAME)
514#define VK_NAME_DEVICE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkDevice, DEVICE, (uintptr_t)OBJ, NAME)
515#define VK_NAME_QUEUE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkQueue, QUEUE, (uintptr_t)OBJ, NAME)
516#define VK_NAME_COMMAND_BUFFER(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkCommandBuffer, COMMAND_BUFFER, (uintptr_t)OBJ, NAME)
517// VK_DEFINE_NON_DISPATCHABLE_HANDLE types are pointers in 64-bits and uint64_t in 32-bits
518#define VK_NAME_SEMAPHORE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkSemaphore, SEMAPHORE, OBJ, NAME)
519#define VK_NAME_FENCE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkFence, FENCE, OBJ, NAME)
520#define VK_NAME_DEVICE_MEMORY(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkDeviceMemory, DEVICE_MEMORY, OBJ, NAME)
521#define VK_NAME_BUFFER(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkBuffer, BUFFER, OBJ, NAME)
522#define VK_NAME_IMAGE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkImage, IMAGE, OBJ, NAME)
523#define VK_NAME_EVENT(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkEvent, EVENT, OBJ, NAME)
524#define VK_NAME_QUERY_POOL(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkQueryPool, QUERY_POOL, OBJ, NAME)
525#define VK_NAME_BUFFER_VIEW(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkBufferView, BUFFER_VIEW, OBJ, NAME)
526#define VK_NAME_IMAGE_VIEW(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkImageView, IMAGE_VIEW, OBJ, NAME)
527#define VK_NAME_SHADER_MODULE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkShaderModule, SHADER_MODULE, OBJ, NAME)
528#define VK_NAME_PIPELINE_CACHE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkPipelineCache, PIPELINE_CACHE, OBJ, NAME)
529#define VK_NAME_PIPELINE_LAYOUT(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkPipelineLayout, PIPELINE_LAYOUT, OBJ, NAME)
530#define VK_NAME_RENDER_PASS(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkRenderPass, RENDER_PASS, OBJ, NAME)
531#define VK_NAME_PIPELINE(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkPipeline, PIPELINE, OBJ, NAME)
532#define VK_NAME_DESCRIPTOR_SET_LAYOUT(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkDescriptorSetLayout, DESCRIPTOR_SET_LAYOUT, OBJ, NAME)
533#define VK_NAME_SAMPLER(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkSampler, SAMPLER, OBJ, NAME)
534#define VK_NAME_DESCRIPTOR_POOL(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkDescriptorPool, DESCRIPTOR_POOL, OBJ, NAME)
535#define VK_NAME_DESCRIPTOR_SET(VK, OBJ, NAME) VK_NAME_OBJ_DISABLED(VK, VkDescriptorSet, OBJ)
536#define VK_NAME_FRAMEBUFFER(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkFramebuffer, FRAMEBUFFER, OBJ, NAME)
537#define VK_NAME_COMMAND_POOL(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkCommandPool, COMMAND_POOL, OBJ, NAME)
538
539#define VK_NAME_SURFACE(VK, OBJ, NAME) VK_NAME_OBJ_DISABLED(VK, VkSurfaceKHR, OBJ)
540#define VK_NAME_SWAPCHAIN(VK, OBJ, NAME) VK_NAME_OBJ(VK, VkSwapchainKHR, SWAPCHAIN_KHR, OBJ, NAME)
541// clang-format on
542
543
544/*
545 *
546 * Enumeration helpers, in the vk_enumerate.c file.
547 *
548 */
549
550/*!
551 * Return the @p VkExtensionProperties of the given @p layer_name, NULL means
552 * the "base" driver instance.
553 *
554 * @ingroup aux_vk
555 */
556VkResult
558 const char *layer_name,
559 uint32_t *out_prop_count,
560 VkExtensionProperties **out_props);
561
562/*!
563 * Enumerate the physical devices of the @p VkInstance that has been opened on
564 * the given @ref vk_bundle.
565 *
566 * @ingroup aux_vk
567 */
568VkResult
570 uint32_t *out_physical_device_count,
571 VkPhysicalDevice **out_physical_devices);
572
573/*!
574 * Enumerate the extension properties of the given @p VkPhysicalDevice for the
575 * named @p layer_name, NULL means the "base" driver physical device.
576 *
577 * @ingroup aux_vk
578 */
579VkResult
581 VkPhysicalDevice physical_device,
582 const char *layer_name,
583 uint32_t *out_prop_count,
584 VkExtensionProperties **out_props);
585
586/*!
587 * Get the queue family properties of the given @p VkPhysicalDevice, note this
588 * function does not return a result, it will assert if it can not allocate the
589 * array of properties. If there are no queue family properties, the function
590 * will return a count of 0 and set the output pointer to NULL.
591 *
592 * @ingroup aux_vk
593 */
594void
596 VkPhysicalDevice physical_device,
597 uint32_t *out_prop_count,
598 VkQueueFamilyProperties **out_props);
599
600#if defined(VK_KHR_surface) || defined(XRT_DOXYGEN)
601/*!
602 * Enumerate the surface formats of the given @p VkSurfaceKHR,
603 * returns a list of @p VkSurfaceFormatKHR, not @p VkFormat.
604 *
605 * @ingroup aux_vk
606 */
607VkResult
609 VkSurfaceKHR surface,
610 uint32_t *out_format_count,
611 VkSurfaceFormatKHR **out_formats);
612
613/*!
614 * Enumerate the present modes of the given @p VkSurfaceKHR.
615 *
616 * @ingroup aux_vk
617 */
618VkResult
620 VkSurfaceKHR surface,
621 uint32_t *out_present_mode_count,
622 VkPresentModeKHR **out_present_modes);
623#endif
624
625#if defined(VK_KHR_swapchain) || defined(XRT_DOXYGEN)
626/*!
627 * Enumerate the images of the given @p VkSwapchainKHR.
628 *
629 * @ingroup aux_vk
630 */
631VkResult
633 VkSwapchainKHR swapchain,
634 uint32_t *out_image_count,
635 VkImage **out_images);
636#endif
637
638#if defined(VK_USE_PLATFORM_DISPLAY_KHR) || defined(XRT_DOXYGEN)
639/*!
640 * Enumerate the display properties of the given @p VkPhysicalDevice.
641 *
642 * @ingroup aux_vk
643 */
644VkResult
646 VkPhysicalDevice physical_device,
647 uint32_t *out_prop_count,
648 VkDisplayPropertiesKHR **out_props);
649
650/*!
651 * Enumerate the display plane properties of the given @p VkPhysicalDevice.
652 *
653 * @ingroup aux_vk
654 */
655VkResult
657 VkPhysicalDevice physical_device,
658 uint32_t *out_prop_count,
659 VkDisplayPlanePropertiesKHR **out_props);
660
661/*!
662 * Enumerate the mode properties of the given @p VkDisplayKHR, which belongs
663 * to the given @p VkPhysicalDevice.
664 *
665 * @ingroup aux_vk
666 */
667VkResult
669 VkPhysicalDevice physical_device,
670 VkDisplayKHR display,
671 uint32_t *out_prop_count,
672 VkDisplayModePropertiesKHR **out_props);
673#endif
674
675
676/*
677 *
678 * Struct init functions, in the vk_function_loaders.c file.
679 *
680 */
681
682/*!
683 * Can be done on a completely bare bundle.
684 *
685 * @ingroup aux_vk
686 */
687VkResult
688vk_get_loader_functions(struct vk_bundle *vk, PFN_vkGetInstanceProcAddr g);
689
690/*!
691 * Requires a instance to have been created and set on the bundle.
692 *
693 * @ingroup aux_vk
694 */
695VkResult
697
698/*!
699 * Requires a device to have been created and set on the bundle.
700 *
701 * @ingroup aux_vk
702 */
703VkResult
705
706
707/*
708 *
709 * Bundle init functions, in the vk_bundle_init.c file.
710 *
711 */
712
713/*!
714 * Check if the required instance extensions are supported, if not print error
715 * message with all extensions missing, returns VK_ERROR_EXTENSION_NOT_PRESENT
716 * if not all extensions are supported.
717 *
718 * @ingroup aux_vk
719 */
720VkResult
721vk_check_required_instance_extensions(struct vk_bundle *vk, struct u_extension_list *required_instance_ext_list);
722
723/*!
724 * Build instance extensions from required and optional instance extensions.
725 * This function enumerates available instance extensions, checks required ones,
726 * and builds a final list. Returns VK_SUCCESS if successful.
727 * Only requires @ref vk_get_loader_functions to have been called.
728 *
729 * @ingroup aux_vk
730 */
731VkResult
733 struct u_extension_list *required_instance_ext_list,
734 struct u_extension_list *optional_instance_ext_list,
735 struct u_extension_list **out_instance_ext_list);
736
737/*!
738 * Fills in has_* in vk_bundle given a string of prefiltered instance extensions
739 */
740void
742
743/*!
744 * Setup the physical device, this is called by vk_create_device but has uses
745 * for outside of that.
746 *
747 * @ingroup aux_vk
748 */
749VkResult
750vk_select_physical_device(struct vk_bundle *vk, int forced_index);
751
752/*!
753 * Used to enable device features as a argument @ref vk_create_device.
754 *
755 * @ingroup aux_vk
756 */
758{
759 bool shader_image_gather_extended;
760 bool shader_storage_image_write_without_format;
761 bool null_descriptor;
762 bool timeline_semaphore;
763 bool synchronization_2;
764 bool ext_fmt_resolve;
765 bool storage_buffer_8bit_access;
766 bool present_id;
767 bool present_id2;
768 bool present_wait;
769 bool video_maintenance_1;
770};
771
772/*!
773 * Creates a VkDevice and initialises the VkQueue.
774 *
775 * The @p vk_bundle must have been zero initialized, have the instance functions
776 * loaded and a valid instance.
777 *
778 * @ingroup aux_vk
779 */
780XRT_CHECK_RESULT VkResult
781vk_create_device(struct vk_bundle *vk,
782 int forced_index,
783 bool only_compute,
784 VkQueueGlobalPriorityEXT global_priority,
785 struct u_extension_list *required_device_ext_list,
786 struct u_extension_list *optional_device_ext_list,
787 const struct vk_device_features *optional_device_features);
788
789/*!
790 * @brief Initialize mutexes in the @ref vk_bundle.
791 *
792 * Not required for all uses, but a precondition for some.
793 *
794 * @ingroup aux_vk
795 */
796VkResult
797vk_init_mutex(struct vk_bundle *vk);
798
799/*!
800 * @brief De-initialize mutexes in the @ref vk_bundle.
801 *
802 * @ingroup aux_vk
803 */
804VkResult
805vk_deinit_mutex(struct vk_bundle *vk);
806
807static inline void
808vk_queue_lock(struct vk_bundle_queue *q)
809{
810 assert(q != NULL);
811 os_mutex_lock(&q->mutex);
812}
813
814static inline int
815vk_queue_trylock(struct vk_bundle_queue *q)
816{
817 assert(q != NULL);
818 return os_mutex_trylock(&q->mutex);
819}
820
821static inline void
822vk_queue_unlock(struct vk_bundle_queue *q)
823{
824 assert(q != NULL);
825 os_mutex_unlock(&q->mutex);
826}
827
828/*!
829 * Initialize a bundle with objects given to us by client code,
830 * used by @ref client_vk_compositor in @ref comp_client.
831 *
832 * @ingroup aux_vk
833 */
834XRT_CHECK_RESULT VkResult
836 PFN_vkGetInstanceProcAddr vkGetInstanceProcAddr,
837 VkInstance instance,
838 VkPhysicalDevice physical_device,
839 VkDevice device,
840 uint32_t queue_family_index,
841 uint32_t queue_index,
842 bool external_fence_fd_enabled,
843 bool external_semaphore_fd_enabled,
844 bool timeline_semaphore_enabled,
845 bool image_format_list_enabled,
846 bool debug_utils_enabled,
847 enum u_logging_level log_level);
848
849
850/*
851 *
852 * Other functions.
853 *
854 */
855
856/*!
857 * @ingroup aux_vk
858 */
859bool
860vk_get_memory_type(struct vk_bundle *vk, uint32_t type_bits, VkMemoryPropertyFlags memory_props, uint32_t *out_type_id);
861
862/*!
863 * Allocate memory for an image and bind it to that image.
864 *
865 * Handles the following steps:
866 *
867 * - calling vkGetImageMemoryRequirements
868 * - comparing against the max_size
869 * - getting the memory type (as dictated by the VkMemoryRequirements and
870 * VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT)
871 * - calling vkAllocateMemory
872 * - calling vkBindImageMemory
873 * - calling vkDestroyMemory in case of an error.
874 *
875 * If this fails, it cleans up the VkDeviceMemory.
876 *
877 * @param vk Vulkan bundle
878 * @param image The VkImage to allocate for and bind.
879 * @param requirements Memory requirements used for finding the memory type and the size.
880 * @param pNext_for_allocate (Optional) a pointer to use in the pNext chain of
881 * VkMemoryAllocateInfo.
882 * @param caller_name Used for error printing, this function is called from
883 * various sources and takes next chains that could influence the result
884 * of various calls inside of it. Since it's up to this function to print
885 * any errors it will add the caller name to error messages.
886 * @param out_mem Output parameter: will be set to the allocated memory if
887 * everything succeeds. Not modified if there is an error.
888 *
889 * If this fails, you may want to destroy your VkImage as well, since this
890 * routine is usually used in combination with vkCreateImage.
891 *
892 * @ingroup aux_vk
893 */
894XRT_CHECK_RESULT VkResult
896 VkImage image,
897 const VkMemoryRequirements *requirements,
898 const void *pNext_for_allocate,
899 const char *caller_name,
900 VkDeviceMemory *out_mem);
901
902/*!
903 *
904 * @brief Creates a Vulkan device memory and image from a native graphics buffer handle.
905 *
906 * In case of error, ownership is never transferred and the caller should close the handle themselves.
907 *
908 * In case of success, the underlying Vulkan functionality's ownership semantics apply: ownership of the @p image_native
909 * handle may have transferred, a reference may have been added, or the Vulkan objects may rely on the caller to keep
910 * the native handle alive until the Vulkan objects are destroyed. Which option applies depends on the particular native
911 * handle type used.
912 *
913 * See the corresponding specification texts:
914 *
915 * - Windows:
916 * https://www.khronos.org/registry/vulkan/specs/1.2-extensions/html/vkspec.html#VkImportMemoryWin32HandleInfoKHR
917 * - Linux: https://www.khronos.org/registry/vulkan/specs/1.2-extensions/html/vkspec.html#VkImportMemoryFdInfoKHR
918 * - Android:
919 * https://www.khronos.org/registry/vulkan/specs/1.2-extensions/html/vkspec.html#VkImportAndroidHardwareBufferInfoANDROID
920 *
921 * @ingroup aux_vk
922 */
923XRT_CHECK_RESULT VkResult
925 const struct xrt_swapchain_create_info *info,
926 struct xrt_image_native *image_native,
927 VkImage *out_image,
928 VkDeviceMemory *out_mem);
929
930/*!
931 * Given a DeviceMemory handle created to be exportable, outputs the native buffer type (FD on desktop Linux)
932 * equivalent.
933 *
934 * Caller assumes ownership of handle which should be unreferenced with @ref u_graphics_buffer_unref when no longer
935 * needed.
936 *
937 * @param vk Vulkan bundle
938 * @param device_memory The memory to get the handle of
939 * @param[out] out_handle A pointer to the handle to populate
940 *
941 * @ingroup aux_vk
942 */
943XRT_CHECK_RESULT VkResult
945 VkDeviceMemory device_memory,
946 xrt_graphics_buffer_handle_t *out_handle);
947
948/*!
949 * @ingroup aux_vk
950 * Helper to create a VkImage
951 */
952VkResult
954 VkExtent2D extent,
955 VkFormat format,
956 VkImageUsageFlags usage,
957 VkDeviceMemory *out_mem,
958 VkImage *out_image);
959
960/*!
961 * Helper to create a mutable RG88B8A8 VkImage that specializes in the two
962 * UNORM and SRGB variants of that formats.
963 *
964 * @ingroup aux_vk
965 */
966VkResult
968 struct vk_bundle *vk, VkExtent2D extent, VkImageUsageFlags usage, VkDeviceMemory *out_mem, VkImage *out_image);
969
970/*!
971 * @ingroup aux_vk
972 * Helper to create a VkImage, with more options for tiling and memory storage.
973 */
974VkResult
976 VkExtent3D extent,
977 VkFormat format,
978 VkImageTiling image_tiling,
979 VkImageUsageFlags image_usage_flags,
980 VkMemoryPropertyFlags memory_property_flags,
981 VkDeviceMemory *out_mem,
982 VkImage *out_image);
983
984/*!
985 * @ingroup aux_vk
986 */
987VkResult
988vk_create_sampler(struct vk_bundle *vk, VkSamplerAddressMode clamp_mode, VkSampler *out_sampler);
989
990
991/*
992 *
993 * Helpers for creating ímage views.
994 *
995 */
996
997/*!
998 * @ingroup aux_vk
999 */
1000VkResult
1001vk_create_view(struct vk_bundle *vk,
1002 VkImage image,
1003 VkImageViewType type,
1004 VkFormat format,
1005 VkImageSubresourceRange subresource_range,
1006 VkImageView *out_view);
1007
1008/*!
1009 * @ingroup aux_vk
1010 */
1011VkResult
1012vk_create_view_swizzle(struct vk_bundle *vk,
1013 VkImage image,
1014 VkImageViewType type,
1015 VkFormat format,
1016 VkImageSubresourceRange subresource_range,
1017 VkComponentMapping components,
1018 VkImageView *out_view);
1019
1020/*!
1021 * Creates a swizzled image view with a specific subset of usage, useful for a mutable image where one format might
1022 * not support all usages defined by the image.
1023 *
1024 * @ingroup aux_vk
1025 */
1026VkResult
1028 VkImage image,
1029 VkImageViewType type,
1030 VkFormat format,
1031 VkImageUsageFlags image_usage,
1032 VkImageSubresourceRange subresource_range,
1033 VkComponentMapping components,
1034 VkImageView *out_view);
1035
1036/*!
1037 * Creates a image with a specific subset of usage, useful for a mutable images
1038 * where one format might not support all usages defined by the image.
1039 *
1040 * @ingroup aux_vk
1041 */
1042VkResult
1044 VkImage image,
1045 VkImageViewType type,
1046 VkFormat format,
1047 VkImageUsageFlags image_usage,
1048 VkImageSubresourceRange subresource_range,
1049 VkImageView *out_view);
1050
1051
1052/*
1053 *
1054 * Helpers for creating descriptor pools and sets.
1055 *
1056 */
1057
1058bool
1059vk_init_descriptor_pool(struct vk_bundle *vk,
1060 const VkDescriptorPoolSize *pool_sizes,
1061 uint32_t pool_size_count,
1062 uint32_t set_count,
1063 VkDescriptorPool *out_descriptor_pool);
1064
1065bool
1066vk_allocate_descriptor_sets(struct vk_bundle *vk,
1067 VkDescriptorPool descriptor_pool,
1068 uint32_t count,
1069 const VkDescriptorSetLayout *set_layout,
1070 VkDescriptorSet *sets);
1071
1072
1073/*
1074 *
1075 * Helpers for creating buffers.
1076 *
1077 */
1078
1079bool
1080vk_buffer_init(struct vk_bundle *vk,
1081 VkDeviceSize size,
1082 VkBufferUsageFlags usage,
1083 VkMemoryPropertyFlags properties,
1084 VkBuffer *out_buffer,
1085 VkDeviceMemory *out_mem);
1086
1087void
1088vk_buffer_destroy(struct vk_buffer *self, struct vk_bundle *vk);
1089
1090bool
1091vk_update_buffer(struct vk_bundle *vk, float *buffer, size_t buffer_size, VkDeviceMemory memory);
1092
1093
1094/*
1095 *
1096 * Helpers for writing command buffers, in the vk_helpers.c file.
1097 *
1098 */
1099
1100/*!
1101 * Inserts a image barrier command, doesn't take any locks, the calling code
1102 * will need hold the lock for the pool that cmd_buffer is from or ensure it is
1103 * externally synchronized.
1104 *
1105 * @ingroup aux_vk
1106 */
1107void
1109 VkCommandBuffer cmd_buffer,
1110 VkImage image,
1111 VkAccessFlags src_access_mask,
1112 VkAccessFlags dst_access_mask,
1113 VkImageLayout old_image_layout,
1114 VkImageLayout new_image_layout,
1115 VkPipelineStageFlags src_stage_mask,
1116 VkPipelineStageFlags dst_stage_mask,
1117 VkImageSubresourceRange subresource_range);
1118
1119/*!
1120 * Inserts a image barrier command specifically for GPU commands, doesn't take
1121 * any locks, the calling code will need hold the lock for the pool that
1122 * cmd_buffer is from or ensure it is externally synchronized.
1123 *
1124 * @ingroup aux_vk
1125 */
1126void
1128 VkCommandBuffer cmd_buffer,
1129 VkImage image,
1130 VkAccessFlags src_access_mask,
1131 VkAccessFlags dst_access_mask,
1132 VkImageLayout old_layout,
1133 VkImageLayout new_layout,
1134 VkImageSubresourceRange subresource_range);
1135
1136#if defined(VK_EXT_debug_utils) || defined(XRT_DOXYGEN)
1137/*!
1138 * Uses VK_EXT_debug_utils to insert debug label into a VkCommandBuffer.
1139 *
1140 * In the vk_debug.c file.
1141 *
1142 * @ingroup aux_vk
1143 */
1144void
1145vk_cmd_insert_label(struct vk_bundle *vk, VkCommandBuffer cmd_buffer, const char *name);
1146#endif
1147
1148
1149/*
1150 *
1151 * State creation helpers, in the vk_state_creators.c file.
1152 *
1153 */
1154
1155/*!
1156 * Arguments to @ref vk_create_descriptor_pool function.
1157 */
1159{
1160 uint32_t uniform_per_descriptor_count; //!< VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER
1161 uint32_t sampler_per_descriptor_count; //!< VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER
1162 uint32_t storage_image_per_descriptor_count; //!< VK_DESCRIPTOR_TYPE_STORAGE_IMAGE
1163 uint32_t storage_buffer_per_descriptor_count; //!< VK_DESCRIPTOR_TYPE_STORAGE_BUFFER
1164
1165 //! The max count of created descriptors.
1167
1168 //! Are descriptors freeable, or must vkResetDescriptorPool be used.
1170};
1171
1172/*!
1173 * Creates a descriptor pool, made for a single layout.
1174 *
1175 * Does error logging.
1176 */
1177VkResult
1179 const struct vk_descriptor_pool_info *info,
1180 VkDescriptorPool *out_descriptor_pool);
1181
1182/*!
1183 * Creates a descriptor set.
1184 *
1185 * Does error logging.
1186 */
1187VkResult
1189 VkDescriptorPool descriptor_pool,
1190 VkDescriptorSetLayout descriptor_layout,
1191 VkDescriptorSet *out_descriptor_set);
1192
1193/*!
1194 * Creates a pipeline layout from a single descriptor set layout.
1195 *
1196 * Does error logging.
1197 */
1198VkResult
1200 VkDescriptorSetLayout descriptor_set_layout,
1201 VkPipelineLayout *out_pipeline_layout);
1202
1203/*!
1204 * Creates a pipeline cache.
1205 *
1206 * Does error logging.
1207 */
1208VkResult
1209vk_create_pipeline_cache(struct vk_bundle *vk, VkPipelineCache *out_pipeline_cache);
1210
1211/*!
1212 * Creates a compute pipeline, assumes entry function is called 'main'.
1213 *
1214 * Does error logging.
1215 */
1216VkResult
1218 VkPipelineCache pipeline_cache,
1219 VkShaderModule shader,
1220 VkPipelineLayout pipeline_layout,
1221 const VkSpecializationInfo *specialization_info,
1222 VkPipeline *out_compute_pipeline);
1223
1224
1225/*
1226 *
1227 * Sync objects, in the vk_sync_objects.c file.
1228 *
1229 */
1230
1231/*!
1232 * Is there a good likelihood that the import/export of a timeline semaphore
1233 * will succeed, in other words will the below functions work.
1234 *
1235 * @ingroup aux_vk
1236 */
1237XRT_CHECK_RESULT bool
1239
1240/*!
1241 * @brief Creates a Vulkan fence, submits it to the default VkQueue and return
1242 * its native graphics sync handle.
1243 *
1244 * In case of error, out_native is not touched by the function.
1245 *
1246 * See @ref vk_create_fence_sync_from_native for ownership semantics on import.
1247 *
1248 * @ingroup aux_vk
1249 */
1250XRT_CHECK_RESULT VkResult
1252
1253/*!
1254 * @brief Creates a Vulkan fence from a native graphics sync handle.
1255 *
1256 * In case of error, ownership is never transferred and the caller should close the handle themselves.
1257 *
1258 * In case of success, the underlying Vulkan functionality's ownership semantics apply: ownership of the @p native
1259 * handle may have transferred, a reference may have been added, or the Vulkan object may rely on the caller to keep the
1260 * native handle alive until the Vulkan object is destroyed. Which option applies depends on the particular native
1261 * handle type used.
1262 *
1263 * See the corresponding Vulkan specification text:
1264 * https://www.khronos.org/registry/vulkan/specs/1.2-extensions/html/vkspec.html#synchronization-fences-importing
1265 *
1266 * @ingroup aux_vk
1267 */
1268XRT_CHECK_RESULT VkResult
1269vk_create_fence_sync_from_native(struct vk_bundle *vk, xrt_graphics_sync_handle_t native, VkFence *out_fence);
1270
1271/*!
1272 * Creates a Vulkan semaphore and a native graphics sync handle.
1273 *
1274 * In case of success, the underlying Vulkan functionality's ownership semantics
1275 * apply: ownership of the @p native handle may have transferred, a reference
1276 * may have been added, or the Vulkan object may rely on the caller to keep the
1277 * native handle alive until the Vulkan object is destroyed. Which option
1278 * applies depends on the particular native handle type used.
1279 *
1280 * In case of error, neither @p out_sem and @p out_native is not touched by the
1281 * function so the caller only becomes responsible for the output on success.
1282 *
1283 * See the corresponding Vulkan specification text:
1284 * https://www.khronos.org/registry/vulkan/specs/1.3-extensions/html/vkspec.html#synchronization-semaphores
1285 *
1286 * @ingroup aux_vk
1287 */
1288XRT_CHECK_RESULT VkResult
1289vk_create_semaphore_and_native(struct vk_bundle *vk, VkSemaphore *out_sem, xrt_graphics_sync_handle_t *out_native);
1290
1291#if defined(VK_KHR_timeline_semaphore) || defined(XRT_DOXYGEN)
1292/*
1293 * Creates a Vulkan timeline semaphore and a native graphics sync
1294 * handle, see @ref vk_create_semaphore_and_native for more details.
1295 *
1296 * @ingroup aux_vk
1297 */
1298XRT_CHECK_RESULT VkResult
1299vk_create_timeline_semaphore_and_native(struct vk_bundle *vk,
1300 VkSemaphore *out_sem,
1301 xrt_graphics_sync_handle_t *out_native);
1302#endif
1303
1304/*!
1305 * @brief Creates a Vulkan semaphore from a native graphics sync handle.
1306 *
1307 * In case of error, ownership is never transferred and the caller should close the handle themselves.
1308 *
1309 * In case of success, the underlying Vulkan functionality's ownership semantics apply: ownership of the @p native
1310 * handle may have transferred, a reference may have been added, or the Vulkan object may rely on the caller to keep the
1311 * native handle alive until the Vulkan object is destroyed. Which option applies depends on the particular native
1312 * handle type used.
1313 *
1314 * @ingroup aux_vk
1315 */
1316XRT_CHECK_RESULT VkResult
1317vk_create_semaphore_from_native(struct vk_bundle *vk, xrt_graphics_sync_handle_t native, VkSemaphore *out_sem);
1318
1319#if defined(VK_KHR_timeline_semaphore) || defined(XRT_DOXYGEN)
1320/*!
1321 * @brief Creates a Vulkan timeline semaphore from a native graphics sync
1322 * handle, see @ref vk_create_semaphore_from_native for more details.
1323 *
1324 * @ingroup aux_vk
1325 */
1326XRT_CHECK_RESULT VkResult
1328#endif
1329
1330
1331/*
1332 *
1333 * Time function(s), in the vk_time.c file.
1334 *
1335 */
1336
1337#if defined(VK_EXT_calibrated_timestamps) || defined(VK_KHR_calibrated_timestamps) || defined(XRT_DOXYGEN)
1338/*!
1339 * Convert timestamps in GPU ticks (as return by VkQueryPool timestamp queries)
1340 * into host CPU nanoseconds, same time domain as @ref os_monotonic_get_ns.
1341 *
1342 * Note the timestamp needs to be in the past and not to old, this is because
1343 * not all GPU has full 64 bit timer resolution. For instance a Intel GPU "only"
1344 * have 36 bits of valid timestamp and a tick period 83.3333 nanosecond,
1345 * equating to an epoch of 5726 seconds before overflowing. The function can
1346 * handle overflows happening between the given timestamps and when it is called
1347 * but only for one such epoch overflow, any more will only be treated as one
1348 * such overflow. So timestamps needs to be converted reasonably soon after they
1349 * have been captured.
1350 *
1351 * @param vk The Vulkan bundle.
1352 * @param count Number of timestamps to be converted.
1353 * @param[in,out] in_out_timestamps Array of timestamps to be converted, done in place.
1354 *
1355 * @ingroup aux_vk
1356 */
1357XRT_CHECK_RESULT VkResult
1358vk_convert_timestamps_to_host_ns(struct vk_bundle *vk, uint32_t count, uint64_t *in_out_timestamps);
1359#endif
1360
1361
1362#ifdef __cplusplus
1363}
1364#endif
u_logging_level
Logging level enum.
Definition u_logging.h:45
VkResult vk_enumerate_display_mode_properties(struct vk_bundle *vk, VkPhysicalDevice physical_device, VkDisplayKHR display, uint32_t *out_prop_count, VkDisplayModePropertiesKHR **out_props)
Enumerate the mode properties of the given VkDisplayKHR, which belongs to the given VkPhysicalDevice.
VkResult vk_enumerate_physical_device_extension_properties(struct vk_bundle *vk, VkPhysicalDevice physical_device, const char *layer_name, uint32_t *out_prop_count, VkExtensionProperties **out_props)
Enumerate the extension properties of the given VkPhysicalDevice for the named layer_name,...
Definition vk_enumerate.c:103
VkResult vk_create_image_advanced(struct vk_bundle *vk, VkExtent3D extent, VkFormat format, VkImageTiling image_tiling, VkImageUsageFlags image_usage_flags, VkMemoryPropertyFlags memory_property_flags, VkDeviceMemory *out_mem, VkImage *out_image)
Helper to create a VkImage, with more options for tiling and memory storage.
Definition vk_helpers.c:256
VkResult vk_enumerate_physical_display_plane_properties(struct vk_bundle *vk, VkPhysicalDevice physical_device, uint32_t *out_prop_count, VkDisplayPlanePropertiesKHR **out_props)
Enumerate the display plane properties of the given VkPhysicalDevice.
void vk_cmd_image_barrier_gpu_locked(struct vk_bundle *vk, VkCommandBuffer cmd_buffer, VkImage image, VkAccessFlags src_access_mask, VkAccessFlags dst_access_mask, VkImageLayout old_layout, VkImageLayout new_layout, VkImageSubresourceRange subresource_range)
Inserts a image barrier command specifically for GPU commands, doesn't take any locks,...
Definition vk_helpers.c:1041
XRT_CHECK_RESULT VkResult vk_init_from_given(struct vk_bundle *vk, PFN_vkGetInstanceProcAddr vkGetInstanceProcAddr, VkInstance instance, VkPhysicalDevice physical_device, VkDevice device, uint32_t queue_family_index, uint32_t queue_index, bool external_fence_fd_enabled, bool external_semaphore_fd_enabled, bool timeline_semaphore_enabled, bool image_format_list_enabled, bool debug_utils_enabled, enum u_logging_level log_level)
Initialize a bundle with objects given to us by client code, used by client_vk_compositor in Composit...
Definition vk_bundle_init.c:1220
VkResult vk_create_image_mutable_rgba(struct vk_bundle *vk, VkExtent2D extent, VkImageUsageFlags usage, VkDeviceMemory *out_mem, VkImage *out_image)
Helper to create a mutable RG88B8A8 VkImage that specializes in the two UNORM and SRGB variants of th...
Definition vk_helpers.c:219
VkResult vk_create_view_swizzle_usage(struct vk_bundle *vk, VkImage image, VkImageViewType type, VkFormat format, VkImageUsageFlags image_usage, VkImageSubresourceRange subresource_range, VkComponentMapping components, VkImageView *out_view)
Creates a swizzled image view with a specific subset of usage, useful for a mutable image where one f...
Definition vk_helpers.c:797
XRT_CHECK_RESULT VkResult vk_convert_timestamps_to_host_ns(struct vk_bundle *vk, uint32_t count, uint64_t *in_out_timestamps)
Convert timestamps in GPU ticks (as return by VkQueryPool timestamp queries) into host CPU nanosecond...
XRT_CHECK_RESULT VkResult vk_create_semaphore_from_native(struct vk_bundle *vk, xrt_graphics_sync_handle_t native, VkSemaphore *out_sem)
Creates a Vulkan semaphore from a native graphics sync handle.
Definition vk_sync_objects.c:461
void vk_cmd_image_barrier_locked(struct vk_bundle *vk, VkCommandBuffer cmd_buffer, VkImage image, VkAccessFlags src_access_mask, VkAccessFlags dst_access_mask, VkImageLayout old_image_layout, VkImageLayout new_image_layout, VkPipelineStageFlags src_stage_mask, VkPipelineStageFlags dst_stage_mask, VkImageSubresourceRange subresource_range)
Inserts a image barrier command, doesn't take any locks, the calling code will need hold the lock for...
Definition vk_helpers.c:1004
VkResult vk_enumerate_physical_device_display_properties(struct vk_bundle *vk, VkPhysicalDevice physical_device, uint32_t *out_prop_count, VkDisplayPropertiesKHR **out_props)
Enumerate the display properties of the given VkPhysicalDevice.
XRT_CHECK_RESULT VkResult vk_create_timeline_semaphore_from_native(struct vk_bundle *vk, xrt_graphics_sync_handle_t native, VkSemaphore *out_sem)
Creates a Vulkan timeline semaphore from a native graphics sync handle, see vk_create_semaphore_from_...
VkResult vk_create_image_simple(struct vk_bundle *vk, VkExtent2D extent, VkFormat format, VkImageUsageFlags usage, VkDeviceMemory *out_mem, VkImage *out_image)
Helper to create a VkImage.
Definition vk_helpers.c:198
void vk_get_physical_device_queue_family_properties(struct vk_bundle *vk, VkPhysicalDevice physical_device, uint32_t *out_prop_count, VkQueueFamilyProperties **out_props)
Get the queue family properties of the given VkPhysicalDevice, note this function does not return a r...
Definition vk_enumerate.c:128
VkResult vk_select_physical_device(struct vk_bundle *vk, int forced_index)
Setup the physical device, this is called by vk_create_device but has uses for outside of that.
Definition vk_bundle_init.c:858
XRT_CHECK_RESULT VkResult vk_create_device(struct vk_bundle *vk, int forced_index, bool only_compute, VkQueueGlobalPriorityEXT global_priority, struct u_extension_list *required_device_ext_list, struct u_extension_list *optional_device_ext_list, const struct vk_device_features *optional_device_features)
Creates a VkDevice and initialises the VkQueue.
Definition vk_bundle_init.c:864
VkResult vk_enumerate_swapchain_images(struct vk_bundle *vk, VkSwapchainKHR swapchain, uint32_t *out_image_count, VkImage **out_images)
Enumerate the images of the given VkSwapchainKHR.
VkResult vk_deinit_mutex(struct vk_bundle *vk)
De-initialize mutexes in the vk_bundle.
Definition vk_bundle_init.c:1201
XRT_CHECK_RESULT VkResult vk_create_semaphore_and_native(struct vk_bundle *vk, VkSemaphore *out_sem, xrt_graphics_sync_handle_t *out_native)
Creates a Vulkan semaphore and a native graphics sync handle.
Definition vk_sync_objects.c:282
XRT_CHECK_RESULT VkResult vk_create_and_submit_fence_native(struct vk_bundle *vk, xrt_graphics_sync_handle_t *out_native)
Creates a Vulkan fence, submits it to the default VkQueue and return its native graphics sync handle.
Definition vk_sync_objects.c:105
VkResult vk_enumerate_surface_present_modes(struct vk_bundle *vk, VkSurfaceKHR surface, uint32_t *out_present_mode_count, VkPresentModeKHR **out_present_modes)
Enumerate the present modes of the given VkSurfaceKHR.
XRT_CHECK_RESULT VkResult vk_create_image_from_native(struct vk_bundle *vk, const struct xrt_swapchain_create_info *info, struct xrt_image_native *image_native, VkImage *out_image, VkDeviceMemory *out_mem)
Creates a Vulkan device memory and image from a native graphics buffer handle.
Definition vk_helpers.c:359
VkResult vk_get_loader_functions(struct vk_bundle *vk, PFN_vkGetInstanceProcAddr g)
Can be done on a completely bare bundle.
Definition vk_function_loaders.c:41
XRT_CHECK_RESULT bool vk_can_import_and_export_timeline_semaphore(struct vk_bundle *vk)
Is there a good likelihood that the import/export of a timeline semaphore will succeed,...
Definition vk_sync_objects.c:77
VkResult vk_enumerate_physical_devices(struct vk_bundle *vk, uint32_t *out_physical_device_count, VkPhysicalDevice **out_physical_devices)
Enumerate the physical devices of the VkInstance that has been opened on the given vk_bundle.
Definition vk_enumerate.c:80
XRT_CHECK_RESULT VkResult vk_create_fence_sync_from_native(struct vk_bundle *vk, xrt_graphics_sync_handle_t native, VkFence *out_fence)
Creates a Vulkan fence from a native graphics sync handle.
Definition vk_sync_objects.c:338
VkResult vk_enumerate_instance_extensions_properties(struct vk_bundle *vk, const char *layer_name, uint32_t *out_prop_count, VkExtensionProperties **out_props)
Return the VkExtensionProperties of the given layer_name, NULL means the "base" driver instance.
Definition vk_enumerate.c:56
VkResult vk_create_view_usage(struct vk_bundle *vk, VkImage image, VkImageViewType type, VkFormat format, VkImageUsageFlags image_usage, VkImageSubresourceRange subresource_range, VkImageView *out_view)
Creates a image with a specific subset of usage, useful for a mutable images where one format might n...
Definition vk_helpers.c:839
VkResult vk_check_required_instance_extensions(struct vk_bundle *vk, struct u_extension_list *required_instance_ext_list)
Check if the required instance extensions are supported, if not print error message with all extensio...
Definition vk_bundle_init.c:100
XRT_CHECK_RESULT VkResult vk_alloc_and_bind_image_memory(struct vk_bundle *vk, VkImage image, const VkMemoryRequirements *requirements, const void *pNext_for_allocate, const char *caller_name, VkDeviceMemory *out_mem)
Allocate memory for an image and bind it to that image.
Definition vk_helpers.c:90
VkResult vk_enumerate_surface_formats(struct vk_bundle *vk, VkSurfaceKHR surface, uint32_t *out_format_count, VkSurfaceFormatKHR **out_formats)
Enumerate the surface formats of the given VkSurfaceKHR, returns a list of VkSurfaceFormatKHR,...
void vk_name_object(struct vk_bundle *vk, VkObjectType type, uint64_t object, const char *name)
Uses VK_EXT_debug_utils to set a name for an object, for easier debugging.
VkResult vk_get_device_functions(struct vk_bundle *vk)
Requires a device to have been created and set on the bundle.
Definition vk_function_loaders.c:64
XRT_CHECK_RESULT VkResult vk_get_native_handle_from_device_memory(struct vk_bundle *vk, VkDeviceMemory device_memory, xrt_graphics_buffer_handle_t *out_handle)
Given a DeviceMemory handle created to be exportable, outputs the native buffer type (FD on desktop L...
Definition vk_helpers.c:654
VkResult vk_get_instance_functions(struct vk_bundle *vk)
Requires a instance to have been created and set on the bundle.
Definition vk_function_loaders.c:55
void vk_cmd_insert_label(struct vk_bundle *vk, VkCommandBuffer cmd_buffer, const char *name)
Uses VK_EXT_debug_utils to insert debug label into a VkCommandBuffer.
VkResult vk_init_mutex(struct vk_bundle *vk)
Initialize mutexes in the vk_bundle.
Definition vk_bundle_init.c:1185
VkResult vk_build_instance_extensions(struct vk_bundle *vk, struct u_extension_list *required_instance_ext_list, struct u_extension_list *optional_instance_ext_list, struct u_extension_list **out_instance_ext_list)
Build instance extensions from required and optional instance extensions.
Definition vk_bundle_init.c:86
Wrapper around OS threading native functions.
Definition t_rift_blobwatch.c:106
A wrapper around a native mutex.
Definition os_threading.h:69
Definition u_extension_list.cpp:33
Definition vk_helpers.h:257
Definition vk_helpers.h:62
uint32_t family_index
The queue family index.
Definition vk_helpers.h:66
VkQueue queue
The Vulkan queue handle.
Definition vk_helpers.h:64
struct os_mutex mutex
The queue mutex -.
Definition vk_helpers.h:70
uint32_t index
The queue (instance) index.
Definition vk_helpers.h:68
A bundle of Vulkan functions and objects, used by both Compositor and Compositor client code.
Definition vk_helpers.h:81
uint32_t max_bound_descriptor_sets
Maximum number of descriptor sets that can be simultaneously used by a pipeline.
Definition vk_helpers.h:221
bool synchronization_2
Was synchronization2 requested, available, and enabled?
Definition vk_helpers.h:200
uint32_t max_descriptor_set_samplers
Maximum number of samplers that can be included in a pipeline layout.
Definition vk_helpers.h:224
bool timeline_semaphore
Were timeline semaphore requested, available, and enabled?
Definition vk_helpers.h:197
uint32_t max_per_stage_descriptor_samplers
Maximum number of samplers that can be accessible to a single shader stage in a pipeline layout.
Definition vk_helpers.h:230
bool present_id
Was KHR_present_id requested, available, and enabled?
Definition vk_helpers.h:203
bool video_maintenance_1
Was KHR_video_maintenance1 requested, available, and enabled?
Definition vk_helpers.h:212
bool present_id2
Was KHR_present_id2 requested, available, and enabled?
Definition vk_helpers.h:206
uint32_t timestamp_valid_bits
Valid bits in the queue selected.
Definition vk_helpers.h:194
uint32_t max_sampler_allocation_count
Maximum number of sampler objects, as created by vkCreateSampler, which can simultaneously exist on.
Definition vk_helpers.h:218
uint32_t max_descriptor_set_sampled_images
Maximum number of sampled images that can be included in a pipeline layout.
Definition vk_helpers.h:227
uint32_t max_per_stage_descriptor_storage_images
Per stage limit on storage images.
Definition vk_helpers.h:236
bool is_tegra
Is the GPU a tegra device.
Definition vk_helpers.h:240
struct vk_bundle_queue * main_queue
Main queue for general work.
Definition vk_helpers.h:108
bool timestamp_compute_and_graphics
Are timestamps available for compute and graphics queues?
Definition vk_helpers.h:188
bool present_wait
Was KHR_present_wait requested, available, and enabled?
Definition vk_helpers.h:209
struct vk_bundle_queue queues[3]
queues - a free list of unique queues
Definition vk_helpers.h:98
uint32_t max_per_stage_descriptor_sampled_images
Per stage limit on sampled images (includes combined).
Definition vk_helpers.h:233
float timestamp_period
Nanoseconds per gpu tick.
Definition vk_helpers.h:191
struct vk_bundle_queue * graphics_queue
Graphics queue.
Definition vk_helpers.h:117
Arguments to vk_create_descriptor_pool function.
Definition vk_helpers.h:1159
uint32_t descriptor_count
The max count of created descriptors.
Definition vk_helpers.h:1166
uint32_t uniform_per_descriptor_count
VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER.
Definition vk_helpers.h:1160
bool freeable
Are descriptors freeable, or must vkResetDescriptorPool be used.
Definition vk_helpers.h:1169
uint32_t sampler_per_descriptor_count
VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER.
Definition vk_helpers.h:1161
uint32_t storage_image_per_descriptor_count
VK_DESCRIPTOR_TYPE_STORAGE_IMAGE.
Definition vk_helpers.h:1162
uint32_t storage_buffer_per_descriptor_count
VK_DESCRIPTOR_TYPE_STORAGE_BUFFER.
Definition vk_helpers.h:1163
Used to enable device features as a argument vk_create_device.
Definition vk_helpers.h:758
Definition vk_helpers.h:48
uint32_t index
The queue (instance) index.
Definition vk_helpers.h:52
uint32_t family_index
The queue family index.
Definition vk_helpers.h:50
A single image of a swapchain based on native buffer handles.
Definition xrt_compositor.h:2216
Swapchain creation info.
Definition xrt_compositor.h:924
A collection of strings, like a list of extensions to enable.
Basic logging functionality.
VkResult vk_create_descriptor_set(struct vk_bundle *vk, VkDescriptorPool descriptor_pool, VkDescriptorSetLayout descriptor_layout, VkDescriptorSet *out_descriptor_set)
Creates a descriptor set.
Definition vk_state_creators.c:88
XRT_CHECK_RESULT const char * vk_surface_transform_flag_string(VkSurfaceTransformFlagBitsKHR bits, bool null_on_unknown)
Returns the surface transform flag if one valid bit is set, if multiple bits are set,...
Definition vk_print.c:983
void vk_fill_in_has_instance_extensions(struct vk_bundle *vk, struct u_extension_list *ext_list)
Fills in has_* in vk_bundle given a string of prefiltered instance extensions.
Definition vk_bundle_init.c:132
VkResult vk_create_pipeline_cache(struct vk_bundle *vk, VkPipelineCache *out_pipeline_cache)
Creates a pipeline cache.
Definition vk_state_creators.c:147
VkResult vk_create_descriptor_pool(struct vk_bundle *vk, const struct vk_descriptor_pool_info *info, VkDescriptorPool *out_descriptor_pool)
Creates a descriptor pool, made for a single layout.
Definition vk_state_creators.c:16
XRT_CHECK_RESULT const char * vk_image_usage_flag_string(VkImageUsageFlagBits bits, bool null_on_unknown)
Returns the image usage flag if one valid bit is set, if multiple bits are set, will return 'MULTIPLE...
Definition vk_print.c:912
XRT_CHECK_RESULT const char * vk_format_feature_flag_string(VkFormatFeatureFlagBits bits, bool null_on_unknown)
Returns the format feature flag if one valid bit is set, if multiple bits are set,...
Definition vk_print.c:892
XRT_CHECK_RESULT const char * vk_composite_alpha_flag_string(VkCompositeAlphaFlagBitsKHR bits, bool null_on_unknown)
Returns the composite alpha flag if one valid bit is set, if multiple bits are set,...
Definition vk_print.c:964
VkResult vk_create_compute_pipeline(struct vk_bundle *vk, VkPipelineCache pipeline_cache, VkShaderModule shader, VkPipelineLayout pipeline_layout, const VkSpecializationInfo *specialization_info, VkPipeline *out_compute_pipeline)
Creates a compute pipeline, assumes entry function is called 'main'.
Definition vk_state_creators.c:172
VkResult vk_create_pipeline_layout(struct vk_bundle *vk, VkDescriptorSetLayout descriptor_set_layout, VkPipelineLayout *out_pipeline_layout)
Creates a pipeline layout from a single descriptor set layout.
Definition vk_state_creators.c:118
Printing helper code.
Header holding common defines.
Header declaring XRT graphics interfaces.
Native handle types.
int xrt_graphics_buffer_handle_t
The type underlying buffers shared between compositor clients and the main compositor.
Definition xrt_handles.h:252
int xrt_graphics_sync_handle_t
The type underlying synchronization primitives (semaphores, etc) shared between compositor clients an...
Definition xrt_handles.h:354
Include all of the Vulkan headers in one place, and cope with any "messy" includes implied by it.