Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dynamic state3 multisample rasterization #856

Open
wants to merge 61 commits into
base: main
Choose a base branch
from

Conversation

pawel-jastrzebski-mobica
Copy link
Contributor

@pawel-jastrzebski-mobica pawel-jastrzebski-mobica commented Nov 28, 2023

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:

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

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

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

Signed-off-by: Pawel Jastrzebski <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
@pawel-jastrzebski-mobica pawel-jastrzebski-mobica marked this pull request as ready for review November 29, 2023 14:10
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
Signed-off-by: pawel-jastrzebski-mobica <pawel.jastrzebski@mobica.com>
@asuessenbach
Copy link
Contributor

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);

@Mateusz-Kowalewski-Mobica
Copy link
Contributor

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.

@Mateusz-Kowalewski-Mobica
Copy link
Contributor

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.

@asuessenbach
Copy link
Contributor

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.

@SaschaWillems SaschaWillems self-requested a review May 15, 2024 15:14
Copy link
Collaborator

@SaschaWillems SaschaWillems left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This works fine on my setup (Win 11, NV RTX 4070). Validation is clean, and changing MSAA modes has a clear visual effect. 👍🏻

I only noticed a few minor issues not directly related to the rendering part itself.

Those should be easy to fix, and once done I'll approve this :)

@SaschaWillems SaschaWillems self-requested a review June 3, 2024 15:47
SaschaWillems
SaschaWillems previously approved these changes Jun 3, 2024
@marty-johnson59 marty-johnson59 requested a review from gpx1000 June 3, 2024 19:41
@asuessenbach
Copy link
Contributor

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.

@marty-johnson59
Copy link
Contributor

Hi @pawel-jastrzebski-mobica, this looks close. Can you please take a look at Andreas' comments and then resolve the merge conflicts here so we can get this merged shortly? Thanks!

@pj87
Copy link

pj87 commented Aug 30, 2024

I don't know if anybody is still working on this PR.

@Mateusz-Kowalewski-Mobica
Copy link
Contributor

@asuessenbach Hello and sorry for long time not responding. I saw from meeting minutes that this PR can be easy fixed and merged, so I will add your changes and resolve merge conflicts.

@marty-johnson59
Copy link
Contributor

Hi @pawel-jastrzebski-mobica, we were discussing how to move this one forward on the Samples call this week. We're happy to help out here if resources are limited at Mobica - if it makes sense, we could merge this as is and then make any PRs needed to fix remaining issues. Would that work for you? If so, we'd just need you to fix the merge conflicts so we can merge. LMK how you'd like to proceed. Thanks!

@Mateusz-Kowalewski-Mobica
Copy link
Contributor

I wanted to fix this PR fast and probably I made a mistake by merge --squash instead of normal merge, so github on my Mobica branch still is seeing 107 commits behind Khronos:main.

I will work on that today after regular working hours.

@Mateusz-Kowalewski-Mobica
Copy link
Contributor

Is there a neat way to revers that merge commit? - 2d48c2e

I know it is a way to use push with --force to overwrite, but this PR is close to end and I don't want to do more mess here by testing different methods for fixing it.

@Mateusz-Kowalewski-Mobica Mateusz-Kowalewski-Mobica force-pushed the dynamic_state3_multisample_rasterization branch from bb6cd2c to 1be1bed Compare December 7, 2024 10:44
@Mateusz-Kowalewski-Mobica
Copy link
Contributor

I was cleaned my previous mess. PR is ready to be check :) @asuessenbach @SaschaWillems

Copy link
Collaborator

@SaschaWillems SaschaWillems left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Almost there :)

Only found a few minor things. For the documentation related minor issues see my comments.

The other minor issue I found is with resizing. If you change the size of the window, the projection matrix is not updated. So in order to get that to properly adjust, you need to click into the sample (which probably updates the camera settings.

Example after resizing:

image

It's clearly visible, that there is something wrong with projection. If I then click into the window, the projection is corrected:

image

Other than that I'm happy with the sample. Hope those minor issues are easy to fix :)


To be able to use this extension in Vulkan API:
`VK_EXT_extended_dynamic_state3` depends on `VK_KHR_get_physical_device_properties2`, which is promoted to Vulkan 1.1. That is, to use this extension, `VK_EXT_extended_dynamic_state3` and either `VK_KHR_get_physical_device_properties2` or Vulkan 1.1 are required.
Additionally this sample uses `VK_KHR_dynamic_rendering" which required Vulkan 1.2.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

VK_KHR_dynamic_rendering should be in single quotation marks, otherwise it won't render properly in asciidoc.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.


== Resources

https://registry.khronos.org/vulkan/specs/1.3-extensions/man/html/VK_EXT_extended_dynamic_state3.html
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Versioned spec is no longer build, so these should be updated to use /latest/ instead of /1.3-extensions/

The latter still works due to a redirect but might stop working at some point in the future.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

Copy link
Contributor

@asuessenbach asuessenbach left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just two minor issues from my side.

for (auto &node : scene_nodes_transparent_flipped)
{
draw_node(draw_cmd_buffers[i], node);
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Before binding a pipeline, one could check if there are nodes for that pipeline at all, like

		if (!scene_nodes_opaque.empty())
		{
			vkCmdBindPipeline(draw_cmd_buffers[i], VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_opaque);
			for (auto &node : scene_nodes_opaque)
			{
				draw_node(draw_cmd_buffers[i], node);
			}
		}

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Changes applied.


bool DynamicMultisampleRasterization::resize(const uint32_t _width, const uint32_t _height)
{
sample_count = VK_SAMPLE_COUNT_1_BIT;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Some comment why you need to switch sample_count to 1_BIT here and back to the "actual" value right after resizing would be fine.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is related to this VL Error

Validation Error: [ VUID-VkFramebufferCreateInfo-pAttachments-00881 ] Object 0: handle = 0xba7514000000002a, type = VK_OBJECT_TYPE_RENDER_PASS; Object 1: handle = 0x2002ea00000002ad, type = VK_OBJECT_TYPE_IMAGE_VIEW; Object 2: handle = 0x46b46400000002ab, type = VK_OBJECT_TYPE_IMAGE; | MessageID = 0x2ff52eec | vkCreateFramebuffer(): pCreateInfo->pAttachments[1] has VK_SAMPLE_COUNT_4_BIT samples that do not match the VK_SAMPLE_COUNT_1_BIT samples used by the corresponding attachment for VkRenderPass 0xba7514000000002a[].

While window is resized recreation of framebuffer is performing. When using other sample count then VK_SAMPLE_COUNT_1_BIT it is complaining because renderpass sample count is by default set to VK_SAMPLE_COUNT_1_BIT

I can think about more neat solution, but if needed only :)

@asuessenbach
Copy link
Contributor

asuessenbach commented Dec 9, 2024

The resizing issue is probably not specific to this sample.
It could be easily resolved by setting updated = true; in Camera::set_perspective and Camera::update_aspect_ratio in framework/camera_core.cpp.

@Mateusz-Kowalewski-Mobica
Copy link
Contributor

The resizing issue is probably not specific to this sample. It could be easily resolved by setting updated = true; in Camera::set_perspective and Camera::update_aspect_ratio in framework/camera_core.cpp.

I confirm that change resolve that issue. Thanks for pointing it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants