diff options
| author | ladevieq <ladevie.quentin@gmail.com> | 2023-01-12 00:47:59 +0100 |
|---|---|---|
| committer | ladevieq <ladevie.quentin@gmail.com> | 2023-01-12 00:47:59 +0100 |
| commit | 5e3bb454d50091e581d5d1d03af34e38277694b3 (patch) | |
| tree | 06eada2111afb56a24d0ced89685587400041c8d | |
| parent | b47e177898657e435cb5bc913a4a783fddbe1f3d (diff) | |
WIP new rendering api
| -rw-r--r-- | api-proto.txt | 29 | ||||
| -rw-r--r-- | api-test/CMakeLists.txt | 1 | ||||
| -rw-r--r-- | api-test/command-buffer.cpp | 54 | ||||
| -rw-r--r-- | api-test/main.cpp | 18 | ||||
| -rw-r--r-- | api-test/vk-command-buffer.cpp | 25 | ||||
| -rw-r--r-- | api-test/vk-device.cpp | 468 | ||||
| -rw-r--r-- | include/api-test/command-buffer.hpp | 44 | ||||
| -rw-r--r-- | include/api-test/handle.hpp | 2 | ||||
| -rw-r--r-- | include/api-test/vk-command-buffer.hpp | 14 | ||||
| -rw-r--r-- | include/api-test/vk-device.hpp | 65 | ||||
| -rw-r--r-- | include/resource-manager.hpp | 6 | ||||
| -rw-r--r-- | include/texture.hpp | 83 | ||||
| -rw-r--r-- | include/vec3.hpp | 20 | ||||
| -rw-r--r-- | include/vk-api.hpp | 217 | ||||
| -rw-r--r-- | include/vk-context.hpp | 2 | ||||
| -rw-r--r-- | include/vk-renderer.hpp | 65 | ||||
| -rw-r--r-- | src/CMakeLists.txt | 4 | ||||
| -rw-r--r-- | src/main.cpp | 2 | ||||
| -rw-r--r-- | src/resource-manager.cpp | 10 | ||||
| -rw-r--r-- | src/scene.cpp | 16 | ||||
| -rw-r--r-- | src/vec3.cpp | 54 | ||||
| -rw-r--r-- | src/vk-api.cpp | 1096 | ||||
| -rw-r--r-- | src/vk-context.cpp | 4 |
23 files changed, 1201 insertions, 1098 deletions
diff --git a/api-proto.txt b/api-proto.txt index 751f390..a8ca1ff 100644 --- a/api-proto.txt +++ b/api-proto.txt @@ -4,19 +4,18 @@ enum CMD_BUF_TYPE { ASYNC_COMPUTE, } -class command_buffer { +class device_command_buffer { void start(); void stop(); VkCommandBuffer handle; - queue owner; } -class graphics_command_buffer : command_buffer { +class graphics_device_command_buffer : device_command_buffer { void image_barrier(handle tex, State new_state) { texture = rm::get_texture(tex); - cmd.barrier(texture.img.device_image, texture.current_state, new_state); + vkCmdBarrier(texture.img.device_image, texture.current_state, new_state, handle); texture.current_state = new_state; } @@ -35,7 +34,7 @@ class device_buffer { VkDeviceAddr gpu_address; } -class device_image { +class device_texture { VkImage handle; VmaAllocation allocation; array<uint, max_usage> bindless_id; // TODO: Handle this in a higher level ? @@ -46,27 +45,25 @@ class device_image { const uint invalid_id = -1; } -class device_command_buffer { - CMD_BUF_TYPE buf_type = CMD_BUF_TYPE::MAX; - VkCommandBuffer handle; -} - class global_descriptor_set { VkDescritptorSetLayout layout; VkDescriptorSet set; }; class device { - device_image create_image(TextureDesc desc) { - img {}; - img.handle = vmaCreateImage(&img.alloc); + device_image create_texture(TextureDesc desc) { + auto tex {}; + tex.handle = vmaCreateImage(&tex.alloc); } device_buffer create_buffer(BufferDesc desc); - device_command_buffer allocate_command_buffer(uint32_t count); + template<typename command_buffer_type> + void allocate_command_buffers(command_buffer_type ptr, uint32_t count, CMD_BUF_TYPE type) { + vkAllocate(ptr, count, queue[type]); + } - submit(span<device_command_buffer> cmd_buffers, semaphore) + fence submit(span<device_command_buffer> cmd_buffers, CMD_BUF_TYPE type); wait(fence); wait_idle(); @@ -78,7 +75,7 @@ class device { device_swapchain sc; - array<device_image> sc_images; + array<device_texture> sc_textures; array<queue, CMD_BUF_TYPE::MAX> queues; global_descriptor_set global_set; diff --git a/api-test/CMakeLists.txt b/api-test/CMakeLists.txt index 3b39ea3..849f242 100644 --- a/api-test/CMakeLists.txt +++ b/api-test/CMakeLists.txt @@ -2,6 +2,7 @@ add_executable( api-test main.cpp vk-device.cpp + command-buffer.cpp ${CMAKE_SOURCE_DIR}/src/window.cpp ${CMAKE_SOURCE_DIR}/src/utils.cpp ${CMAKE_SOURCE_DIR}/src/vulkan-loader.cpp diff --git a/api-test/command-buffer.cpp b/api-test/command-buffer.cpp new file mode 100644 index 0000000..9e37f95 --- /dev/null +++ b/api-test/command-buffer.cpp @@ -0,0 +1,54 @@ +#include "command-buffer.hpp" + +#include <cassert> + +#include "vulkan-loader.hpp" + +#include"vk-device.hpp" + +#ifdef _DEBUG +#define VKCHECK(result) assert(result == VK_SUCCESS); +#else +#define VKCHECK(result) result; +#endif + +void command_buffer::start() const { + VkCommandBufferBeginInfo begin_info { + .sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO, + .pNext = nullptr, + .flags = 0U, + .pInheritanceInfo = nullptr + }; + + VKCHECK(vkBeginCommandBuffer(handle, &begin_info)) +} + +void command_buffer::stop() const { + VKCHECK(vkEndCommandBuffer(handle)) +} + +void transfer_command_buffer::copy(::handle<device_buffer> buffer_handle, ::handle<device_texture> texture_handle) { + const auto& buffer = vkdevice::get_buffer(buffer_handle); + const auto& texture = vkdevice::get_texture(texture_handle); + VkImageSubresourceLayers image_subresource_layers { + .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT, + .mipLevel = 0, + .baseArrayLayer = 0, + .layerCount = 1, + }; + + VkBufferImageCopy buffer_to_image_copy { + .bufferOffset = 0, + .bufferRowLength = 0, + .bufferImageHeight = 0, + .imageSubresource = image_subresource_layers, + .imageOffset = { .x = 0, .y = 0, .z = 0 }, + .imageExtent = { + .width = texture.desc.width, + .height = texture.desc.height, + .depth = texture.desc.depth, + }, + }; + + vkCmdCopyBufferToImage(handle, buffer.handle, texture.handle, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, &buffer_to_image_copy); +} diff --git a/api-test/main.cpp b/api-test/main.cpp index 61db6be..40f5c72 100644 --- a/api-test/main.cpp +++ b/api-test/main.cpp @@ -34,7 +34,7 @@ int main() { vkdevice device { wnd }; - auto gpu_texture = device.create_texture({ + auto gpu_texture_handle = device.create_texture({ .width = 1024U, .height = 1024U, .usages = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT, @@ -49,21 +49,27 @@ int main() { .memory_usage = VMA_MEMORY_USAGE_GPU_ONLY, })); - auto staging_buffer = device.get_buffer(device.create_buffer({ + auto staging_buffer_handle = device.create_buffer({ .size = 1024U * sizeof(uint32_t), .usages = VK_BUFFER_USAGE_TRANSFER_SRC_BIT, .memory_properties = VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT, .memory_usage = VMA_MEMORY_USAGE_CPU_TO_GPU, - })); + }); + auto staging_buffer = device.get_buffer(staging_buffer_handle); uint64_t t = 7; (*(uint64_t*)staging_buffer.mapped_ptr) = t; - auto command_buffer = device.get_command_buffer(); + transfer_command_buffer command_buffer; + device.allocate_command_buffers(&command_buffer, 1, QueueType::GRAPHICS); + + command_buffer.start(); + + command_buffer.copy(staging_buffer_handle, gpu_texture_handle); - command_buffer.copy(staging_buffer, gpu_texture); + command_buffer.stop(); - device.submit(command_buffer); + device.submit(&command_buffer, 1); #ifdef ENABLE_RENDERDOC if(rdoc_api != nullptr) rdoc_api->EndFrameCapture(nullptr, nullptr); diff --git a/api-test/vk-command-buffer.cpp b/api-test/vk-command-buffer.cpp deleted file mode 100644 index b9eed19..0000000 --- a/api-test/vk-command-buffer.cpp +++ /dev/null @@ -1,25 +0,0 @@ -#include "vk-command-buffer.hpp" - -#include <cassert> - -#include "vulkan-loader.hpp" - -#ifdef _DEBUG -#define VKCHECK(result) assert(result == VK_SUCCESS); -#else -#define VKCHECK(result) result; -#endif - -void command_buffer::start() { - VkCommandBufferBeginInfo begin_info = {}; - begin_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; - begin_info.pNext = nullptr; - begin_info.flags = 0U; - begin_info.pInheritanceInfo = nullptr; - - VKCHECK(vkBeginCommandBuffer(handle, &begin_info)) -} - -void command_buffer::stop() { - VKCHECK(vkEndCommandBuffer(handle)) -} diff --git a/api-test/vk-device.cpp b/api-test/vk-device.cpp index 4b7c0d0..ef57f01 100644 --- a/api-test/vk-device.cpp +++ b/api-test/vk-device.cpp @@ -1,9 +1,7 @@ #include "vk-device.hpp" -#include "color.hpp" #include <cassert> #include <iostream> -#include <thread> #include <vector> #define VMA_IMPLEMENTATION @@ -61,11 +59,18 @@ VKAPI_ATTR VkBool32 VKAPI_CALL debug_callback(VkDebugUtilsMessageSeverityFlagBit vkdevice::vkdevice(const window& window) : queues{ - { - .usages = VK_QUEUE_GRAPHICS_BIT, - }, - // { .usages = VK_QUEUE_TRANSFER_BIT, }, - } { + { + .usages = VK_QUEUE_GRAPHICS_BIT | + VK_QUEUE_COMPUTE_BIT | + VK_QUEUE_TRANSFER_BIT, + }, + { + .usages = VK_QUEUE_COMPUTE_BIT, + }, + { + .usages = VK_QUEUE_TRANSFER_BIT, + }, + } { load_vulkan(); create_instance(); @@ -83,40 +88,43 @@ vkdevice::vkdevice(const window& window) } handle<device_texture> vkdevice::create_texture(const texture_desc& desc) { - device_texture device_texture = {}; - device_texture.desc = desc; + device_texture device_texture { + .desc = desc, + }; assert(desc.mips <= texture_desc::max_mips); - VkImageCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO; - create_info.pNext = nullptr; - create_info.flags = 0U; - create_info.imageType = desc.type; - create_info.format = desc.format; - create_info.extent = { - .width = desc.width, - .height = desc.height, - .depth = desc.depth + VkImageCreateInfo create_info { + .sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, + .pNext = nullptr, + .flags = 0U, + .imageType = desc.type, + .format = desc.format, + .extent = { + .width = desc.width, + .height = desc.height, + .depth = desc.depth + }, + .mipLevels = desc.mips, + .arrayLayers = 1, + .samples = VK_SAMPLE_COUNT_1_BIT, + .tiling = VK_IMAGE_TILING_OPTIMAL, + .usage = desc.usages, + .sharingMode = VK_SHARING_MODE_EXCLUSIVE, + .queueFamilyIndexCount = 0, + .pQueueFamilyIndices = nullptr, + .initialLayout = VK_IMAGE_LAYOUT_UNDEFINED, }; - create_info.mipLevels = desc.mips; - create_info.arrayLayers = 1; - create_info.samples = VK_SAMPLE_COUNT_1_BIT; - create_info.tiling = VK_IMAGE_TILING_OPTIMAL; - create_info.usage = desc.usages; - create_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; - create_info.queueFamilyIndexCount = 0; - create_info.pQueueFamilyIndices = nullptr; - create_info.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; - VmaAllocationCreateInfo alloc_create_info = {}; - alloc_create_info.flags = 0U; - alloc_create_info.usage = VMA_MEMORY_USAGE_GPU_ONLY; - alloc_create_info.requiredFlags = VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT; - alloc_create_info.preferredFlags = 0U; - alloc_create_info.memoryTypeBits = 0U; - alloc_create_info.pool = nullptr; - alloc_create_info.pUserData = nullptr; + VmaAllocationCreateInfo alloc_create_info { + .flags = 0U, + .usage = VMA_MEMORY_USAGE_GPU_ONLY, + .requiredFlags = VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT, + .preferredFlags = 0U, + .memoryTypeBits = 0U, + .pool = nullptr, + .pUserData = nullptr, + }; VKCHECK(vmaCreateImage(gpu_allocator, &create_info, &alloc_create_info, &device_texture.handle, &device_texture.alloc, nullptr)) @@ -129,33 +137,36 @@ handle<device_texture> vkdevice::create_texture(const texture_desc& desc) { } handle<device_buffer> vkdevice::create_buffer(const buffer_desc& desc) { - device_buffer device_buffer = {}; - device_buffer.desc = desc; + device_buffer device_buffer { + .desc = desc, + }; - VkBufferCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO; - create_info.pNext = nullptr; - create_info.flags = 0U; - create_info.size = desc.size; - create_info.usage = desc.usages; - create_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; - create_info.queueFamilyIndexCount = 0; - create_info.pQueueFamilyIndices = nullptr; + VkBufferCreateInfo create_info { + .sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, + .pNext = nullptr, + .flags = 0U, + .size = desc.size, + .usage = desc.usages, + .sharingMode = VK_SHARING_MODE_EXCLUSIVE, + .queueFamilyIndexCount = 0, + .pQueueFamilyIndices = nullptr, + }; VmaAllocatorCreateFlags alloc_create_flags = desc.memory_usage != VMA_MEMORY_USAGE_GPU_ONLY ? VMA_ALLOCATION_CREATE_MAPPED_BIT : 0U; - - VmaAllocationCreateInfo alloc_create_info = {}; - alloc_create_info.flags = alloc_create_flags; - alloc_create_info.usage = static_cast<VmaMemoryUsage>(desc.memory_usage); - alloc_create_info.requiredFlags = desc.memory_properties; - alloc_create_info.preferredFlags = 0U; - alloc_create_info.memoryTypeBits = 0U; - alloc_create_info.pool = nullptr; - alloc_create_info.pUserData = nullptr; - VmaAllocationInfo alloc_info = {}; + VmaAllocationCreateInfo alloc_create_info { + .flags = alloc_create_flags, + .usage = static_cast<VmaMemoryUsage>(desc.memory_usage), + .requiredFlags = desc.memory_properties, + .preferredFlags = 0U, + .memoryTypeBits = 0U, + .pool = nullptr, + .pUserData = nullptr, + }; + + VmaAllocationInfo alloc_info {}; VKCHECK(vmaCreateBuffer(gpu_allocator, &create_info, &alloc_create_info, &device_buffer.handle, &device_buffer.alloc, &alloc_info)) @@ -164,47 +175,77 @@ handle<device_buffer> vkdevice::create_buffer(const buffer_desc& desc) { return { buffers.add(device_buffer) }; } -void vkdevice::submit(std::span<graphics_command_buffer> command_buffers) { - VkSubmitInfo submit_info = {}; - submit_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; - submit_info.pNext = nullptr; - submit_info.waitSemaphoreCount; - submit_info.pWaitSemaphores; - submit_info.pWaitDstStageMask; - submit_info.commandBufferCount; - submit_info.pCommandBuffers; - submit_info.signalSemaphoreCount; - submit_info.pSignalSemaphores; +void vkdevice::submit(command_buffer* buffers, size_t count) { + assert((count - max_submitable_command_buffers) <= 0); + const auto queue_type = buffers[0].queue_type; + VkCommandBuffer to_submit[max_submitable_command_buffers]; + + for (auto index { 0U }; index < count; index++) { + assert(queue_type == buffers[index].queue_type); + to_submit[index] = buffers[index].handle; + } + + VkSubmitInfo submit_info { + .sType = VK_STRUCTURE_TYPE_SUBMIT_INFO, + .pNext = nullptr, + .waitSemaphoreCount = 0U, + .pWaitSemaphores = nullptr, + .pWaitDstStageMask = nullptr, + .commandBufferCount = static_cast<uint32_t>(count), + .pCommandBuffers = to_submit, + .signalSemaphoreCount = 0U, + .pSignalSemaphores = nullptr, + }; - vkQueueSubmit() + VKCHECK(vkQueueSubmit(queues[static_cast<uint32_t>(queue_type)].handle, 1, &submit_info, nullptr)) } // private +void vkdevice::allocate_command_buffers(command_buffer* buffers, size_t count, QueueType type) { + assert((count - max_allocable_command_buffers) <= 0); + const auto& queue = queues[static_cast<uint32_t>(type)]; + VkCommandBuffer command_buffers[max_allocable_command_buffers]; + + VkCommandBufferAllocateInfo allocate_info { + .sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO, + .pNext = nullptr, + .commandPool = queue.command_pool, + .level = VK_COMMAND_BUFFER_LEVEL_PRIMARY, + .commandBufferCount = static_cast<uint32_t>(count), + }; + + VKCHECK(vkAllocateCommandBuffers(device, &allocate_info, command_buffers)) + + for (auto index { 0U }; index < count; index++) { + buffers[index].handle = command_buffers[index]; + } +} void vkdevice::create_views(device_texture& texture) { VkImageAspectFlags aspect_mask = ((texture.desc.usages & VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT) != 0U) ? VK_IMAGE_ASPECT_COLOR_BIT : VK_IMAGE_ASPECT_DEPTH_BIT; - VkImageViewCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO; - create_info.pNext = nullptr; - create_info.flags = 0U; - create_info.image = texture.handle; - create_info.viewType = VK_IMAGE_VIEW_TYPE_2D; - create_info.format = texture.desc.format; - create_info.components = { - .r = VK_COMPONENT_SWIZZLE_R, - .g = VK_COMPONENT_SWIZZLE_G, - .b = VK_COMPONENT_SWIZZLE_B, - .a = VK_COMPONENT_SWIZZLE_A, - }; - create_info.subresourceRange = { - .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT, // TODO: Choose either color or depth based on format ? - .baseMipLevel = 0, - .levelCount = 1, - .baseArrayLayer = 0, - .layerCount = 1, + VkImageViewCreateInfo create_info { + .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, + .pNext = nullptr, + .flags = 0U, + .image = texture.handle, + .viewType = VK_IMAGE_VIEW_TYPE_2D, + .format = texture.desc.format, + .components = { + .r = VK_COMPONENT_SWIZZLE_R, + .g = VK_COMPONENT_SWIZZLE_G, + .b = VK_COMPONENT_SWIZZLE_B, + .a = VK_COMPONENT_SWIZZLE_A, + }, + .subresourceRange = { + .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT, // TODO: Choose either color or depth based on format ? + .baseMipLevel = 0, + .levelCount = 1, + .baseArrayLayer = 0, + .layerCount = 1, + }, }; for (auto mip_index{ 0 }; mip_index < texture.desc.mips; mip_index++) { @@ -218,19 +259,20 @@ void vkdevice::create_views(device_texture& texture) { } void vkdevice::create_surface(const window& window) { - VkWin32SurfaceCreateInfoKHR create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_WIN32_SURFACE_CREATE_INFO_KHR; - create_info.pNext = nullptr; - create_info.flags = 0U; - create_info.hinstance = GetModuleHandle(nullptr); - create_info.hwnd = window.handle; + VkWin32SurfaceCreateInfoKHR create_info { + .sType = VK_STRUCTURE_TYPE_WIN32_SURFACE_CREATE_INFO_KHR, + .pNext = nullptr, + .flags = 0U, + .hinstance = GetModuleHandle(nullptr), + .hwnd = window.handle, + }; VKCHECK(vkCreateWin32SurfaceKHR(instance, &create_info, nullptr, &surface)) } void vkdevice::create_swapchain() { VkBool32 supported = VK_FALSE; - for (auto index{ 0U }; index < QueueTypes::MAX; index++) { + for (auto index{ 0U }; index < static_cast<uint32_t>(QueueType::MAX); index++) { auto& queue = queues[index]; VKCHECK(vkGetPhysicalDeviceSurfaceSupportKHR(physical_device, queue.index, surface, &supported)) @@ -268,25 +310,26 @@ void vkdevice::create_swapchain() { VKCHECK(vkGetPhysicalDeviceSurfacePresentModesKHR(physical_device, surface, &supported_present_modes_count, supported_present_modes.data())) - VkSwapchainCreateInfoKHR create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR; - create_info.pNext = nullptr; - create_info.flags = 0U; - create_info.surface = surface; - create_info.minImageCount = surface_capabilities.minImageCount; - create_info.imageFormat = supported_formats[0].format; - create_info.imageColorSpace = supported_formats[0].colorSpace; - create_info.imageExtent = extent; - create_info.imageArrayLayers = 1U; - create_info.imageUsage = VK_IMAGE_USAGE_TRANSFER_DST_BIT; - create_info.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE; - create_info.queueFamilyIndexCount = 0U; - create_info.pQueueFamilyIndices = nullptr; - create_info.preTransform = VK_SURFACE_TRANSFORM_IDENTITY_BIT_KHR; - create_info.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR; - create_info.presentMode = supported_present_modes[0]; - create_info.clipped = VK_TRUE; - create_info.oldSwapchain = nullptr; + VkSwapchainCreateInfoKHR create_info = { + .sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR, + .pNext = nullptr, + .flags = 0U, + .surface = surface, + .minImageCount = surface_capabilities.minImageCount, + .imageFormat = supported_formats[0].format, + .imageColorSpace = supported_formats[0].colorSpace, + .imageExtent = extent, + .imageArrayLayers = 1U, + .imageUsage = VK_IMAGE_USAGE_TRANSFER_DST_BIT, + .imageSharingMode = VK_SHARING_MODE_EXCLUSIVE, + .queueFamilyIndexCount = 0U, + .pQueueFamilyIndices = nullptr, + .preTransform = VK_SURFACE_TRANSFORM_IDENTITY_BIT_KHR, + .compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR, + .presentMode = supported_present_modes[0], + .clipped = VK_TRUE, + .oldSwapchain = nullptr, + }; VKCHECK(vkCreateSwapchainKHR(device, &create_info, nullptr, &swapchain)) } @@ -294,33 +337,35 @@ void vkdevice::create_swapchain() { // ----------------- vkadapter ----------------- void vkdevice::create_instance() { - VkApplicationInfo app_info = {}; - app_info.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO; - app_info.pApplicationName = "path-tracer"; - app_info.applicationVersion = VK_MAKE_VERSION(1, 0, 0); - app_info.pEngineName = "gpu-path-tracer"; - app_info.engineVersion = VK_MAKE_VERSION(1, 0, 0); - app_info.apiVersion = VK_API_VERSION_1_3; + VkApplicationInfo app_info { + .sType = VK_STRUCTURE_TYPE_APPLICATION_INFO, + .pApplicationName = "path-tracer", + .applicationVersion = VK_MAKE_VERSION(1, 0, 0), + .pEngineName = "gpu-path-tracer", + .engineVersion = VK_MAKE_VERSION(1, 0, 0), + .apiVersion = VK_API_VERSION_1_3, + }; - constexpr const char* instance_layers[] = { + constexpr const char* instance_layers[] { "VK_LAYER_KHRONOS_validation", }; - constexpr const char* instance_extensions[] = { + constexpr const char* instance_extensions[] { VK_EXT_DEBUG_UTILS_EXTENSION_NAME, "VK_KHR_surface", "VK_KHR_win32_surface" }; - VkInstanceCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO; - create_info.pNext = nullptr; - create_info.flags = 0U; - create_info.pApplicationInfo = &app_info; - create_info.enabledLayerCount = sizeof(instance_layers) / sizeof(instance_layers[0]); - create_info.ppEnabledLayerNames = instance_layers; - create_info.enabledExtensionCount = sizeof(instance_extensions) / sizeof(instance_extensions[0]); - create_info.ppEnabledExtensionNames = instance_extensions; + VkInstanceCreateInfo create_info { + .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, + .pNext = nullptr, + .flags = 0U, + .pApplicationInfo = &app_info, + .enabledLayerCount = sizeof(instance_layers) / sizeof(instance_layers[0]), + .ppEnabledLayerNames = instance_layers, + .enabledExtensionCount = sizeof(instance_extensions) / sizeof(instance_extensions[0]), + .ppEnabledExtensionNames = instance_extensions, + }; VKCHECK(vkCreateInstance(&create_info, nullptr, &instance)) @@ -330,56 +375,58 @@ void vkdevice::create_instance() { void vkdevice::create_device() { pick_physical_device(); - VkDeviceQueueCreateInfo queue_create_infos[QueueTypes::MAX] = {}; - float queue_priority = 1.f; - - for (auto index{ 0U }; index < QueueTypes::MAX; index++) { - auto& queue = queues[index]; - auto queue_index = pick_queue(queue.usages); + float queue_priority = 1.f; + VkDeviceQueueCreateInfo queue_create_infos[static_cast<uint32_t>(QueueType::MAX)] { + VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO, + nullptr, + 0U, + 0, + 1, + &queue_priority, + }; - queue_create_infos[index].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; - queue_create_infos[index].pNext = nullptr; - queue_create_infos[index].flags = 0U; - queue_create_infos[index].queueFamilyIndex = 0; - queue_create_infos[index].queueCount = 1; - queue_create_infos[index].pQueuePriorities = &queue_priority; + for (auto index{ 0U }; index < static_cast<uint32_t>(QueueType::MAX); index++) { + auto& queue = queues[index]; + auto queue_index = pick_queue(queue.usages); - queue.index = queue_index; + queue.index = queue_index; } constexpr const char* device_extensions[] = { VK_KHR_SWAPCHAIN_EXTENSION_NAME, }; - VkPhysicalDeviceVulkan12Features physical_device_12_features = {}; - physical_device_12_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_2_FEATURES; - physical_device_12_features.pNext = VK_NULL_HANDLE; - physical_device_12_features.bufferDeviceAddress = VK_TRUE; - physical_device_12_features.runtimeDescriptorArray = VK_TRUE; - physical_device_12_features.shaderStorageImageArrayNonUniformIndexing = VK_TRUE; - physical_device_12_features.shaderSampledImageArrayNonUniformIndexing = VK_TRUE; - physical_device_12_features.descriptorBindingPartiallyBound = VK_TRUE; - physical_device_12_features.descriptorBindingPartiallyBound = VK_TRUE; - physical_device_12_features.descriptorBindingUpdateUnusedWhilePending = VK_TRUE; - physical_device_12_features.imagelessFramebuffer = VK_TRUE; + VkPhysicalDeviceVulkan12Features physical_device_12_features { + .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_2_FEATURES, + .pNext = VK_NULL_HANDLE, + .shaderSampledImageArrayNonUniformIndexing = VK_TRUE, + .shaderStorageImageArrayNonUniformIndexing = VK_TRUE, + .descriptorBindingUpdateUnusedWhilePending = VK_TRUE, + .descriptorBindingPartiallyBound = VK_TRUE, + .runtimeDescriptorArray = VK_TRUE, + .imagelessFramebuffer = VK_TRUE, + .bufferDeviceAddress = VK_TRUE, + }; - VkPhysicalDeviceVulkan13Features physical_device_13_features = {}; - physical_device_13_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_FEATURES; - physical_device_13_features.pNext = &physical_device_12_features; - physical_device_13_features.synchronization2 = VK_TRUE; - physical_device_13_features.dynamicRendering = VK_TRUE; + VkPhysicalDeviceVulkan13Features physical_device_13_features { + .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_FEATURES, + .pNext = &physical_device_12_features, + .synchronization2 = VK_TRUE, + .dynamicRendering = VK_TRUE, + }; - VkDeviceCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO; - create_info.pNext = &physical_device_13_features; - create_info.flags = 0U; - create_info.queueCreateInfoCount = QueueTypes::MAX; - create_info.pQueueCreateInfos = queue_create_infos; - create_info.enabledLayerCount = 0; - create_info.ppEnabledLayerNames = nullptr; - create_info.enabledExtensionCount = sizeof(device_extensions) / sizeof(device_extensions[0]); - create_info.ppEnabledExtensionNames = device_extensions; - create_info.pEnabledFeatures = nullptr; + VkDeviceCreateInfo create_info { + .sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO, + .pNext = &physical_device_13_features, + .flags = 0U, + .queueCreateInfoCount = static_cast<uint32_t>(QueueType::MAX), + .pQueueCreateInfos = queue_create_infos, + .enabledLayerCount = 0, + .ppEnabledLayerNames = nullptr, + .enabledExtensionCount = sizeof(device_extensions) / sizeof(device_extensions[0]), + .ppEnabledExtensionNames = device_extensions, + .pEnabledFeatures = nullptr, + }; VKCHECK(vkCreateDevice(physical_device, &create_info, nullptr, &device)) @@ -393,21 +440,23 @@ void vkdevice::create_device() { } void vkdevice::create_memory_allocator() { - VmaAllocatorCreateInfo create_info = {}; - create_info.flags = VMA_ALLOCATOR_CREATE_BUFFER_DEVICE_ADDRESS_BIT; - create_info.physicalDevice = physical_device; - create_info.device = device; - create_info.instance = instance; - create_info.vulkanApiVersion = VK_API_VERSION_1_2; + VmaAllocatorCreateInfo create_info { + .flags = VMA_ALLOCATOR_CREATE_BUFFER_DEVICE_ADDRESS_BIT, + .physicalDevice = physical_device, + .device = device, + .instance = instance, + .vulkanApiVersion = VK_API_VERSION_1_2, + }; VKCHECK(vmaCreateAllocator(&create_info, &gpu_allocator)) } void vkdevice::create_command_pools() { - VkCommandPoolCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO; - create_info.pNext = nullptr; - create_info.flags = 0U; + VkCommandPoolCreateInfo create_info { + .sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO, + .pNext = nullptr, + .flags = 0U, + }; for (auto& queue : queues) { create_info.queueFamilyIndex = queue.index; @@ -420,7 +469,7 @@ uint32_t vkdevice::pick_queue(VkQueueFlags queue_usages) const { auto queue_properties_count = 0U; vkGetPhysicalDeviceQueueFamilyProperties(physical_device, &queue_properties_count, nullptr); - std::vector<VkQueueFamilyProperties> queue_properties{ queue_properties_count }; + std::vector<VkQueueFamilyProperties> queue_properties { queue_properties_count }; vkGetPhysicalDeviceQueueFamilyProperties(physical_device, &queue_properties_count, queue_properties.data()); for (auto properties_index{ 0U }; properties_index < queue_properties_count; properties_index++) { @@ -439,7 +488,7 @@ void vkdevice::pick_physical_device() { assert(physical_devices_count > 0); - std::vector<VkPhysicalDevice> physical_devices{ physical_devices_count }; + std::vector<VkPhysicalDevice> physical_devices { physical_devices_count }; vkEnumeratePhysicalDevices(instance, &physical_devices_count, physical_devices.data()); for (auto& physical_dev : physical_devices) { @@ -453,18 +502,16 @@ void vkdevice::pick_physical_device() { } bool vkdevice::device_support_features(VkPhysicalDevice physical_dev) { - VkPhysicalDeviceProperties physical_device_properties = {}; - - vkGetPhysicalDeviceProperties(physical_dev, &physical_device_properties); - // Vulkan 1.2 physical device features support { - VkPhysicalDeviceVulkan12Features vulkan_12_features = {}; - vulkan_12_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_2_FEATURES; + VkPhysicalDeviceVulkan12Features vulkan_12_features { + .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_2_FEATURES, + }; - VkPhysicalDeviceFeatures2 physical_device_features = {}; - physical_device_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2; - physical_device_features.pNext = &vulkan_12_features; + VkPhysicalDeviceFeatures2 physical_device_features { + .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2, + .pNext = &vulkan_12_features, + }; vkGetPhysicalDeviceFeatures2(physical_dev, &physical_device_features); @@ -484,12 +531,14 @@ bool vkdevice::device_support_features(VkPhysicalDevice physical_dev) { // Vulkan 1.3 physical device features support { - VkPhysicalDeviceVulkan13Features vulkan_13_features = {}; - vulkan_13_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_FEATURES; + VkPhysicalDeviceVulkan13Features vulkan_13_features { + .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_FEATURES, + }; - VkPhysicalDeviceFeatures2 physical_device_features = {}; - physical_device_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2; - physical_device_features.pNext = &vulkan_13_features; + VkPhysicalDeviceFeatures2 physical_device_features { + .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2, + .pNext = &vulkan_13_features, + }; vkGetPhysicalDeviceFeatures2(physical_dev, &physical_device_features); @@ -503,17 +552,18 @@ bool vkdevice::device_support_features(VkPhysicalDevice physical_dev) { } void vkdevice::create_debug_layer_callback() { - VkDebugUtilsMessengerCreateInfoEXT create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_MESSENGER_CREATE_INFO_EXT; - create_info.pNext = nullptr; - create_info.flags = 0U; - create_info.messageSeverity = VK_DEBUG_UTILS_MESSAGE_SEVERITY_ERROR_BIT_EXT | - VK_DEBUG_UTILS_MESSAGE_SEVERITY_WARNING_BIT_EXT; - create_info.messageType = VK_DEBUG_UTILS_MESSAGE_TYPE_GENERAL_BIT_EXT | - VK_DEBUG_UTILS_MESSAGE_TYPE_PERFORMANCE_BIT_EXT | - VK_DEBUG_UTILS_MESSAGE_TYPE_VALIDATION_BIT_EXT; - create_info.pfnUserCallback = debug_callback; - create_info.pUserData = nullptr; + VkDebugUtilsMessengerCreateInfoEXT create_info { + .sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_MESSENGER_CREATE_INFO_EXT, + .pNext = nullptr, + .flags = 0U, + .messageSeverity = VK_DEBUG_UTILS_MESSAGE_SEVERITY_ERROR_BIT_EXT | + VK_DEBUG_UTILS_MESSAGE_SEVERITY_WARNING_BIT_EXT, + .messageType = VK_DEBUG_UTILS_MESSAGE_TYPE_GENERAL_BIT_EXT | + VK_DEBUG_UTILS_MESSAGE_TYPE_PERFORMANCE_BIT_EXT | + VK_DEBUG_UTILS_MESSAGE_TYPE_VALIDATION_BIT_EXT, + .pfnUserCallback = debug_callback, + .pUserData = nullptr, + }; VKCHECK(vkCreateDebugUtilsMessengerEXT(instance, &create_info, nullptr, &debug_messenger)) } diff --git a/include/api-test/command-buffer.hpp b/include/api-test/command-buffer.hpp new file mode 100644 index 0000000..140a291 --- /dev/null +++ b/include/api-test/command-buffer.hpp @@ -0,0 +1,44 @@ +#pragma once + +#include <cstdint> + +#include <vulkan/vulkan_core.h> + +#include "handle.hpp" + +enum class QueueType : uint32_t { + GRAPHICS, + ASYNC_COMPUTE, + TRANSFER, + MAX, +}; + + +struct device_buffer; +struct device_texture; + +struct command_buffer { + void start() const; + void stop() const; + + void barrier(); + + VkCommandBuffer handle; + QueueType queue_type; +}; + +struct graphics_command_buffer : public command_buffer { + void set_pipeline(); + + void dispatch(); +}; + +struct compute_command_buffer : public command_buffer { + void set_pipeline(); + + void dispatch(); +}; + +struct transfer_command_buffer : public command_buffer { + void copy(::handle<device_buffer> buffer_handle, ::handle<device_texture> texture_handle); +}; diff --git a/include/api-test/handle.hpp b/include/api-test/handle.hpp index 90c1ade..c14e212 100644 --- a/include/api-test/handle.hpp +++ b/include/api-test/handle.hpp @@ -4,5 +4,5 @@ template<typename T> struct handle { - const uint32_t handle; + const uint32_t id; }; diff --git a/include/api-test/vk-command-buffer.hpp b/include/api-test/vk-command-buffer.hpp deleted file mode 100644 index c1f1899..0000000 --- a/include/api-test/vk-command-buffer.hpp +++ /dev/null @@ -1,14 +0,0 @@ -#pragma once - -#include <vulkan/vulkan_core.h> - -class command_buffer { - void start(); - void stop(); - - VkCommandBuffer handle; -}; - -class graphics_command_buffer : command_buffer { - -}; diff --git a/include/api-test/vk-device.hpp b/include/api-test/vk-device.hpp index f931c70..f010cc5 100644 --- a/include/api-test/vk-device.hpp +++ b/include/api-test/vk-device.hpp @@ -8,28 +8,11 @@ #include "freelist.hpp" #include "texture.hpp" #include "buffer.hpp" +#include "command-buffer.hpp" using VmaAllocator = struct VmaAllocator_T*; using VmaAllocation = struct VmaAllocation_T*; -// typedef struct VkInstance_T* VkInstance; -// typedef struct VkDevice_T* VkDevice; -// typedef struct VkPhysicalDevice_T* VkPhysicalDevice; -// typedef struct VkQueue_T* VkQueue; -// typedef uint32_t VkFlags; -// typedef VkFlags VkQueueUsageFlags; -// typedef struct VkImage_T* VkImage; -// typedef struct VkImageView_T* VkImageView; -// typedef struct VkBuffer_T* VkBuffer; -// typedef enum VkImageType VkImageType; -// typedef enum VkFormat VkFormat; -// typedef VkFlags VkImageUsageFlags; -// -// #ifdef _DEBUG -// typedef struct VkDebugUtilsMessengerEXT_T* VkDebugUtilsMessengerEXT; -// #endif // _DEBUG - - struct device_texture { VkImage handle; VkImageView whole_view; @@ -51,6 +34,13 @@ struct device_buffer { class window; class vkdevice { + struct queue { + VkQueue handle; + uint32_t index; + VkQueueFlags usages; + VkCommandPool command_pool; + }; + public: vkdevice(const window& window); @@ -59,18 +49,25 @@ public: handle<device_buffer> create_buffer(const buffer_desc& desc); + template<typename cmd_buf_type> + void allocate_command_buffers(cmd_buf_type* buffers, size_t count, QueueType queue_type) { + allocate_command_buffers(buffers, count, queue_type); + } + const device_texture& get_texture(handle<device_texture> handle) { - return textures[handle.handle]; + return textures[handle.id]; } const device_buffer& get_buffer(handle<device_buffer> handle) { - return buffers[handle.handle]; + return buffers[handle.id]; } - void submit(/*std::span<command_buffer>*/); + void submit(command_buffer* buffers, size_t count); private: + void allocate_command_buffers(command_buffer* buffers, size_t count, QueueType type); + void create_views(device_texture& texture); void create_surface(const window& window); @@ -98,29 +95,19 @@ private: void create_debug_layer_callback(); - enum QueueTypes : uint32_t { - GRAPHICS, - // COPY, - MAX, - }; - - struct queue { - VkQueue handle; - uint32_t index; - VkQueueFlags usages; - VkCommandPool command_pool; - }; + queue queues[static_cast<uint32_t>(QueueType::MAX)]; - queue queues[QueueTypes::MAX]; + VkInstance instance; + VkPhysicalDevice physical_device; + VkDevice device; - VkInstance instance; - VkPhysicalDevice physical_device; - VkDevice device; + VmaAllocator gpu_allocator; - VmaAllocator gpu_allocator; + static constexpr size_t max_allocable_command_buffers = 16; + static constexpr size_t max_submitable_command_buffers = 16; #ifdef _DEBUG - VkDebugUtilsMessengerEXT debug_messenger; + VkDebugUtilsMessengerEXT debug_messenger; #endif // _DEBUG freelist<device_texture> textures; diff --git a/include/resource-manager.hpp b/include/resource-manager.hpp deleted file mode 100644 index 2a8a787..0000000 --- a/include/resource-manager.hpp +++ /dev/null @@ -1,6 +0,0 @@ -#pragma once - -class resourcemanager { - public: - static const resourcemanager resource_manager; -}; diff --git a/include/texture.hpp b/include/texture.hpp new file mode 100644 index 0000000..aac7b69 --- /dev/null +++ b/include/texture.hpp @@ -0,0 +1,83 @@ +#include <cstdint> + +using VkImage = struct VkImage_T*; + +struct TextureDesc { + VkImageType type; + VkFormat format; + VkExtent size; + VkImageUsageFlags usages; +}; + +class Texture { + public: + Texture(const TextureDesc desc) + : description(desc) { + create_device_image(); + } + + // Texture(handle image_handle) { + // const auto& image = vkrenderer::api.get_image(image_handle); + // width = image.size.width; + // height = image.size.height; + // depth = image.size.depth; + + // device_image = image_handle; + // } + + // Texture(size_t width, size_t height, size_t depth, VkFormat format = VK_FORMAT_R8G8B8A8_UNORM, Sampler* texture_sampler = nullptr) + // : width(width), height(height), depth(depth) { + // sampler = texture_sampler; + // device_image = vkrenderer::api.create_image( + // { .width = (uint32_t)width, .height = (uint32_t)height, .depth = 1 }, + // format, + // VK_IMAGE_USAGE_STORAGE_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_SAMPLED_BIT); + // } + + void update(void* new_data) { + if (data == nullptr) { + free(data); + } + data = new_data; + + vkrenderer::queue_image_update(this); + } + + ~Texture() { + vkrenderer::api.destroy_image(device_image); + + if (data == nullptr) { + free(data); + } + } + + [[nodiscard]] size_t size() const { + const auto& image = vkrenderer::api.get_image(device_image); + return width * height * depth * pixel_size(image.format); + } + + static size_t pixel_size(VkFormat format) { + switch (format) { + case VK_FORMAT_R8G8B8A8_UNORM: + return 4; + default: + return 0; + } + } + + // Sampler* sampler = nullptr; + + private: + void create_device_image(); + + void* data = nullptr; + + size_t width = 0; + size_t height = 0; + size_t depth = 0; + + TextureDesc description; + + VmaAllocationInfo alloc_info; + VkImage device_image; +}; diff --git a/include/vec3.hpp b/include/vec3.hpp index 6513ce8..2fec69e 100644 --- a/include/vec3.hpp +++ b/include/vec3.hpp @@ -4,7 +4,7 @@ #include <xmmintrin.h> class vec3 { - public: + public: vec3(); vec3(float x); @@ -12,7 +12,7 @@ class vec3 { vec3(__m128& v); vec3(__m128&& v); vec3(const vec3& vec); - vec3(const vec3&& vec); + vec3(const vec3&& vec) noexcept; vec3 operator-() const; @@ -26,21 +26,21 @@ class vec3 { float operator[](int axis); - float length() const; + [[nodiscard]] float length() const; - float length_sq() const; + [[nodiscard]] float length_sq() const; - float dot(const vec3& vec) const; + [[nodiscard]] float dot(const vec3& vec) const; - vec3 cross(const vec3& vec) const; + [[nodiscard]] vec3 cross(const vec3& vec) const; - vec3 min(const vec3& vec) const; + [[nodiscard]] vec3 min(const vec3& vec) const; - vec3 max(const vec3& vec) const; + [[nodiscard]] vec3 max(const vec3& vec) const; vec3& normalize(); - bool near_zero() const; + [[nodiscard]] bool near_zero() const; void print() const; @@ -72,4 +72,4 @@ vec3 refract(const vec3& uv, const vec3& n, float etai_over_etat); using point3 = vec3; using color = vec3; -#endif // !__VEC3_HPP_ +#endif // !_ diff --git a/include/vk-api.hpp b/include/vk-api.hpp index b50e751..a3442f1 100644 --- a/include/vk-api.hpp +++ b/include/vk-api.hpp @@ -1,71 +1,70 @@ #ifndef __VK_API_HPP_ #define __VK_API_HPP_ -#include <vector> #include <cassert> +#include <vector> -#include "vulkan-loader.hpp" +#include <vulkan/vulkan_core.h> using VmaAllocation = struct VmaAllocation_T*; struct buffer { - VmaAllocation alloc; - void* device_ptr; - VkBuffer handle; - size_t size; - VkDeviceAddress device_address; + VmaAllocation alloc; + void* device_ptr; + VkBuffer handle; + size_t size; + VkDeviceAddress device_address; }; struct pipeline { std::vector<VkShaderModule> shader_modules; - VkPipeline handle = VK_NULL_HANDLE; - VkPipelineBindPoint bind_point; + VkPipeline handle = VK_NULL_HANDLE; + VkPipelineBindPoint bind_point; }; using bindless_index = uint32_t; using handle = uint32_t; struct image { - VkImage handle; - VkImageView view; - VmaAllocation alloc; - void* device_ptr; + VkImage handle; + VkImageView view; + VmaAllocation alloc; VkImageSubresourceRange subresource_range; - VkFormat format; - VkExtent3D size; - VkImageUsageFlags usages; - bindless_index bindless_storage_index = 0; - bindless_index bindless_sampled_index = 0; + VkFormat format; + VkExtent3D size; + VkImageUsageFlags usages; + bindless_index bindless_storage_index = 0; + bindless_index bindless_sampled_index = 0; - VkImageLayout previous_layout = VK_IMAGE_LAYOUT_UNDEFINED; - VkPipelineStageFlags previous_stage = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT; - VkAccessFlags previous_access = 0; + VkImageLayout previous_layout = VK_IMAGE_LAYOUT_UNDEFINED; + VkPipelineStageFlags previous_stage = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT; + VkAccessFlags previous_access = 0; }; struct swapchain { - uint32_t image_count; - std::vector<handle> images; - VkSwapchainKHR handle; - VkSurfaceFormatKHR surface_format; - VkExtent2D extent; + uint32_t image_count; + std::vector<handle> images; + VkSwapchainKHR handle; + VkSurfaceFormatKHR surface_format; + VkExtent2D extent; }; struct framebuffer { - VkFramebuffer handle; - VkExtent2D size; + VkFramebuffer handle; + VkExtent2D size; }; struct sampler { - VkSampler handle; - bindless_index bindless_index; + VkSampler handle; + bindless_index bindless_index; }; struct global_descriptor { - VkDescriptorSetLayout set_layout; - VkPipelineLayout pipeline_layout; - VkDescriptorSet set; + VkDescriptorSetLayout set_layout; + VkPipelineLayout pipeline_layout; + VkDescriptorSet set; - std::vector<uint32_t> index_pool[3]; + std::vector<uint32_t> index_pool[3]; static constexpr uint32_t pool_size = 1024U; @@ -78,7 +77,7 @@ struct global_descriptor { } uint32_t allocate(VkDescriptorType type) { - auto &pool = index_pool[descriptor_type_binding(type)]; + auto& pool = index_pool[descriptor_type_binding(type)]; auto index = pool.back(); pool.pop_back(); @@ -91,16 +90,16 @@ struct global_descriptor { } static int32_t descriptor_type_binding(VkDescriptorType type) { - switch(type) { - case VK_DESCRIPTOR_TYPE_SAMPLER: - return 0; - case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE: - return 1; - case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE: - return 2; - default: - assert(true && "descriptor type not supported"); - return -1; + switch (type) { + case VK_DESCRIPTOR_TYPE_SAMPLER: + return 0; + case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE: + return 1; + case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE: + return 2; + default: + assert(true && "descriptor type not supported"); + return -1; } } }; @@ -110,111 +109,111 @@ class vkcontext; class vkapi { public: - vkapi(vkcontext& context); - ~vkapi(); + vkapi(vkcontext& context); + ~vkapi(); - handle create_buffer(size_t data_size, VkBufferUsageFlags buffer_usage, uint32_t mem_usage); - void copy_buffer(VkCommandBuffer cmd_buf, handle src, handle dst, size_t size); - void copy_buffer(VkCommandBuffer cmd_buf, handle src, handle dst, size_t size, size_t buffer_offset = 0); - void destroy_buffer(handle buffer); + handle create_buffer(size_t data_size, VkBufferUsageFlags buffer_usage, uint32_t mem_usage); + void copy_buffer(VkCommandBuffer cmd_buf, handle src, handle dst, size_t size); + void copy_buffer(VkCommandBuffer cmd_buf, handle src, handle dst, size_t size, size_t buffer_offset = 0); + void destroy_buffer(handle buffer); - handle create_image(VkExtent3D size, VkFormat format, VkImageUsageFlags usages); - void destroy_image(handle image); - std::vector<handle> create_images(VkExtent3D size, VkFormat format, VkImageUsageFlags usages, size_t image_count); - void destroy_images(std::vector<handle>& imgs); + handle create_image(VkExtent3D size, VkFormat format, VkImageUsageFlags usages); + void destroy_image(handle image); + std::vector<handle> create_images(VkExtent3D size, VkFormat format, VkImageUsageFlags usages, size_t image_count); + void destroy_images(std::vector<handle>& imgs); - [[nodiscard]] VkFence create_fence() const; - void destroy_fence(VkFence fence) const; - [[nodiscard]] std::vector<VkFence> create_fences(size_t fences_count) const; - void destroy_fences(VkFence fences[], size_t fences_count) const; + [[nodiscard]] VkFence create_fence() const; + void destroy_fence(VkFence fence) const; + [[nodiscard]] std::vector<VkFence> create_fences(size_t fences_count) const; + void destroy_fences(VkFence fences[], size_t fences_count) const; - [[nodiscard]] VkSemaphore create_semaphore() const; - void destroy_semaphore(VkSemaphore semaphore) const; - [[nodiscard]] std::vector<VkSemaphore> create_semaphores(size_t semaphores_count) const; - void destroy_semaphores(VkSemaphore semaphores[], size_t semaphores_count) const; + [[nodiscard]] VkSemaphore create_semaphore() const; + void destroy_semaphore(VkSemaphore semaphore) const; + [[nodiscard]] std::vector<VkSemaphore> create_semaphores(size_t semaphores_count) const; + void destroy_semaphores(VkSemaphore semaphores[], size_t semaphores_count) const; - handle create_sampler(VkFilter filter, VkSamplerAddressMode address_mode); - void destroy_sampler(handle sampler); + handle create_sampler(VkFilter filter, VkSamplerAddressMode address_mode); + void destroy_sampler(handle sampler); - [[nodiscard]] VkCommandPool create_command_pool() const; + [[nodiscard]] VkCommandPool create_command_pool() const; - void allocate_command_buffers(VkCommandPool command_pool, VkCommandBuffer* command_buffers, size_t count) const; + void allocate_command_buffers(VkCommandPool command_pool, VkCommandBuffer* command_buffers, size_t count) const; - VkRenderPass create_render_pass(std::vector<VkFormat>& color_attachments_format, VkImageLayout initial_layout, VkImageLayout final_layout); - VkRenderPass create_render_pass(std::vector<VkFormat>& color_attachments_format, VkFormat depth_attachement_format); - void destroy_render_pass(VkRenderPass render_pass); + VkRenderPass create_render_pass(std::vector<VkFormat>& color_attachments_format, VkImageLayout initial_layout, VkImageLayout final_layout); + VkRenderPass create_render_pass(std::vector<VkFormat>& color_attachments_format, VkFormat depth_attachement_format); + void destroy_render_pass(VkRenderPass render_pass); - framebuffer create_framebuffer(VkRenderPass render_pass, std::vector<VkFormat>& formats, VkExtent2D size); - std::vector<framebuffer> create_framebuffers(VkRenderPass render_pass, std::vector<VkFormat>& formats, VkExtent2D size, uint32_t framebuffer_count); - void destroy_framebuffer(framebuffer framebuffer) const; - void destroy_framebuffers(std::vector<framebuffer>& framebuffers) const; + framebuffer create_framebuffer(VkRenderPass render_pass, std::vector<VkFormat>& formats, VkExtent2D size); + std::vector<framebuffer> create_framebuffers(VkRenderPass render_pass, std::vector<VkFormat>& formats, VkExtent2D size, uint32_t framebuffer_count); + void destroy_framebuffer(framebuffer framebuffer) const; + void destroy_framebuffers(std::vector<framebuffer>& framebuffers) const; - pipeline create_compute_pipeline(const char* shader_name) const; - pipeline create_graphics_pipeline(const char* shader_name, VkShaderStageFlagBits shader_stages, VkRenderPass render_pass, std::vector<VkDynamicState>& dynamic_states) const; - void destroy_pipeline(pipeline &pipeline) const; + pipeline create_compute_pipeline(const char* shader_name) const; + pipeline create_graphics_pipeline(const char* shader_name, VkShaderStageFlagBits shader_stages, VkRenderPass render_pass, std::vector<VkDynamicState>& dynamic_states) const; + void destroy_pipeline(pipeline& pipeline) const; - VkSurfaceKHR create_surface(window& wnd) const; - void destroy_surface(VkSurfaceKHR surface); + VkSurfaceKHR create_surface(window& wnd) const; + void destroy_surface(VkSurfaceKHR surface); - swapchain create_swapchain(VkSurfaceKHR surface, size_t min_image_count, VkImageUsageFlags usages, VkSwapchainKHR old_swapchain); - void destroy_swapchain(swapchain& swapchain); + swapchain create_swapchain(VkSurfaceKHR surface, size_t min_image_count, VkImageUsageFlags usages, VkSwapchainKHR old_swapchain); + void destroy_swapchain(swapchain& swapchain); - void update_descriptor_image(handle img, VkDescriptorType type); - void update_descriptor_images(std::vector<handle> &images, VkDescriptorType type); - void update_descriptor_sampler(handle sampler); - void update_descriptor_samplers(std::vector<handle> &samplers); + void update_descriptor_image(handle img, VkDescriptorType type); + void update_descriptor_images(std::vector<handle>& images, VkDescriptorType type); + void update_descriptor_sampler(handle sampler); + void update_descriptor_samplers(std::vector<handle>& samplers); - void update_constants(VkCommandBuffer command_buffer, VkShaderStageFlagBits shader_stage, off_t offset, size_t size, void* data); + void update_constants(VkCommandBuffer command_buffer, VkShaderStageFlagBits shader_stage, off_t offset, size_t size, void* data); - void start_record(VkCommandBuffer command_buffer); + void start_record(VkCommandBuffer command_buffer); - void image_barrier(VkCommandBuffer command_buffer, VkImageLayout dst_layout, VkPipelineStageFlagBits dst_stage, VkAccessFlags dst_access, handle image); + void image_barrier(VkCommandBuffer command_buffer, VkImageLayout dst_layout, VkPipelineStageFlagBits dst_stage, VkAccessFlags dst_access, handle image); - void begin_render_pass(VkCommandBuffer command_buffer, VkRenderPass render_pass, std::vector<VkImageView>& attachments, framebuffer framebuffer, VkExtent2D size); - void end_render_pass(VkCommandBuffer command_buffer); + void begin_render_pass(VkCommandBuffer command_buffer, VkRenderPass render_pass, std::vector<VkImageView>& attachments, framebuffer framebuffer, VkExtent2D size); + void end_render_pass(VkCommandBuffer command_buffer); - void run_compute_pipeline(VkCommandBuffer command_buffer, pipeline& pipeline, size_t group_count_x, size_t group_count_y, size_t group_count_z); + void run_compute_pipeline(VkCommandBuffer command_buffer, pipeline& pipeline, size_t group_count_x, size_t group_count_y, size_t group_count_z); - void draw(VkCommandBuffer command_buffer, pipeline& pipeline, uint32_t vertex_count, uint32_t vertex_offset); - void draw(VkCommandBuffer command_buffer, pipeline& pipeline, handle index_buffer, uint32_t primitive_count, uint32_t indices_offset, uint32_t vertices_offset); + void draw(VkCommandBuffer command_buffer, pipeline& pipeline, uint32_t vertex_count, uint32_t vertex_offset); + void draw(VkCommandBuffer command_buffer, pipeline& pipeline, handle index_buffer, uint32_t primitive_count, uint32_t indices_offset, uint32_t vertices_offset); - void blit_full(VkCommandBuffer command_buffer, handle src_image, handle dst_image); + void blit_full(VkCommandBuffer command_buffer, handle src_image, handle dst_image); - void end_record(VkCommandBuffer command_buffer); + void end_record(VkCommandBuffer command_buffer); - VkResult submit(VkCommandBuffer command_buffers[], size_t command_buffers_count, VkSemaphore wait_semaphore, VkSemaphore signal_semaphore, VkFence submission_fence) const; + VkResult submit(VkCommandBuffer command_buffers[], size_t command_buffers_count, VkSemaphore wait_semaphore, VkSemaphore signal_semaphore, VkFence submission_fence) const; - VkResult present(swapchain& swapchain, uint32_t image_index, VkSemaphore wait_semaphore) const; + VkResult present(swapchain& swapchain, uint32_t image_index, VkSemaphore wait_semaphore) const; - const buffer& get_buffer(handle buffer_handle) { return *buffers[buffer_handle]; }; - const image& get_image(handle image_handle) { return *images[image_handle]; }; - const sampler& get_sampler(handle sampler_handle) { return *samplers[sampler_handle]; }; + const buffer& get_buffer(handle buffer_handle) { return *buffers[buffer_handle]; }; - vkcontext& context; + const image& get_image(handle image_handle) { return *images[image_handle]; }; - private: + const sampler& get_sampler(handle sampler_handle) { return *samplers[sampler_handle]; }; - global_descriptor bindless_descriptor; + vkcontext& context; - static const char* shader_stage_extension(VkShaderStageFlags shader_stage); + private: + global_descriptor bindless_descriptor; - // TODO: Use freelists instead - std::vector<buffer*> buffers; - std::vector<image*> images; - std::vector<sampler*> samplers; + static const char* shader_stage_extension(VkShaderStageFlags shader_stage); - VkDescriptorPool descriptor_pool; + // TODO: Use freelists instead + std::vector<buffer*> buffers; + std::vector<image*> images; + std::vector<sampler*> samplers; + VkDescriptorPool descriptor_pool; }; #endif // !__VK_API_HPP_ diff --git a/include/vk-context.hpp b/include/vk-context.hpp index 58d7ce9..0dfd256 100644 --- a/include/vk-context.hpp +++ b/include/vk-context.hpp @@ -1,6 +1,6 @@ #pragma once -#include "vulkan-loader.hpp" +#include <vulkan/vulkan_core.h> using VmaAllocator = struct VmaAllocator_T*; diff --git a/include/vk-renderer.hpp b/include/vk-renderer.hpp index ab15cd1..1317912 100644 --- a/include/vk-renderer.hpp +++ b/include/vk-renderer.hpp @@ -61,8 +61,6 @@ class vkrenderer { static Buffer* create_staging_buffer(size_t size); - static Texture* create_2d_texture(size_t width, size_t height, VkFormat format, Sampler *sampler = nullptr); - static Sampler* create_sampler(VkFilter filter, VkSamplerAddressMode address_mode); @@ -163,67 +161,4 @@ class Sampler { handle device_sampler; }; -class Texture { - public: - - Texture(handle image_handle) { - const auto &image = vkrenderer::api.get_image(image_handle); - width = image.size.width; - height = image.size.height; - depth = image.size.depth; - - device_image = image_handle; - } - - Texture(size_t width, size_t height, size_t depth, VkFormat format = VK_FORMAT_R8G8B8A8_UNORM, Sampler* texture_sampler = nullptr) - : width(width), height(height), depth(depth) { - sampler = texture_sampler; - device_image = vkrenderer::api.create_image( - { .width = (uint32_t)width, .height = (uint32_t)height, .depth = 1 }, - format, - VK_IMAGE_USAGE_STORAGE_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_SAMPLED_BIT - ); - } - - void update(void* new_data) { - if (data == nullptr) { - free(data); - } - data = new_data; - - vkrenderer::queue_image_update(this); - } - - ~Texture() { - vkrenderer::api.destroy_image(device_image); - - if (data == nullptr) { - free(data); - } - } - - [[nodiscard]]size_t size() const { - const auto& image = vkrenderer::api.get_image(device_image); - return width * height * depth * pixel_size(image.format); - } - - static size_t pixel_size(VkFormat format) { - switch (format) { - case VK_FORMAT_R8G8B8A8_UNORM: - return 4; - default: - return 0; - } - } - - Sampler* sampler = nullptr; - - void* data = nullptr; - - size_t width = 0; - size_t height = 0; - size_t depth = 0; - - handle device_image; -}; #endif // !__VK_RENDERER_HPP_ diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 54a4c54..1f514f0 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -29,6 +29,7 @@ add_executable( primitive-renderpass.cpp bvh.cpp mesh.cpp + resource-manager.cpp ) if("${CMAKE_CXX_COMPILER_ID}" STREQUAL "Clang") @@ -58,8 +59,9 @@ target_compile_definitions(path-tracer PUBLIC ${DEFINES}) target_include_directories(path-tracer SYSTEM PUBLIC ${CMAKE_SOURCE_DIR}/thirdparty) +target_include_directories(path-tracer SYSTEM PUBLIC ${Vulkan_INCLUDE_DIRS}) + target_include_directories(path-tracer PUBLIC ${CMAKE_SOURCE_DIR}/include) -target_include_directories(path-tracer PUBLIC ${Vulkan_INCLUDE_DIRS}) if(UNIX AND NOT APPLE) target_include_directories(path-tracer PUBLIC ${X11_xcb_INCLUDE_PATH}) diff --git a/src/main.cpp b/src/main.cpp index 805a0b4..1acf2fb 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -320,7 +320,7 @@ int main() { main_scene.meta.cam.set_aspect_ratio((float)event.width / (float)event.height); delete accumulation_texture; - delete output_texture; + delete output_texture); accumulation_texture = vkrenderer::create_2d_texture(event.width, event.height, VK_FORMAT_R32G32B32A32_SFLOAT); output_texture = vkrenderer::create_2d_texture(event.width, event.height, VK_FORMAT_R32G32B32A32_SFLOAT); raytracing_pass->set_dispatch_size(event.width / 8 + 1, event.height / 8 + 1, 1); diff --git a/src/resource-manager.cpp b/src/resource-manager.cpp index e0b00aa..067107d 100644 --- a/src/resource-manager.cpp +++ b/src/resource-manager.cpp @@ -1,2 +1,8 @@ -#include "resourcemanager.hpp" -static const resour +#include "resource-manager.hpp" + +const auto ResourceManager::resource_manager = ResourceManager(); + +Handle<Texture> ResourceManager::create_texture(const TextureDesc &desc) { + textures.add({}); + return { 0 }; +} diff --git a/src/scene.cpp b/src/scene.cpp index f560d03..9980e75 100644 --- a/src/scene.cpp +++ b/src/scene.cpp @@ -142,24 +142,24 @@ scene::scene(const camera& cam, uint32_t width, uint32_t height) indices[triangle_offset + 2] = (submesh_level_index_3 + vertex_offset) | (0xff000000 & (materials.size() << 24));
}
- const auto& albedo_image = vkrenderer::api.get_image(material.base_color_texture->device_image);
- const auto& albedo_sampler = vkrenderer::api.get_sampler(material.base_color_texture->sampler->device_sampler);
+// const auto& albedo_image = vkrenderer::api.get_image(material.base_color_texture->device_image);
+// const auto& albedo_sampler = vkrenderer::api.get_sampler(material.base_color_texture->sampler->device_sampler);
materials.emplace_back(gpu_material {
.base_color = material.base_color,
- .albedo_texture_id = albedo_image.bindless_sampled_index,
- .albedo_texture_sampler_id = albedo_sampler.bindless_index,
+// .albedo_texture_id = albedo_image.bindless_sampled_index,
+// .albedo_texture_sampler_id = albedo_sampler.bindless_index,
.metalness = material.metalness,
.roughness = material.roughness
});
if (material.metallic_roughness_texture != nullptr) {
auto& gpu_material = materials.back();
- const auto& metallic_roughness_image = vkrenderer::api.get_image(material.metallic_roughness_texture->device_image);
- const auto& metallic_roughness_sampler = vkrenderer::api.get_sampler(material.metallic_roughness_texture->sampler->device_sampler);
+// const auto& metallic_roughness_image = vkrenderer::api.get_image(material.metallic_roughness_texture->device_image);
+// const auto& metallic_roughness_sampler = vkrenderer::api.get_sampler(material.metallic_roughness_texture->sampler->device_sampler);
- gpu_material.metallic_roughness_texture_id = metallic_roughness_image.bindless_sampled_index;
- gpu_material.metallic_roughness_texture_sampler_id = metallic_roughness_sampler.bindless_index;
+// gpu_material.metallic_roughness_texture_id = metallic_roughness_image.bindless_sampled_index;
+// gpu_material.metallic_roughness_texture_sampler_id = metallic_roughness_sampler.bindless_index;
}
}
diff --git a/src/vec3.cpp b/src/vec3.cpp index 1bd068f..0e08f16 100644 --- a/src/vec3.cpp +++ b/src/vec3.cpp @@ -6,38 +6,41 @@ #include "vec3.hpp" vec3::vec3() : v(_mm_setzero_ps()) {} + vec3::vec3(float x) : v(_mm_set1_ps(x)) {} + vec3::vec3(float x, float y, float z) : v(_mm_set_ps(0.f, z, y, x)) {} -vec3::vec3(__m128 &v) : v(v) {} -vec3::vec3(__m128 &&v) : v(v) {} +vec3::vec3(__m128& v) : v(v) {} -vec3::vec3(const vec3 &vec) { v = _mm_load_ps((float *)&vec.v); } +vec3::vec3(__m128&& v) : v(v) {} -vec3::vec3(const vec3 &&vec) { v = _mm_load_ps((float *)&vec.v); } +vec3::vec3(const vec3& vec) { v = _mm_load_ps((float*)&vec.v); } + +vec3::vec3(const vec3&& vec) noexcept { v = _mm_load_ps((float*)&vec.v); } vec3 vec3::operator-() const { return { _mm_xor_ps(v, _mm_set1_ps(-0.0f)) }; } -vec3 &vec3::operator=(const vec3 &vec) { - v = _mm_load_ps((float *)&vec.v); +vec3& vec3::operator=(const vec3& vec) { + v = _mm_load_ps((float*)&vec.v); return *this; } -vec3 &vec3::operator+=(const vec3 &vec) { +vec3& vec3::operator+=(const vec3& vec) { v = _mm_add_ps(v, vec.v); return *this; } -vec3 &vec3::operator*=(float scale) { +vec3& vec3::operator*=(float scale) { __m128 s = _mm_set1_ps(scale); v = _mm_mul_ps(v, s); return *this; } -vec3 &vec3::operator/=(float numerator) { +vec3& vec3::operator/=(float numerator) { __m128 s = _mm_set1_ps(numerator); v = _mm_div_ps(v, s); @@ -45,7 +48,9 @@ vec3 &vec3::operator/=(float numerator) { } float vec3::operator[](const int axis) { - if (axis > 2) { return std::numeric_limits<float>::infinity(); } + if (axis > 2) { + return std::numeric_limits<float>::infinity(); + } return v[axis]; } @@ -57,9 +62,9 @@ float vec3::length() const { float vec3::length_sq() const { return (_mm_dp_ps(v, v, 0b11110001))[0]; } -float vec3::dot(const vec3 &vec) const { return (_mm_dp_ps(v, vec.v, 0b11110001))[0]; } +float vec3::dot(const vec3& vec) const { return (_mm_dp_ps(v, vec.v, 0b11110001))[0]; } -vec3 vec3::cross(const vec3 &vec) const { +vec3 vec3::cross(const vec3& vec) const { __m128 tmp0 = _mm_shuffle_ps(v, v, _MM_SHUFFLE(3, 0, 2, 1)); __m128 tmp1 = _mm_shuffle_ps(vec.v, vec.v, _MM_SHUFFLE(3, 1, 0, 2)); __m128 tmp2 = _mm_mul_ps(tmp0, vec.v); @@ -68,15 +73,15 @@ vec3 vec3::cross(const vec3 &vec) const { return _mm_sub_ps(tmp3, tmp4); } -vec3 vec3::min(const vec3 &vec) const { +vec3 vec3::min(const vec3& vec) const { return { _mm_min_ps(v, vec.v) }; } -vec3 vec3::max(const vec3 &vec) const { +vec3 vec3::max(const vec3& vec) const { return { _mm_max_ps(v, vec.v) }; } -vec3 &vec3::normalize() { +vec3& vec3::normalize() { v = _mm_div_ps(v, _mm_sqrt_ps(_mm_dp_ps(v, v, 0xff))); return *this; @@ -96,36 +101,35 @@ vec3 vec3::random() { return { randd(), randd(), randd() }; } vec3 vec3::random(float min, float max) { return { randd(min, max), randd(min, max), randd(min, max) }; } - // TODO: Use simd instructions -vec3 lerp(const vec3 &u, const vec3 &v, float t) { return (1.f - t) * u + t * v; } +vec3 lerp(const vec3& u, const vec3& v, float t) { return (1.f - t) * u + t * v; } -vec3 operator+(const vec3 &u, const vec3 &v) { return vec3(_mm_add_ps(u.v, v.v)); } +vec3 operator+(const vec3& u, const vec3& v) { return vec3(_mm_add_ps(u.v, v.v)); } -vec3 operator-(const vec3 &u, const vec3 &v) { return vec3(_mm_sub_ps(u.v, v.v)); } +vec3 operator-(const vec3& u, const vec3& v) { return vec3(_mm_sub_ps(u.v, v.v)); } -vec3 operator*(const vec3 &u, const vec3 &v) { return vec3(_mm_mul_ps(u.v, v.v)); } +vec3 operator*(const vec3& u, const vec3& v) { return vec3(_mm_mul_ps(u.v, v.v)); } -vec3 operator*(const vec3 &u, float scale) { +vec3 operator*(const vec3& u, float scale) { __m128 s = _mm_set1_ps(scale); return vec3(_mm_mul_ps(u.v, s)); } -vec3 operator*(float scale, const vec3 &u) { +vec3 operator*(float scale, const vec3& u) { __m128 s = _mm_set1_ps(scale); return vec3(_mm_mul_ps(u.v, s)); } -vec3 operator/(const vec3 &u, float scale) { +vec3 operator/(const vec3& u, float scale) { __m128 s = _mm_set1_ps(scale); return vec3(_mm_div_ps(u.v, s)); } // TODO: Use simd instructions -vec3 reflect(const vec3 &v, const vec3 &n) { return v - 2 * v.dot(n) * n; } +vec3 reflect(const vec3& v, const vec3& n) { return v - 2 * v.dot(n) * n; } // TODO: Use simd instructions -vec3 refract(const vec3 &uv, const vec3 &n, float etai_over_etat) { +vec3 refract(const vec3& uv, const vec3& n, float etai_over_etat) { auto cos_theta = fmin(n.dot(-uv), 1.f); vec3 r_out_perp = etai_over_etat * (uv + cos_theta * n); vec3 r_out_parallel = -sqrt(fabs(1.f - r_out_perp.length_sq())) * n; diff --git a/src/vk-api.cpp b/src/vk-api.cpp index 60ab6d4..f0d21de 100644 --- a/src/vk-api.cpp +++ b/src/vk-api.cpp @@ -1,13 +1,13 @@ #include "vk-api.hpp" -#include <filesystem> #include <cassert> +#include <filesystem> #include <vk_mem_alloc.h> -#include "window.hpp" #include "utils.hpp" #include "vk-context.hpp" +#include "window.hpp" #include "vulkan-loader.hpp" @@ -19,89 +19,88 @@ vkapi::vkapi(vkcontext& context) - : context(context) { + : context(context) { VkDescriptorPoolSize descriptor_pools_sizes[] = { { - .type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, - .descriptorCount = (uint32_t)global_descriptor::pool_size, + .type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, + .descriptorCount = (uint32_t)global_descriptor::pool_size, }, { - .type = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, - .descriptorCount = (uint32_t)global_descriptor::pool_size, + .type = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, + .descriptorCount = (uint32_t)global_descriptor::pool_size, }, { - .type = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, - .descriptorCount = (uint32_t)global_descriptor::pool_size, + .type = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, + .descriptorCount = (uint32_t)global_descriptor::pool_size, }, { - .type = VK_DESCRIPTOR_TYPE_SAMPLER, - .descriptorCount = (uint32_t)global_descriptor::pool_size, + .type = VK_DESCRIPTOR_TYPE_SAMPLER, + .descriptorCount = (uint32_t)global_descriptor::pool_size, } }; - VkDescriptorPoolCreateInfo descriptor_pool_create_info = {}; - descriptor_pool_create_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO; - descriptor_pool_create_info.pNext = nullptr; - descriptor_pool_create_info.flags = VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT; - descriptor_pool_create_info.maxSets = 0xff; - descriptor_pool_create_info.poolSizeCount = sizeof(descriptor_pools_sizes) / sizeof(descriptor_pools_sizes[0]); - descriptor_pool_create_info.pPoolSizes = descriptor_pools_sizes; + VkDescriptorPoolCreateInfo descriptor_pool_create_info = {}; + descriptor_pool_create_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO; + descriptor_pool_create_info.pNext = nullptr; + descriptor_pool_create_info.flags = VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT; + descriptor_pool_create_info.maxSets = 0xff; + descriptor_pool_create_info.poolSizeCount = sizeof(descriptor_pools_sizes) / sizeof(descriptor_pools_sizes[0]); + descriptor_pool_create_info.pPoolSizes = descriptor_pools_sizes; VKRESULT(vkCreateDescriptorPool(context.device, &descriptor_pool_create_info, nullptr, &descriptor_pool)) // Global descriptor - VkDescriptorSetLayoutBinding bindless_layout_bindings[] = { - { - .binding = 0, - .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER, - .descriptorCount = global_descriptor::pool_size, - .stageFlags = VK_SHADER_STAGE_ALL, - }, - { - .binding = 1, - .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, - .descriptorCount = global_descriptor::pool_size, - .stageFlags = VK_SHADER_STAGE_ALL, - }, - { - .binding = 2, - .descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, - .descriptorCount = global_descriptor::pool_size, - .stageFlags = VK_SHADER_STAGE_ALL, - }, + VkDescriptorSetLayoutBinding bindless_layout_bindings[] = { + { + .binding = 0, + .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER, + .descriptorCount = global_descriptor::pool_size, + .stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT, + }, + { + .binding = 1, + .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, + .descriptorCount = global_descriptor::pool_size, + .stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT, + }, + { + .binding = 2, + .descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, + .descriptorCount = global_descriptor::pool_size, + .stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT, + }, }; - VkDescriptorBindingFlags flags[] = { - VK_DESCRIPTOR_BINDING_PARTIALLY_BOUND_BIT | VK_DESCRIPTOR_BINDING_UPDATE_UNUSED_WHILE_PENDING_BIT, - VK_DESCRIPTOR_BINDING_PARTIALLY_BOUND_BIT | VK_DESCRIPTOR_BINDING_UPDATE_UNUSED_WHILE_PENDING_BIT, + VkDescriptorBindingFlags flags[3] = { VK_DESCRIPTOR_BINDING_PARTIALLY_BOUND_BIT | VK_DESCRIPTOR_BINDING_UPDATE_UNUSED_WHILE_PENDING_BIT, }; + VkDescriptorSetLayoutBindingFlagsCreateInfo descriptor_set_layout_binding_flags = {}; - descriptor_set_layout_binding_flags.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_BINDING_FLAGS_CREATE_INFO; - descriptor_set_layout_binding_flags.pNext = VK_NULL_HANDLE; - descriptor_set_layout_binding_flags.bindingCount = sizeof(flags) / sizeof(VkDescriptorBindingFlags); - descriptor_set_layout_binding_flags.pBindingFlags = flags; + descriptor_set_layout_binding_flags.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_BINDING_FLAGS_CREATE_INFO; + descriptor_set_layout_binding_flags.pNext = VK_NULL_HANDLE; + descriptor_set_layout_binding_flags.bindingCount = sizeof(flags) / sizeof(VkDescriptorBindingFlags); + descriptor_set_layout_binding_flags.pBindingFlags = flags; VkDescriptorSetLayoutCreateInfo descriptor_set_layout_create_info = {}; - descriptor_set_layout_create_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO; - descriptor_set_layout_create_info.pNext = &descriptor_set_layout_binding_flags; - descriptor_set_layout_create_info.flags = 0; - descriptor_set_layout_create_info.bindingCount = sizeof(bindless_layout_bindings) / sizeof(VkDescriptorSetLayoutBinding); - descriptor_set_layout_create_info.pBindings = bindless_layout_bindings; + descriptor_set_layout_create_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO; + descriptor_set_layout_create_info.pNext = &descriptor_set_layout_binding_flags; + descriptor_set_layout_create_info.flags = 0; + descriptor_set_layout_create_info.bindingCount = sizeof(bindless_layout_bindings) / sizeof(VkDescriptorSetLayoutBinding); + descriptor_set_layout_create_info.pBindings = bindless_layout_bindings; VKRESULT(vkCreateDescriptorSetLayout(context.device, &descriptor_set_layout_create_info, nullptr, &bindless_descriptor.set_layout)) VkPushConstantRange push_constants[] = { { - .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, - .offset = 0, - .size = 64, + .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, + .offset = 0, + .size = 64, }, { - .stageFlags = VK_SHADER_STAGE_ALL_GRAPHICS, - .offset = 64, - .size = 64, + .stageFlags = VK_SHADER_STAGE_ALL_GRAPHICS, + .offset = 64, + .size = 64, }, // { // .stageFlags = VK_SHADER_STAGE_VERTEX_BIT, @@ -115,24 +114,24 @@ vkapi::vkapi(vkcontext& context) // }, }; - VkPipelineLayoutCreateInfo layout_create_info = {}; - layout_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO; - layout_create_info.pNext = nullptr; - layout_create_info.flags = 0; - layout_create_info.setLayoutCount = 1; - layout_create_info.pSetLayouts = &bindless_descriptor.set_layout; - layout_create_info.pushConstantRangeCount = sizeof(push_constants) / sizeof(VkPushConstantRange); - layout_create_info.pPushConstantRanges = push_constants; + VkPipelineLayoutCreateInfo layout_create_info = {}; + layout_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO; + layout_create_info.pNext = nullptr; + layout_create_info.flags = 0; + layout_create_info.setLayoutCount = 1; + layout_create_info.pSetLayouts = &bindless_descriptor.set_layout; + layout_create_info.pushConstantRangeCount = sizeof(push_constants) / sizeof(VkPushConstantRange); + layout_create_info.pPushConstantRanges = push_constants; VKRESULT(vkCreatePipelineLayout(context.device, &layout_create_info, nullptr, &bindless_descriptor.pipeline_layout)) - VkDescriptorSetAllocateInfo descriptor_set_allocate_info = {}; - descriptor_set_allocate_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO; - descriptor_set_allocate_info.pNext = VK_NULL_HANDLE; - descriptor_set_allocate_info.descriptorPool = descriptor_pool; - descriptor_set_allocate_info.descriptorSetCount = 1; - descriptor_set_allocate_info.pSetLayouts = &bindless_descriptor.set_layout; + VkDescriptorSetAllocateInfo descriptor_set_allocate_info = {}; + descriptor_set_allocate_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO; + descriptor_set_allocate_info.pNext = VK_NULL_HANDLE; + descriptor_set_allocate_info.descriptorPool = descriptor_pool; + descriptor_set_allocate_info.descriptorSetCount = 1; + descriptor_set_allocate_info.pSetLayouts = &bindless_descriptor.set_layout; vkAllocateDescriptorSets(context.device, &descriptor_set_allocate_info, &bindless_descriptor.set); } @@ -147,7 +146,7 @@ vkapi::~vkapi() { destroy_image(image_handle); } - for(handle sampler_handle = 0; sampler_handle < samplers.size(); sampler_handle++) { + for (handle sampler_handle = 0; sampler_handle < samplers.size(); sampler_handle++) { destroy_sampler(sampler_handle); } @@ -159,27 +158,26 @@ vkapi::~vkapi() { vkDestroyDescriptorPool(context.device, descriptor_pool, nullptr); } - handle vkapi::create_buffer(size_t data_size, VkBufferUsageFlags buffer_usage, uint32_t mem_usage) { auto* buffer = new struct buffer(); - VkBufferCreateInfo buffer_info = {}; - buffer_info.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO; - buffer_info.size = data_size; - buffer_info.usage = buffer_usage | VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT_KHR; + VkBufferCreateInfo buffer_info = {}; + buffer_info.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO; + buffer_info.size = data_size; + buffer_info.usage = buffer_usage | VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT_KHR; VmaAllocationCreateInfo alloc_create_info = {}; alloc_create_info.usage = (VmaMemoryUsage)mem_usage; alloc_create_info.flags = VMA_ALLOCATION_CREATE_MAPPED_BIT; - VmaAllocationInfo alloc_info {}; + VmaAllocationInfo alloc_info{}; VKRESULT(vmaCreateBuffer(context.allocator, &buffer_info, &alloc_create_info, &buffer->handle, &buffer->alloc, &alloc_info)) VkBufferDeviceAddressInfo buffer_device_address_info = {}; - buffer_device_address_info.sType = VK_STRUCTURE_TYPE_BUFFER_DEVICE_ADDRESS_INFO; - buffer_device_address_info.pNext = VK_NULL_HANDLE; - buffer_device_address_info.buffer = buffer->handle; + buffer_device_address_info.sType = VK_STRUCTURE_TYPE_BUFFER_DEVICE_ADDRESS_INFO; + buffer_device_address_info.pNext = VK_NULL_HANDLE; + buffer_device_address_info.buffer = buffer->handle; buffer->size = data_size; @@ -204,19 +202,19 @@ void vkapi::copy_buffer(VkCommandBuffer cmd_buf, handle src, handle dst, size_t void vkapi::copy_buffer(VkCommandBuffer cmd_buf, handle src, handle dst, size_t size, size_t buffer_offset) { auto& dst_image = images[dst]; - VkImageSubresourceLayers image_subresource_layers = {}; - image_subresource_layers.aspectMask = dst_image->subresource_range.aspectMask; - image_subresource_layers.mipLevel = 0; - image_subresource_layers.baseArrayLayer = 0; - image_subresource_layers.layerCount = 1; + VkImageSubresourceLayers image_subresource_layers = {}; + image_subresource_layers.aspectMask = dst_image->subresource_range.aspectMask; + image_subresource_layers.mipLevel = 0; + image_subresource_layers.baseArrayLayer = 0; + image_subresource_layers.layerCount = 1; - VkBufferImageCopy buffer_to_image_copy = {}; - buffer_to_image_copy.bufferOffset = buffer_offset; - buffer_to_image_copy.bufferRowLength = 0; - buffer_to_image_copy.bufferImageHeight = 0; - buffer_to_image_copy.imageSubresource = image_subresource_layers; - buffer_to_image_copy.imageOffset = { 0, 0, 0 }; - buffer_to_image_copy.imageExtent = dst_image->size; + VkBufferImageCopy buffer_to_image_copy = {}; + buffer_to_image_copy.bufferOffset = buffer_offset; + buffer_to_image_copy.bufferRowLength = 0; + buffer_to_image_copy.bufferImageHeight = 0; + buffer_to_image_copy.imageSubresource = image_subresource_layers; + buffer_to_image_copy.imageOffset = { 0, 0, 0 }; + buffer_to_image_copy.imageExtent = dst_image->size; vkCmdCopyBufferToImage(cmd_buf, buffers[src]->handle, dst_image->handle, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, &buffer_to_image_copy); } @@ -228,62 +226,60 @@ void vkapi::destroy_buffer(handle buffer) { // buffers.erase(buffer.handle); } - handle vkapi::create_image(VkExtent3D size, VkFormat format, VkImageUsageFlags usages) { auto* image = new struct image(); image->size = size; - image->subresource_range.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - image->subresource_range.baseMipLevel = 0; - image->subresource_range.levelCount = 1; - image->subresource_range.baseArrayLayer = 0; - image->subresource_range.layerCount = 1; + image->subresource_range.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; + image->subresource_range.baseMipLevel = 0; + image->subresource_range.levelCount = 1; + image->subresource_range.baseArrayLayer = 0; + image->subresource_range.layerCount = 1; - VkImageCreateInfo img_create_info = {}; - img_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO; - img_create_info.pNext = VK_NULL_HANDLE; - img_create_info.flags = 0; - img_create_info.imageType = VK_IMAGE_TYPE_2D; - img_create_info.format = format; - img_create_info.extent = size; - img_create_info.mipLevels = 1; - img_create_info.arrayLayers = 1; - img_create_info.samples = VK_SAMPLE_COUNT_1_BIT; - img_create_info.tiling = VK_IMAGE_TILING_OPTIMAL; - img_create_info.usage = usages; - img_create_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; - img_create_info.queueFamilyIndexCount = 0; - img_create_info.pQueueFamilyIndices = nullptr; - img_create_info.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; + VkImageCreateInfo img_create_info = {}; + img_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO; + img_create_info.pNext = VK_NULL_HANDLE; + img_create_info.flags = 0; + img_create_info.imageType = VK_IMAGE_TYPE_2D; + img_create_info.format = format; + img_create_info.extent = size; + img_create_info.mipLevels = 1; + img_create_info.arrayLayers = 1; + img_create_info.samples = VK_SAMPLE_COUNT_1_BIT; + img_create_info.tiling = VK_IMAGE_TILING_OPTIMAL; + img_create_info.usage = usages; + img_create_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; + img_create_info.queueFamilyIndexCount = 0; + img_create_info.pQueueFamilyIndices = nullptr; + img_create_info.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; VmaAllocationCreateInfo alloc_create_info = {}; alloc_create_info.usage = VMA_MEMORY_USAGE_GPU_ONLY; - VmaAllocationInfo alloc_info {}; + VmaAllocationInfo alloc_info{}; VKRESULT(vmaCreateImage(context.allocator, &img_create_info, &alloc_create_info, &image->handle, &image->alloc, &alloc_info)) - VkImageViewCreateInfo image_view_create_info = {}; - image_view_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO; - image_view_create_info.pNext = nullptr; - image_view_create_info.flags = 0; - image_view_create_info.image = image->handle; - image_view_create_info.viewType = VK_IMAGE_VIEW_TYPE_2D; - image_view_create_info.format = format; - image_view_create_info.components = { + VkImageViewCreateInfo image_view_create_info = {}; + image_view_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO; + image_view_create_info.pNext = nullptr; + image_view_create_info.flags = 0; + image_view_create_info.image = image->handle; + image_view_create_info.viewType = VK_IMAGE_VIEW_TYPE_2D; + image_view_create_info.format = format; + image_view_create_info.components = { VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY }; - image_view_create_info.subresourceRange = image->subresource_range; + image_view_create_info.subresourceRange = image->subresource_range; VKRESULT(vkCreateImageView(context.device, &image_view_create_info, VK_NULL_HANDLE, &image->view)) image->format = format; image->usages = usages; - image->device_ptr = alloc_info.pMappedData; images.push_back(image); @@ -301,6 +297,7 @@ handle vkapi::create_image(VkExtent3D size, VkFormat format, VkImageUsageFlags u return image_handle; } + void vkapi::destroy_image(handle image) { auto* current_image = images[image]; @@ -317,7 +314,6 @@ void vkapi::destroy_image(handle image) { // TODO: Free once using freelist // images.erase(image.handle); - } std::vector<handle> vkapi::create_images(VkExtent3D size, VkFormat format, VkImageUsageFlags usages, size_t image_count) { @@ -330,19 +326,18 @@ std::vector<handle> vkapi::create_images(VkExtent3D size, VkFormat format, VkIma return images_handles; } -void vkapi::destroy_images(std::vector<handle> &imgs) { - for (auto handle: imgs) { +void vkapi::destroy_images(std::vector<handle>& imgs) { + for (auto handle : imgs) { destroy_image(handle); } } - VkFence vkapi::create_fence() const { VkFence fence; - VkFenceCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO; - create_info.pNext = nullptr; - create_info.flags = VK_FENCE_CREATE_SIGNALED_BIT; + VkFenceCreateInfo create_info = {}; + create_info.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO; + create_info.pNext = nullptr; + create_info.flags = VK_FENCE_CREATE_SIGNALED_BIT; VKRESULT(vkCreateFence(context.device, &create_info, nullptr, &fence)) @@ -354,9 +349,9 @@ void vkapi::destroy_fence(VkFence fence) const { } std::vector<VkFence> vkapi::create_fences(size_t fences_count) const { - std::vector<VkFence> fences { fences_count }; + std::vector<VkFence> fences{ fences_count }; - for(size_t fence_index = 0; fence_index < fences_count; fence_index++) { + for (size_t fence_index = 0; fence_index < fences_count; fence_index++) { fences[fence_index] = create_fence(); } @@ -364,18 +359,17 @@ std::vector<VkFence> vkapi::create_fences(size_t fences_count) const { } void vkapi::destroy_fences(VkFence fences[], size_t fences_count) const { - for(size_t index { 0 }; index < fences_count; index++) { + for (size_t index{ 0 }; index < fences_count; index++) { vkDestroyFence(context.device, fences[index], nullptr); } } - VkSemaphore vkapi::create_semaphore() const { VkSemaphore semaphore; - VkSemaphoreCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO; - create_info.pNext = nullptr; - create_info.flags = 0; + VkSemaphoreCreateInfo create_info = {}; + create_info.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO; + create_info.pNext = nullptr; + create_info.flags = 0; VKRESULT(vkCreateSemaphore(context.device, &create_info, nullptr, &semaphore)) @@ -387,9 +381,9 @@ void vkapi::destroy_semaphore(VkSemaphore semaphore) const { } std::vector<VkSemaphore> vkapi::create_semaphores(size_t semaphores_count) const { - std::vector<VkSemaphore> semaphores { semaphores_count }; + std::vector<VkSemaphore> semaphores{ semaphores_count }; - for (size_t semaphore_index { 0 }; semaphore_index < semaphores_count; semaphore_index++) { + for (size_t semaphore_index{ 0 }; semaphore_index < semaphores_count; semaphore_index++) { semaphores[semaphore_index] = create_semaphore(); } @@ -397,30 +391,29 @@ std::vector<VkSemaphore> vkapi::create_semaphores(size_t semaphores_count) const } void vkapi::destroy_semaphores(VkSemaphore semaphores[], size_t semaphores_count) const { - for(size_t index { 0 }; index < semaphores_count; index++) { + for (size_t index{ 0 }; index < semaphores_count; index++) { vkDestroySemaphore(context.device, semaphores[index], nullptr); } } - handle vkapi::create_sampler(VkFilter filter, VkSamplerAddressMode address_mode) { - VkSamplerCreateInfo sampler_create_info = {}; - sampler_create_info.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO; - sampler_create_info.pNext = VK_NULL_HANDLE; - sampler_create_info.flags = 0; - sampler_create_info.magFilter = filter; - sampler_create_info.minFilter = filter; - sampler_create_info.mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST; - sampler_create_info.addressModeU = address_mode; - sampler_create_info.addressModeV = address_mode; - sampler_create_info.addressModeW = address_mode; - sampler_create_info.mipLodBias = 0.f; - sampler_create_info.anisotropyEnable = VK_FALSE; - sampler_create_info.compareEnable = VK_FALSE; - sampler_create_info.compareOp = VK_COMPARE_OP_ALWAYS; - sampler_create_info.minLod = 0.f; - sampler_create_info.maxLod = 0.f; - sampler_create_info.borderColor = VK_BORDER_COLOR_FLOAT_TRANSPARENT_BLACK; + VkSamplerCreateInfo sampler_create_info = {}; + sampler_create_info.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO; + sampler_create_info.pNext = VK_NULL_HANDLE; + sampler_create_info.flags = 0; + sampler_create_info.magFilter = filter; + sampler_create_info.minFilter = filter; + sampler_create_info.mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST; + sampler_create_info.addressModeU = address_mode; + sampler_create_info.addressModeV = address_mode; + sampler_create_info.addressModeW = address_mode; + sampler_create_info.mipLodBias = 0.f; + sampler_create_info.anisotropyEnable = VK_FALSE; + sampler_create_info.compareEnable = VK_FALSE; + sampler_create_info.compareOp = VK_COMPARE_OP_ALWAYS; + sampler_create_info.minLod = 0.f; + sampler_create_info.maxLod = 0.f; + sampler_create_info.borderColor = VK_BORDER_COLOR_FLOAT_TRANSPARENT_BLACK; sampler_create_info.unnormalizedCoordinates = VK_FALSE; struct sampler* sampler = new struct sampler(); @@ -445,13 +438,12 @@ void vkapi::destroy_sampler(handle sampler) { // samplers.erase(sampler.handle); } - VkCommandPool vkapi::create_command_pool() const { - VkCommandPoolCreateInfo cmd_pool_create_info = {}; - cmd_pool_create_info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO; - cmd_pool_create_info.pNext = nullptr; - cmd_pool_create_info.flags = VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT; - cmd_pool_create_info.queueFamilyIndex = context.graphics_queue.index; + VkCommandPoolCreateInfo cmd_pool_create_info = {}; + cmd_pool_create_info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO; + cmd_pool_create_info.pNext = nullptr; + cmd_pool_create_info.flags = VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT; + cmd_pool_create_info.queueFamilyIndex = context.graphics_queue.index; VkCommandPool command_pool; VKRESULT(vkCreateCommandPool(context.device, &cmd_pool_create_info, nullptr, &command_pool)) @@ -459,88 +451,86 @@ VkCommandPool vkapi::create_command_pool() const { return command_pool; } - void vkapi::allocate_command_buffers(VkCommandPool command_pool, VkCommandBuffer* command_buffers, size_t count) const { - VkCommandBufferAllocateInfo cmd_buf_allocate_info = {}; - cmd_buf_allocate_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO; - cmd_buf_allocate_info.pNext = VK_NULL_HANDLE; - cmd_buf_allocate_info.commandPool = command_pool; - cmd_buf_allocate_info.level = VK_COMMAND_BUFFER_LEVEL_PRIMARY; - cmd_buf_allocate_info.commandBufferCount = count; + VkCommandBufferAllocateInfo cmd_buf_allocate_info = {}; + cmd_buf_allocate_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO; + cmd_buf_allocate_info.pNext = VK_NULL_HANDLE; + cmd_buf_allocate_info.commandPool = command_pool; + cmd_buf_allocate_info.level = VK_COMMAND_BUFFER_LEVEL_PRIMARY; + cmd_buf_allocate_info.commandBufferCount = count; vkAllocateCommandBuffers(context.device, &cmd_buf_allocate_info, command_buffers); } // TODO: attachment structure VkRenderPass vkapi::create_render_pass(std::vector<VkFormat>& color_attachments_format, VkImageLayout initial_layout, VkImageLayout final_layout) { - std::vector<VkAttachmentDescription> attachments_description = {}; - std::vector<VkAttachmentReference> attachments_reference = {}; + std::vector<VkAttachmentDescription> attachments_description = {}; + std::vector<VkAttachmentReference> attachments_reference = {}; for (size_t attachment_index = 0; attachment_index < color_attachments_format.size(); attachment_index++) { auto format = color_attachments_format[attachment_index]; - VkAttachmentDescription attachment_description = {}; - attachment_description.flags = 0; - attachment_description.format = format; - attachment_description.samples = VK_SAMPLE_COUNT_1_BIT; - attachment_description.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD; // TODO: Set based on render pass usage - attachment_description.storeOp = VK_ATTACHMENT_STORE_OP_STORE; // TODO: Set based on render pass usage + VkAttachmentDescription attachment_description = {}; + attachment_description.flags = 0; + attachment_description.format = format; + attachment_description.samples = VK_SAMPLE_COUNT_1_BIT; + attachment_description.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD; // TODO: Set based on render pass usage + attachment_description.storeOp = VK_ATTACHMENT_STORE_OP_STORE; // TODO: Set based on render pass usage - attachment_description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE; - attachment_description.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE; - attachment_description.initialLayout = initial_layout; - attachment_description.finalLayout = final_layout; + attachment_description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE; + attachment_description.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE; + attachment_description.initialLayout = initial_layout; + attachment_description.finalLayout = final_layout; attachments_description.push_back(attachment_description); - VkAttachmentReference attachment_reference = {}; - attachment_reference.attachment = attachment_index; - attachment_reference.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; + VkAttachmentReference attachment_reference = {}; + attachment_reference.attachment = attachment_index; + attachment_reference.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; attachments_reference.push_back(attachment_reference); } - VkSubpassDescription subpass_description = {}; - subpass_description.flags = 0; - subpass_description.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS; - subpass_description.colorAttachmentCount = attachments_reference.size(); - subpass_description.pColorAttachments = attachments_reference.data(); - subpass_description.pDepthStencilAttachment = VK_NULL_HANDLE; - subpass_description.pResolveAttachments = VK_NULL_HANDLE; - subpass_description.preserveAttachmentCount = 0; - subpass_description.pPreserveAttachments = VK_NULL_HANDLE; + VkSubpassDescription subpass_description = {}; + subpass_description.flags = 0; + subpass_description.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS; + subpass_description.colorAttachmentCount = attachments_reference.size(); + subpass_description.pColorAttachments = attachments_reference.data(); + subpass_description.pDepthStencilAttachment = VK_NULL_HANDLE; + subpass_description.pResolveAttachments = VK_NULL_HANDLE; + subpass_description.preserveAttachmentCount = 0; + subpass_description.pPreserveAttachments = VK_NULL_HANDLE; + VkSubpassDependency subpass_dependency[2] = {}; + subpass_dependency[0].srcSubpass = VK_SUBPASS_EXTERNAL; + subpass_dependency[0].dstSubpass = 1; // First subpass attachment is used in + subpass_dependency[0].srcStageMask = VK_PIPELINE_STAGE_NONE_KHR; + subpass_dependency[0].dstStageMask = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT; + subpass_dependency[0].srcAccessMask = 0; + subpass_dependency[0].dstAccessMask = VK_ACCESS_INPUT_ATTACHMENT_READ_BIT | + VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | + VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; + subpass_dependency[0].dependencyFlags = 0; - VkSubpassDependency subpass_dependency[2] = {}; - subpass_dependency[0].srcSubpass = VK_SUBPASS_EXTERNAL; - subpass_dependency[0].dstSubpass = 1; // First subpass attachment is used in - subpass_dependency[0].srcStageMask = VK_PIPELINE_STAGE_NONE_KHR; - subpass_dependency[0].dstStageMask = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT; - subpass_dependency[0].srcAccessMask = 0; - subpass_dependency[0].dstAccessMask = VK_ACCESS_INPUT_ATTACHMENT_READ_BIT | - VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | - VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; - subpass_dependency[0].dependencyFlags = 0; - - subpass_dependency[1].srcSubpass = 1; // Last subpass attachment is used in - subpass_dependency[1].dstSubpass = VK_SUBPASS_EXTERNAL; - subpass_dependency[1].srcStageMask = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT; - subpass_dependency[1].dstStageMask = VK_PIPELINE_STAGE_NONE_KHR; - subpass_dependency[1].srcAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; - subpass_dependency[1].dstAccessMask = 0; - subpass_dependency[1].dependencyFlags = 0; + subpass_dependency[1].srcSubpass = 1; // Last subpass attachment is used in + subpass_dependency[1].dstSubpass = VK_SUBPASS_EXTERNAL; + subpass_dependency[1].srcStageMask = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT; + subpass_dependency[1].dstStageMask = VK_PIPELINE_STAGE_NONE_KHR; + subpass_dependency[1].srcAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; + subpass_dependency[1].dstAccessMask = 0; + subpass_dependency[1].dependencyFlags = 0; VkRenderPass render_pass; - VkRenderPassCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO; - create_info.pNext = VK_NULL_HANDLE; - create_info.flags = 0; - create_info.attachmentCount = attachments_description.size(); - create_info.pAttachments = attachments_description.data(); - create_info.subpassCount = 1; - create_info.pSubpasses = &subpass_description; + VkRenderPassCreateInfo create_info = {}; + create_info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO; + create_info.pNext = VK_NULL_HANDLE; + create_info.flags = 0; + create_info.attachmentCount = attachments_description.size(); + create_info.pAttachments = attachments_description.data(); + create_info.subpassCount = 1; + create_info.pSubpasses = &subpass_description; // create_info.dependencyCount = sizeof(subpass_dependency) / sizeof(VkSubpassDependency); // create_info.pDependencies = subpass_dependency; @@ -553,42 +543,41 @@ void vkapi::destroy_render_pass(VkRenderPass render_pass) { vkDestroyRenderPass(context.device, render_pass, VK_NULL_HANDLE); } - framebuffer vkapi::create_framebuffer(VkRenderPass render_pass, std::vector<VkFormat>& formats, VkExtent2D size) { VkFramebuffer framebuffer_handle; std::vector<VkFramebufferAttachmentImageInfo> attachments_image_infos(formats.size()); for (size_t index = 0; index < formats.size(); index++) { VkFramebufferAttachmentImageInfo attachments_image_info = {}; - attachments_image_info.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO; - attachments_image_info.pNext = VK_NULL_HANDLE; - attachments_image_info.flags = 0; - attachments_image_info.usage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT; - attachments_image_info.width = size.width; - attachments_image_info.height = size.height; - attachments_image_info.layerCount = 1; - attachments_image_info.viewFormatCount = 1; - attachments_image_info.pViewFormats = &formats[index]; + attachments_image_info.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO; + attachments_image_info.pNext = VK_NULL_HANDLE; + attachments_image_info.flags = 0; + attachments_image_info.usage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT; + attachments_image_info.width = size.width; + attachments_image_info.height = size.height; + attachments_image_info.layerCount = 1; + attachments_image_info.viewFormatCount = 1; + attachments_image_info.pViewFormats = &formats[index]; attachments_image_infos[index] = attachments_image_info; } VkFramebufferAttachmentsCreateInfo attachments_create_info = {}; - attachments_create_info.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO; - attachments_create_info.pNext = VK_NULL_HANDLE; - attachments_create_info.attachmentImageInfoCount = attachments_image_infos.size(); - attachments_create_info.pAttachmentImageInfos = attachments_image_infos.data(); + attachments_create_info.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO; + attachments_create_info.pNext = VK_NULL_HANDLE; + attachments_create_info.attachmentImageInfoCount = attachments_image_infos.size(); + attachments_create_info.pAttachmentImageInfos = attachments_image_infos.data(); VkFramebufferCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO; - create_info.pNext = &attachments_create_info; - create_info.flags = VK_FRAMEBUFFER_CREATE_IMAGELESS_BIT; - create_info.renderPass = render_pass; - create_info.attachmentCount = formats.size(); - create_info.pAttachments = VK_NULL_HANDLE; - create_info.width = size.width; - create_info.height = size.height; - create_info.layers = 1; + create_info.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO; + create_info.pNext = &attachments_create_info; + create_info.flags = VK_FRAMEBUFFER_CREATE_IMAGELESS_BIT; + create_info.renderPass = render_pass; + create_info.attachmentCount = formats.size(); + create_info.pAttachments = VK_NULL_HANDLE; + create_info.width = size.width; + create_info.height = size.height; + create_info.layers = 1; VKRESULT(vkCreateFramebuffer(context.device, &create_info, VK_NULL_HANDLE, &framebuffer_handle)) @@ -596,9 +585,9 @@ framebuffer vkapi::create_framebuffer(VkRenderPass render_pass, std::vector<VkFo } std::vector<framebuffer> vkapi::create_framebuffers(VkRenderPass render_pass, std::vector<VkFormat>& formats, VkExtent2D size, uint32_t framebuffer_count) { - std::vector<framebuffer> framebuffers { framebuffer_count }; + std::vector<framebuffer> framebuffers{ framebuffer_count }; - for (auto& framebuffer: framebuffers) { + for (auto& framebuffer : framebuffers) { framebuffer = create_framebuffer(render_pass, formats, size); } @@ -614,14 +603,13 @@ void vkapi::destroy_framebuffer(framebuffer framebuffer) const { void vkapi::destroy_framebuffers(std::vector<framebuffer>& framebuffers) const { VKRESULT(vkDeviceWaitIdle(context.device)) - for (auto& framebuffer: framebuffers) { + for (auto& framebuffer : framebuffers) { vkDestroyFramebuffer(context.device, framebuffer.handle, VK_NULL_HANDLE); } } - pipeline vkapi::create_compute_pipeline(const char* shader_name) const { - pipeline pipeline { + pipeline pipeline{ .bind_point = VK_PIPELINE_BIND_POINT_COMPUTE }; @@ -632,31 +620,31 @@ pipeline vkapi::create_compute_pipeline(const char* shader_name) const { pipeline.shader_modules.resize(1); - VkShaderModuleCreateInfo shader_create_info = {}; - shader_create_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO; - shader_create_info.pNext = VK_NULL_HANDLE; - shader_create_info.flags = 0; - shader_create_info.codeSize = shader_code.size(); - shader_create_info.pCode = reinterpret_cast<uint32_t*>(shader_code.data()); + VkShaderModuleCreateInfo shader_create_info = {}; + shader_create_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO; + shader_create_info.pNext = VK_NULL_HANDLE; + shader_create_info.flags = 0; + shader_create_info.codeSize = shader_code.size(); + shader_create_info.pCode = reinterpret_cast<uint32_t*>(shader_code.data()); VKRESULT(vkCreateShaderModule(context.device, &shader_create_info, VK_NULL_HANDLE, (pipeline.shader_modules).data())) VkPipelineShaderStageCreateInfo stage_create_info = {}; - stage_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO; - stage_create_info.pNext = VK_NULL_HANDLE; - stage_create_info.flags = 0; - stage_create_info.stage = VK_SHADER_STAGE_COMPUTE_BIT; - stage_create_info.module = pipeline.shader_modules[0]; - stage_create_info.pName = "main"; - stage_create_info.pSpecializationInfo = VK_NULL_HANDLE; + stage_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO; + stage_create_info.pNext = VK_NULL_HANDLE; + stage_create_info.flags = 0; + stage_create_info.stage = VK_SHADER_STAGE_COMPUTE_BIT; + stage_create_info.module = pipeline.shader_modules[0]; + stage_create_info.pName = "main"; + stage_create_info.pSpecializationInfo = VK_NULL_HANDLE; - VkComputePipelineCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO; - create_info.pNext = VK_NULL_HANDLE; - create_info.flags = 0; - create_info.stage = stage_create_info; - create_info.layout = bindless_descriptor.pipeline_layout; + VkComputePipelineCreateInfo create_info = {}; + create_info.sType = VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO; + create_info.pNext = VK_NULL_HANDLE; + create_info.flags = 0; + create_info.stage = stage_create_info; + create_info.layout = bindless_descriptor.pipeline_layout; VKRESULT(vkCreateComputePipelines( context.device, @@ -664,14 +652,13 @@ pipeline vkapi::create_compute_pipeline(const char* shader_name) const { 1, &create_info, nullptr, - &pipeline.handle - )) + &pipeline.handle)) return pipeline; } pipeline vkapi::create_graphics_pipeline(const char* shader_name, VkShaderStageFlagBits shader_stages, VkRenderPass render_pass, std::vector<VkDynamicState>& dynamic_states) const { - pipeline pipeline { + pipeline pipeline{ .bind_point = VK_PIPELINE_BIND_POINT_GRAPHICS }; @@ -686,151 +673,150 @@ pipeline vkapi::create_graphics_pipeline(const char* shader_name, VkShaderStageF std::vector<uint8_t> shader_code = read_file(shader_path.string().c_str()); assert(!shader_code.empty()); - VkShaderModuleCreateInfo shader_create_info = {}; - shader_create_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO; - shader_create_info.pNext = nullptr; - shader_create_info.flags = 0; - shader_create_info.codeSize = shader_code.size(); - shader_create_info.pCode = reinterpret_cast<uint32_t*>(shader_code.data()); + VkShaderModuleCreateInfo shader_create_info = {}; + shader_create_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO; + shader_create_info.pNext = nullptr; + shader_create_info.flags = 0; + shader_create_info.codeSize = shader_code.size(); + shader_create_info.pCode = reinterpret_cast<uint32_t*>(shader_code.data()); VKRESULT(vkCreateShaderModule(context.device, &shader_create_info, nullptr, &shader_module)) pipeline.shader_modules.push_back(shader_module); VkPipelineShaderStageCreateInfo stage_create_info = {}; - stage_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO; - stage_create_info.pNext = nullptr; - stage_create_info.flags = 0; - stage_create_info.stage = (VkShaderStageFlagBits)stage_flag; - stage_create_info.module = shader_module; - stage_create_info.pName = "main"; - stage_create_info.pSpecializationInfo = nullptr; + stage_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO; + stage_create_info.pNext = nullptr; + stage_create_info.flags = 0; + stage_create_info.stage = (VkShaderStageFlagBits)stage_flag; + stage_create_info.module = shader_module; + stage_create_info.pName = "main"; + stage_create_info.pSpecializationInfo = nullptr; stages_create_info.push_back(stage_create_info); } } - VkPipelineVertexInputStateCreateInfo vertex_input_state_create_info = {}; - vertex_input_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO; + VkPipelineVertexInputStateCreateInfo vertex_input_state_create_info = {}; + vertex_input_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO; VkPipelineInputAssemblyStateCreateInfo input_assembly_state_create_info = {}; - input_assembly_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO; - input_assembly_state_create_info.pNext = nullptr; - input_assembly_state_create_info.flags = 0; - input_assembly_state_create_info.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST; + input_assembly_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO; + input_assembly_state_create_info.pNext = nullptr; + input_assembly_state_create_info.flags = 0; + input_assembly_state_create_info.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST; - VkPipelineViewportStateCreateInfo viewport_state_create_info = {}; - viewport_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO; - viewport_state_create_info.pNext = nullptr; - viewport_state_create_info.flags = 0; - viewport_state_create_info.viewportCount = 1; - viewport_state_create_info.pViewports = VK_NULL_HANDLE; - viewport_state_create_info.scissorCount = 1; - viewport_state_create_info.pScissors = VK_NULL_HANDLE; + VkPipelineViewportStateCreateInfo viewport_state_create_info = {}; + viewport_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO; + viewport_state_create_info.pNext = nullptr; + viewport_state_create_info.flags = 0; + viewport_state_create_info.viewportCount = 1; + viewport_state_create_info.pViewports = VK_NULL_HANDLE; + viewport_state_create_info.scissorCount = 1; + viewport_state_create_info.pScissors = VK_NULL_HANDLE; - VkPipelineRasterizationStateCreateInfo rasterization_state_create_info = {}; - rasterization_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO; - rasterization_state_create_info.pNext = nullptr; - rasterization_state_create_info.flags = 0; - rasterization_state_create_info.depthClampEnable = VK_FALSE; - rasterization_state_create_info.rasterizerDiscardEnable = VK_FALSE; - rasterization_state_create_info.polygonMode = VK_POLYGON_MODE_FILL; - rasterization_state_create_info.cullMode = VK_CULL_MODE_NONE; - rasterization_state_create_info.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE; - rasterization_state_create_info.depthBiasEnable = VK_FALSE; - rasterization_state_create_info.lineWidth = 1.f; + VkPipelineRasterizationStateCreateInfo rasterization_state_create_info = {}; + rasterization_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO; + rasterization_state_create_info.pNext = nullptr; + rasterization_state_create_info.flags = 0; + rasterization_state_create_info.depthClampEnable = VK_FALSE; + rasterization_state_create_info.rasterizerDiscardEnable = VK_FALSE; + rasterization_state_create_info.polygonMode = VK_POLYGON_MODE_FILL; + rasterization_state_create_info.cullMode = VK_CULL_MODE_NONE; + rasterization_state_create_info.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE; + rasterization_state_create_info.depthBiasEnable = VK_FALSE; + rasterization_state_create_info.lineWidth = 1.f; - VkPipelineMultisampleStateCreateInfo multisample_state_create_info = {}; - multisample_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO; - multisample_state_create_info.pNext = nullptr; - multisample_state_create_info.flags = 0; - multisample_state_create_info.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT; - multisample_state_create_info.sampleShadingEnable = VK_FALSE; - multisample_state_create_info.minSampleShading = 1.f; + VkPipelineMultisampleStateCreateInfo multisample_state_create_info = {}; + multisample_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO; + multisample_state_create_info.pNext = nullptr; + multisample_state_create_info.flags = 0; + multisample_state_create_info.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT; + multisample_state_create_info.sampleShadingEnable = VK_FALSE; + multisample_state_create_info.minSampleShading = 1.f; - VkPipelineColorBlendAttachmentState color_attachment_state = {}; - color_attachment_state.blendEnable = VK_TRUE; - color_attachment_state.srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA; - color_attachment_state.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA; - color_attachment_state.colorBlendOp = VK_BLEND_OP_ADD; - color_attachment_state.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE; - color_attachment_state.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA; - color_attachment_state.alphaBlendOp = VK_BLEND_OP_ADD; - color_attachment_state.colorWriteMask = VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT; + VkPipelineColorBlendAttachmentState color_attachment_state = {}; + color_attachment_state.blendEnable = VK_TRUE; + color_attachment_state.srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA; + color_attachment_state.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA; + color_attachment_state.colorBlendOp = VK_BLEND_OP_ADD; + color_attachment_state.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE; + color_attachment_state.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA; + color_attachment_state.alphaBlendOp = VK_BLEND_OP_ADD; + color_attachment_state.colorWriteMask = VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT; - VkPipelineColorBlendStateCreateInfo color_blend_state_create_info = {}; - color_blend_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO; - color_blend_state_create_info.pNext = nullptr; - color_blend_state_create_info.flags = 0; - color_blend_state_create_info.logicOpEnable = VK_FALSE; - color_blend_state_create_info.attachmentCount = 1; - color_blend_state_create_info.pAttachments = &color_attachment_state; + VkPipelineColorBlendStateCreateInfo color_blend_state_create_info = {}; + color_blend_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO; + color_blend_state_create_info.pNext = nullptr; + color_blend_state_create_info.flags = 0; + color_blend_state_create_info.logicOpEnable = VK_FALSE; + color_blend_state_create_info.attachmentCount = 1; + color_blend_state_create_info.pAttachments = &color_attachment_state; - VkPipelineDynamicStateCreateInfo dynamic_state_create_info = {}; - dynamic_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO; - dynamic_state_create_info.pNext = VK_NULL_HANDLE; - dynamic_state_create_info.flags = 0; - dynamic_state_create_info.dynamicStateCount = dynamic_states.size(); - dynamic_state_create_info.pDynamicStates = dynamic_states.data(); + VkPipelineDynamicStateCreateInfo dynamic_state_create_info = {}; + dynamic_state_create_info.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO; + dynamic_state_create_info.pNext = VK_NULL_HANDLE; + dynamic_state_create_info.flags = 0; + dynamic_state_create_info.dynamicStateCount = dynamic_states.size(); + dynamic_state_create_info.pDynamicStates = dynamic_states.data(); - VkGraphicsPipelineCreateInfo pipeline_create_info = {}; - pipeline_create_info.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO; - pipeline_create_info.pNext = nullptr; - pipeline_create_info.flags = 0; - pipeline_create_info.stageCount = stages_create_info.size(); - pipeline_create_info.pStages = stages_create_info.data(); - pipeline_create_info.pVertexInputState = &vertex_input_state_create_info; - pipeline_create_info.pInputAssemblyState = &input_assembly_state_create_info; - pipeline_create_info.pViewportState = &viewport_state_create_info; - pipeline_create_info.pRasterizationState = &rasterization_state_create_info; - pipeline_create_info.pMultisampleState = &multisample_state_create_info; - pipeline_create_info.pColorBlendState = &color_blend_state_create_info; - pipeline_create_info.pDynamicState = &dynamic_state_create_info; - pipeline_create_info.layout = bindless_descriptor.pipeline_layout; - pipeline_create_info.renderPass = render_pass; - pipeline_create_info.subpass = 0; + VkGraphicsPipelineCreateInfo pipeline_create_info = {}; + pipeline_create_info.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO; + pipeline_create_info.pNext = nullptr; + pipeline_create_info.flags = 0; + pipeline_create_info.stageCount = stages_create_info.size(); + pipeline_create_info.pStages = stages_create_info.data(); + pipeline_create_info.pVertexInputState = &vertex_input_state_create_info; + pipeline_create_info.pInputAssemblyState = &input_assembly_state_create_info; + pipeline_create_info.pViewportState = &viewport_state_create_info; + pipeline_create_info.pRasterizationState = &rasterization_state_create_info; + pipeline_create_info.pMultisampleState = &multisample_state_create_info; + pipeline_create_info.pColorBlendState = &color_blend_state_create_info; + pipeline_create_info.pDynamicState = &dynamic_state_create_info; + pipeline_create_info.layout = bindless_descriptor.pipeline_layout; + pipeline_create_info.renderPass = render_pass; + pipeline_create_info.subpass = 0; VKRESULT(vkCreateGraphicsPipelines(context.device, VK_NULL_HANDLE, 1, &pipeline_create_info, VK_NULL_HANDLE, &pipeline.handle)) return pipeline; } -void vkapi::destroy_pipeline(pipeline &pipeline) const { - for (auto& shader_module: pipeline.shader_modules) { +void vkapi::destroy_pipeline(pipeline& pipeline) const { + for (auto& shader_module : pipeline.shader_modules) { vkDestroyShaderModule(context.device, shader_module, nullptr); } vkDestroyPipeline(context.device, pipeline.handle, nullptr); } - VkSurfaceKHR vkapi::create_surface(window& wnd) const { VkSurfaceKHR surface; #if defined(LINUX) - VkXcbSurfaceCreateInfoKHR create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_XCB_SURFACE_CREATE_INFO_KHR; - create_info.pNext = nullptr; - create_info.flags = 0; - create_info.connection = wnd.connection; - create_info.window = wnd.win; + VkXcbSurfaceCreateInfoKHR create_info = {}; + create_info.sType = VK_STRUCTURE_TYPE_XCB_SURFACE_CREATE_INFO_KHR; + create_info.pNext = nullptr; + create_info.flags = 0; + create_info.connection = wnd.connection; + create_info.window = wnd.win; VKRESULT(vkCreateXcbSurfaceKHR(context.instance, &create_info, nullptr, &surface)) #elif defined(WINDOWS) - VkWin32SurfaceCreateInfoKHR create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_WIN32_SURFACE_CREATE_INFO_KHR; - create_info.pNext = nullptr; - create_info.flags = 0; - create_info.hinstance = GetModuleHandle(nullptr); - create_info.hwnd = wnd.window_handle; + VkWin32SurfaceCreateInfoKHR create_info = {}; + create_info.sType = VK_STRUCTURE_TYPE_WIN32_SURFACE_CREATE_INFO_KHR; + create_info.pNext = nullptr; + create_info.flags = 0; + create_info.hinstance = GetModuleHandle(nullptr); + create_info.hwnd = wnd.window_handle; VKRESULT(vkCreateWin32SurfaceKHR(context.instance, &create_info, nullptr, &surface)) #elif defined(MACOS) VkMetalSurfaceCreateInfoEXT create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_METAL_SURFACE_CREATE_INFO_EXT; - create_info.pNext = nullptr; - create_info.flags = 0; + create_info.sType = VK_STRUCTURE_TYPE_METAL_SURFACE_CREATE_INFO_EXT; + create_info.pNext = nullptr; + create_info.flags = 0; // create_info.pLayer = GetModuleHandle(NULL); VKRESULT(vkCreateMetalSurfaceEXT(context.instance, &create_info, nullptr, &surface)) @@ -843,7 +829,6 @@ void vkapi::destroy_surface(VkSurfaceKHR surface) { vkDestroySurfaceKHR(context.instance, surface, nullptr); } - swapchain vkapi::create_swapchain(VkSurfaceKHR surface, size_t min_image_count, VkImageUsageFlags usages, VkSwapchainKHR old_swapchain) { swapchain swapchain; @@ -871,38 +856,38 @@ swapchain vkapi::create_swapchain(VkSurfaceKHR surface, size_t min_image_count, uint32_t supported_formats_count = 0; - VKRESULT(vkGetPhysicalDeviceSurfaceFormatsKHR(context.physical_device, surface, &supported_formats_count, VK_NULL_HANDLE)) + VKRESULT(vkGetPhysicalDeviceSurfaceFormatsKHR(context.physical_device, surface, &supported_formats_count, VK_NULL_HANDLE)) - std::vector<VkSurfaceFormatKHR> supported_formats { supported_formats_count }; - VKRESULT(vkGetPhysicalDeviceSurfaceFormatsKHR(context.physical_device, surface, &supported_formats_count, supported_formats.data())) + std::vector<VkSurfaceFormatKHR> supported_formats{ supported_formats_count }; + VKRESULT(vkGetPhysicalDeviceSurfaceFormatsKHR(context.physical_device, surface, &supported_formats_count, supported_formats.data())) uint32_t supported_present_modes_count = 0; VKRESULT(vkGetPhysicalDeviceSurfacePresentModesKHR(context.physical_device, surface, &supported_present_modes_count, VK_NULL_HANDLE)) - std::vector<VkPresentModeKHR> supported_present_modes { supported_present_modes_count }; + std::vector<VkPresentModeKHR> supported_present_modes{ supported_present_modes_count }; VKRESULT(vkGetPhysicalDeviceSurfacePresentModesKHR(context.physical_device, surface, &supported_present_modes_count, supported_present_modes.data())) swapchain.surface_format = supported_formats[0]; - VkSwapchainCreateInfoKHR create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR; - create_info.pNext = nullptr; - create_info.flags = 0; - create_info.surface = surface; - create_info.minImageCount = min_image_count; - create_info.imageFormat = swapchain.surface_format.format; - create_info.imageColorSpace = swapchain.surface_format.colorSpace; - create_info.imageExtent = swapchain.extent; - create_info.imageArrayLayers = 1; - create_info.imageUsage = usages; - create_info.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE; - create_info.preTransform = caps.currentTransform; - create_info.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR; - create_info.presentMode = supported_present_modes[0]; - create_info.clipped = VK_TRUE; - create_info.oldSwapchain = old_swapchain; + VkSwapchainCreateInfoKHR create_info = {}; + create_info.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR; + create_info.pNext = nullptr; + create_info.flags = 0; + create_info.surface = surface; + create_info.minImageCount = min_image_count; + create_info.imageFormat = swapchain.surface_format.format; + create_info.imageColorSpace = swapchain.surface_format.colorSpace; + create_info.imageExtent = swapchain.extent; + create_info.imageArrayLayers = 1; + create_info.imageUsage = usages; + create_info.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE; + create_info.preTransform = caps.currentTransform; + create_info.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR; + create_info.presentMode = supported_present_modes[0]; + create_info.clipped = VK_TRUE; + create_info.oldSwapchain = old_swapchain; VKRESULT(vkCreateSwapchainKHR(context.device, &create_info, nullptr, &swapchain.handle)) @@ -916,16 +901,16 @@ swapchain vkapi::create_swapchain(VkSurfaceKHR surface, size_t min_image_count, VkImageSubresourceRange image_subresource_range = {}; - image_subresource_range.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - image_subresource_range.baseMipLevel = 0; - image_subresource_range.levelCount = 1; - image_subresource_range.baseArrayLayer = 0; - image_subresource_range.layerCount = 1; + image_subresource_range.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; + image_subresource_range.baseMipLevel = 0; + image_subresource_range.levelCount = 1; + image_subresource_range.baseArrayLayer = 0; + image_subresource_range.layerCount = 1; VkExtent3D image_size = { - .width = swapchain.extent.width, - .height = swapchain.extent.height, - .depth = 1, + .width = swapchain.extent.width, + .height = swapchain.extent.height, + .depth = 1, }; for (size_t image_index = 0; image_index < swapchain.image_count; image_index++) { @@ -937,20 +922,20 @@ swapchain vkapi::create_swapchain(VkSurfaceKHR surface, size_t min_image_count, current_image->usages = usages; - VkImageViewCreateInfo image_view_create_info = {}; - image_view_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO; - image_view_create_info.pNext = nullptr; - image_view_create_info.flags = 0; - image_view_create_info.image = current_image->handle; - image_view_create_info.viewType = VK_IMAGE_VIEW_TYPE_2D; - image_view_create_info.format = swapchain.surface_format.format; - image_view_create_info.components = { + VkImageViewCreateInfo image_view_create_info = {}; + image_view_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO; + image_view_create_info.pNext = nullptr; + image_view_create_info.flags = 0; + image_view_create_info.image = current_image->handle; + image_view_create_info.viewType = VK_IMAGE_VIEW_TYPE_2D; + image_view_create_info.format = swapchain.surface_format.format; + image_view_create_info.components = { VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY }; - image_view_create_info.subresourceRange = image_subresource_range; + image_view_create_info.subresourceRange = image_subresource_range; VKRESULT(vkCreateImageView(context.device, &image_view_create_info, nullptr, ¤t_image->view)) @@ -977,63 +962,62 @@ swapchain vkapi::create_swapchain(VkSurfaceKHR surface, size_t min_image_count, void vkapi::destroy_swapchain(swapchain& swapchain) { VKRESULT(vkDeviceWaitIdle(context.device)) - for(auto &image: swapchain.images) { + for (auto& image : swapchain.images) { // TODO: Change this if (images[image]->bindless_storage_index != 0) bindless_descriptor.free(images[image]->bindless_storage_index, VK_DESCRIPTOR_TYPE_STORAGE_IMAGE); if (images[image]->bindless_sampled_index != 0) - bindless_descriptor.free(images[image]->bindless_sampled_index, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE); + bindless_descriptor.free(images[image]->bindless_sampled_index, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE); vkDestroyImageView(context.device, images[image]->view, nullptr); } vkDestroySwapchainKHR(context.device, swapchain.handle, nullptr); } - void vkapi::update_descriptor_image(handle img, VkDescriptorType type) { VkDescriptorImageInfo descriptor_image_info; VkWriteDescriptorSet write_descriptor; auto* current_image = images[img]; - descriptor_image_info.sampler = VK_NULL_HANDLE; - descriptor_image_info.imageView = current_image->view; - descriptor_image_info.imageLayout = VK_IMAGE_LAYOUT_GENERAL; + descriptor_image_info.sampler = VK_NULL_HANDLE; + descriptor_image_info.imageView = current_image->view; + descriptor_image_info.imageLayout = VK_IMAGE_LAYOUT_GENERAL; - write_descriptor.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; - write_descriptor.pNext = nullptr; - write_descriptor.dstSet = bindless_descriptor.set; - write_descriptor.dstBinding = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? 2 : 1; - write_descriptor.dstArrayElement = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? current_image->bindless_storage_index : current_image->bindless_sampled_index; - write_descriptor.descriptorCount = 1; - write_descriptor.descriptorType = type; - write_descriptor.pImageInfo = &descriptor_image_info; - write_descriptor.pBufferInfo = VK_NULL_HANDLE; - write_descriptor.pTexelBufferView = VK_NULL_HANDLE; + write_descriptor.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; + write_descriptor.pNext = nullptr; + write_descriptor.dstSet = bindless_descriptor.set; + write_descriptor.dstBinding = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? 2 : 1; + write_descriptor.dstArrayElement = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? current_image->bindless_storage_index : current_image->bindless_sampled_index; + write_descriptor.descriptorCount = 1; + write_descriptor.descriptorType = type; + write_descriptor.pImageInfo = &descriptor_image_info; + write_descriptor.pBufferInfo = VK_NULL_HANDLE; + write_descriptor.pTexelBufferView = VK_NULL_HANDLE; vkUpdateDescriptorSets(context.device, 1, &write_descriptor, 0, nullptr); } -void vkapi::update_descriptor_images(std::vector<handle> &handles, VkDescriptorType type) { - std::vector<VkDescriptorImageInfo> descriptor_images_info { images.size() }; - std::vector<VkWriteDescriptorSet> writes_descriptor { images.size() }; +void vkapi::update_descriptor_images(std::vector<handle>& handles, VkDescriptorType type) { + std::vector<VkDescriptorImageInfo> descriptor_images_info{ images.size() }; + std::vector<VkWriteDescriptorSet> writes_descriptor{ images.size() }; for (size_t image_index = 0; image_index < images.size(); image_index++) { auto image = images[handles[image_index]]; - descriptor_images_info[image_index].sampler = VK_NULL_HANDLE; - descriptor_images_info[image_index].imageView = image->view; - descriptor_images_info[image_index].imageLayout = VK_IMAGE_LAYOUT_GENERAL; + descriptor_images_info[image_index].sampler = VK_NULL_HANDLE; + descriptor_images_info[image_index].imageView = image->view; + descriptor_images_info[image_index].imageLayout = VK_IMAGE_LAYOUT_GENERAL; - writes_descriptor[image_index].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; - writes_descriptor[image_index].pNext = nullptr; - writes_descriptor[image_index].dstSet = bindless_descriptor.set; - writes_descriptor[image_index].dstBinding = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? 2 : 1; - writes_descriptor[image_index].dstArrayElement = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? image->bindless_storage_index : image->bindless_sampled_index; - writes_descriptor[image_index].descriptorCount = 1; - writes_descriptor[image_index].descriptorType = type; - writes_descriptor[image_index].pImageInfo = &descriptor_images_info[image_index]; - writes_descriptor[image_index].pBufferInfo = VK_NULL_HANDLE; - writes_descriptor[image_index].pTexelBufferView = VK_NULL_HANDLE; + writes_descriptor[image_index].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; + writes_descriptor[image_index].pNext = nullptr; + writes_descriptor[image_index].dstSet = bindless_descriptor.set; + writes_descriptor[image_index].dstBinding = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? 2 : 1; + writes_descriptor[image_index].dstArrayElement = type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE ? image->bindless_storage_index : image->bindless_sampled_index; + writes_descriptor[image_index].descriptorCount = 1; + writes_descriptor[image_index].descriptorType = type; + writes_descriptor[image_index].pImageInfo = &descriptor_images_info[image_index]; + writes_descriptor[image_index].pBufferInfo = VK_NULL_HANDLE; + writes_descriptor[image_index].pTexelBufferView = VK_NULL_HANDLE; } vkUpdateDescriptorSets(context.device, writes_descriptor.size(), writes_descriptor.data(), 0, nullptr); @@ -1044,44 +1028,44 @@ void vkapi::update_descriptor_sampler(handle sampler) { VkWriteDescriptorSet write_descriptor; auto current_sampler = samplers[sampler]; - descriptor_image_info.sampler = current_sampler->handle; - descriptor_image_info.imageView = VK_NULL_HANDLE; - descriptor_image_info.imageLayout = VK_IMAGE_LAYOUT_GENERAL; + descriptor_image_info.sampler = current_sampler->handle; + descriptor_image_info.imageView = VK_NULL_HANDLE; + descriptor_image_info.imageLayout = VK_IMAGE_LAYOUT_GENERAL; - write_descriptor.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; - write_descriptor.pNext = nullptr; - write_descriptor.dstSet = bindless_descriptor.set; - write_descriptor.dstBinding = 0; - write_descriptor.dstArrayElement = current_sampler->bindless_index; - write_descriptor.descriptorCount = 1; - write_descriptor.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER; - write_descriptor.pImageInfo = &descriptor_image_info; - write_descriptor.pBufferInfo = VK_NULL_HANDLE; - write_descriptor.pTexelBufferView = VK_NULL_HANDLE; + write_descriptor.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; + write_descriptor.pNext = nullptr; + write_descriptor.dstSet = bindless_descriptor.set; + write_descriptor.dstBinding = 0; + write_descriptor.dstArrayElement = current_sampler->bindless_index; + write_descriptor.descriptorCount = 1; + write_descriptor.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER; + write_descriptor.pImageInfo = &descriptor_image_info; + write_descriptor.pBufferInfo = VK_NULL_HANDLE; + write_descriptor.pTexelBufferView = VK_NULL_HANDLE; vkUpdateDescriptorSets(context.device, 1, &write_descriptor, 0, nullptr); } -void vkapi::update_descriptor_samplers(std::vector<handle> &handles) { - std::vector<VkDescriptorImageInfo> descriptor_images_info { samplers.size() }; - std::vector<VkWriteDescriptorSet> writes_descriptor { samplers.size() }; +void vkapi::update_descriptor_samplers(std::vector<handle>& handles) { + std::vector<VkDescriptorImageInfo> descriptor_images_info{ samplers.size() }; + std::vector<VkWriteDescriptorSet> writes_descriptor{ samplers.size() }; for (size_t sampler_index = 0; sampler_index < samplers.size(); sampler_index++) { auto sampler = samplers[handles[sampler_index]]; - descriptor_images_info[sampler_index].sampler = sampler->handle; - descriptor_images_info[sampler_index].imageView = VK_NULL_HANDLE; - descriptor_images_info[sampler_index].imageLayout = VK_IMAGE_LAYOUT_GENERAL; + descriptor_images_info[sampler_index].sampler = sampler->handle; + descriptor_images_info[sampler_index].imageView = VK_NULL_HANDLE; + descriptor_images_info[sampler_index].imageLayout = VK_IMAGE_LAYOUT_GENERAL; - writes_descriptor[sampler_index].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; - writes_descriptor[sampler_index].pNext = nullptr; - writes_descriptor[sampler_index].dstSet = bindless_descriptor.set; - writes_descriptor[sampler_index].dstBinding = 0; - writes_descriptor[sampler_index].dstArrayElement = sampler->bindless_index; - writes_descriptor[sampler_index].descriptorCount = 1; - writes_descriptor[sampler_index].descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER; - writes_descriptor[sampler_index].pImageInfo = &descriptor_images_info[sampler_index]; - writes_descriptor[sampler_index].pBufferInfo = VK_NULL_HANDLE; - writes_descriptor[sampler_index].pTexelBufferView = VK_NULL_HANDLE; + writes_descriptor[sampler_index].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; + writes_descriptor[sampler_index].pNext = nullptr; + writes_descriptor[sampler_index].dstSet = bindless_descriptor.set; + writes_descriptor[sampler_index].dstBinding = 0; + writes_descriptor[sampler_index].dstArrayElement = sampler->bindless_index; + writes_descriptor[sampler_index].descriptorCount = 1; + writes_descriptor[sampler_index].descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER; + writes_descriptor[sampler_index].pImageInfo = &descriptor_images_info[sampler_index]; + writes_descriptor[sampler_index].pBufferInfo = VK_NULL_HANDLE; + writes_descriptor[sampler_index].pTexelBufferView = VK_NULL_HANDLE; } vkUpdateDescriptorSets(context.device, writes_descriptor.size(), writes_descriptor.data(), 0, nullptr); @@ -1093,28 +1077,28 @@ void vkapi::update_constants(VkCommandBuffer command_buffer, VkShaderStageFlagBi void vkapi::start_record(VkCommandBuffer command_buffer) { VkCommandBufferBeginInfo cmd_buf_begin_info = {}; - cmd_buf_begin_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; - cmd_buf_begin_info.pNext = nullptr; - cmd_buf_begin_info.flags = 0; - cmd_buf_begin_info.pInheritanceInfo = nullptr; + cmd_buf_begin_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; + cmd_buf_begin_info.pNext = nullptr; + cmd_buf_begin_info.flags = 0; + cmd_buf_begin_info.pInheritanceInfo = nullptr; vkBeginCommandBuffer(command_buffer, &cmd_buf_begin_info); } void vkapi::image_barrier(VkCommandBuffer command_buffer, VkImageLayout dst_layout, VkPipelineStageFlagBits dst_stage, VkAccessFlags dst_access, handle image) { - auto *current_image = images[image]; + auto* current_image = images[image]; - VkImageMemoryBarrier image_barrier = {}; - image_barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER; - image_barrier.pNext = nullptr; - image_barrier.srcAccessMask = current_image->previous_access; - image_barrier.dstAccessMask = dst_access; - image_barrier.oldLayout = current_image->previous_layout; - image_barrier.newLayout = dst_layout; - image_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; - image_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; - image_barrier.image = current_image->handle; - image_barrier.subresourceRange = current_image->subresource_range; + VkImageMemoryBarrier image_barrier = {}; + image_barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER; + image_barrier.pNext = nullptr; + image_barrier.srcAccessMask = current_image->previous_access; + image_barrier.dstAccessMask = dst_access; + image_barrier.oldLayout = current_image->previous_layout; + image_barrier.newLayout = dst_layout; + image_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; + image_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; + image_barrier.image = current_image->handle; + image_barrier.subresourceRange = current_image->subresource_range; vkCmdPipelineBarrier( command_buffer, @@ -1126,15 +1110,13 @@ void vkapi::image_barrier(VkCommandBuffer command_buffer, VkImageLayout dst_layo 0, nullptr, 1, - &image_barrier - ); + &image_barrier); current_image->previous_layout = dst_layout; current_image->previous_access = dst_access; current_image->previous_stage = dst_stage; } - void vkapi::begin_render_pass(VkCommandBuffer command_buffer, VkRenderPass render_pass, std::vector<VkImageView>& attachments, framebuffer framebuffer, VkExtent2D size) { VkRect2D render_area = { { @@ -1145,20 +1127,20 @@ void vkapi::begin_render_pass(VkCommandBuffer command_buffer, VkRenderPass rende }; VkRenderPassAttachmentBeginInfo attachment_begin_info = {}; - attachment_begin_info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO; - attachment_begin_info.pNext = VK_NULL_HANDLE; - attachment_begin_info.attachmentCount = attachments.size(); - attachment_begin_info.pAttachments = attachments.data(); + attachment_begin_info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO; + attachment_begin_info.pNext = VK_NULL_HANDLE; + attachment_begin_info.attachmentCount = attachments.size(); + attachment_begin_info.pAttachments = attachments.data(); - VkClearValue clear_value { .color { .float32 { 0.f, 0.f, 0.f, 1.f } } }; - VkRenderPassBeginInfo render_pass_begin_info = {}; - render_pass_begin_info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; - render_pass_begin_info.pNext = &attachment_begin_info; - render_pass_begin_info.renderPass = render_pass; - render_pass_begin_info.framebuffer = framebuffer.handle; - render_pass_begin_info.renderArea = render_area; - render_pass_begin_info.clearValueCount = 1; - render_pass_begin_info.pClearValues = &clear_value; + VkClearValue clear_value{ .color{ .float32{ 0.f, 0.f, 0.f, 1.f } } }; + VkRenderPassBeginInfo render_pass_begin_info = {}; + render_pass_begin_info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; + render_pass_begin_info.pNext = &attachment_begin_info; + render_pass_begin_info.renderPass = render_pass; + render_pass_begin_info.framebuffer = framebuffer.handle; + render_pass_begin_info.renderArea = render_area; + render_pass_begin_info.clearValueCount = 1; + render_pass_begin_info.pClearValues = &clear_value; vkCmdBeginRenderPass(command_buffer, &render_pass_begin_info, VK_SUBPASS_CONTENTS_INLINE); } @@ -1167,7 +1149,6 @@ void vkapi::end_render_pass(VkCommandBuffer command_buffer) { vkCmdEndRenderPass(command_buffer); } - void vkapi::run_compute_pipeline(VkCommandBuffer command_buffer, pipeline& pipeline, size_t group_count_x, size_t group_count_y, size_t group_count_z) { vkCmdBindDescriptorSets(command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, bindless_descriptor.pipeline_layout, 0, 1, &bindless_descriptor.set, 0, nullptr); @@ -1192,86 +1173,85 @@ void vkapi::draw(VkCommandBuffer command_buffer, pipeline& pipeline, handle inde } void vkapi::blit_full(VkCommandBuffer command_buffer, handle src, handle dst) { - auto *src_image = images[src]; - auto *dst_image = images[dst]; + auto* src_image = images[src]; + auto* dst_image = images[dst]; - VkImageSubresourceLayers images_subres_layers { - .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT, - .mipLevel = 0, + VkImageSubresourceLayers images_subres_layers{ + .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT, + .mipLevel = 0, .baseArrayLayer = 0, - .layerCount = 1, + .layerCount = 1, }; - VkOffset3D start_offset { - .x = 0, - .y = 0, - .z = 0, + VkOffset3D start_offset{ + .x = 0, + .y = 0, + .z = 0, }; - VkOffset3D end_offset { - .x = (int32_t)dst_image->size.width, - .y = (int32_t)dst_image->size.height, - .z = (int32_t)dst_image->size.depth, + VkOffset3D end_offset{ + .x = (int32_t)dst_image->size.width, + .y = (int32_t)dst_image->size.height, + .z = (int32_t)dst_image->size.depth, }; - VkImageBlit blit_region { + VkImageBlit blit_region{ .srcSubresource = images_subres_layers, - .srcOffsets = { start_offset, end_offset }, + .srcOffsets = { start_offset, end_offset }, .dstSubresource = images_subres_layers, - .dstOffsets = { start_offset, end_offset }, + .dstOffsets = { start_offset, end_offset }, }; vkCmdBlitImage(command_buffer, src_image->handle, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, dst_image->handle, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, &blit_region, VK_FILTER_NEAREST); } -void vkapi::end_record(VkCommandBuffer command_buffer) { +void vkapi::end_record(VkCommandBuffer command_buffer){ VKRESULT(vkEndCommandBuffer(command_buffer)) } VkResult vkapi::submit(VkCommandBuffer command_buffers[], size_t command_buffers_count, VkSemaphore wait_semaphore, VkSemaphore signal_semaphore, VkFence submission_fence) const { VkPipelineStageFlags wait_stage = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT; - VkSubmitInfo submit_info = {}; - submit_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; - submit_info.pNext = nullptr; - submit_info.waitSemaphoreCount = wait_semaphore != nullptr ? 1 : 0; - submit_info.pWaitSemaphores = &wait_semaphore; - submit_info.pWaitDstStageMask = wait_semaphore != nullptr ? &wait_stage : VK_NULL_HANDLE; - submit_info.signalSemaphoreCount = signal_semaphore != nullptr ? 1 : 0; - submit_info.pSignalSemaphores = &signal_semaphore; - submit_info.commandBufferCount = command_buffers_count; - submit_info.pCommandBuffers = command_buffers; + VkSubmitInfo submit_info = {}; + submit_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; + submit_info.pNext = nullptr; + submit_info.waitSemaphoreCount = wait_semaphore != nullptr ? 1 : 0; + submit_info.pWaitSemaphores = &wait_semaphore; + submit_info.pWaitDstStageMask = wait_semaphore != nullptr ? &wait_stage : VK_NULL_HANDLE; + submit_info.signalSemaphoreCount = signal_semaphore != nullptr ? 1 : 0; + submit_info.pSignalSemaphores = &signal_semaphore; + submit_info.commandBufferCount = command_buffers_count; + submit_info.pCommandBuffers = command_buffers; return vkQueueSubmit(context.graphics_queue.handle, 1, &submit_info, submission_fence); } VkResult vkapi::present(swapchain& swapchain, uint32_t image_index, VkSemaphore wait_semaphore) const { - VkPresentInfoKHR present_info = {}; - present_info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR; - present_info.pNext = nullptr; + VkPresentInfoKHR present_info = {}; + present_info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR; + present_info.pNext = nullptr; present_info.waitSemaphoreCount = 1; - present_info.pWaitSemaphores = &wait_semaphore; - present_info.swapchainCount = 1; - present_info.pSwapchains = &swapchain.handle; - present_info.pImageIndices = &image_index; - present_info.pResults = nullptr; + present_info.pWaitSemaphores = &wait_semaphore; + present_info.swapchainCount = 1; + present_info.pSwapchains = &swapchain.handle; + present_info.pImageIndices = &image_index; + present_info.pResults = nullptr; return vkQueuePresentKHR(context.graphics_queue.handle, &present_info); } - const char* vkapi::shader_stage_extension(VkShaderStageFlags shader_stage) { - switch(shader_stage) { - case VK_SHADER_STAGE_VERTEX_BIT: { - return ".vert"; - } - case VK_SHADER_STAGE_FRAGMENT_BIT: { - return ".frag"; - } - case VK_SHADER_STAGE_COMPUTE_BIT: { - return ".comp"; - } - default: - assert(true && "Stage not supported"); - return ""; + switch (shader_stage) { + case VK_SHADER_STAGE_VERTEX_BIT: { + return ".vert"; + } + case VK_SHADER_STAGE_FRAGMENT_BIT: { + return ".frag"; + } + case VK_SHADER_STAGE_COMPUTE_BIT: { + return ".comp"; + } + default: + assert(true && "Stage not supported"); + return ""; } } diff --git a/src/vk-context.cpp b/src/vk-context.cpp index 824c216..1a6a78d 100644 --- a/src/vk-context.cpp +++ b/src/vk-context.cpp @@ -94,7 +94,7 @@ void vkcontext::create_instance() { check_available_instance_layers(needed_layers, needed_layers_count); - const char* needed_extensions[] = { + constexpr const char* needed_extensions[] = { VK_EXT_DEBUG_UTILS_EXTENSION_NAME, "VK_KHR_surface", #if defined(LINUX) @@ -105,7 +105,7 @@ void vkcontext::create_instance() { "VK_EXT_metal_surface" #endif }; - auto needed_extensions_count = sizeof(needed_extensions) / sizeof(needed_extensions[0]); + constexpr auto needed_extensions_count = sizeof(needed_extensions) / sizeof(needed_extensions[0]); check_available_instance_extensions(needed_extensions, needed_extensions_count); |
