WIP: Vulkan: Workbench #107886

Closed
Jeroen Bakker wants to merge 88 commits from Jeroen-Bakker:vulkan-draw-manager-workbench into main

When changing the target branch, be careful to rebase the branch in your fork to match. See documentation.
9 changed files with 143 additions and 31 deletions
Showing only changes of commit e1e5f0bf54 - Show all commits

View File

@ -215,6 +215,7 @@ set(VULKAN_SRC
vulkan/vk_drawlist.cc
vulkan/vk_fence.cc
vulkan/vk_framebuffer.cc
vulkan/vk_image_view.cc
vulkan/vk_immediate.cc
vulkan/vk_index_buffer.cc
vulkan/vk_memory.cc
@ -250,6 +251,7 @@ set(VULKAN_SRC
vulkan/vk_drawlist.hh
vulkan/vk_fence.hh
vulkan/vk_framebuffer.hh
vulkan/vk_image_view.hh
vulkan/vk_immediate.hh
vulkan/vk_index_buffer.hh
vulkan/vk_memory.hh

View File

@ -131,7 +131,9 @@ void VKBuffer::unmap()
BLI_assert(is_mapped());
const VKDevice &device = VKBackend::get().device_get();
VmaAllocator allocator = device.mem_allocator_get();
vmaUnmapMemory(allocator, allocation_);
if (allocator != VK_NULL_HANDLE) {
vmaUnmapMemory(allocator, allocation_);
}
mapped_memory_ = nullptr;
}
@ -143,7 +145,9 @@ bool VKBuffer::free()
const VKDevice &device = VKBackend::get().device_get();
VmaAllocator allocator = device.mem_allocator_get();
vmaDestroyBuffer(allocator, vk_buffer_, allocation_);
if (allocator != VK_NULL_HANDLE) {
vmaDestroyBuffer(allocator, vk_buffer_, allocation_);
}
return true;
}

View File

@ -174,7 +174,7 @@ void VKDescriptorSetTracker::update(VKContext &context)
binding.texture->layout_ensure(context, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
VkDescriptorImageInfo image_info = {};
image_info.sampler = binding.vk_sampler;
image_info.imageView = binding.texture->vk_image_view_handle();
image_info.imageView = binding.texture->image_view_get().vk_handle();
image_info.imageLayout = binding.texture->current_layout_get();
image_infos.append(image_info);

View File

@ -372,6 +372,8 @@ void VKFrameBuffer::render_pass_create()
std::array<VkAttachmentDescription, GPU_FB_MAX_ATTACHMENT> attachment_descriptions;
std::array<VkImageView, GPU_FB_MAX_ATTACHMENT> image_views;
std::array<VkAttachmentReference, GPU_FB_MAX_ATTACHMENT> attachment_references;
image_views_.clear();
bool has_depth_attachment = false;
bool found_attachment = false;
int depth_location = -1;
@ -402,9 +404,8 @@ void VKFrameBuffer::render_pass_create()
/* Ensure texture is allocated to ensure the image view. */
VKTexture &texture = *static_cast<VKTexture *>(unwrap(attachment.tex));
texture.ensure_allocated();
/* TODO: use image_view for attachment.mip */
// texture.mip_range_set(attachment.mip, attachment.mip);
image_views[attachment_location] = texture.vk_image_view_handle();
image_views_.append(VKImageView(texture, attachment.mip, name_));
image_views[attachment_location] = image_views_.last().vk_handle();
VkAttachmentDescription &attachment_description =
attachment_descriptions[attachment_location];
@ -505,6 +506,7 @@ void VKFrameBuffer::render_pass_free()
vkDestroyRenderPass(device.device_get(), vk_render_pass_, vk_allocation_callbacks);
vkDestroyFramebuffer(device.device_get(), vk_framebuffer_, vk_allocation_callbacks);
}
image_views_.clear();
vk_render_pass_ = VK_NULL_HANDLE;
vk_framebuffer_ = VK_NULL_HANDLE;
}

