Skip to content

Commit

Permalink
tests: Add test to reproduce issue
Browse files Browse the repository at this point in the history
SYNC-HAZARD-WRITE-AFTER-READ happens when we use
VK_PIPELINE_STAGE_2_NONE as source stage. Also, for some reason,
VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT produces different behavior, which
suggest something is wrong with flag handling.

SYNC-HAZARD-PRESENT-AFTER-WRITE happens if vkQueuePresentKHR does not
wait on semaphore signaled by vkQueueSubmit2 (in that case it's app
issue).
  • Loading branch information
artem-lunarg committed Jul 27, 2023
1 parent 6bbff10 commit 1831fcf
Showing 1 changed file with 93 additions and 0 deletions.
93 changes: 93 additions & 0 deletions tests/unit/sync_val_positive.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -411,3 +411,96 @@ TEST_F(PositiveSyncVal, ShaderReferencesNotBoundSet) {
vk::CmdEndRenderPass(*m_commandBuffer);
m_commandBuffer->end();
}

TEST_F(PositiveSyncVal, Issue6177) {
SetTargetApiVersion(VK_API_VERSION_1_3);
AddSurfaceExtension();
ASSERT_NO_FATAL_FAILURE(InitSyncValFramework(true));
if (DeviceValidationVersion() < VK_API_VERSION_1_3) {
GTEST_SKIP() << "Test requires at least Vulkan 1.3";
}
if (!AreRequiredExtensionsEnabled()) {
GTEST_SKIP() << RequiredExtensionsNotSupported() << " not supported.";
}
auto sync2_features = LvlInitStruct<VkPhysicalDeviceSynchronization2FeaturesKHR>();
GetPhysicalDeviceFeatures2(sync2_features);
if (!sync2_features.synchronization2) {
GTEST_SKIP() << "synchronization2 required";
}
ASSERT_NO_FATAL_FAILURE(InitState(nullptr, &sync2_features));
if (!InitSwapchain()) {
GTEST_SKIP() << "Cannot create surface or swapchain";
}

const vk_testing::Semaphore acquire_semaphore(*m_device);
const vk_testing::Semaphore submit_semaphore(*m_device);
const auto swapchain_images = GetSwapchainImages(m_swapchain);

uint32_t image_index = 0;
ASSERT_VK_SUCCESS(
vk::AcquireNextImageKHR(device(), m_swapchain, kWaitTimeout, acquire_semaphore, VK_NULL_HANDLE, &image_index));

auto image_barrier = LvlInitStruct<VkImageMemoryBarrier2>();

// NOTE: VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT should be identical to VK_PIPELINE_STAGE_2_NONE but for some
// reason it does not.
//
// VK_PIPELINE_STAGE_2_NONE produces the first error
// reported here https://github.com/KhronosGroup/Vulkan-ValidationLayers/issues/6177.
//
// The second error happens either when VkPresentInfoKHR does not specify waiting semaphore, or
// for some reason when we use VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT instead of NONE, but in that
// case we don't get the first error. Because TOP_OF_PIPE and NONE in source stage should be
// the same it's one more evidence something is wrong.

// image_barrier.srcStageMask = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT;
image_barrier.srcStageMask = VK_PIPELINE_STAGE_2_NONE;
image_barrier.srcAccessMask = 0;
image_barrier.dstStageMask = VK_PIPELINE_STAGE_2_NONE;
image_barrier.dstAccessMask = 0;
image_barrier.oldLayout = VK_IMAGE_LAYOUT_UNDEFINED;
image_barrier.newLayout = VK_IMAGE_LAYOUT_PRESENT_SRC_KHR;
image_barrier.image = swapchain_images[image_index];
image_barrier.subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
image_barrier.subresourceRange.baseMipLevel = 0;
image_barrier.subresourceRange.levelCount = 1;
image_barrier.subresourceRange.baseArrayLayer = 0;
image_barrier.subresourceRange.layerCount = 1;

auto dep_info = LvlInitStruct<VkDependencyInfoKHR>();
dep_info.imageMemoryBarrierCount = 1;
dep_info.pImageMemoryBarriers = &image_barrier;

m_commandBuffer->begin();
vk::CmdPipelineBarrier2(*m_commandBuffer, &dep_info);
m_commandBuffer->end();

auto wait_info = LvlInitStruct<VkSemaphoreSubmitInfo>();
wait_info.semaphore = acquire_semaphore;
wait_info.stageMask = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT;

auto command_buffer_info = LvlInitStruct<VkCommandBufferSubmitInfo>();
command_buffer_info.commandBuffer = *m_commandBuffer;

auto signal_info = LvlInitStruct<VkSemaphoreSubmitInfo>();
signal_info.semaphore = submit_semaphore;
signal_info.stageMask = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT;

auto submit = LvlInitStruct<VkSubmitInfo2>();
submit.waitSemaphoreInfoCount = 1;
submit.pWaitSemaphoreInfos = &wait_info;
submit.commandBufferInfoCount = 1;
submit.pCommandBufferInfos = &command_buffer_info;
submit.signalSemaphoreInfoCount = 1;
submit.pSignalSemaphoreInfos = &signal_info;
ASSERT_VK_SUCCESS(vk::QueueSubmit2(m_device->m_queue, 1, &submit, VK_NULL_HANDLE));

auto present = LvlInitStruct<VkPresentInfoKHR>();
present.waitSemaphoreCount = 1;
present.pWaitSemaphores = &submit_semaphore.handle();
present.swapchainCount = 1;
present.pSwapchains = &m_swapchain;
present.pImageIndices = &image_index;
ASSERT_VK_SUCCESS(vk::QueuePresentKHR(m_device->m_queue, &present));
ASSERT_VK_SUCCESS(vk::QueueWaitIdle(m_device->m_queue));
}

0 comments on commit 1831fcf

Please sign in to comment.