Vulkan-Samples icon indicating copy to clipboard operation
Vulkan-Samples copied to clipboard

Dynamic state3 multisample rasterization

Open pawel-jastrzebski-mobica opened this issue 1 year ago • 17 comments

Overview

This sample demonstrates one of the functionalities of VK_EXT_extended_dynamic_state3 related to rasterization samples. The extension can be used to dynamically change sampling without any need to restart the application. image

Enabling the extension

To be able to use this extension in Vulkan API:

  1. At least Vulkan API version 1.1 must be supported.
  2. Set of VkPhysicalDeviceExtendedDynamicStateFeaturesEXT, VkPhysicalDeviceExtendedDynamicState2FeaturesEXT, VkPhysicalDeviceExtendedDynamicState3FeaturesEXT must be added to the feature chain of VkPhysicalDeviceProperties2 and VkPhysicalDeviceExtendedDynamicState3PropertiesEXT must be added to VkPhysicalDeviceProperties2.

Using the extension

To use the extension:

  1. VK_DYNAMIC_STATE_RASTERIZATION_SAMPLES_EXT must be added to VkPipelineDynamicStateCreateInfo.
  2. Method void vkCmdSetRasterizationSamplesEXT(VkCommandBuffer commandBuffer, VkSampleCountFlagBits rasterizationSamples) should be called between vkCmdBeginRenderPass and vkCmdEndRenderPass.

Known issues

The extension always reports the following validation error when enabled:

[error] [framework\core\instance.cpp:50] -1100021871 - UNASSIGNED-GeneralParameterError-UnrecognizedValue: Validation Error: [ UNASSIGNED-GeneralParameterError-UnrecognizedValue ] Object 0: handle = 0x15d301ca4e0, type = VK_OBJECT_TYPE_DEVICE; | MessageID = 0xbe6eff91 | vkCreateGraphicsPipelines: value of pCreateInfos[0].pDynamicState->pDynamicStates[2] (1000455005) does not fall within the begin..end range of the core VkDynamicState enumeration tokens and is not an extension added token

This implies several other validation errors during runtime:

