summaryrefslogtreecommitdiff
path: root/drivers/vulkan
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/vulkan')
-rw-r--r--drivers/vulkan/SCsub143
-rw-r--r--drivers/vulkan/rendering_device_vulkan.cpp158
-rw-r--r--drivers/vulkan/rendering_device_vulkan.h8
-rw-r--r--drivers/vulkan/vulkan_context.cpp63
-rw-r--r--drivers/vulkan/vulkan_context.h9
5 files changed, 214 insertions, 167 deletions
diff --git a/drivers/vulkan/SCsub b/drivers/vulkan/SCsub
index 6a2a57d18c..8fe75367a8 100644
--- a/drivers/vulkan/SCsub
+++ b/drivers/vulkan/SCsub
@@ -3,116 +3,45 @@
Import("env")
thirdparty_obj = []
+thirdparty_dir = "#thirdparty/vulkan"
+thirdparty_volk_dir = "#thirdparty/volk"
-# FIXME: Refactor all this to reduce code duplication.
-if env["platform"] == "android":
- # Use NDK Vulkan headers
- thirdparty_dir = env["ANDROID_NDK_ROOT"] + "/sources/third_party/vulkan/src"
- thirdparty_includes = [
- thirdparty_dir,
- thirdparty_dir + "/include",
- thirdparty_dir + "/layers",
- thirdparty_dir + "/layers/generated",
- ]
- env.Prepend(CPPPATH=thirdparty_includes)
-
- # Build Vulkan memory allocator
- env_thirdparty = env.Clone()
- env_thirdparty.disable_warnings()
-
- thirdparty_dir = "#thirdparty/vulkan"
- vma_sources = [thirdparty_dir + "/android/vk_mem_alloc.cpp"]
- env_thirdparty.add_source_files(thirdparty_obj, vma_sources)
+# Use bundled Vulkan headers
+env.Prepend(CPPPATH=[thirdparty_dir, thirdparty_dir + "/include"])
+
+if env["use_volk"]:
+ env.AppendUnique(CPPDEFINES=["USE_VOLK"])
+ env.Prepend(CPPPATH=[thirdparty_volk_dir])
+if env["platform"] == "android":
+ env.AppendUnique(CPPDEFINES=["VK_USE_PLATFORM_ANDROID_KHR"])
elif env["platform"] == "iphone":
- # Use bundled Vulkan headers
- thirdparty_dir = "#thirdparty/vulkan"
- env.Prepend(CPPPATH=[thirdparty_dir, thirdparty_dir + "/include", thirdparty_dir + "/loader"])
-
- # Build Vulkan memory allocator
- env_thirdparty = env.Clone()
- env_thirdparty.disable_warnings()
-
- vma_sources = [thirdparty_dir + "/vk_mem_alloc.cpp"]
- env_thirdparty.add_source_files(thirdparty_obj, vma_sources)
-
-elif env["builtin_vulkan"]:
- # Use bundled Vulkan headers
- thirdparty_dir = "#thirdparty/vulkan"
- env.Prepend(CPPPATH=[thirdparty_dir, thirdparty_dir + "/include", thirdparty_dir + "/loader"])
-
- # Build Vulkan loader library
- env_thirdparty = env.Clone()
- env_thirdparty.disable_warnings()
-
- loader_sources = [
- "cJSON.c",
- "debug_utils.c",
- "dev_ext_trampoline.c",
- "loader.c",
- "murmurhash.c",
- "phys_dev_ext.c",
- "trampoline.c",
- "unknown_ext_chain.c",
- "wsi.c",
- "extension_manual.c",
- ]
- vma_sources = [thirdparty_dir + "/vk_mem_alloc.cpp"]
-
- if env["platform"] == "windows":
- loader_sources.append("dirent_on_windows.c")
- env_thirdparty.AppendUnique(
- CPPDEFINES=[
- "VK_USE_PLATFORM_WIN32_KHR",
- "VULKAN_NON_CMAKE_BUILD",
- "WIN32_LEAN_AND_MEAN",
- 'API_NAME=\\"%s\\"' % "Vulkan",
- ]
- )
- if not env.msvc: # Windows 7+, missing in mingw headers
- env_thirdparty.AppendUnique(
- CPPDEFINES=["CM_GETIDLIST_FILTER_CLASS=0x00000200", "CM_GETIDLIST_FILTER_PRESENT=0x00000100"]
- )
- elif env["platform"] == "osx":
- env_thirdparty.AppendUnique(
- CPPDEFINES=[
- "VK_USE_PLATFORM_MACOS_MVK",
- "VULKAN_NON_CMAKE_BUILD",
- 'SYSCONFDIR=\\"%s\\"' % "/etc",
- 'FALLBACK_DATA_DIRS=\\"%s\\"' % "/usr/local/share:/usr/share",
- 'FALLBACK_CONFIG_DIRS=\\"%s\\"' % "/etc/xdg",
- ]
- )
- elif env["platform"] == "linuxbsd":
- env_thirdparty.AppendUnique(
- CPPDEFINES=[
- "VK_USE_PLATFORM_XLIB_KHR",
- "VULKAN_NON_CMAKE_BUILD",
- 'SYSCONFDIR=\\"%s\\"' % "/etc",
- 'FALLBACK_DATA_DIRS=\\"%s\\"' % "/usr/local/share:/usr/share",
- 'FALLBACK_CONFIG_DIRS=\\"%s\\"' % "/etc/xdg",
- ]
- )
- import platform
-
- if platform.system() == "Linux":
- # In glibc since 2.17 and musl libc since 1.1.24. Used by loader.c.
- env_thirdparty.AppendUnique(CPPDEFINES=["HAVE_SECURE_GETENV"])
-
- loader_sources = [thirdparty_dir + "/loader/" + file for file in loader_sources]
- env_thirdparty.add_source_files(thirdparty_obj, loader_sources)
- env_thirdparty.add_source_files(thirdparty_obj, vma_sources)
-
-else: # Always build VMA.
- thirdparty_dir = "#thirdparty/vulkan"
- env.Prepend(CPPPATH=[thirdparty_dir, thirdparty_dir + "/include"])
-
- # Build Vulkan loader library
- env_thirdparty = env.Clone()
- env_thirdparty.disable_warnings()
- vma_sources = [thirdparty_dir + "/vk_mem_alloc.cpp"]
-
- env_thirdparty.add_source_files(thirdparty_obj, vma_sources)
+ env.AppendUnique(CPPDEFINES=["VK_USE_PLATFORM_IOS_MVK"])
+elif env["platform"] == "linuxbsd":
+ env.AppendUnique(CPPDEFINES=["VK_USE_PLATFORM_XLIB_KHR"])
+elif env["platform"] == "osx":
+ env.AppendUnique(CPPDEFINES=["VK_USE_PLATFORM_MACOS_MVK"])
+elif env["platform"] == "windows":
+ env.AppendUnique(CPPDEFINES=["VK_USE_PLATFORM_WIN32_KHR"])
+
+# Build Vulkan memory allocator and volk
+env_thirdparty_vma = env.Clone()
+env_thirdparty_vma.disable_warnings()
+thirdparty_sources_vma = [thirdparty_dir + "/vk_mem_alloc.cpp"]
+
+if env["use_volk"]:
+ env_thirdparty_vma.AppendUnique(CPPDEFINES=["VMA_STATIC_VULKAN_FUNCTIONS=1"])
+ env_thirdparty_volk = env.Clone()
+ env_thirdparty_volk.disable_warnings()
+
+ thirdparty_sources_volk = [thirdparty_volk_dir + "/volk.c"]
+ env_thirdparty_volk.add_source_files(thirdparty_obj, thirdparty_sources_volk)
+elif env["platform"] == "android":
+ # Our current NDK version only provides old Vulkan headers,
+ # so we have to limit VMA.
+ env_thirdparty_vma.AppendUnique(CPPDEFINES=["VMA_VULKAN_VERSION=1000000"])
+
+env_thirdparty_vma.add_source_files(thirdparty_obj, thirdparty_sources_vma)
env.drivers_sources += thirdparty_obj
diff --git a/drivers/vulkan/rendering_device_vulkan.cpp b/drivers/vulkan/rendering_device_vulkan.cpp
index b5bd6cef38..6ad24f255f 100644
--- a/drivers/vulkan/rendering_device_vulkan.cpp
+++ b/drivers/vulkan/rendering_device_vulkan.cpp
@@ -2740,6 +2740,14 @@ bool RenderingDeviceVulkan::texture_is_valid(RID p_texture) {
return texture_owner.owns(p_texture);
}
+Size2i RenderingDeviceVulkan::texture_size(RID p_texture) {
+ _THREAD_SAFE_METHOD_
+
+ Texture *tex = texture_owner.getornull(p_texture);
+ ERR_FAIL_COND_V(!tex, Size2i());
+ return Size2i(tex->width, tex->height);
+}
+
Error RenderingDeviceVulkan::texture_copy(RID p_from_texture, RID p_to_texture, const Vector3 &p_from, const Vector3 &p_to, const Vector3 &p_size, uint32_t p_src_mipmap, uint32_t p_dst_mipmap, uint32_t p_src_layer, uint32_t p_dst_layer, uint32_t p_post_barrier) {
_THREAD_SAFE_METHOD_
@@ -3299,13 +3307,25 @@ VkRenderPass RenderingDeviceVulkan::_render_pass_create(const Vector<AttachmentF
// Also, each UNDEFINED will do an immediate layout transition (write), s.t. we must ensure execution synchronization vs.
// the read. If this is a performance issue, one could track the actual last accessor of each resource, adding only that
// stage
+
switch (is_depth ? p_initial_depth_action : p_initial_action) {
case INITIAL_ACTION_CLEAR_REGION:
case INITIAL_ACTION_CLEAR: {
- description.loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
- description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
- description.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; //don't care what is there
- dependency_from_external.srcStageMask |= reading_stages;
+ if (p_attachments[i].usage_flags & TEXTURE_USAGE_COLOR_ATTACHMENT_BIT) {
+ description.loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
+ description.initialLayout = is_sampled ? VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL : (is_storage ? VK_IMAGE_LAYOUT_GENERAL : VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL);
+ description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
+ } else if (p_attachments[i].usage_flags & TEXTURE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT) {
+ description.loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
+ description.initialLayout = is_sampled ? VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL : (is_storage ? VK_IMAGE_LAYOUT_GENERAL : VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL);
+ description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
+ dependency_from_external.srcStageMask |= reading_stages;
+ } else {
+ description.loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
+ description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
+ description.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; //don't care what is there
+ dependency_from_external.srcStageMask |= reading_stages;
+ }
} break;
case INITIAL_ACTION_KEEP: {
if (p_attachments[i].usage_flags & TEXTURE_USAGE_COLOR_ATTACHMENT_BIT) {
@@ -3363,7 +3383,58 @@ VkRenderPass RenderingDeviceVulkan::_render_pass_create(const Vector<AttachmentF
}
}
- switch (is_depth ? p_final_depth_action : p_final_action) {
+ bool used_last = false;
+
+ {
+ int last_pass = p_passes.size() - 1;
+
+ if (is_depth) {
+ //likely missing depth resolve?
+ if (p_passes[last_pass].depth_attachment == i) {
+ used_last = true;
+ }
+ } else {
+ if (p_passes[last_pass].resolve_attachments.size()) {
+ //if using resolve attachments, check resolve attachments
+ for (int j = 0; j < p_passes[last_pass].resolve_attachments.size(); j++) {
+ if (p_passes[last_pass].resolve_attachments[j] == i) {
+ used_last = true;
+ break;
+ }
+ }
+ } else {
+ for (int j = 0; j < p_passes[last_pass].color_attachments.size(); j++) {
+ if (p_passes[last_pass].color_attachments[j] == i) {
+ used_last = true;
+ break;
+ }
+ }
+ }
+ }
+
+ if (!used_last) {
+ for (int j = 0; j < p_passes[last_pass].preserve_attachments.size(); j++) {
+ if (p_passes[last_pass].preserve_attachments[j] == i) {
+ used_last = true;
+ break;
+ }
+ }
+ }
+ }
+
+ FinalAction final_action = p_final_action;
+ FinalAction final_depth_action = p_final_depth_action;
+
+ if (!used_last) {
+ if (is_depth) {
+ final_depth_action = FINAL_ACTION_DISCARD;
+
+ } else {
+ final_action = FINAL_ACTION_DISCARD;
+ }
+ }
+
+ switch (is_depth ? final_depth_action : final_action) {
case FINAL_ACTION_READ: {
if (p_attachments[i].usage_flags & TEXTURE_USAGE_COLOR_ATTACHMENT_BIT) {
description.storeOp = VK_ATTACHMENT_STORE_OP_STORE;
@@ -3516,21 +3587,6 @@ VkRenderPass RenderingDeviceVulkan::_render_pass_create(const Vector<AttachmentF
resolve_references.push_back(reference);
}
- LocalVector<uint32_t> &preserve_references = preserve_reference_array[i];
-
- for (int j = 0; j < pass->preserve_attachments.size(); j++) {
- int32_t attachment = pass->preserve_attachments[j];
-
- ERR_FAIL_COND_V_MSG(attachment == FramebufferPass::ATTACHMENT_UNUSED, VK_NULL_HANDLE, "Invalid framebuffer format attachment(" + itos(attachment) + "), in pass (" + itos(i) + "), preserve attachment (" + itos(j) + "). Preserve attachments can't be unused.");
-
- ERR_FAIL_INDEX_V_MSG(attachment, p_attachments.size(), VK_NULL_HANDLE, "Invalid framebuffer format attachment(" + itos(attachment) + "), in pass (" + itos(i) + "), preserve attachment (" + itos(j) + ").");
- ERR_FAIL_COND_V_MSG(attachment_last_pass[attachment] == i, VK_NULL_HANDLE, "Invalid framebuffer format attachment(" + itos(attachment) + "), in pass (" + itos(i) + "), it already was used for something else before in this pass.");
-
- attachment_last_pass[attachment] = i;
-
- preserve_references.push_back(attachment);
- }
-
VkAttachmentReference &depth_stencil_reference = depth_reference_array[i];
if (pass->depth_attachment != FramebufferPass::ATTACHMENT_UNUSED) {
@@ -3554,6 +3610,22 @@ VkRenderPass RenderingDeviceVulkan::_render_pass_create(const Vector<AttachmentF
depth_stencil_reference.layout = VK_IMAGE_LAYOUT_UNDEFINED;
}
+ LocalVector<uint32_t> &preserve_references = preserve_reference_array[i];
+
+ for (int j = 0; j < pass->preserve_attachments.size(); j++) {
+ int32_t attachment = pass->preserve_attachments[j];
+
+ ERR_FAIL_COND_V_MSG(attachment == FramebufferPass::ATTACHMENT_UNUSED, VK_NULL_HANDLE, "Invalid framebuffer format attachment(" + itos(attachment) + "), in pass (" + itos(i) + "), preserve attachment (" + itos(j) + "). Preserve attachments can't be unused.");
+
+ ERR_FAIL_INDEX_V_MSG(attachment, p_attachments.size(), VK_NULL_HANDLE, "Invalid framebuffer format attachment(" + itos(attachment) + "), in pass (" + itos(i) + "), preserve attachment (" + itos(j) + ").");
+
+ if (attachment_last_pass[attachment] != i) {
+ //preserve can still be used to keep depth or color from being discarded after use
+ attachment_last_pass[attachment] = i;
+ preserve_references.push_back(attachment);
+ }
+ }
+
VkSubpassDescription &subpass = subpasses[i];
subpass.flags = 0;
subpass.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS;
@@ -3761,7 +3833,7 @@ RenderingDevice::FramebufferFormatID RenderingDeviceVulkan::framebuffer_format_c
VkRenderPass render_pass;
VkResult res = vkCreateRenderPass(device, &render_pass_create_info, nullptr, &render_pass);
- ERR_FAIL_COND_V_MSG(res, VK_NULL_HANDLE, "vkCreateRenderPass for empty fb failed with error " + itos(res) + ".");
+ ERR_FAIL_COND_V_MSG(res, 0, "vkCreateRenderPass for empty fb failed with error " + itos(res) + ".");
if (render_pass == VK_NULL_HANDLE) { //was likely invalid
return INVALID_ID;
@@ -4378,7 +4450,10 @@ bool RenderingDeviceVulkan::_uniform_add_binding(Vector<Vector<VkDescriptorSetLa
}
#endif
-#define SHADER_BINARY_VERSION 1
+//version 1: initial
+//version 2: Added shader name
+
+#define SHADER_BINARY_VERSION 2
String RenderingDeviceVulkan::shader_get_binary_cache_key() const {
return "Vulkan-SV" + itos(SHADER_BINARY_VERSION);
@@ -4412,9 +4487,10 @@ struct RenderingDeviceVulkanShaderBinaryData {
uint32_t push_constant_size;
uint32_t push_constants_vk_stage;
uint32_t stage_count;
+ uint32_t shader_name_len;
};
-Vector<uint8_t> RenderingDeviceVulkan::shader_compile_binary_from_spirv(const Vector<ShaderStageSPIRVData> &p_spirv) {
+Vector<uint8_t> RenderingDeviceVulkan::shader_compile_binary_from_spirv(const Vector<ShaderStageSPIRVData> &p_spirv, const String &p_shader_name) {
RenderingDeviceVulkanShaderBinaryData binary_data;
binary_data.vertex_input_mask = 0;
binary_data.fragment_outputs = 0;
@@ -4771,9 +4847,19 @@ Vector<uint8_t> RenderingDeviceVulkan::shader_compile_binary_from_spirv(const Ve
binary_data.set_count = uniform_info.size();
binary_data.stage_count = p_spirv.size();
+ CharString shader_name_utf = p_shader_name.utf8();
+
+ binary_data.shader_name_len = shader_name_utf.length();
+
uint32_t total_size = sizeof(uint32_t) * 3; //header + version + main datasize;
total_size += sizeof(RenderingDeviceVulkanShaderBinaryData);
+ total_size += binary_data.shader_name_len;
+
+ if ((binary_data.shader_name_len % 4) != 0) { //alignment rules are really strange
+ total_size += 4 - (binary_data.shader_name_len % 4);
+ }
+
for (int i = 0; i < uniform_info.size(); i++) {
total_size += sizeof(uint32_t);
total_size += uniform_info[i].size() * sizeof(RenderingDeviceVulkanShaderBinaryDataBinding);
@@ -4800,6 +4886,12 @@ Vector<uint8_t> RenderingDeviceVulkan::shader_compile_binary_from_spirv(const Ve
offset += sizeof(uint32_t);
memcpy(binptr + offset, &binary_data, sizeof(RenderingDeviceVulkanShaderBinaryData));
offset += sizeof(RenderingDeviceVulkanShaderBinaryData);
+ memcpy(binptr + offset, shader_name_utf.ptr(), binary_data.shader_name_len);
+ offset += binary_data.shader_name_len;
+
+ if ((binary_data.shader_name_len % 4) != 0) { //alignment rules are really strange
+ offset += 4 - (binary_data.shader_name_len % 4);
+ }
for (int i = 0; i < uniform_info.size(); i++) {
int count = uniform_info[i].size();
@@ -4870,6 +4962,16 @@ RID RenderingDeviceVulkan::shader_create_from_bytecode(const Vector<uint8_t> &p_
read_offset += sizeof(uint32_t) * 3 + bin_data_size;
+ String name;
+
+ if (binary_data.shader_name_len) {
+ name.parse_utf8((const char *)(binptr + read_offset), binary_data.shader_name_len);
+ read_offset += binary_data.shader_name_len;
+ if ((binary_data.shader_name_len % 4) != 0) { //alignment rules are really strange
+ read_offset += 4 - (binary_data.shader_name_len % 4);
+ }
+ }
+
Vector<Vector<VkDescriptorSetLayoutBinding>> set_bindings;
Vector<Vector<UniformInfo>> uniform_info;
@@ -5024,6 +5126,7 @@ RID RenderingDeviceVulkan::shader_create_from_bytecode(const Vector<uint8_t> &p_
shader.compute_local_size[1] = compute_local_size[1];
shader.compute_local_size[2] = compute_local_size[2];
shader.specialization_constants = specialization_constants;
+ shader.name = name;
String error_text;
@@ -6385,7 +6488,6 @@ RID RenderingDeviceVulkan::render_pipeline_create(RID p_shader, FramebufferForma
specialization_info.write[i].pData = data_ptr;
specialization_info.write[i].mapEntryCount = specialization_map_entries[i].size();
specialization_info.write[i].pMapEntries = specialization_map_entries[i].ptr();
-
pipeline_stages.write[i].pSpecializationInfo = specialization_info.ptr() + i;
}
}
@@ -6412,7 +6514,7 @@ RID RenderingDeviceVulkan::render_pipeline_create(RID p_shader, FramebufferForma
RenderPipeline pipeline;
VkResult err = vkCreateGraphicsPipelines(device, VK_NULL_HANDLE, 1, &graphics_pipeline_create_info, nullptr, &pipeline.pipeline);
- ERR_FAIL_COND_V_MSG(err, RID(), "vkCreateGraphicsPipelines failed with error " + itos(err) + ".");
+ ERR_FAIL_COND_V_MSG(err, RID(), "vkCreateGraphicsPipelines failed with error " + itos(err) + " for shader '" + shader->name + "'.");
pipeline.set_formats = shader->set_formats;
pipeline.push_constant_stages = shader->push_constant.push_constants_vk_stage;
@@ -7863,13 +7965,13 @@ void RenderingDeviceVulkan::compute_list_bind_uniform_set(ComputeListID p_list,
textures_to_storage[i]->used_in_compute = false;
textures_to_storage[i]->used_in_raster = false;
- textures_to_storage[i]->used_in_compute = false;
+ textures_to_storage[i]->used_in_transfer = false;
} else {
src_access_flags = 0;
textures_to_storage[i]->used_in_compute = false;
textures_to_storage[i]->used_in_raster = false;
- textures_to_storage[i]->used_in_compute = false;
+ textures_to_storage[i]->used_in_transfer = false;
textures_to_storage[i]->used_in_frame = frames_drawn;
}
@@ -8730,6 +8832,7 @@ void RenderingDeviceVulkan::initialize(VulkanContext *p_context, bool p_local_de
memset(&allocatorInfo, 0, sizeof(VmaAllocatorCreateInfo));
allocatorInfo.physicalDevice = p_context->get_physical_device();
allocatorInfo.device = device;
+ allocatorInfo.instance = p_context->get_instance();
vmaCreateAllocator(&allocatorInfo, &allocator);
}
@@ -8864,6 +8967,7 @@ void RenderingDeviceVulkan::_free_rids(T &p_owner, const char *p_type) {
}
void RenderingDeviceVulkan::capture_timestamp(const String &p_name) {
+ ERR_FAIL_COND_MSG(draw_list != nullptr, "Capturing timestamps during draw list creation is not allowed. Offending timestap was: " + p_name);
ERR_FAIL_COND(frames[frame].timestamp_count >= max_timestamp_query_elements);
//this should be optional for profiling, else it will slow things down
diff --git a/drivers/vulkan/rendering_device_vulkan.h b/drivers/vulkan/rendering_device_vulkan.h
index dc4583d837..dc1b78c1d5 100644
--- a/drivers/vulkan/rendering_device_vulkan.h
+++ b/drivers/vulkan/rendering_device_vulkan.h
@@ -44,7 +44,11 @@
#endif
#include "vk_mem_alloc.h"
+#ifdef USE_VOLK
+#include <volk.h>
+#else
#include <vulkan/vulkan.h>
+#endif
class VulkanContext;
@@ -635,6 +639,7 @@ class RenderingDeviceVulkan : public RenderingDevice {
Vector<VkPipelineShaderStageCreateInfo> pipeline_stages;
Vector<SpecializationConstant> specialization_constants;
VkPipelineLayout pipeline_layout = VK_NULL_HANDLE;
+ String name; //used for debug
};
String _shader_uniform_debug(RID p_shader, int p_set = -1);
@@ -1039,6 +1044,7 @@ public:
virtual bool texture_is_format_supported_for_usage(DataFormat p_format, uint32_t p_usage) const;
virtual bool texture_is_shared(RID p_texture);
virtual bool texture_is_valid(RID p_texture);
+ virtual Size2i texture_size(RID p_texture);
virtual Error texture_copy(RID p_from_texture, RID p_to_texture, const Vector3 &p_from, const Vector3 &p_to, const Vector3 &p_size, uint32_t p_src_mipmap, uint32_t p_dst_mipmap, uint32_t p_src_layer, uint32_t p_dst_layer, uint32_t p_post_barrier = BARRIER_MASK_ALL);
virtual Error texture_clear(RID p_texture, const Color &p_color, uint32_t p_base_mipmap, uint32_t p_mipmaps, uint32_t p_base_layer, uint32_t p_layers, uint32_t p_post_barrier = BARRIER_MASK_ALL);
@@ -1084,7 +1090,7 @@ public:
/****************/
virtual String shader_get_binary_cache_key() const;
- virtual Vector<uint8_t> shader_compile_binary_from_spirv(const Vector<ShaderStageSPIRVData> &p_spirv);
+ virtual Vector<uint8_t> shader_compile_binary_from_spirv(const Vector<ShaderStageSPIRVData> &p_spirv, const String &p_shader_name = "");
virtual RID shader_create_from_bytecode(const Vector<uint8_t> &p_shader_binary);
diff --git a/drivers/vulkan/vulkan_context.cpp b/drivers/vulkan/vulkan_context.cpp
index a9d0fb6fed..625c222b67 100644
--- a/drivers/vulkan/vulkan_context.cpp
+++ b/drivers/vulkan/vulkan_context.cpp
@@ -681,6 +681,10 @@ Error VulkanContext::_create_physical_device() {
inst_initialized = true;
+#ifdef USE_VOLK
+ volkLoadInstance(inst);
+#endif
+
/* Make initial call to query gpu_count, then second call for gpu info*/
err = vkEnumeratePhysicalDevices(inst, &gpu_count, nullptr);
ERR_FAIL_COND_V(err, ERR_CANT_CREATE);
@@ -972,37 +976,35 @@ Error VulkanContext::_create_device() {
sdevice.queueCreateInfoCount = 2;
}
-#ifdef VK_VERSION_1_2
VkPhysicalDeviceVulkan11Features vulkan11features;
-
- vulkan11features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_1_FEATURES;
- vulkan11features.pNext = nullptr;
- // !BAS! Need to figure out which ones of these we want enabled...
- vulkan11features.storageBuffer16BitAccess = 0;
- vulkan11features.uniformAndStorageBuffer16BitAccess = 0;
- vulkan11features.storagePushConstant16 = 0;
- vulkan11features.storageInputOutput16 = 0;
- vulkan11features.multiview = multiview_capabilities.is_supported;
- vulkan11features.multiviewGeometryShader = multiview_capabilities.geometry_shader_is_supported;
- vulkan11features.multiviewTessellationShader = multiview_capabilities.tessellation_shader_is_supported;
- vulkan11features.variablePointersStorageBuffer = 0;
- vulkan11features.variablePointers = 0;
- vulkan11features.protectedMemory = 0;
- vulkan11features.samplerYcbcrConversion = 0;
- vulkan11features.shaderDrawParameters = 0;
-
- sdevice.pNext = &vulkan11features;
-#elif VK_VERSION_1_1
VkPhysicalDeviceMultiviewFeatures multiview_features;
+ if (vulkan_major > 1 || vulkan_minor >= 2) {
+ vulkan11features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_1_FEATURES;
+ vulkan11features.pNext = nullptr;
+ // !BAS! Need to figure out which ones of these we want enabled...
+ vulkan11features.storageBuffer16BitAccess = 0;
+ vulkan11features.uniformAndStorageBuffer16BitAccess = 0;
+ vulkan11features.storagePushConstant16 = 0;
+ vulkan11features.storageInputOutput16 = 0;
+ vulkan11features.multiview = multiview_capabilities.is_supported;
+ vulkan11features.multiviewGeometryShader = multiview_capabilities.geometry_shader_is_supported;
+ vulkan11features.multiviewTessellationShader = multiview_capabilities.tessellation_shader_is_supported;
+ vulkan11features.variablePointersStorageBuffer = 0;
+ vulkan11features.variablePointers = 0;
+ vulkan11features.protectedMemory = 0;
+ vulkan11features.samplerYcbcrConversion = 0;
+ vulkan11features.shaderDrawParameters = 0;
+
+ sdevice.pNext = &vulkan11features;
+ } else if (vulkan_major == 1 && vulkan_minor == 1) {
+ multiview_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTIVIEW_FEATURES;
+ multiview_features.pNext = nullptr;
+ multiview_features.multiview = multiview_capabilities.is_supported;
+ multiview_features.multiviewGeometryShader = multiview_capabilities.geometry_shader_is_supported;
+ multiview_features.multiviewTessellationShader = multiview_capabilities.tessellation_shader_is_supported;
- multiview_features.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTIVIEW_FEATURES;
- multiview_features.pNext = nullptr;
- multiview_features.multiview = multiview_capabilities.is_supported;
- multiview_features.multiviewGeometryShader = multiview_capabilities.geometry_shader_is_supported;
- multiview_features.multiviewTessellationShader = multiview_capabilities.tessellation_shader_is_supported;
-
- sdevice.pNext = &multiview_features;
-#endif
+ sdevice.pNext = &multiview_features;
+ }
err = vkCreateDevice(gpu, &sdevice, nullptr, &device);
ERR_FAIL_COND_V(err, ERR_CANT_CREATE);
@@ -1669,6 +1671,11 @@ Error VulkanContext::_update_swap_chain(Window *window) {
}
Error VulkanContext::initialize() {
+#ifdef USE_VOLK
+ if (volkInitialize() != VK_SUCCESS) {
+ return FAILED;
+ }
+#endif
Error err = _create_physical_device();
if (err) {
return err;
diff --git a/drivers/vulkan/vulkan_context.h b/drivers/vulkan/vulkan_context.h
index 83e9524046..fe09d4c497 100644
--- a/drivers/vulkan/vulkan_context.h
+++ b/drivers/vulkan/vulkan_context.h
@@ -38,7 +38,11 @@
#include "core/templates/rid_owner.h"
#include "servers/display_server.h"
+#ifdef USE_VOLK
+#include <volk.h>
+#else
#include <vulkan/vulkan.h>
+#endif
class VulkanContext {
public:
@@ -229,10 +233,6 @@ protected:
Error _get_preferred_validation_layers(uint32_t *count, const char *const **names);
- VkInstance _get_instance() {
- return inst;
- }
-
public:
uint32_t get_vulkan_major() const { return vulkan_major; };
uint32_t get_vulkan_minor() const { return vulkan_minor; };
@@ -241,6 +241,7 @@ public:
VkDevice get_device();
VkPhysicalDevice get_physical_device();
+ VkInstance get_instance() { return inst; }
int get_swapchain_image_count() const;
uint32_t get_graphics_queue() const;