Commit 806d812e1a1123b9232d0259e1f2e673abc4a55e

Shahbaz Youssefi 2020-01-03T13:48:30

Vulkan: Reorder descriptor sets This change moves driver uniforms to a set with a lower id than the one that includes (emulation) transform feedback buffers. Imagine the following: - Program 1 with xfb: UniformsSet: 1 VS uniforms buffer, 1 FS uniforms buffer, 1 xfb buffer - Program 2 without xfb: UniformsSet: 1 VS uniforms bufer, 1 FS uniforms buffer. Previously, UniformsSet was index 0, and DriverUniformsSet was index 3. When switching from Program 1 to Program 2, the layout of UniformsSet changes, which means every subsequent set needs to be rebound. This is a Vulkan pipeline layout compatibility rule. This is done with invalidateCurrentTextures() and invalidateCurrentShaderResources() already when handling gl::State::DIRTY_BIT_PROGRAM_EXECUTABLE. The bug is that the driver uniforms are not invalidated. This is normally not an issue, because usually when switching from Program 1 to Program 2, transform feedback is paused, and this state change does invalidate driver uniforms. However, the following scenario doesn't do this: - Begin Xfb - Pause Xfb - Use Program 1 - Draw - Use Program 2 - Draw - End Xfb There is no driver state change between the two draw calls, which means the second draw will attempt to draw using the driver uniforms bound for the first draw call. There is a Vulkan validation error here due to the above pipeline layout validation rule. The issue manifests itself only when the second draw call actually uses driver uniforms, as otherwise that set is inactive and not validated; i.e. when line raster emulation is used. In summary, the validation error manifests itself when: - Transform feedback and line raster both use emulation - Transform feedback is paused - A draw with an xfb program is followed by a non-xfb program - The second draw is a line draw A test is added for this. The solution is to reorder the sets so that DriverUniformsSet is placed before UniformsSet. This way, changes to the layout of UniformsSet don't invalidate DriverUniformsSet. In fact, based on the above, any change in the layout of the program should have required an invalidation of the driver uniforms. This bug is probably masked by the fact that ContextVk::handleDirtyDescriptorSetsImpl() always rebinds the graphics driver every time any descriptor set needs rebinding. That should be removed in a follow up change. Bug: angleproject:4261 Change-Id: I21ad4152b454a1fe70554be02e18a9c94fb3e7a8 Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/1986927 Reviewed-by: Tobin Ehlis <tobine@google.com> Reviewed-by: Jamie Madill <jmadill@chromium.org> Commit-Queue: Shahbaz Youssefi <syoussefi@chromium.org>