diff --git a/src/video_core/renderer_vulkan/vk_instance.cpp b/src/video_core/renderer_vulkan/vk_instance.cpp index e64cae87d..c712f4e0c 100644 --- a/src/video_core/renderer_vulkan/vk_instance.cpp +++ b/src/video_core/renderer_vulkan/vk_instance.cpp @@ -214,6 +214,9 @@ bool Instance::CreateDevice() { vk::PhysicalDevicePrimitiveTopologyListRestartFeaturesEXT, vk::PhysicalDevicePortabilitySubsetFeaturesKHR>(); features = feature_chain.get().features; +#ifdef __APPLE__ + portability_features = feature_chain.get(); +#endif const vk::StructureChain properties_chain = physical_device.getProperties2< vk::PhysicalDeviceProperties2, vk::PhysicalDeviceVulkan11Properties, @@ -282,7 +285,7 @@ bool Instance::CreateDevice() { #ifdef __APPLE__ // Required by Vulkan spec if supported. - add_extension(VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME); + portability_subset = add_extension(VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME); #endif const auto family_properties = physical_device.getQueueFamilyProperties(); @@ -403,7 +406,7 @@ bool Instance::CreateDevice() { .legacyVertexAttributes = true, }, #ifdef __APPLE__ - feature_chain.get(), + portability_features, #endif }; diff --git a/src/video_core/renderer_vulkan/vk_instance.h b/src/video_core/renderer_vulkan/vk_instance.h index 1748fcd59..c2322df41 100644 --- a/src/video_core/renderer_vulkan/vk_instance.h +++ b/src/video_core/renderer_vulkan/vk_instance.h @@ -149,6 +149,16 @@ public: return features.tessellationShader; } + /// Returns true when tessellation isolines are supported by the device + bool IsTessellationIsolinesSupported() const { + return !portability_subset || portability_features.tessellationIsolines; + } + + /// Returns true when tessellation point mode is supported by the device + bool IsTessellationPointModeSupported() const { + return !portability_subset || portability_features.tessellationPointMode; + } + /// Returns the vendor ID of the physical device u32 GetVendorID() const { return properties.vendorID; @@ -285,6 +295,7 @@ private: vk::PhysicalDeviceVulkan12Properties vk12_props; vk::PhysicalDevicePushDescriptorPropertiesKHR push_descriptor_props; vk::PhysicalDeviceFeatures features; + vk::PhysicalDevicePortabilitySubsetFeaturesKHR portability_features; vk::DriverIdKHR driver_id; vk::UniqueDebugUtilsMessengerEXT debug_callback{}; std::string vendor_name; @@ -308,6 +319,7 @@ private: bool image_load_store_lod{}; bool amd_gcn_shader{}; bool tooling_info{}; + bool portability_subset{}; }; } // namespace Vulkan diff --git a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp index 16d2187db..4406be439 100644 --- a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp +++ b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp @@ -412,8 +412,10 @@ bool PipelineCache::RefreshGraphicsKey() { break; } case Liverpool::ShaderStageEnable::VgtStages::LsHs: { - if (!instance.IsTessellationSupported()) { - break; + if (!instance.IsTessellationSupported() || + (regs.tess_config.type == AmdGpu::TessellationType::Isoline && + !instance.IsTessellationIsolinesSupported())) { + return false; } if (!TryBindStage(Stage::Hull, LogicalStage::TessellationControl)) { return false;