View File

@ -15,6 +15,7 @@
#include "gpu_framebuffer_private.hh"
#include "vk_common.hh"
#include "vk_image_view.hh"
namespace blender::gpu {
@ -41,6 +42,8 @@ class VKFrameBuffer : public FrameBuffer {
*/
bool flip_viewport_ = false;
Vector<VKImageView, GPU_FB_MAX_ATTACHMENT> image_views_;
public:
/**
* Create a conventional framebuffer to attach texture to.

View File

@ -0,0 +1,68 @@
/* SPDX-FileCopyrightText: 2022 Blender Foundation
*
* SPDX-License-Identifier: GPL-2.0-or-later */
/** \file
* \ingroup gpu
*/
#include "vk_image_view.hh"
#include "vk_backend.hh"
#include "vk_debug.hh"
#include "vk_device.hh"
#include "vk_memory.hh"
#include "vk_texture.hh"
namespace blender::gpu {
VKImageView::VKImageView(VKTexture &texture, int mip_level, StringRefNull name)
: vk_image_view_(create_vk_image_view(texture, mip_level, name))
{
BLI_assert(vk_image_view_ != VK_NULL_HANDLE);
}
VKImageView::VKImageView(VkImageView vk_image_view) : vk_image_view_(vk_image_view)
{
BLI_assert(vk_image_view_ != VK_NULL_HANDLE);
}
VKImageView::VKImageView(VKImageView &&other)
{
vk_image_view_ = other.vk_image_view_;
other.vk_image_view_ = VK_NULL_HANDLE;
}
VKImageView::~VKImageView()
{
if (vk_image_view_ != VK_NULL_HANDLE) {
VK_ALLOCATION_CALLBACKS
const VKDevice &device = VKBackend::get().device_get();
vkDestroyImageView(device.device_get(), vk_image_view_, vk_allocation_callbacks);
}
}
VkImageView VKImageView::create_vk_image_view(VKTexture &texture,
int mip_level,
StringRefNull name)
{
VK_ALLOCATION_CALLBACKS
VkImageViewCreateInfo image_view_info = {};
image_view_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
image_view_info.image = texture.vk_image_handle();
image_view_info.viewType = to_vk_image_view_type(texture.type_get());
image_view_info.format = to_vk_format(texture.format_get());
image_view_info.components = to_vk_component_mapping(texture.format_get());
image_view_info.subresourceRange.aspectMask = to_vk_image_aspect_flag_bits(texture.format_get());
image_view_info.subresourceRange.baseMipLevel = mip_level;
image_view_info.subresourceRange.levelCount = 1;
image_view_info.subresourceRange.baseArrayLayer = 0;
image_view_info.subresourceRange.layerCount = VK_REMAINING_ARRAY_LAYERS;
const VKDevice &device = VKBackend::get().device_get();
VkImageView image_view = VK_NULL_HANDLE;
vkCreateImageView(device.device_get(), &image_view_info, vk_allocation_callbacks, &image_view);
debug::object_label(image_view, name.c_str());
return image_view;
}
} // namespace blender::gpu

View File

@ -0,0 +1,44 @@
/* SPDX-FileCopyrightText: 2022 Blender Foundation
*
* SPDX-License-Identifier: GPL-2.0-or-later */
/** \file
* \ingroup gpu
*/
#pragma once
#include "vk_common.hh"
#include "BLI_string_ref.hh"
#include "BLI_utility_mixins.hh"
namespace blender::gpu {
class VKTexture;
class VKImageView : NonCopyable {
VkImageView vk_image_view_ = VK_NULL_HANDLE;
public:
VKImageView(VKTexture &texture, int mip_level, StringRefNull name);
/**
* Wrap the given vk_image_view handle. Note that the vk_image_view handle ownership is
* transferred to VKImageView.
*/
VKImageView(VkImageView vk_image_view);
VKImageView(VKImageView &&other);
~VKImageView();
VkImageView vk_handle() const
{
BLI_assert(vk_image_view_ != VK_NULL_HANDLE);
return vk_image_view_;
}
private:
static VkImageView create_vk_image_view(VKTexture &texture, int mip_level, StringRefNull name);
};
} // namespace blender::gpu

View File

@ -25,11 +25,9 @@ namespace blender::gpu {
VKTexture::~VKTexture()
{
VK_ALLOCATION_CALLBACKS
if (is_allocated()) {
const VKDevice &device = VKBackend::get().device_get();
vmaDestroyImage(device.mem_allocator_get(), vk_image_, allocation_);
vkDestroyImageView(device.device_get(), vk_image_view_, vk_allocation_callbacks);
}
}
@ -526,26 +524,13 @@ void VKTexture::layout_ensure(VKContext &context,
void VKTexture::vk_image_view_ensure()
{
if (flags_ & IMAGE_VIEW_DIRTY) {
vk_image_view_free();
vk_image_view_create();
image_view_update();
flags_ &= ~IMAGE_VIEW_DIRTY;
}
BLI_assert(vk_image_view_ != VK_NULL_HANDLE);
}
void VKTexture::vk_image_view_free()
void VKTexture::image_view_update()
{
if (vk_image_view_ != VK_NULL_HANDLE) {
VK_ALLOCATION_CALLBACKS
const VKDevice &device = VKBackend::get().device_get();
vkDestroyImageView(device.device_get(), vk_image_view_, vk_allocation_callbacks);
vk_image_view_ = VK_NULL_HANDLE;
}
}
void VKTexture::vk_image_view_create()
{
BLI_assert(vk_image_view_ == VK_NULL_HANDLE);
VK_ALLOCATION_CALLBACKS
VkImageViewCreateInfo image_view_info = {};
image_view_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
@ -560,9 +545,10 @@ void VKTexture::vk_image_view_create()
image_view_info.subresourceRange.layerCount = VK_REMAINING_ARRAY_LAYERS;
const VKDevice &device = VKBackend::get().device_get();
vkCreateImageView(
device.device_get(), &image_view_info, vk_allocation_callbacks, &vk_image_view_);
debug::object_label(vk_image_view_, name_);
VkImageView image_view = VK_NULL_HANDLE;
vkCreateImageView(device.device_get(), &image_view_info, vk_allocation_callbacks, &image_view);
debug::object_label(image_view, name_);
image_view_.emplace(image_view);
}
IndexRange VKTexture::mip_map_range() const

View File

@ -9,7 +9,9 @@
#pragma once
#include "gpu_texture_private.hh"
#include "vk_context.hh"
#include "vk_image_view.hh"
namespace blender::gpu {
@ -17,9 +19,11 @@ class VKSampler;
class VKTexture : public Texture {
VkImage vk_image_ = VK_NULL_HANDLE;
VkImageView vk_image_view_ = VK_NULL_HANDLE;
VmaAllocation allocation_ = VK_NULL_HANDLE;
/* Image view when used in a shader. */
std::optional<VKImageView> image_view_;
/* Last image layout of the texture. Frame-buffer and barriers can alter/require the actual
* layout to be changed. During this it requires to set the current layout in order to know which
* conversion should happen. #current_layout_ keep track of the layout so the correct conversion
@ -127,17 +131,16 @@ class VKTexture : public Texture {
/** \name Mipmapping
* \{ */
public:
VkImageView vk_image_view_handle()
VKImageView &image_view_get()
{
vk_image_view_ensure();
return vk_image_view_;
return *image_view_;
}
private:
IndexRange mip_map_range() const;
void vk_image_view_ensure();
void vk_image_view_free();
void vk_image_view_create();
void image_view_update();
/** \} */
};