Commit 4921e457 by Shahbaz Youssefi Committed by Commit Bot

Vulkan: Avoid unnecessary pipeline rebinds

Bug: angleproject:5528 Change-Id: I5502498fa5d6767f55635fe9fff949d7fd644f4f Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/2645640 Commit-Queue: Shahbaz Youssefi <syoussefi@chromium.org> Reviewed-by: 's avatarTim Van Patten <timvp@google.com> Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org>
parent c38413f8
......@@ -755,26 +755,38 @@ void State::setDepthMask(bool mask)
void State::setRasterizerDiscard(bool enabled)
{
mRasterizer.rasterizerDiscard = enabled;
mDirtyBits.set(DIRTY_BIT_RASTERIZER_DISCARD_ENABLED);
if (mRasterizer.rasterizerDiscard != enabled)
{
mRasterizer.rasterizerDiscard = enabled;
mDirtyBits.set(DIRTY_BIT_RASTERIZER_DISCARD_ENABLED);
}
}
void State::setCullFace(bool enabled)
{
mRasterizer.cullFace = enabled;
mDirtyBits.set(DIRTY_BIT_CULL_FACE_ENABLED);
if (mRasterizer.cullFace != enabled)
{
mRasterizer.cullFace = enabled;
mDirtyBits.set(DIRTY_BIT_CULL_FACE_ENABLED);
}
}
void State::setCullMode(CullFaceMode mode)
{
mRasterizer.cullMode = mode;
mDirtyBits.set(DIRTY_BIT_CULL_FACE);
if (mRasterizer.cullMode != mode)
{
mRasterizer.cullMode = mode;
mDirtyBits.set(DIRTY_BIT_CULL_FACE);
}
}
void State::setFrontFace(GLenum front)
{
mRasterizer.frontFace = front;
mDirtyBits.set(DIRTY_BIT_FRONT_FACE);
if (mRasterizer.frontFace != front)
{
mRasterizer.frontFace = front;
mDirtyBits.set(DIRTY_BIT_FRONT_FACE);
}
}
void State::setDepthTest(bool enabled)
......@@ -991,8 +1003,11 @@ void State::setStencilBackOperations(GLenum stencilBackFail,
void State::setPolygonOffsetFill(bool enabled)
{
mRasterizer.polygonOffsetFill = enabled;
mDirtyBits.set(DIRTY_BIT_POLYGON_OFFSET_FILL_ENABLED);
if (mRasterizer.polygonOffsetFill != enabled)
{
mRasterizer.polygonOffsetFill = enabled;
mDirtyBits.set(DIRTY_BIT_POLYGON_OFFSET_FILL_ENABLED);
}
}
void State::setPolygonOffsetParams(GLfloat factor, GLfloat units)
......@@ -1005,14 +1020,20 @@ void State::setPolygonOffsetParams(GLfloat factor, GLfloat units)
void State::setSampleAlphaToCoverage(bool enabled)
{
mSampleAlphaToCoverage = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_ALPHA_TO_COVERAGE_ENABLED);
if (mSampleAlphaToCoverage != enabled)
{
mSampleAlphaToCoverage = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_ALPHA_TO_COVERAGE_ENABLED);
}
}
void State::setSampleCoverage(bool enabled)
{
mSampleCoverage = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_COVERAGE_ENABLED);
if (mSampleCoverage != enabled)
{
mSampleCoverage = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_COVERAGE_ENABLED);
}
}
void State::setSampleCoverageParams(GLclampf value, bool invert)
......@@ -1024,8 +1045,11 @@ void State::setSampleCoverageParams(GLclampf value, bool invert)
void State::setSampleMaskEnabled(bool enabled)
{
mSampleMask = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_MASK_ENABLED);
if (mSampleMask != enabled)
{
mSampleMask = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_MASK_ENABLED);
}
}
void State::setSampleMaskParams(GLuint maskNumber, GLbitfield mask)
......@@ -1038,21 +1062,30 @@ void State::setSampleMaskParams(GLuint maskNumber, GLbitfield mask)
void State::setSampleAlphaToOne(bool enabled)
{
mSampleAlphaToOne = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_ALPHA_TO_ONE);
if (mSampleAlphaToOne != enabled)
{
mSampleAlphaToOne = enabled;
mDirtyBits.set(DIRTY_BIT_SAMPLE_ALPHA_TO_ONE);
}
}
void State::setMultisampling(bool enabled)
{
mMultiSampling = enabled;
mDirtyBits.set(DIRTY_BIT_MULTISAMPLING);
if (mMultiSampling != enabled)
{
mMultiSampling = enabled;
mDirtyBits.set(DIRTY_BIT_MULTISAMPLING);
}
}
void State::setSampleShading(bool enabled)
{
mIsSampleShadingEnabled = enabled;
mMinSampleShading = (enabled) ? 1.0f : mMinSampleShading;
mDirtyBits.set(DIRTY_BIT_SAMPLE_SHADING);
if (mIsSampleShadingEnabled != enabled)
{
mIsSampleShadingEnabled = enabled;
mMinSampleShading = (enabled) ? 1.0f : mMinSampleShading;
mDirtyBits.set(DIRTY_BIT_SAMPLE_SHADING);
}
}
void State::setMinSampleShading(float value)
......@@ -1090,14 +1123,20 @@ void State::setScissorParams(GLint x, GLint y, GLsizei width, GLsizei height)
void State::setDither(bool enabled)
{
mRasterizer.dither = enabled;
mDirtyBits.set(DIRTY_BIT_DITHER_ENABLED);
if (mRasterizer.dither != enabled)
{
mRasterizer.dither = enabled;
mDirtyBits.set(DIRTY_BIT_DITHER_ENABLED);
}
}
void State::setPrimitiveRestart(bool enabled)
{
mPrimitiveRestart = enabled;
mDirtyBits.set(DIRTY_BIT_PRIMITIVE_RESTART_ENABLED);
if (mPrimitiveRestart != enabled)
{
mPrimitiveRestart = enabled;
mDirtyBits.set(DIRTY_BIT_PRIMITIVE_RESTART_ENABLED);
}
}
void State::setClipDistanceEnable(int idx, bool enable)
......@@ -2194,14 +2233,20 @@ void State::setUnpackSkipPixels(GLint skipPixels)
void State::setCoverageModulation(GLenum components)
{
mCoverageModulation = components;
mDirtyBits.set(DIRTY_BIT_COVERAGE_MODULATION);
if (mCoverageModulation != components)
{
mCoverageModulation = components;
mDirtyBits.set(DIRTY_BIT_COVERAGE_MODULATION);
}
}
void State::setFramebufferSRGB(bool sRGB)
{
mFramebufferSRGB = sRGB;
mDirtyBits.set(DIRTY_BIT_FRAMEBUFFER_SRGB);
if (mFramebufferSRGB != sRGB)
{
mFramebufferSRGB = sRGB;
mDirtyBits.set(DIRTY_BIT_FRAMEBUFFER_SRGB);
}
}
void State::setMaxShaderCompilerThreads(GLuint count)
......
......@@ -378,19 +378,21 @@ void VertexArray::setVertexAttribBinding(const Context *context,
{
ASSERT(attribIndex < getMaxAttribs() && bindingIndex < getMaxBindings());
if (mState.mVertexAttributes[attribIndex].bindingIndex != bindingIndex)
if (mState.mVertexAttributes[attribIndex].bindingIndex == bindingIndex)
{
// In ES 3.0 contexts, the binding cannot change, hence the code below is unreachable.
ASSERT(context->getClientVersion() >= ES_3_1);
return;
}
mState.setAttribBinding(context, attribIndex, bindingIndex);
// In ES 3.0 contexts, the binding cannot change, hence the code below is unreachable.
ASSERT(context->getClientVersion() >= ES_3_1);
setDirtyAttribBit(attribIndex, DIRTY_ATTRIB_BINDING);
mState.setAttribBinding(context, attribIndex, bindingIndex);
// Update client attribs mask.
bool hasBuffer = mState.mVertexBindings[bindingIndex].getBuffer().get() != nullptr;
mState.mClientMemoryAttribsMask.set(attribIndex, !hasBuffer);
}
setDirtyAttribBit(attribIndex, DIRTY_ATTRIB_BINDING);
// Update client attribs mask.
bool hasBuffer = mState.mVertexBindings[bindingIndex].getBuffer().get() != nullptr;
mState.mClientMemoryAttribsMask.set(attribIndex, !hasBuffer);
}
void VertexArray::setVertexBindingDivisor(size_t bindingIndex, GLuint divisor)
......
......@@ -465,8 +465,35 @@ ContextVk::ContextVk(const gl::State &state, gl::ErrorSet *errorSet, RendererVk
mActiveTextures.fill({nullptr, nullptr, true});
mActiveImages.fill(nullptr);
// The following dirty bits don't affect the program pipeline:
//
// - READ_FRAMEBUFFER_BINDING only affects operations that read from said framebuffer,
// - CLEAR_* only affect following clear calls,
// - PACK/UNPACK_STATE only affect texture data upload/download,
// - *_BINDING only affect descriptor sets,
// - CURRENT_VALUES only affects (default) vertex attributes.
//
mPipelineDirtyBitsMask.set();
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_READ_FRAMEBUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_CLEAR_COLOR);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_CLEAR_DEPTH);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_CLEAR_STENCIL);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_UNPACK_STATE);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_UNPACK_BUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_PACK_STATE);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_PACK_BUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_RENDERBUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_VERTEX_ARRAY_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_DRAW_INDIRECT_BUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_DISPATCH_INDIRECT_BUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_SAMPLER_BINDINGS);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_TEXTURE_BINDINGS);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_IMAGE_BINDINGS);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_TRANSFORM_FEEDBACK_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_UNIFORM_BUFFER_BINDINGS);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_SHADER_STORAGE_BUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_ATOMIC_COUNTER_BUFFER_BINDING);
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_CURRENT_VALUES);
// Reserve reasonable amount of spaces so that for majority of apps we don't need to grow at all
mDescriptorBufferInfos.reserve(kDescriptorBufferInfosInitialSize);
......@@ -2726,6 +2753,7 @@ angle::Result ContextVk::invalidateProgramExecutableHelper(const gl::Context *co
// No additional work is needed here. We will update the pipeline desc
// later.
invalidateDefaultAttributes(context->getStateCache().getActiveDefaultAttribsMask());
invalidateCurrentGraphicsPipeline();
invalidateVertexAndIndexBuffers();
bool useVertexBuffer = (executable->getMaxActiveAttribLocation() > 0);
mNonIndexedDirtyBitsMask.set(DIRTY_BIT_VERTEX_BUFFERS, useVertexBuffer);
......
......@@ -292,7 +292,6 @@ class ContextVk : public ContextImpl, public vk::Context, public MultisampleText
ANGLE_INLINE void invalidateVertexAndIndexBuffers()
{
invalidateCurrentGraphicsPipeline();
mGraphicsDirtyBits.set(DIRTY_BIT_VERTEX_BUFFERS);
mGraphicsDirtyBits.set(DIRTY_BIT_INDEX_BUFFER);
}
......
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