Commit 14bbb3f9 by Jamie Madill Committed by Commit Bot

Context: Remove recompilation trigger impl method.

Move this down into the D3D11 renderer. Achieve this by passing a mutable pointer to the memory program cache to the ContextImpl. This will allow the D3D11 back-end to more easily sync state then apply state changes. It also cleans up the gl-side Context a bit. BUG=angleproject:1155 Change-Id: Ia2c63c05cf414e0d0b22b69c3ed7128f0e405933 Reviewed-on: https://chromium-review.googlesource.com/659230 Commit-Queue: Jamie Madill <jmadill@chromium.org> Reviewed-by: 's avatarGeoff Lang <geofflang@chromium.org>
parent 096fd623
...@@ -280,6 +280,8 @@ Context::Context(rx::EGLImplFactory *implFactory, ...@@ -280,6 +280,8 @@ Context::Context(rx::EGLImplFactory *implFactory,
mScratchBuffer(1000u), mScratchBuffer(1000u),
mZeroFilledBuffer(1000u) mZeroFilledBuffer(1000u)
{ {
mImplementation->setMemoryProgramCache(memoryProgramCache);
initCaps(displayExtensions); initCaps(displayExtensions);
initWorkarounds(); initWorkarounds();
...@@ -1750,14 +1752,14 @@ void Context::texParameteriv(GLenum target, GLenum pname, const GLint *params) ...@@ -1750,14 +1752,14 @@ void Context::texParameteriv(GLenum target, GLenum pname, const GLint *params)
void Context::drawArrays(GLenum mode, GLint first, GLsizei count) void Context::drawArrays(GLenum mode, GLint first, GLsizei count)
{ {
ANGLE_CONTEXT_TRY(prepareForDraw(mode)); syncRendererState();
ANGLE_CONTEXT_TRY(mImplementation->drawArrays(this, mode, first, count)); ANGLE_CONTEXT_TRY(mImplementation->drawArrays(this, mode, first, count));
MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback()); MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
} }
void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsizei instanceCount) void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsizei instanceCount)
{ {
ANGLE_CONTEXT_TRY(prepareForDraw(mode)); syncRendererState();
ANGLE_CONTEXT_TRY( ANGLE_CONTEXT_TRY(
mImplementation->drawArraysInstanced(this, mode, first, count, instanceCount)); mImplementation->drawArraysInstanced(this, mode, first, count, instanceCount));
MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback()); MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
...@@ -1765,7 +1767,7 @@ void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsiz ...@@ -1765,7 +1767,7 @@ void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsiz
void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices) void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices)
{ {
ANGLE_CONTEXT_TRY(prepareForDraw(mode)); syncRendererState();
ANGLE_CONTEXT_TRY(mImplementation->drawElements(this, mode, count, type, indices)); ANGLE_CONTEXT_TRY(mImplementation->drawElements(this, mode, count, type, indices));
} }
...@@ -1775,7 +1777,7 @@ void Context::drawElementsInstanced(GLenum mode, ...@@ -1775,7 +1777,7 @@ void Context::drawElementsInstanced(GLenum mode,
const void *indices, const void *indices,
GLsizei instances) GLsizei instances)
{ {
ANGLE_CONTEXT_TRY(prepareForDraw(mode)); syncRendererState();
ANGLE_CONTEXT_TRY( ANGLE_CONTEXT_TRY(
mImplementation->drawElementsInstanced(this, mode, count, type, indices, instances)); mImplementation->drawElementsInstanced(this, mode, count, type, indices, instances));
} }
...@@ -1787,20 +1789,20 @@ void Context::drawRangeElements(GLenum mode, ...@@ -1787,20 +1789,20 @@ void Context::drawRangeElements(GLenum mode,
GLenum type, GLenum type,
const void *indices) const void *indices)
{ {
ANGLE_CONTEXT_TRY(prepareForDraw(mode)); syncRendererState();
ANGLE_CONTEXT_TRY( ANGLE_CONTEXT_TRY(
mImplementation->drawRangeElements(this, mode, start, end, count, type, indices)); mImplementation->drawRangeElements(this, mode, start, end, count, type, indices));
} }
void Context::drawArraysIndirect(GLenum mode, const void *indirect) void Context::drawArraysIndirect(GLenum mode, const void *indirect)
{ {
ANGLE_CONTEXT_TRY(prepareForDraw(mode)); syncRendererState();
ANGLE_CONTEXT_TRY(mImplementation->drawArraysIndirect(this, mode, indirect)); ANGLE_CONTEXT_TRY(mImplementation->drawArraysIndirect(this, mode, indirect));
} }
void Context::drawElementsIndirect(GLenum mode, GLenum type, const void *indirect) void Context::drawElementsIndirect(GLenum mode, GLenum type, const void *indirect)
{ {
ANGLE_CONTEXT_TRY(prepareForDraw(mode)); syncRendererState();
ANGLE_CONTEXT_TRY(mImplementation->drawElementsIndirect(this, mode, type, indirect)); ANGLE_CONTEXT_TRY(mImplementation->drawElementsIndirect(this, mode, type, indirect));
} }
...@@ -2769,20 +2771,6 @@ void Context::initWorkarounds() ...@@ -2769,20 +2771,6 @@ void Context::initWorkarounds()
mWorkarounds.loseContextOnOutOfMemory = (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT); mWorkarounds.loseContextOnOutOfMemory = (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
} }
Error Context::prepareForDraw(GLenum drawMode)
{
syncRendererState();
InfoLog infoLog;
Error err = mImplementation->triggerDrawCallProgramRecompilation(this, &infoLog,
mMemoryProgramCache, drawMode);
if (err.isError() || infoLog.getLength() > 0)
{
WARN() << "Dynamic recompilation error log: " << infoLog.str();
}
return err;
}
void Context::syncRendererState() void Context::syncRendererState()
{ {
mGLState.syncDirtyObjects(this); mGLState.syncDirtyObjects(this);
......
...@@ -937,7 +937,6 @@ class Context final : public ValidationContext ...@@ -937,7 +937,6 @@ class Context final : public ValidationContext
egl::Surface *getCurrentReadSurface() const { return mCurrentSurface; } egl::Surface *getCurrentReadSurface() const { return mCurrentSurface; }
private: private:
Error prepareForDraw(GLenum drawMode);
void syncRendererState(); void syncRendererState();
void syncRendererState(const State::DirtyBits &bitMask, const State::DirtyObjects &objectMask); void syncRendererState(const State::DirtyBits &bitMask, const State::DirtyObjects &objectMask);
void syncStateForReadPixels(); void syncStateForReadPixels();
......
...@@ -12,7 +12,8 @@ ...@@ -12,7 +12,8 @@
namespace rx namespace rx
{ {
ContextImpl::ContextImpl(const gl::ContextState &state) : mState(state) ContextImpl::ContextImpl(const gl::ContextState &state)
: mState(state), mMemoryProgramCache(nullptr)
{ {
} }
...@@ -110,4 +111,9 @@ void ContextImpl::stencilThenCoverStrokePathInstanced(const std::vector<gl::Path ...@@ -110,4 +111,9 @@ void ContextImpl::stencilThenCoverStrokePathInstanced(const std::vector<gl::Path
UNREACHABLE(); UNREACHABLE();
} }
void ContextImpl::setMemoryProgramCache(gl::MemoryProgramCache *memoryProgramCache)
{
mMemoryProgramCache = memoryProgramCache;
}
} // namespace rx } // namespace rx
...@@ -156,18 +156,6 @@ class ContextImpl : public GLImplFactory ...@@ -156,18 +156,6 @@ class ContextImpl : public GLImplFactory
GLuint numGroupsY, GLuint numGroupsY,
GLuint numGroupsZ) = 0; GLuint numGroupsZ) = 0;
// This does not correspond to a GL API, but matches a common GL driver behaviour where
// draw call states can trigger dynamic shader recompilation. We pass the Program cache
// handle as a mutable pointer to this Impl method to both trigger dynamic recompilations
// and to allow the back-end to store the refreshed shaders in the cache.
virtual gl::Error triggerDrawCallProgramRecompilation(const gl::Context *context,
gl::InfoLog *infoLog,
gl::MemoryProgramCache *memoryCache,
GLenum drawMode)
{
return gl::NoError();
}
const gl::ContextState &getContextState() { return mState; } const gl::ContextState &getContextState() { return mState; }
int getClientMajorVersion() const { return mState.getClientMajorVersion(); } int getClientMajorVersion() const { return mState.getClientMajorVersion(); }
int getClientMinorVersion() const { return mState.getClientMinorVersion(); } int getClientMinorVersion() const { return mState.getClientMinorVersion(); }
...@@ -177,8 +165,14 @@ class ContextImpl : public GLImplFactory ...@@ -177,8 +165,14 @@ class ContextImpl : public GLImplFactory
const gl::Extensions &getExtensions() const { return mState.getExtensions(); } const gl::Extensions &getExtensions() const { return mState.getExtensions(); }
const gl::Limitations &getLimitations() const { return mState.getLimitations(); } const gl::Limitations &getLimitations() const { return mState.getLimitations(); }
// A common GL driver behaviour is to trigger dynamic shader recompilation on a draw call,
// based on the current render states. We store a mutable pointer to the program cache so
// on draw calls we can store the refreshed shaders in the cache.
void setMemoryProgramCache(gl::MemoryProgramCache *memoryProgramCache);
protected: protected:
const gl::ContextState &mState; const gl::ContextState &mState;
gl::MemoryProgramCache *mMemoryProgramCache;
}; };
} // namespace rx } // namespace rx
......
...@@ -153,9 +153,7 @@ gl::Error Context11::finish() ...@@ -153,9 +153,7 @@ gl::Error Context11::finish()
gl::Error Context11::drawArrays(const gl::Context *context, GLenum mode, GLint first, GLsizei count) gl::Error Context11::drawArrays(const gl::Context *context, GLenum mode, GLint first, GLsizei count)
{ {
// TODO(jmadill): Update state in syncState before the draw call. ANGLE_TRY(prepareForDrawCall(context, mode));
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, mode));
return mRenderer->genericDrawArrays(context, mode, first, count, 0); return mRenderer->genericDrawArrays(context, mode, first, count, 0);
} }
...@@ -165,9 +163,7 @@ gl::Error Context11::drawArraysInstanced(const gl::Context *context, ...@@ -165,9 +163,7 @@ gl::Error Context11::drawArraysInstanced(const gl::Context *context,
GLsizei count, GLsizei count,
GLsizei instanceCount) GLsizei instanceCount)
{ {
// TODO(jmadill): Update state in syncState before the draw call. ANGLE_TRY(prepareForDrawCall(context, mode));
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, mode));
return mRenderer->genericDrawArrays(context, mode, first, count, instanceCount); return mRenderer->genericDrawArrays(context, mode, first, count, instanceCount);
} }
...@@ -177,9 +173,7 @@ gl::Error Context11::drawElements(const gl::Context *context, ...@@ -177,9 +173,7 @@ gl::Error Context11::drawElements(const gl::Context *context,
GLenum type, GLenum type,
const void *indices) const void *indices)
{ {
// TODO(jmadill): Update state in syncState before the draw call. ANGLE_TRY(prepareForDrawCall(context, mode));
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, mode));
return mRenderer->genericDrawElements(context, mode, count, type, indices, 0); return mRenderer->genericDrawElements(context, mode, count, type, indices, 0);
} }
...@@ -190,9 +184,7 @@ gl::Error Context11::drawElementsInstanced(const gl::Context *context, ...@@ -190,9 +184,7 @@ gl::Error Context11::drawElementsInstanced(const gl::Context *context,
const void *indices, const void *indices,
GLsizei instances) GLsizei instances)
{ {
// TODO(jmadill): Update state in syncState before the draw call. ANGLE_TRY(prepareForDrawCall(context, mode));
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, mode));
return mRenderer->genericDrawElements(context, mode, count, type, indices, instances); return mRenderer->genericDrawElements(context, mode, count, type, indices, instances);
} }
...@@ -204,9 +196,7 @@ gl::Error Context11::drawRangeElements(const gl::Context *context, ...@@ -204,9 +196,7 @@ gl::Error Context11::drawRangeElements(const gl::Context *context,
GLenum type, GLenum type,
const void *indices) const void *indices)
{ {
// TODO(jmadill): Update state in syncState before the draw call. ANGLE_TRY(prepareForDrawCall(context, mode));
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, mode));
return mRenderer->genericDrawElements(context, mode, count, type, indices, 0); return mRenderer->genericDrawElements(context, mode, count, type, indices, 0);
} }
...@@ -214,9 +204,7 @@ gl::Error Context11::drawArraysIndirect(const gl::Context *context, ...@@ -214,9 +204,7 @@ gl::Error Context11::drawArraysIndirect(const gl::Context *context,
GLenum mode, GLenum mode,
const void *indirect) const void *indirect)
{ {
// TODO(jmadill): Update state in syncState before the draw call. ANGLE_TRY(prepareForDrawCall(context, mode));
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, mode));
return mRenderer->genericDrawIndirect(context, mode, GL_NONE, indirect); return mRenderer->genericDrawIndirect(context, mode, GL_NONE, indirect);
} }
...@@ -225,9 +213,7 @@ gl::Error Context11::drawElementsIndirect(const gl::Context *context, ...@@ -225,9 +213,7 @@ gl::Error Context11::drawElementsIndirect(const gl::Context *context,
GLenum type, GLenum type,
const void *indirect) const void *indirect)
{ {
// TODO(jmadill): Update state in syncState before the draw call. ANGLE_TRY(prepareForDrawCall(context, mode));
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, mode));
return mRenderer->genericDrawIndirect(context, mode, type, indirect); return mRenderer->genericDrawIndirect(context, mode, type, indirect);
} }
...@@ -318,8 +304,6 @@ gl::Error Context11::dispatchCompute(const gl::Context *context, ...@@ -318,8 +304,6 @@ gl::Error Context11::dispatchCompute(const gl::Context *context,
} }
gl::Error Context11::triggerDrawCallProgramRecompilation(const gl::Context *context, gl::Error Context11::triggerDrawCallProgramRecompilation(const gl::Context *context,
gl::InfoLog *infoLog,
gl::MemoryProgramCache *memoryCache,
GLenum drawMode) GLenum drawMode)
{ {
const auto &glState = context->getGLState(); const auto &glState = context->getGLState();
...@@ -343,13 +327,18 @@ gl::Error Context11::triggerDrawCallProgramRecompilation(const gl::Context *cont ...@@ -343,13 +327,18 @@ gl::Error Context11::triggerDrawCallProgramRecompilation(const gl::Context *cont
// Load the compiler if necessary and recompile the programs. // Load the compiler if necessary and recompile the programs.
ANGLE_TRY(mRenderer->ensureHLSLCompilerInitialized()); ANGLE_TRY(mRenderer->ensureHLSLCompilerInitialized());
gl::InfoLog infoLog;
if (recompileVS) if (recompileVS)
{ {
ShaderExecutableD3D *vertexExe = nullptr; ShaderExecutableD3D *vertexExe = nullptr;
ANGLE_TRY(programD3D->getVertexExecutableForCachedInputLayout(&vertexExe, infoLog)); ANGLE_TRY(programD3D->getVertexExecutableForCachedInputLayout(&vertexExe, &infoLog));
if (!programD3D->hasVertexExecutableForCachedInputLayout()) if (!programD3D->hasVertexExecutableForCachedInputLayout())
{ {
return gl::InternalError() << "Error compiling dynamic vertex executable."; ASSERT(infoLog.getLength() > 0);
ERR() << "Dynamic recompilation error log: " << infoLog.str();
return gl::InternalError()
<< "Error compiling dynamic vertex executable:" << infoLog.str();
} }
} }
...@@ -357,30 +346,46 @@ gl::Error Context11::triggerDrawCallProgramRecompilation(const gl::Context *cont ...@@ -357,30 +346,46 @@ gl::Error Context11::triggerDrawCallProgramRecompilation(const gl::Context *cont
{ {
ShaderExecutableD3D *geometryExe = nullptr; ShaderExecutableD3D *geometryExe = nullptr;
ANGLE_TRY(programD3D->getGeometryExecutableForPrimitiveType(context, drawMode, &geometryExe, ANGLE_TRY(programD3D->getGeometryExecutableForPrimitiveType(context, drawMode, &geometryExe,
infoLog)); &infoLog));
if (!programD3D->hasGeometryExecutableForPrimitiveType(drawMode)) if (!programD3D->hasGeometryExecutableForPrimitiveType(drawMode))
{ {
return gl::InternalError() << "Error compiling dynamic geometry executable."; ASSERT(infoLog.getLength() > 0);
ERR() << "Dynamic recompilation error log: " << infoLog.str();
return gl::InternalError()
<< "Error compiling dynamic geometry executable:" << infoLog.str();
} }
} }
if (recompilePS) if (recompilePS)
{ {
ShaderExecutableD3D *pixelExe = nullptr; ShaderExecutableD3D *pixelExe = nullptr;
ANGLE_TRY(programD3D->getPixelExecutableForCachedOutputLayout(&pixelExe, infoLog)); ANGLE_TRY(programD3D->getPixelExecutableForCachedOutputLayout(&pixelExe, &infoLog));
if (!programD3D->hasPixelExecutableForCachedOutputLayout()) if (!programD3D->hasPixelExecutableForCachedOutputLayout())
{ {
return gl::InternalError() << "Error compiling dynamic pixel executable."; ASSERT(infoLog.getLength() > 0);
ERR() << "Dynamic recompilation error log: " << infoLog.str();
return gl::InternalError()
<< "Error compiling dynamic pixel executable:" << infoLog.str();
} }
} }
// Refresh the program cache entry. // Refresh the program cache entry.
if (memoryCache) if (mMemoryProgramCache)
{ {
memoryCache->updateProgram(context, program); mMemoryProgramCache->updateProgram(context, program);
} }
return gl::NoError(); return gl::NoError();
} }
gl::Error Context11::prepareForDrawCall(const gl::Context *context, GLenum drawMode)
{
ANGLE_TRY(triggerDrawCallProgramRecompilation(context, drawMode));
// TODO(jmadill): Update state in syncState before the draw call.
ANGLE_TRY(mRenderer->getStateManager()->updateState(context, drawMode));
return gl::NoError();
}
} // namespace rx } // namespace rx
...@@ -135,12 +135,10 @@ class Context11 : public ContextImpl ...@@ -135,12 +135,10 @@ class Context11 : public ContextImpl
GLuint numGroupsY, GLuint numGroupsY,
GLuint numGroupsZ) override; GLuint numGroupsZ) override;
gl::Error triggerDrawCallProgramRecompilation(const gl::Context *context,
gl::InfoLog *infoLog,
gl::MemoryProgramCache *memoryCache,
GLenum drawMode) override;
private: private:
gl::Error triggerDrawCallProgramRecompilation(const gl::Context *context, GLenum drawMode);
gl::Error prepareForDrawCall(const gl::Context *context, GLenum drawMode);
Renderer11 *mRenderer; Renderer11 *mRenderer;
}; };
......
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