[error] [framework\core\instance.cpp:50] -1052047544 - VUID-vkCmdDraw-rasterizationSamples-04740: Validation Error: [ VUID-vkCmdDraw-rasterizationSamples-04740 ] Object 0: handle = 0xf6d9250000000139, type = VK_OBJECT_TYPE_PIPELINE; Object 1: handle = 0xfc06e9000000013d, type = VK_OBJECT_TYPE_RENDER_PASS; | MessageID = 0xc14b0748 | vkCmdDraw: In VkPipeline 0xf6d9250000000139[] the sample count is VK_SAMPLE_COUNT_1_BIT while the current VkRenderPass 0xfc06e9000000013d[] has VK_SAMPLE_COUNT_4_BIT and they need to be the same. The Vulkan spec states: If rasterization is not disabled in the bound graphics pipeline, and neither the VK_AMD_mixed_attachment_samples nor the VK_NV_framebuffer_mixed_samples extensions are enabled, then VkPipelineMultisampleStateCreateInfo::rasterizationSamples must be the same as the current subpass color and/or depth/stencil attachments (https://vulkan.lunarg.com/doc/view/1.3.216.0/windows/1.3-extensions/vkspec.html#VUID-vkCmdDraw-rasterizationSamples-04740)
[error] [framework\core\instance.cpp:50] 1349015333 - VUID-vkCmdDraw-renderPass-02684: Validation Error: [ VUID-vkCmdDraw-renderPass-02684 ] Object 0: handle = 0xfc06e9000000013d, type = VK_OBJECT_TYPE_RENDER_PASS; Object 1: handle = 0xab64de0000000020, type = VK_OBJECT_TYPE_RENDER_PASS; | MessageID = 0x50685725 | vkCmdDraw: RenderPasses incompatible between active render pass w/ VkRenderPass 0xfc06e9000000013d[] and pipeline state object w/ VkRenderPass 0xab64de0000000020[] Attachment 0 is not compatible with 0: They have different samples.. The Vulkan spec states: The current render pass must be compatible with the renderPass member of the VkGraphicsPipelineCreateInfo structure specified when creating the VkPipeline bound to VK_PIPELINE_BIND_POINT_GRAPHICS (https://vulkan.lunarg.com/doc/view/1.3.216.0/windows/1.3-extensions/vkspec.html#VUID-vkCmdDraw-renderPass-02684)
[error] [framework\core\instance.cpp:50] -329854293 - VUID-vkCmdDrawIndexed-rasterizationSamples-04740: Validation Error: [ VUID-vkCmdDrawIndexed-rasterizationSamples-04740 ] Object 0: handle = 0x9f9b41000000003c, type = VK_OBJECT_TYPE_PIPELINE; Object 1: handle = 0xfc06e9000000013d, type = VK_OBJECT_TYPE_RENDER_PASS; | MessageID = 0xec56d2ab | vkCmdDrawIndexed: In VkPipeline 0x9f9b41000000003c[] the sample count is VK_SAMPLE_COUNT_1_BIT while the current VkRenderPass 0xfc06e9000000013d[] has VK_SAMPLE_COUNT_4_BIT and they need to be the same. The Vulkan spec states: If rasterization is not disabled in the bound graphics pipeline, and neither the VK_AMD_mixed_attachment_samples nor the VK_NV_framebuffer_mixed_samples extensions are enabled, then VkPipelineMultisampleStateCreateInfo::rasterizationSamples must be the same as the current subpass color and/or depth/stencil attachments (https://vulkan.lunarg.com/doc/view/1.3.216.0/windows/1.3-extensions/vkspec.html#VUID-vkCmdDrawIndexed-rasterizationSamples-04740)
[error] [framework\core\instance.cpp:50] -1934215230 - VUID-vkCmdDrawIndexed-renderPass-02684: Validation Error: [ VUID-vkCmdDrawIndexed-renderPass-02684 ] Object 0: handle = 0xfc06e9000000013d, type = VK_OBJECT_TYPE_RENDER_PASS; Object 1: handle = 0xab64de0000000020, type = VK_OBJECT_TYPE_RENDER_PASS; | MessageID = 0x8cb637c2 | vkCmdDrawIndexed: RenderPasses incompatible between active render pass w/ VkRenderPass 0xfc06e9000000013d[] and pipeline state object w/ VkRenderPass 0xab64de0000000020[] Attachment 0 is not compatible with 0: They have different samples.. The Vulkan spec states: The current render pass must be compatible with the renderPass member of the VkGraphicsPipelineCreateInfo structure specified when creating the VkPipeline bound to VK_PIPELINE_BIND_POINT_GRAPHICS (https://vulkan.lunarg.com/doc/view/1.3.216.0/windows/1.3-extensions/vkspec.html#VUID-vkCmdDrawIndexed-renderPass-02684)

Resources

https://registry.khronos.org/vulkan/specs/1.3-extensions/man/html/VK_EXT_extended_dynamic_state3.html https://registry.khronos.org/vulkan/specs/1.3-extensions/man/html/vkCmdSetRasterizationSamplesEXT.html

Please ensure the following points are checked:

  • [x] My code follows the coding style
  • [x] I have reviewed file licenses
  • [x] I have commented any added functions (in line with Doxygen)
  • [x] I have commented any code that could be hard to understand
  • [x] My changes do not add any new compiler warnings
  • [x] My changes do not add any new validation layer errors or warnings
  • [x] I have used existing framework/helper functions where possible
  • [x] My changes do not add any regressions
  • [x] I have tested every sample to ensure everything runs correctly
  • [x] This PR describes the scope and expected impact of the changes I am making

Note: The Samples CI runs a number of checks including:

  • [x] I have updated the header Copyright to reflect the current year (CI build will fail if Copyright is out of date)
  • [x] My changes build on Windows, Linux, macOS and Android. Otherwise I have documented any exceptions

@asuessenbach :

When I run this sample, I get this validation layer error, which definitely needs to be resolved: Validation Error: [ VUID-VkSubpassDescription-pResolveAttachments-00848 ] | MessageID = 0xfad6c3cb | vkCreateRenderPass(): pCreateInfo->pAttachments[0].samples is VK_SAMPLE_COUNT_1_BIT. The Vulkan spec states: If pResolveAttachments is not NULL, for each resolve attachment that is not VK_ATTACHMENT_UNUSED, the corresponding color attachment must not have a sample count of VK_SAMPLE_COUNT_1_BIT (https://vulkan.lunarg.com/doc/view/1.3.268.0/windows/1.3-extensions/vkspec.html#VUID-VkSubpassDescription-pResolveAttachments-00848)

I have already addressed the validation layers errors here: https://github.com/KhronosGroup/Vulkan-Samples/pull/856#discussion_r1417325069

@SaschaWillems :

Can you rename the sample to something like "extended_dynamic_state_3"? That would be more in line with the naming of the already existing dynamic state 2 sample.

Done, however it turn out that the new name is too long (it may cause problems during compilation due to path characters limit). Also, I don't think we want to merge all of the extended_dynamic_state_3 samples so we need a suffix. Maybe extended_dynamic_state_3_multisampling would be better than extended_dynamic_state_3_multisampling_rasterization?

@gary-sweet :

I can only confirm that the sample correctly reports that we don't support dynamic sample state changing.

Does it mean that the validation layers don't support this extension?

I can only confirm that the sample correctly reports that we don't support dynamic sample state changing.

Does it mean that the validation layers don't support this extension?

No, it means that my hardware cannot support dynamic changes to sampling.

gary-sweet avatar Dec 18 '23 14:12 gary-sweet

Also, I don't think we want to merge all of the extended_dynamic_state_3 samples so we need a suffix. Maybe extended_dynamic_state_3_multisampling would be better than extended_dynamic_state_3_multisampling_rasterization?

Afaik we don't have a dynamic state 3 sample yet (only 2), so why not call this "extended_dynamic_state3"? If additional stuff from dynamic state 3 makes sense for our samples, we simply add it to that sample, similar to the "2" sample.

SaschaWillems avatar Dec 18 '23 15:12 SaschaWillems

With the latest changes, I get this validation layer error: Validation Error: [ VUID-VkGraphicsPipelineCreateInfo-multisampledRenderToSingleSampled-06853 ] | MessageID = 0x3108bb9b | vkCreateGraphicsPipelines(): pCreateInfos[0].pMultisampleState->rasterizationSamples (1) does not match the number of samples of the RenderPass color and/or depth attachment (4). The Vulkan spec states: If the pipeline requires fragment output interface state, and none of the VK_AMD_mixed_attachment_samples extension, the VK_NV_framebuffer_mixed_samples extension, or the multisampledRenderToSingleSampled feature are enabled, rasterizationSamples is not dynamic, and if subpass uses color and/or depth/stencil attachments, then the rasterizationSamples member of pMultisampleState must be the same as the sample count for those subpass attachments (https://vulkan.lunarg.com/doc/view/1.3.268.0/windows/1.3-extensions/vkspec.html#VUID-VkGraphicsPipelineCreateInfo-multisampledRenderToSingleSampled-06853)

Can't tell, if that's a validation layer issue, or if you should change something in your code.

asuessenbach avatar Jan 16 '24 13:01 asuessenbach

@asuessenbach, @SaschaWillems, @gary-sweet: I have re-worked the GUI to support multi-sampling. Thanks to this change I was able to get rid of one validation error: msrtss_rasterization_samples_07284. VVL complained that one of the pipelines did not support multi-sampling. I think that adding multi-sampled GUI should be harmless regardless of whether the change was necessary or not. As for the other validation errors, they still remain

rasterizationSamples-07474
vkCmdDraw-renderPass-02684
VUID-VkSubpassDescription-pResolveAttachments-00848

I created a bug for the VVL team but I have no idea when or how they could be fixed: https://github.com/KhronosGroup/Vulkan-ValidationLayers/issues/7327

All files affected by this PR have copyrights corrected. CI passed. Do we want to wait for update's in VVL issue created by @pawel-jastrzebski-mobica or PR can be merged in current state?

We should wait until validation is fixed. The error is per draw call, so with validation the sample right now will spam lots of (the same) validation errors.

SaschaWillems avatar Feb 13 '24 18:02 SaschaWillems

Status of resolving VVL issues:

  1. rasterizationSamples-07474 -> waiting for VVL team response (they are working on updating code for dynamic state's)
  2. vkCmdDraw-renderPass-02684 -> after initial investigation I think that can be resolved by implementing dynamic rendering in this sample.
  3. VUID-VkSubpassDescription-pResolveAttachments-00848 -> resolved on Samples side

About second VL It have issue when sample count is changed (by creating new renderpass/framebuffer and invoking vkCmdSetRasterizationSamplesEXT) to other from value which have been set on pipeline creation. From my point of view it can be avoided by using dynamic rendering extension, so renderpass can be replace with dynamic rendering structs.

Is my thoughts make sense?

After implementing dynamic rendering into that Sample I solved all previous VL issues.

Unfortunately I found new one related to necessary image transition (same as was presented in dynamic_rendering sample). VL error: SYNC-HAZARD-WRITE-AFTER-READ: Validation Error: [ SYNC-HAZARD-WRITE-AFTER-READ ] Object 0: handle = 0x555556f1c930, type = VK_OBJECT_TYPE_QUEUE; | MessageID = 0x376bc9df | vkQueueSubmit(): Hazard WRITE_AFTER_READ for entry 0, VkCommandBuffer 0x555558e8b710[], Submitted access info (submitted_usage: SYNC_IMAGE_LAYOUT_TRANSITION, command: vkCmdPipelineBarrier, seq_no: 1, VkImage 0xe7f79a0000000005[], reset_no: 2). Access info (prior_usage: SYNC_PRESENT_ENGINE_SYNCVAL_PRESENT_ACQUIRE_READ_SYNCVAL, read_barriers: VK_PIPELINE_STAGE_2_COLOR_ATTACHMENT_OUTPUT_BIT|VK_PIPELINE_STAGE_2_BOTTOM_OF_PIPE_BIT, , batch_tag: 52, vkAcquireNextImageKHR aquire_tag:52: VkSwapchainKHR 0xf56c9b0000000004[], image_index: 0image: VkImage 0xe7f79a0000000005[]).

I checked Dynamic Rendering sample and the same issue is visible there. After resolving that on this PR I will create new one to fix it in Dynamic Rendering sample.

Fix for synchronization issue was provided. That issue was known and here is explanation of my changes #7129 breaks dynamic rendering examples

When I start this sample, I get this error message: Validation Error: [ VUID-VkRenderingInfo-pNext-pNext ] Object 0: handle = 0x2cff0107020, type = VK_OBJECT_TYPE_INSTANCE; | MessageID = 0xdc5df1d | vkCmdBeginRenderingKHR(): pRenderingInfo->pNext<VkMultisampledRenderToSingleSampledInfoEXT> extended struct requires the extensions VK_EXT_multisampled_render_to_single_sampled. The Vulkan spec states: Each pNext member of any structure (including this one) in the pNext chain must be either NULL or a pointer to a valid instance of VkDeviceGroupRenderPassBeginInfo, VkMultisampledRenderToSingleSampledInfoEXT, VkMultiviewPerViewAttributesInfoNVX, VkMultiviewPerViewRenderAreasRenderPassBeginInfoQCOM, VkRenderPassStripeBeginInfoARM, VkRenderingFragmentDensityMapAttachmentInfoEXT, or VkRenderingFragmentShadingRateAttachmentInfoKHR (https://vulkan.lunarg.com/doc/view/1.3.280.0/windows/1.3-extensions/vkspec.html#VUID-VkRenderingInfo-pNext-pNext)

That is, you would need to add_device_extension(VK_EXT_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_EXTENSION_NAME);

asuessenbach avatar Apr 23 '24 08:04 asuessenbach

Thanks for letting me know about that VL error. On which platform do you test? I didn't see that issue on ubuntu, but I will add that line and please give me feedback if that resolve your VL issue.

Strange, I can use structs from this extension without add add_device_extension(VK_EXT_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_EXTENSION_NAME);

but when I add that line I get error because of not having that extension available on my GPU. That extension have very low amount of device supported: https://vulkan.gpuinfo.org/listdevicescoverage.php?extension=VK_EXT_multisampled_render_to_single_sampled&platform=all

I think something is not right, because I obviously can use features of that extension without adding it to application.

On which platform do you test?

I see that on Win10, using an NVIDIA GPU, Vulkan SDK 1.3.280. And yes, that extension seems to be available on some mobile devices only.

asuessenbach avatar Apr 29 '24 07:04 asuessenbach

As stated half a year ago, you nicely sort the triangles into four different buckets, but use just two different pipelines to render them: all opaque and transparent triangles are rendered with blending enabled, even though that's only needed for the transparent ones. The same holds for the flipped triangles. Please find attached a patch introducing two more pipelines. I hope, that makes more clear what I mean with that. 0001-Introduce-additional-pipelines-for-opaque-vs.-transp.patch

Besides that, I increased the camera's rotation speed by 10.

asuessenbach avatar Aug 13 '24 19:08 asuessenbach