diff --git a/Ryujinx.Graphics.Vulkan/HardwareCapabilities.cs b/Ryujinx.Graphics.Vulkan/HardwareCapabilities.cs index 4512d375f..a45c2409b 100644 --- a/Ryujinx.Graphics.Vulkan/HardwareCapabilities.cs +++ b/Ryujinx.Graphics.Vulkan/HardwareCapabilities.cs @@ -33,6 +33,8 @@ namespace Ryujinx.Graphics.Vulkan public readonly bool SupportsMultiView; public readonly bool SupportsNullDescriptors; public readonly bool SupportsPushDescriptors; + public readonly bool SupportsPrimitiveTopologyListRestart; + public readonly bool SupportsPrimitiveTopologyPatchListRestart; public readonly bool SupportsTransformFeedback; public readonly bool SupportsTransformFeedbackQueries; public readonly bool SupportsPreciseOcclusionQueries; @@ -63,6 +65,8 @@ namespace Ryujinx.Graphics.Vulkan bool supportsMultiView, bool supportsNullDescriptors, bool supportsPushDescriptors, + bool supportsPrimitiveTopologyListRestart, + bool supportsPrimitiveTopologyPatchListRestart, bool supportsTransformFeedback, bool supportsTransformFeedbackQueries, bool supportsPreciseOcclusionQueries, @@ -92,6 +96,8 @@ namespace Ryujinx.Graphics.Vulkan SupportsMultiView = supportsMultiView; SupportsNullDescriptors = supportsNullDescriptors; SupportsPushDescriptors = supportsPushDescriptors; + SupportsPrimitiveTopologyListRestart = supportsPrimitiveTopologyListRestart; + SupportsPrimitiveTopologyPatchListRestart = supportsPrimitiveTopologyPatchListRestart; SupportsTransformFeedback = supportsTransformFeedback; SupportsTransformFeedbackQueries = supportsTransformFeedbackQueries; SupportsPreciseOcclusionQueries = supportsPreciseOcclusionQueries; diff --git a/Ryujinx.Graphics.Vulkan/PipelineState.cs b/Ryujinx.Graphics.Vulkan/PipelineState.cs index 0d5494766..dccc8ce68 100644 --- a/Ryujinx.Graphics.Vulkan/PipelineState.cs +++ b/Ryujinx.Graphics.Vulkan/PipelineState.cs @@ -417,11 +417,22 @@ namespace Ryujinx.Graphics.Vulkan bool primitiveRestartEnable = PrimitiveRestartEnable; - primitiveRestartEnable &= Topology == PrimitiveTopology.LineStrip || - Topology == PrimitiveTopology.TriangleStrip || - Topology == PrimitiveTopology.TriangleFan || - Topology == PrimitiveTopology.LineStripWithAdjacency || - Topology == PrimitiveTopology.TriangleStripWithAdjacency; + bool topologySupportsRestart; + + if (gd.Capabilities.SupportsPrimitiveTopologyListRestart) + { + topologySupportsRestart = gd.Capabilities.SupportsPrimitiveTopologyPatchListRestart || Topology != PrimitiveTopology.PatchList; + } + else + { + topologySupportsRestart = Topology == PrimitiveTopology.LineStrip || + Topology == PrimitiveTopology.TriangleStrip || + Topology == PrimitiveTopology.TriangleFan || + Topology == PrimitiveTopology.LineStripWithAdjacency || + Topology == PrimitiveTopology.TriangleStripWithAdjacency; + } + + primitiveRestartEnable &= topologySupportsRestart; var inputAssemblyState = new PipelineInputAssemblyStateCreateInfo() { diff --git a/Ryujinx.Graphics.Vulkan/VulkanInitialization.cs b/Ryujinx.Graphics.Vulkan/VulkanInitialization.cs index 353b219ac..ba3b5ef65 100644 --- a/Ryujinx.Graphics.Vulkan/VulkanInitialization.cs +++ b/Ryujinx.Graphics.Vulkan/VulkanInitialization.cs @@ -32,6 +32,7 @@ namespace Ryujinx.Graphics.Vulkan "VK_EXT_descriptor_indexing", // Enabling this works around an issue with disposed buffer bindings on RADV. "VK_EXT_fragment_shader_interlock", "VK_EXT_index_type_uint8", + "VK_EXT_primitive_topology_list_restart", "VK_EXT_robustness2", "VK_EXT_shader_stencil_export", "VK_KHR_shader_float16_int8", @@ -429,6 +430,17 @@ namespace Ryujinx.Graphics.Vulkan features2.PNext = &supportedFeaturesCustomBorderColor; } + PhysicalDevicePrimitiveTopologyListRestartFeaturesEXT supportedFeaturesPrimitiveTopologyListRestart = new PhysicalDevicePrimitiveTopologyListRestartFeaturesEXT() + { + SType = StructureType.PhysicalDevicePrimitiveTopologyListRestartFeaturesExt, + PNext = features2.PNext + }; + + if (supportedExtensions.Contains("VK_EXT_primitive_topology_list_restart")) + { + features2.PNext = &supportedFeaturesPrimitiveTopologyListRestart; + } + PhysicalDeviceTransformFeedbackFeaturesEXT supportedFeaturesTransformFeedback = new PhysicalDeviceTransformFeedbackFeaturesEXT() { SType = StructureType.PhysicalDeviceTransformFeedbackFeaturesExt, @@ -497,6 +509,21 @@ namespace Ryujinx.Graphics.Vulkan pExtendedFeatures = &featuresTransformFeedback; } + PhysicalDevicePrimitiveTopologyListRestartFeaturesEXT featuresPrimitiveTopologyListRestart; + + if (supportedExtensions.Contains("VK_EXT_primitive_topology_list_restart")) + { + featuresPrimitiveTopologyListRestart = new PhysicalDevicePrimitiveTopologyListRestartFeaturesEXT() + { + SType = StructureType.PhysicalDevicePrimitiveTopologyListRestartFeaturesExt, + PNext = pExtendedFeatures, + PrimitiveTopologyListRestart = supportedFeaturesPrimitiveTopologyListRestart.PrimitiveTopologyListRestart, + PrimitiveTopologyPatchListRestart = supportedFeaturesPrimitiveTopologyListRestart.PrimitiveTopologyPatchListRestart + }; + + pExtendedFeatures = &featuresPrimitiveTopologyListRestart; + } + PhysicalDeviceRobustness2FeaturesEXT featuresRobustness2; if (supportedExtensions.Contains("VK_EXT_robustness2")) diff --git a/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs b/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs index 6b6352571..8d4e54c4b 100644 --- a/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs +++ b/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs @@ -195,6 +195,11 @@ namespace Ryujinx.Graphics.Vulkan SType = StructureType.PhysicalDeviceFeatures2 }; + PhysicalDevicePrimitiveTopologyListRestartFeaturesEXT featuresPrimitiveTopologyListRestart = new PhysicalDevicePrimitiveTopologyListRestartFeaturesEXT() + { + SType = StructureType.PhysicalDevicePrimitiveTopologyListRestartFeaturesExt + }; + PhysicalDeviceRobustness2FeaturesEXT featuresRobustness2 = new PhysicalDeviceRobustness2FeaturesEXT() { SType = StructureType.PhysicalDeviceRobustness2FeaturesExt @@ -215,8 +220,14 @@ namespace Ryujinx.Graphics.Vulkan SType = StructureType.PhysicalDevicePortabilitySubsetFeaturesKhr }; + if (supportedExtensions.Contains("VK_EXT_primitive_topology_list_restart")) + { + features2.PNext = &featuresPrimitiveTopologyListRestart; + } + if (supportedExtensions.Contains("VK_EXT_robustness2")) { + featuresRobustness2.PNext = features2.PNext; features2.PNext = &featuresRobustness2; } @@ -288,6 +299,8 @@ namespace Ryujinx.Graphics.Vulkan features2.Features.MultiViewport, featuresRobustness2.NullDescriptor || IsMoltenVk, supportedExtensions.Contains(KhrPushDescriptor.ExtensionName), + featuresPrimitiveTopologyListRestart.PrimitiveTopologyListRestart, + featuresPrimitiveTopologyListRestart.PrimitiveTopologyPatchListRestart, supportsTransformFeedback, propertiesTransformFeedback.TransformFeedbackQueries, features2.Features.OcclusionQueryPrecise,