Commit 27c89d2b by Shahbaz Youssefi Committed by Commit Bot

Vulkan: fix BufferVk::map() synchronization

4398b2b6 made finishToSerial() in BufferVk::map() conditional to whether the serial is in use to work around a performance regression. Notes: - Prior to 087f1384, finishToSerial already did that, but that check was inadvertently removed. - finishToSerial waits for the smallest serial that's bigger than or equal to the requested serial. - The flush() call in BufferVk::map() was conditional to whether the serial is in use, but it really meant to check whether the buffer has pending commands in the graph. The end result is that there was an unnecessary flush in BufferVk::map() if we had to wait for a previous serial to finish. This change makes the flush conditional to whether the buffer has pending commands in the graph, and the finishToSerial call to whether the serial is not yet finished. Bug: angleproject:3994 Change-Id: Idca436ef2439bcc8c59396a07b2591c1dfadd669 Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/1932341Reviewed-by: 's avatarBrandon Schade <b.schade@samsung.com> Reviewed-by: 's avatarShahbaz Youssefi <syoussefi@chromium.org> Commit-Queue: Shahbaz Youssefi <syoussefi@chromium.org>
parent 36ab960e
......@@ -222,11 +222,14 @@ angle::Result BufferVk::mapRangeImpl(ContextVk *contextVk,
if ((access & GL_MAP_UNSYNCHRONIZED_BIT) == 0)
{
// If there are pending commands for the buffer, flush them.
if (mBuffer.isResourceInUse(contextVk))
if (mBuffer.isCurrentlyInGraph())
{
ANGLE_TRY(contextVk->flushImpl(nullptr));
}
// Make sure the GPU is done with the buffer.
// Make sure the GPU is done with the buffer.
if (contextVk->isSerialInUse(mBuffer.getLatestSerial()))
{
ANGLE_TRY(contextVk->finishToSerial(mBuffer.getLatestSerial()));
}
......
......@@ -416,6 +416,15 @@ angle::Result CommandQueue::finishToSerial(vk::Context *context, Serial serial,
// Find the first batch with serial equal to or bigger than given serial (note that
// the batch serials are unique, otherwise upper-bound would have been necessary).
//
// Note: we don't check for the exact serial, because it may belong to another context. For
// example, imagine the following submissions:
//
// - Context 1: Serial 1, Serial 3, Serial 5
// - Context 2: Serial 2, Serial 4, Serial 6
//
// And imagine none of the submissions have finished yet. Now if Context 2 asks for
// finishToSerial(3), it will have no choice but to finish until Serial 4 instead.
size_t batchIndex = mInFlightCommands.size() - 1;
for (size_t i = 0; i < mInFlightCommands.size(); ++i)
{
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment