[Vulkan] Load Vulkan manually for more lifetime and extension control

This commit is contained in:
Triang3l
2021-07-11 22:56:01 +03:00
parent 458e4e1a31
commit 692e329e9c
38 changed files with 1224 additions and 788 deletions

View File

@@ -26,6 +26,7 @@ Blitter::~Blitter() { Shutdown(); }
VkResult Blitter::Initialize(VulkanDevice* device) {
device_ = device;
const VulkanDevice::DeviceFunctions& dfn = device_->dfn();
VkResult status = VK_SUCCESS;
// Shaders
@@ -34,8 +35,8 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
shader_create_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
shader_create_info.codeSize = sizeof(blit_vert);
shader_create_info.pCode = reinterpret_cast<const uint32_t*>(blit_vert);
status = vkCreateShaderModule(*device_, &shader_create_info, nullptr,
&blit_vertex_);
status = dfn.vkCreateShaderModule(*device_, &shader_create_info, nullptr,
&blit_vertex_);
CheckResult(status, "vkCreateShaderModule");
if (status != VK_SUCCESS) {
return status;
@@ -46,8 +47,8 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
shader_create_info.codeSize = sizeof(blit_color_frag);
shader_create_info.pCode = reinterpret_cast<const uint32_t*>(blit_color_frag);
status = vkCreateShaderModule(*device_, &shader_create_info, nullptr,
&blit_color_);
status = dfn.vkCreateShaderModule(*device_, &shader_create_info, nullptr,
&blit_color_);
CheckResult(status, "vkCreateShaderModule");
if (status != VK_SUCCESS) {
return status;
@@ -58,8 +59,8 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
shader_create_info.codeSize = sizeof(blit_depth_frag);
shader_create_info.pCode = reinterpret_cast<const uint32_t*>(blit_depth_frag);
status = vkCreateShaderModule(*device_, &shader_create_info, nullptr,
&blit_depth_);
status = dfn.vkCreateShaderModule(*device_, &shader_create_info, nullptr,
&blit_depth_);
CheckResult(status, "vkCreateShaderModule");
if (status != VK_SUCCESS) {
return status;
@@ -83,8 +84,8 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
texture_binding.stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT;
texture_binding.pImmutableSamplers = nullptr;
texture_set_layout_info.pBindings = &texture_binding;
status = vkCreateDescriptorSetLayout(*device_, &texture_set_layout_info,
nullptr, &descriptor_set_layout_);
status = dfn.vkCreateDescriptorSetLayout(*device_, &texture_set_layout_info,
nullptr, &descriptor_set_layout_);
CheckResult(status, "vkCreateDescriptorSetLayout");
if (status != VK_SUCCESS) {
return status;
@@ -119,8 +120,8 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
pipeline_layout_info.pushConstantRangeCount =
static_cast<uint32_t>(xe::countof(push_constant_ranges));
pipeline_layout_info.pPushConstantRanges = push_constant_ranges;
status = vkCreatePipelineLayout(*device_, &pipeline_layout_info, nullptr,
&pipeline_layout_);
status = dfn.vkCreatePipelineLayout(*device_, &pipeline_layout_info, nullptr,
&pipeline_layout_);
CheckResult(status, "vkCreatePipelineLayout");
if (status != VK_SUCCESS) {
return status;
@@ -147,8 +148,8 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
VK_BORDER_COLOR_INT_TRANSPARENT_BLACK,
VK_FALSE,
};
status =
vkCreateSampler(*device_, &sampler_create_info, nullptr, &samp_nearest_);
status = dfn.vkCreateSampler(*device_, &sampler_create_info, nullptr,
&samp_nearest_);
CheckResult(status, "vkCreateSampler");
if (status != VK_SUCCESS) {
return status;
@@ -157,8 +158,8 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
sampler_create_info.minFilter = VK_FILTER_LINEAR;
sampler_create_info.magFilter = VK_FILTER_LINEAR;
sampler_create_info.mipmapMode = VK_SAMPLER_MIPMAP_MODE_LINEAR;
status =
vkCreateSampler(*device_, &sampler_create_info, nullptr, &samp_linear_);
status = dfn.vkCreateSampler(*device_, &sampler_create_info, nullptr,
&samp_linear_);
CheckResult(status, "vkCreateSampler");
if (status != VK_SUCCESS) {
return status;
@@ -168,49 +169,50 @@ VkResult Blitter::Initialize(VulkanDevice* device) {
}
void Blitter::Shutdown() {
const VulkanDevice::DeviceFunctions& dfn = device_->dfn();
if (samp_nearest_) {
vkDestroySampler(*device_, samp_nearest_, nullptr);
dfn.vkDestroySampler(*device_, samp_nearest_, nullptr);
samp_nearest_ = nullptr;
}
if (samp_linear_) {
vkDestroySampler(*device_, samp_linear_, nullptr);
dfn.vkDestroySampler(*device_, samp_linear_, nullptr);
samp_linear_ = nullptr;
}
if (blit_vertex_) {
vkDestroyShaderModule(*device_, blit_vertex_, nullptr);
dfn.vkDestroyShaderModule(*device_, blit_vertex_, nullptr);
blit_vertex_ = nullptr;
}
if (blit_color_) {
vkDestroyShaderModule(*device_, blit_color_, nullptr);
dfn.vkDestroyShaderModule(*device_, blit_color_, nullptr);
blit_color_ = nullptr;
}
if (blit_depth_) {
vkDestroyShaderModule(*device_, blit_depth_, nullptr);
dfn.vkDestroyShaderModule(*device_, blit_depth_, nullptr);
blit_depth_ = nullptr;
}
if (pipeline_color_) {
vkDestroyPipeline(*device_, pipeline_color_, nullptr);
dfn.vkDestroyPipeline(*device_, pipeline_color_, nullptr);
pipeline_color_ = nullptr;
}
if (pipeline_depth_) {
vkDestroyPipeline(*device_, pipeline_depth_, nullptr);
dfn.vkDestroyPipeline(*device_, pipeline_depth_, nullptr);
pipeline_depth_ = nullptr;
}
if (pipeline_layout_) {
vkDestroyPipelineLayout(*device_, pipeline_layout_, nullptr);
dfn.vkDestroyPipelineLayout(*device_, pipeline_layout_, nullptr);
pipeline_layout_ = nullptr;
}
if (descriptor_set_layout_) {
vkDestroyDescriptorSetLayout(*device_, descriptor_set_layout_, nullptr);
dfn.vkDestroyDescriptorSetLayout(*device_, descriptor_set_layout_, nullptr);
descriptor_set_layout_ = nullptr;
}
for (auto& pipeline : pipelines_) {
vkDestroyPipeline(*device_, pipeline.second, nullptr);
dfn.vkDestroyPipeline(*device_, pipeline.second, nullptr);
}
pipelines_.clear();
for (auto& pass : render_passes_) {
vkDestroyRenderPass(*device_, pass.second, nullptr);
dfn.vkDestroyRenderPass(*device_, pass.second, nullptr);
}
render_passes_.clear();
}
@@ -230,6 +232,8 @@ void Blitter::BlitTexture2D(VkCommandBuffer command_buffer, VkFence fence,
VkFramebuffer dst_framebuffer, VkViewport viewport,
VkRect2D scissor, VkFilter filter,
bool color_or_depth, bool swap_channels) {
const VulkanDevice::DeviceFunctions& dfn = device_->dfn();
// Do we need a full draw, or can we cheap out with a blit command?
bool full_draw = swap_channels || true;
if (full_draw) {
@@ -249,18 +253,18 @@ void Blitter::BlitTexture2D(VkCommandBuffer command_buffer, VkFence fence,
nullptr,
};
vkCmdBeginRenderPass(command_buffer, &render_pass_info,
VK_SUBPASS_CONTENTS_INLINE);
dfn.vkCmdBeginRenderPass(command_buffer, &render_pass_info,
VK_SUBPASS_CONTENTS_INLINE);
vkCmdSetViewport(command_buffer, 0, 1, &viewport);
vkCmdSetScissor(command_buffer, 0, 1, &scissor);
dfn.vkCmdSetViewport(command_buffer, 0, 1, &viewport);
dfn.vkCmdSetScissor(command_buffer, 0, 1, &scissor);
// Acquire a pipeline.
auto pipeline =
GetPipeline(render_pass, color_or_depth ? blit_color_ : blit_depth_,
color_or_depth);
vkCmdBindPipeline(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS,
pipeline);
dfn.vkCmdBindPipeline(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS,
pipeline);
// Acquire and update a descriptor set for this image.
auto set = descriptor_pool_->AcquireEntry(descriptor_set_layout_);
@@ -287,10 +291,10 @@ void Blitter::BlitTexture2D(VkCommandBuffer command_buffer, VkFence fence,
write.pImageInfo = &image;
write.pBufferInfo = nullptr;
write.pTexelBufferView = nullptr;
vkUpdateDescriptorSets(*device_, 1, &write, 0, nullptr);
dfn.vkUpdateDescriptorSets(*device_, 1, &write, 0, nullptr);
vkCmdBindDescriptorSets(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS,
pipeline_layout_, 0, 1, &set, 0, nullptr);
dfn.vkCmdBindDescriptorSets(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS,
pipeline_layout_, 0, 1, &set, 0, nullptr);
VtxPushConstants vtx_constants = {
{
@@ -306,9 +310,9 @@ void Blitter::BlitTexture2D(VkCommandBuffer command_buffer, VkFence fence,
float(dst_rect.extent.height) / dst_extents.height,
},
};
vkCmdPushConstants(command_buffer, pipeline_layout_,
VK_SHADER_STAGE_VERTEX_BIT, 0, sizeof(VtxPushConstants),
&vtx_constants);
dfn.vkCmdPushConstants(command_buffer, pipeline_layout_,
VK_SHADER_STAGE_VERTEX_BIT, 0,
sizeof(VtxPushConstants), &vtx_constants);
PixPushConstants pix_constants = {
0,
@@ -316,12 +320,12 @@ void Blitter::BlitTexture2D(VkCommandBuffer command_buffer, VkFence fence,
0,
swap_channels ? 1 : 0,
};
vkCmdPushConstants(command_buffer, pipeline_layout_,
VK_SHADER_STAGE_FRAGMENT_BIT, sizeof(VtxPushConstants),
sizeof(PixPushConstants), &pix_constants);
dfn.vkCmdPushConstants(
command_buffer, pipeline_layout_, VK_SHADER_STAGE_FRAGMENT_BIT,
sizeof(VtxPushConstants), sizeof(PixPushConstants), &pix_constants);
vkCmdDraw(command_buffer, 4, 1, 0, 0);
vkCmdEndRenderPass(command_buffer);
dfn.vkCmdDraw(command_buffer, 4, 1, 0, 0);
dfn.vkCmdEndRenderPass(command_buffer);
}
}
@@ -421,8 +425,9 @@ VkRenderPass Blitter::CreateRenderPass(VkFormat output_format,
nullptr,
};
VkRenderPass renderpass = nullptr;
const VulkanDevice::DeviceFunctions& dfn = device_->dfn();
VkResult result =
vkCreateRenderPass(*device_, &renderpass_info, nullptr, &renderpass);
dfn.vkCreateRenderPass(*device_, &renderpass_info, nullptr, &renderpass);
CheckResult(result, "vkCreateRenderPass");
return renderpass;
@@ -431,6 +436,7 @@ VkRenderPass Blitter::CreateRenderPass(VkFormat output_format,
VkPipeline Blitter::CreatePipeline(VkRenderPass render_pass,
VkShaderModule frag_shader,
bool color_or_depth) {
const VulkanDevice::DeviceFunctions& dfn = device_->dfn();
VkResult result = VK_SUCCESS;
// Pipeline
@@ -576,8 +582,8 @@ VkPipeline Blitter::CreatePipeline(VkRenderPass render_pass,
pipeline_info.basePipelineIndex = -1;
VkPipeline pipeline = nullptr;
result = vkCreateGraphicsPipelines(*device_, nullptr, 1, &pipeline_info,
nullptr, &pipeline);
result = dfn.vkCreateGraphicsPipelines(*device_, nullptr, 1, &pipeline_info,
nullptr, &pipeline);
CheckResult(result, "vkCreateGraphicsPipelines");
return pipeline;