我有这段代码,它基于 Nvidia 的 nvpro-samples/gl_render_vk_ddisplay。
过去它工作正常,但是当我在 GPU 上添加更多 worload(另一个线程在不相关的资源上做一些 OpenGL 的事情)时,突然我开始在 presentKHR 中陷入僵局,使我的应用程序永远等待。
我发现如果我不使用
_imageAcquiredSemaphores[_currentFrameIndex].get()
我不会遇到同样的情况并且它运行正常。
原始的 Nvidia 代码示例根本没有使用栅栏,我认为这是错误的,所以我使用了它们。
我的代码有什么问题以及为什么当信号量 (
_imageAcquiredSemaphores
) 的重用受到 checkForFence(...)
调用中的 waitingFor/重置围栏保护时,究竟会导致问题?
void OutputWindowDedicatedMonitor::submitTexture()
{
// Wait for GPU if necessary.
checkForFence(_inFlightFences[_currentFrameIndex]);
// Signal GL rendering is done.
glSignalSemaphoreEXT(_syncData[_currentFrameIndex].gl.finished, 0, nullptr, 0, nullptr, nullptr);
const uint32_t imageIndex = _device->acquireNextImageKHR(
_swapchain.get(),
UINT64_MAX,
_imageAcquiredSemaphores[_currentFrameIndex].get(),
vk::Fence()
);
if(imageIndex != _currentFrameIndex) {
cerrlog.err() << "Current frame mismatch.";
return;
}
// Wait for GL finished & VK imageAcquired.
std::vector<vk::Semaphore> blitWaitSemaphores{
_syncData[_currentFrameIndex].vk.finished.get(),
//_imageAcquiredSemaphores[_currentFrameIndex].get() --> If I uncomment this presentKHR call stalls forever.
};
// Blit/copy current texture onto current swapchain image, signal VK blit finished.
std::vector<vk::Semaphore> blitSignalSemaphores{
_blitFinishedSemaphores[_currentFrameIndex].get()
};
vk::PipelineStageFlags blitWaitStages{ vk::PipelineStageFlagBits::eTopOfPipe };
vk::SubmitInfo submitInfo{
static_cast<uint32_t>(blitWaitSemaphores.size()),
blitWaitSemaphores.data(),
&blitWaitStages,
1,
&_blitCommandBuffers[_currentFrameIndex],
static_cast<uint32_t>(blitSignalSemaphores.size()),
blitSignalSemaphores.data()
};
_presentQueue.submit(submitInfo, _inFlightFences[_currentFrameIndex]);
// Setup presentation.
std::vector<vk::Semaphore> presentWaitSemaphores{
_blitFinishedSemaphores[_currentFrameIndex].get()
};
std::vector<vk::Semaphore> presentSignalSemaphores{
_syncData[_currentFrameIndex].vk.available.get()
};
// Present on Direct Display output.
_presentQueue.presentKHR(
{
static_cast<uint32_t>(presentWaitSemaphores.size()),
presentWaitSemaphores.data(),
1,
&_swapchain.get(),
&_currentFrameIndex,
nullptr
}
);
_currentFrameIndex = (_currentFrameIndex + 1) % _swapchainImages.size();
glSignalSemaphoreEXT(_syncData[_currentFrameIndex].gl.available, 0, nullptr, 0, nullptr, nullptr);
}
问题可能是包含信号量的向量只是局部变量并且在超出范围时死亡吗?