renderer_vulkan: Create a Vulkan 1.0 instance when 1.1 is not available

This commit doesn't make yuzu compatible with Vulkan 1.0 yet, it only
creates an 1.0 instance.
merge-requests/60/head
ReinUsesLisp 2020-06-29 02:34:17 +07:00
parent 3ea3de4ecd
commit 29a0ca2391
3 changed files with 26 additions and 6 deletions

@ -180,7 +180,10 @@ vk::Instance CreateInstance(Common::DynamicLibrary& library, vk::InstanceDispatc
}
}
vk::Instance instance = vk::Instance::Create(layers, extensions, dld);
// Limit the maximum version of Vulkan to avoid using untested version.
const u32 version = std::min(vk::AvailableVersion(dld), static_cast<u32>(VK_API_VERSION_1_1));
vk::Instance instance = vk::Instance::Create(version, layers, extensions, dld);
if (!instance) {
LOG_ERROR(Render_Vulkan, "Failed to create Vulkan instance");
return {};

@ -10,6 +10,7 @@
#include <vector>
#include "common/common_types.h"
#include "common/logging/log.h"
#include "video_core/renderer_vulkan/wrapper.h"
@ -375,18 +376,17 @@ VkResult Free(VkDevice device, VkCommandPool handle, Span<VkCommandBuffer> buffe
return VK_SUCCESS;
}
Instance Instance::Create(Span<const char*> layers, Span<const char*> extensions,
Instance Instance::Create(u32 version, Span<const char*> layers, Span<const char*> extensions,
InstanceDispatch& dld) noexcept {
static constexpr VkApplicationInfo application_info{
const VkApplicationInfo application_info{
.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO,
.pNext = nullptr,
.pApplicationName = "yuzu Emulator",
.applicationVersion = VK_MAKE_VERSION(0, 1, 0),
.pEngineName = "yuzu Emulator",
.engineVersion = VK_MAKE_VERSION(0, 1, 0),
.apiVersion = VK_API_VERSION_1_1,
.apiVersion = version,
};
const VkInstanceCreateInfo ci{
.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO,
.pNext = nullptr,
@ -775,6 +775,21 @@ VkPhysicalDeviceMemoryProperties PhysicalDevice::GetMemoryProperties() const noe
return properties;
}
u32 AvailableVersion(const InstanceDispatch& dld) noexcept {
PFN_vkEnumerateInstanceVersion vkEnumerateInstanceVersion;
if (!Proc(vkEnumerateInstanceVersion, dld, "vkEnumerateInstanceVersion")) {
// If the procedure is not found, Vulkan 1.0 is assumed
return VK_API_VERSION_1_0;
}
u32 version;
if (const VkResult result = vkEnumerateInstanceVersion(&version); result != VK_SUCCESS) {
LOG_ERROR(Render_Vulkan, "vkEnumerateInstanceVersion returned {}, assuming Vulkan 1.1",
ToString(result));
return VK_API_VERSION_1_1;
}
return version;
}
std::optional<std::vector<VkExtensionProperties>> EnumerateInstanceExtensionProperties(
const InstanceDispatch& dld) {
u32 num;

@ -563,7 +563,7 @@ class Instance : public Handle<VkInstance, NoOwner, InstanceDispatch> {
public:
/// Creates a Vulkan instance. Use "operator bool" for error handling.
static Instance Create(Span<const char*> layers, Span<const char*> extensions,
static Instance Create(u32 version, Span<const char*> layers, Span<const char*> extensions,
InstanceDispatch& dld) noexcept;
/// Enumerates physical devices.
@ -1048,6 +1048,8 @@ private:
const DeviceDispatch* dld;
};
u32 AvailableVersion(const InstanceDispatch& dld) noexcept;
std::optional<std::vector<VkExtensionProperties>> EnumerateInstanceExtensionProperties(
const InstanceDispatch& dld);