Commit 63e4e724 by Jamie Madill

Revert "Using dirty bits notification for blend state"

Failing the dEQP-GLES3 tests: http://build.chromium.org/p/chromium.gpu.fyi/builders/Win7%20Release%20dEQP%20%28NVIDIA%29/builds/4036/ 3 tests failed: dEQP_GLES3.Default/functional_multisample_fbo_4_samples_sample_coverage_invert (c:\b\build\slave\gpu_win_builder\build\src\third_party\angle\src\tests\deqp_support\angle_deqp_gtest.cpp:234) dEQP_GLES3.Default/functional_multisample_fbo_8_samples_sample_coverage_invert (c:\b\build\slave\gpu_win_builder\build\src\third_party\angle\src\tests\deqp_support\angle_deqp_gtest.cpp:234) dEQP_GLES3.Default/functional_multisample_fbo_max_samples_sample_coverage_invert (c:\b\build\slave\gpu_win_builder\build\src\third_party\angle\src\tests\deqp_support\angle_deqp_gtest.cpp:234) BUG=angleproject:1161 This reverts commit ff2ab571. Change-Id: Ibf61fc2c64ffc31778645bfe0292516b1f107397 Reviewed-on: https://chromium-review.googlesource.com/311243Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Tested-by: 's avatarJamie Madill <jmadill@chromium.org>
parent 238827fc
...@@ -1781,7 +1781,7 @@ void Context::syncRendererState() ...@@ -1781,7 +1781,7 @@ void Context::syncRendererState()
const State::DirtyBits &dirtyBits = mState.getDirtyBits(); const State::DirtyBits &dirtyBits = mState.getDirtyBits();
if (dirtyBits.any()) if (dirtyBits.any())
{ {
mRenderer->syncState(getData(), dirtyBits); mRenderer->syncState(mState, dirtyBits);
mState.clearDirtyBits(); mState.clearDirtyBits();
} }
} }
...@@ -1791,7 +1791,7 @@ void Context::syncRendererState(const State::DirtyBits &bitMask) ...@@ -1791,7 +1791,7 @@ void Context::syncRendererState(const State::DirtyBits &bitMask)
const State::DirtyBits &dirtyBits = (mState.getDirtyBits() & bitMask); const State::DirtyBits &dirtyBits = (mState.getDirtyBits() & bitMask);
if (dirtyBits.any()) if (dirtyBits.any())
{ {
mRenderer->syncState(getData(), dirtyBits); mRenderer->syncState(mState, dirtyBits);
mState.clearDirtyBits(dirtyBits); mState.clearDirtyBits(dirtyBits);
} }
} }
......
...@@ -90,7 +90,7 @@ class Renderer : public ImplFactory ...@@ -90,7 +90,7 @@ class Renderer : public ImplFactory
virtual void pushGroupMarker(GLsizei length, const char *marker) = 0; virtual void pushGroupMarker(GLsizei length, const char *marker) = 0;
virtual void popGroupMarker() = 0; virtual void popGroupMarker() = 0;
virtual gl::Error syncState(const gl::Data &data, const gl::State::DirtyBits &dirtyBits) = 0; virtual void syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits) = 0;
// Renderer capabilities // Renderer capabilities
const gl::Caps &getRendererCaps() const; const gl::Caps &getRendererCaps() const;
......
...@@ -8,22 +8,22 @@ ...@@ -8,22 +8,22 @@
#include "libANGLE/renderer/d3d/RendererD3D.h" #include "libANGLE/renderer/d3d/RendererD3D.h"
#include "common/debug.h"
#include "common/MemoryBuffer.h" #include "common/MemoryBuffer.h"
#include "common/debug.h"
#include "common/utilities.h" #include "common/utilities.h"
#include "libANGLE/Display.h" #include "libANGLE/Display.h"
#include "libANGLE/formatutils.h"
#include "libANGLE/Framebuffer.h" #include "libANGLE/Framebuffer.h"
#include "libANGLE/FramebufferAttachment.h" #include "libANGLE/FramebufferAttachment.h"
#include "libANGLE/ResourceManager.h"
#include "libANGLE/State.h"
#include "libANGLE/VertexArray.h"
#include "libANGLE/formatutils.h"
#include "libANGLE/renderer/d3d/BufferD3D.h" #include "libANGLE/renderer/d3d/BufferD3D.h"
#include "libANGLE/renderer/d3d/CompilerD3D.h" #include "libANGLE/renderer/d3d/CompilerD3D.h"
#include "libANGLE/renderer/d3d/DisplayD3D.h" #include "libANGLE/renderer/d3d/DisplayD3D.h"
#include "libANGLE/renderer/d3d/IndexDataManager.h" #include "libANGLE/renderer/d3d/IndexDataManager.h"
#include "libANGLE/renderer/d3d/ProgramD3D.h" #include "libANGLE/renderer/d3d/ProgramD3D.h"
#include "libANGLE/renderer/d3d/SamplerD3D.h" #include "libANGLE/renderer/d3d/SamplerD3D.h"
#include "libANGLE/ResourceManager.h"
#include "libANGLE/State.h"
#include "libANGLE/VertexArray.h"
namespace rx namespace rx
{ {
...@@ -305,16 +305,6 @@ gl::Error RendererD3D::genericDrawArrays(const gl::Data &data, ...@@ -305,16 +305,6 @@ gl::Error RendererD3D::genericDrawArrays(const gl::Data &data,
return gl::Error(GL_NO_ERROR); return gl::Error(GL_NO_ERROR);
} }
gl::Error RendererD3D::syncState(const gl::Data &data, const gl::State::DirtyBits &dirtyBits)
{
// TODO(dianx) mStateManager->syncState when all the states have been moved to manager
// We don't clear the dirty bits here because applyState uses the dirty bits.
// This is a bit of a workaround
mStateManager->syncExternalDirtyBits(dirtyBits);
return gl::Error(GL_NO_ERROR);
}
gl::Error RendererD3D::generateSwizzles(const gl::Data &data, gl::SamplerType type) gl::Error RendererD3D::generateSwizzles(const gl::Data &data, gl::SamplerType type)
{ {
ProgramD3D *programD3D = GetImplAs<ProgramD3D>(data.state->getProgram()); ProgramD3D *programD3D = GetImplAs<ProgramD3D>(data.state->getProgram());
...@@ -389,22 +379,60 @@ gl::Error RendererD3D::applyState(const gl::Data &data, GLenum drawMode) ...@@ -389,22 +379,60 @@ gl::Error RendererD3D::applyState(const gl::Data &data, GLenum drawMode)
const gl::Framebuffer *framebufferObject = data.state->getDrawFramebuffer(); const gl::Framebuffer *framebufferObject = data.state->getDrawFramebuffer();
int samples = framebufferObject->getSamples(data); int samples = framebufferObject->getSamples(data);
// TODO(dianx) drawMode shouldn't be a part of rasterizer state. We should remove it
// from RasterizerState and set a local state only when drawing point sprites in the draw call
gl::RasterizerState rasterizer = data.state->getRasterizerState(); gl::RasterizerState rasterizer = data.state->getRasterizerState();
rasterizer.pointDrawMode = (drawMode == GL_POINTS); rasterizer.pointDrawMode = (drawMode == GL_POINTS);
rasterizer.multiSample = (samples != 0); rasterizer.multiSample = (samples != 0);
gl::Error error = setRasterizerState(rasterizer, data.state->getDirtyBits()); gl::Error error = setRasterizerState(rasterizer);
if (error.isError())
{
return error;
}
unsigned int mask = 0;
if (data.state->isSampleCoverageEnabled())
{
GLclampf coverageValue = data.state->getSampleCoverageValue();
if (coverageValue != 0)
{
float threshold = 0.5f;
for (int i = 0; i < samples; ++i)
{
mask <<= 1;
if ((i + 1) * coverageValue >= threshold)
{
threshold += 1.0f;
mask |= 1;
}
}
}
bool coverageInvert = data.state->getSampleCoverageInvert();
if (coverageInvert)
{
mask = ~mask;
}
}
else
{
mask = 0xFFFFFFFF;
}
error = setBlendState(framebufferObject, data.state->getBlendState(), data.state->getBlendColor(), mask);
if (error.isError()) if (error.isError())
{ {
return error; return error;
} }
error = mStateManager->syncState(data, data.state->getDirtyBits()); error = setDepthStencilState(data.state->getDepthStencilState(), data.state->getStencilRef(),
data.state->getStencilBackRef(), rasterizer.frontFace == GL_CCW);
if (error.isError())
{
return error;
}
return error; return gl::Error(GL_NO_ERROR);
} }
// Applies the shaders and shader constants to the Direct3D device // Applies the shaders and shader constants to the Direct3D device
...@@ -713,4 +741,4 @@ gl::DebugAnnotator *RendererD3D::getAnnotator() ...@@ -713,4 +741,4 @@ gl::DebugAnnotator *RendererD3D::getAnnotator()
return mAnnotator; return mAnnotator;
} }
} // namespace rx }
...@@ -12,13 +12,12 @@ ...@@ -12,13 +12,12 @@
#include "common/debug.h" #include "common/debug.h"
#include "common/MemoryBuffer.h" #include "common/MemoryBuffer.h"
#include "libANGLE/Data.h" #include "libANGLE/Data.h"
#include "libANGLe/formatutils.h" #include "libANGLE/formatutils.h"
#include "libANGLE/renderer/d3d/d3d11/NativeWindow.h" #include "libANGLE/renderer/Renderer.h"
#include "libANGLE/renderer/d3d/formatutilsD3D.h"
#include "libANGLE/renderer/d3d/StateManagerD3D.h"
#include "libANGLE/renderer/d3d/VertexDataManager.h" #include "libANGLE/renderer/d3d/VertexDataManager.h"
#include "libANGLE/renderer/d3d/formatutilsD3D.h"
#include "libANGLE/renderer/d3d/WorkaroundsD3D.h" #include "libANGLE/renderer/d3d/WorkaroundsD3D.h"
#include "libANGLE/renderer/Renderer.h" #include "libANGLE/renderer/d3d/d3d11/NativeWindow.h"
//FIXME(jmadill): std::array is currently prohibited by Chromium style guide //FIXME(jmadill): std::array is currently prohibited by Chromium style guide
#include <array> #include <array>
...@@ -150,12 +149,13 @@ class RendererD3D : public Renderer, public BufferFactoryD3D ...@@ -150,12 +149,13 @@ class RendererD3D : public Renderer, public BufferFactoryD3D
const std::vector<GLint> &vertexUniformBuffers, const std::vector<GLint> &vertexUniformBuffers,
const std::vector<GLint> &fragmentUniformBuffers) = 0; const std::vector<GLint> &fragmentUniformBuffers) = 0;
// Calls state manager to sync state using dirty bits virtual gl::Error setRasterizerState(const gl::RasterizerState &rasterState) = 0;
virtual gl::Error setRasterizerState(const gl::RasterizerState &rasterState, virtual gl::Error setBlendState(const gl::Framebuffer *framebuffer, const gl::BlendState &blendState, const gl::ColorF &blendColor,
const gl::State::DirtyBits &dirtyBits) = 0; unsigned int sampleMask) = 0;
virtual gl::Error setDepthStencilState(const gl::DepthStencilState &depthStencilState, int stencilRef,
int stencilBackRef, bool frontFaceCCW) = 0;
virtual void setScissorRectangle(const gl::Rectangle &scissor, bool enabled) = 0; virtual void setScissorRectangle(const gl::Rectangle &scissor, bool enabled) = 0;
virtual void setViewport(const gl::Rectangle &viewport, float zNear, float zFar, GLenum drawMode, GLenum frontFace, virtual void setViewport(const gl::Rectangle &viewport, float zNear, float zFar, GLenum drawMode, GLenum frontFace,
bool ignoreViewport) = 0; bool ignoreViewport) = 0;
...@@ -220,7 +220,10 @@ class RendererD3D : public Renderer, public BufferFactoryD3D ...@@ -220,7 +220,10 @@ class RendererD3D : public Renderer, public BufferFactoryD3D
virtual gl::Error fastCopyBufferToTexture(const gl::PixelUnpackState &unpack, unsigned int offset, RenderTargetD3D *destRenderTarget, virtual gl::Error fastCopyBufferToTexture(const gl::PixelUnpackState &unpack, unsigned int offset, RenderTargetD3D *destRenderTarget,
GLenum destinationFormat, GLenum sourcePixelsType, const gl::Box &destArea) = 0; GLenum destinationFormat, GLenum sourcePixelsType, const gl::Box &destArea) = 0;
gl::Error syncState(const gl::Data &data, const gl::State::DirtyBits &dirtyBits) override; void syncState(const gl::State & /*state*/, const gl::State::DirtyBits &bitmask) override
{
// TODO(jmadill): implement state sync for D3D renderers;
}
// Device lost // Device lost
void notifyDeviceLost() override; void notifyDeviceLost() override;
...@@ -246,8 +249,6 @@ class RendererD3D : public Renderer, public BufferFactoryD3D ...@@ -246,8 +249,6 @@ class RendererD3D : public Renderer, public BufferFactoryD3D
virtual void createAnnotator() = 0; virtual void createAnnotator() = 0;
StateManagerD3D *mStateManager;
// dirtyPointer is a special value that will make the comparison with any valid pointer fail and force the renderer to re-apply the state. // dirtyPointer is a special value that will make the comparison with any valid pointer fail and force the renderer to re-apply the state.
static const uintptr_t DirtyPointer; static const uintptr_t DirtyPointer;
...@@ -259,10 +260,6 @@ class RendererD3D : public Renderer, public BufferFactoryD3D ...@@ -259,10 +260,6 @@ class RendererD3D : public Renderer, public BufferFactoryD3D
std::vector<TranslatedAttribute> mTranslatedAttribCache; std::vector<TranslatedAttribute> mTranslatedAttribCache;
gl::Rectangle mCurScissor;
bool mScissorEnabled;
bool mForceSetScissor;
private: private:
gl::Error genericDrawArrays(const gl::Data &data, gl::Error genericDrawArrays(const gl::Data &data,
GLenum mode, GLenum mode,
...@@ -336,6 +333,6 @@ struct dx_PixelConstants ...@@ -336,6 +333,6 @@ struct dx_PixelConstants
float depthFront[4]; float depthFront[4];
}; };
} // namespace rx }
#endif // LIBANGLE_RENDERER_D3D_RENDERERD3D_H_ #endif // LIBANGLE_RENDERER_D3D_RENDERERD3D_H_
//
// Copyright (c) 2015 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// StateManagerD3D.cpp: Defines a class for caching D3D state
#include "libANGLE/renderer/d3d/StateManagerD3D.h"
#include "common/BitSetIterator.h"
#include "libANGLE/Framebuffer.h"
namespace rx
{
namespace
{
void SetGivenBitsDirty(gl::State::DirtyBits &dirtyBits,
const gl::State::DirtyBitType *givenBits,
size_t count)
{
for (size_t i = 0; i < count; ++i)
{
dirtyBits.set(givenBits[i]);
}
}
const gl::State::DirtyBitType kRasterizerDirtyBits[] = {
gl::State::DIRTY_BIT_CULL_FACE_ENABLED, gl::State::DIRTY_BIT_CULL_FACE,
gl::State::DIRTY_BIT_FRONT_FACE, gl::State::DIRTY_BIT_POLYGON_OFFSET_FILL_ENABLED,
gl::State::DIRTY_BIT_POLYGON_OFFSET, gl::State::DIRTY_BIT_RASTERIZER_DISCARD_ENABLED};
const gl::State::DirtyBitType kDepthStencilDirtyBits[] = {
gl::State::DIRTY_BIT_DEPTH_MASK,
gl::State::DIRTY_BIT_DEPTH_TEST_ENABLED,
gl::State::DIRTY_BIT_DEPTH_FUNC,
gl::State::DIRTY_BIT_STENCIL_TEST_ENABLED,
gl::State::DIRTY_BIT_STENCIL_FUNCS_FRONT,
gl::State::DIRTY_BIT_STENCIL_FUNCS_BACK,
gl::State::DIRTY_BIT_STENCIL_WRITEMASK_FRONT,
gl::State::DIRTY_BIT_STENCIL_WRITEMASK_BACK,
gl::State::DIRTY_BIT_STENCIL_OPS_FRONT,
gl::State::DIRTY_BIT_STENCIL_OPS_BACK,
};
const gl::State::DirtyBitType kBlendStateDirtyBits[] = {
gl::State::DIRTY_BIT_BLEND_EQUATIONS, gl::State::DIRTY_BIT_BLEND_FUNCS,
gl::State::DIRTY_BIT_BLEND_ENABLED, gl::State::DIRTY_BIT_SAMPLE_ALPHA_TO_COVERAGE_ENABLED,
gl::State::DIRTY_BIT_DITHER_ENABLED, gl::State::DIRTY_BIT_COLOR_MASK,
gl::State::DIRTY_BIT_BLEND_COLOR};
} // anonymous namespace
StateManagerD3D::StateManagerD3D()
: mCurBlendColor(0, 0, 0, 0),
mCurSampleMask(0),
mCurStencilRef(0),
mCurStencilBackRef(0),
mCurStencilSize(0),
mCurScissorTestEnabled(false),
mLocalDirtyBits(),
mExternalDirtyBits()
{
mCurBlendState.blend = false;
mCurBlendState.sourceBlendRGB = GL_ONE;
mCurBlendState.destBlendRGB = GL_ZERO;
mCurBlendState.sourceBlendAlpha = GL_ONE;
mCurBlendState.destBlendAlpha = GL_ZERO;
mCurBlendState.blendEquationRGB = GL_FUNC_ADD;
mCurBlendState.blendEquationAlpha = GL_FUNC_ADD;
mCurBlendState.colorMaskRed = true;
mCurBlendState.colorMaskBlue = true;
mCurBlendState.colorMaskGreen = true;
mCurBlendState.colorMaskAlpha = true;
mCurBlendState.sampleAlphaToCoverage = false;
mCurBlendState.dither = false;
mCurDepthStencilState.depthTest = false;
mCurDepthStencilState.depthFunc = GL_LESS;
mCurDepthStencilState.depthMask = true;
mCurDepthStencilState.stencilTest = false;
mCurDepthStencilState.stencilMask = true;
mCurDepthStencilState.stencilFail = GL_KEEP;
mCurDepthStencilState.stencilPassDepthFail = GL_KEEP;
mCurDepthStencilState.stencilPassDepthPass = GL_KEEP;
mCurDepthStencilState.stencilWritemask = static_cast<GLuint>(-1);
mCurDepthStencilState.stencilBackFunc = GL_ALWAYS;
mCurDepthStencilState.stencilBackMask = static_cast<GLuint>(-1);
mCurDepthStencilState.stencilBackFail = GL_KEEP;
mCurDepthStencilState.stencilBackPassDepthFail = GL_KEEP;
mCurDepthStencilState.stencilBackPassDepthPass = GL_KEEP;
mCurDepthStencilState.stencilBackWritemask = static_cast<GLuint>(-1);
mCurRasterizerState.rasterizerDiscard = false;
mCurRasterizerState.cullFace = false;
mCurRasterizerState.cullMode = GL_BACK;
mCurRasterizerState.frontFace = GL_CCW;
mCurRasterizerState.polygonOffsetFill = false;
mCurRasterizerState.polygonOffsetFactor = 0.0f;
mCurRasterizerState.polygonOffsetUnits = 0.0f;
mCurRasterizerState.pointDrawMode = false;
mCurRasterizerState.multiSample = false;
}
StateManagerD3D::~StateManagerD3D()
{
}
const gl::State::DirtyBits StateManagerD3D::mRasterizerDirtyBits = []()
{
gl::State::DirtyBits rasterizerDirtyBits;
SetGivenBitsDirty(rasterizerDirtyBits, kRasterizerDirtyBits, ArraySize(kRasterizerDirtyBits));
return rasterizerDirtyBits;
}();
const gl::State::DirtyBits StateManagerD3D::mDepthStencilDirtyBits = []()
{
gl::State::DirtyBits depthStencilDirtyBits;
SetGivenBitsDirty(depthStencilDirtyBits, kDepthStencilDirtyBits,
ArraySize(kDepthStencilDirtyBits));
return depthStencilDirtyBits;
}();
const gl::State::DirtyBits StateManagerD3D::mBlendDirtyBits = []()
{
gl::State::DirtyBits blendDirtyBits;
SetGivenBitsDirty(blendDirtyBits, kBlendStateDirtyBits, ArraySize(kBlendStateDirtyBits));
return blendDirtyBits;
}();
bool StateManagerD3D::IsBlendStateDirty(const gl::State::DirtyBits &dirtyBits)
{
return (dirtyBits & mBlendDirtyBits).any();
}
bool StateManagerD3D::IsDepthStencilStateDirty(const gl::State::DirtyBits &dirtyBits)
{
return (dirtyBits & mDepthStencilDirtyBits).any();
}
bool StateManagerD3D::IsRasterizerStateDirty(const gl::State::DirtyBits &dirtyBits)
{
return (dirtyBits & mRasterizerDirtyBits).any();
}
void StateManagerD3D::resetRasterizerForceBits()
{
// If a bit is inside of mRasterizerDirtyBits, we want to reset it, otherwise, leave it alone
mLocalDirtyBits &= (~mRasterizerDirtyBits);
}
void StateManagerD3D::resetBlendForceBits()
{
mLocalDirtyBits &= (~mBlendDirtyBits);
}
void StateManagerD3D::resetDepthStencilForceBits()
{
mLocalDirtyBits &= (~mDepthStencilDirtyBits);
}
bool StateManagerD3D::isForceSetRasterizerState() const
{
return (mLocalDirtyBits & mRasterizerDirtyBits).any();
}
bool StateManagerD3D::isForceSetDepthStencilState() const
{
return (mLocalDirtyBits & mDepthStencilDirtyBits).any();
}
bool StateManagerD3D::isForceSetBlendState() const
{
return (mLocalDirtyBits & mBlendDirtyBits).any();
}
void StateManagerD3D::setCurStencilSize(unsigned int size)
{
mCurStencilSize = size;
}
unsigned int StateManagerD3D::getCurStencilSize() const
{
return mCurStencilSize;
}
void StateManagerD3D::setRasterizerScissorEnabled(bool enabled)
{
mCurScissorTestEnabled = enabled;
}
unsigned int StateManagerD3D::getBlendStateMask(const gl::Framebuffer *framebufferObject,
int samples,
const gl::State &state) const
{
unsigned int mask = 0;
if (state.isSampleCoverageEnabled())
{
GLclampf coverageValue = state.getSampleCoverageValue();
if (coverageValue != 0)
{
float threshold = 0.5f;
for (int i = 0; i < samples; ++i)
{
mask <<= 1;
if ((i + 1) * coverageValue >= threshold)
{
threshold += 1.0f;
mask |= 1;
}
}
}
bool coverageInvert = state.getSampleCoverageInvert();
if (coverageInvert)
{
mask = ~mask;
}
}
else
{
mask = 0xFFFFFFFF;
}
return mask;
}
void StateManagerD3D::forceSetBlendState()
{
mLocalDirtyBits |= mBlendDirtyBits;
}
void StateManagerD3D::forceSetDepthStencilState()
{
mLocalDirtyBits |= mDepthStencilDirtyBits;
}
void StateManagerD3D::forceSetRasterizerState()
{
mLocalDirtyBits |= mRasterizerDirtyBits;
}
void StateManagerD3D::syncExternalDirtyBits(const gl::State::DirtyBits &dirtyBits)
{
mExternalDirtyBits = dirtyBits;
}
gl::Error StateManagerD3D::syncState(const gl::Data &data, const gl::State::DirtyBits &dirtyBits)
{
const gl::Framebuffer *framebufferObject = data.state->getDrawFramebuffer();
int samples = framebufferObject->getSamples(data);
gl::State::DirtyBits allDirtyBits = mExternalDirtyBits | mLocalDirtyBits;
unsigned int sampleMask = getBlendStateMask(framebufferObject, samples, *(data.state));
gl::Error error = setBlendState(framebufferObject, data.state->getBlendState(),
data.state->getBlendColor(), sampleMask, allDirtyBits);
if (error.isError())
{
return error;
}
resetBlendForceBits();
error = setDepthStencilState(data.state->getDepthStencilState(), data.state->getStencilRef(),
data.state->getStencilBackRef(),
data.state->getRasterizerState().frontFace == GL_CCW,
data.state->getDirtyBits());
if (error.isError())
{
return error;
}
resetDepthStencilForceBits();
mExternalDirtyBits.reset();
return gl::Error(GL_NO_ERROR);
}
} // namespace rx
\ No newline at end of file
//
// Copyright (c) 2015 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// StateManagerD3D.h: Defines a class for caching D3D state
#ifndef LIBANGLE_RENDERER_D3D_STATEMANAGERD3D_H_
#define LIBANGLE_RENDERER_D3D_STATEMANAGERD3D_H_
#include "libANGLE/angletypes.h"
#include "libANGLE/Data.h"
#include "libANGLE/State.h"
namespace rx
{
class StateManagerD3D : angle::NonCopyable
{
public:
explicit StateManagerD3D();
virtual ~StateManagerD3D();
void syncExternalDirtyBits(const gl::State::DirtyBits &dirtyBits);
gl::Error syncState(const gl::Data &data, const gl::State::DirtyBits &dirtyBits);
virtual gl::Error setBlendState(const gl::Framebuffer *framebuffer,
const gl::BlendState &blendState,
const gl::ColorF &blendColor,
unsigned int sampleMask,
const gl::State::DirtyBits &dirtyBits) = 0;
virtual gl::Error setDepthStencilState(const gl::DepthStencilState &depthStencilState,
int stencilRef,
int stencilBackRef,
bool frontFaceCCW,
const gl::State::DirtyBits &dirtyBits) = 0;
virtual gl::Error setRasterizerState(const gl::RasterizerState &rasterizerState,
const gl::State::DirtyBits &dirtyBits) = 0;
void setRasterizerScissorEnabled(bool enabled);
void setCurStencilSize(unsigned int size);
unsigned int getCurStencilSize() const;
void forceSetBlendState();
void forceSetDepthStencilState();
void forceSetRasterizerState();
bool isForceSetRasterizerState() const;
bool isForceSetDepthStencilState() const;
bool isForceSetBlendState() const;
protected:
static bool IsBlendStateDirty(const gl::State::DirtyBits &dirtyBits);
static bool IsDepthStencilStateDirty(const gl::State::DirtyBits &dirtyBits);
static bool IsRasterizerStateDirty(const gl::State::DirtyBits &dirtyBits);
void resetRasterizerForceBits();
void resetBlendForceBits();
void resetDepthStencilForceBits();
bool mForceSetDepthStencilState;
bool mForceSetBlendState;
// Blend State
gl::BlendState mCurBlendState;
gl::ColorF mCurBlendColor;
unsigned int mCurSampleMask;
// Depth Stencil State
gl::DepthStencilState mCurDepthStencilState;
int mCurStencilRef;
int mCurStencilBackRef;
unsigned int mCurStencilSize;
// Rasterizer State
gl::RasterizerState mCurRasterizerState;
// Scissor State
bool mCurScissorTestEnabled;
// Local force dirty bits
gl::State::DirtyBits mLocalDirtyBits;
// Copy of dirty bits in state. Synced on syncState. Should be removed after all states are
// moved in
gl::State::DirtyBits mExternalDirtyBits;
static const gl::State::DirtyBits mBlendDirtyBits;
static const gl::State::DirtyBits mDepthStencilDirtyBits;
static const gl::State::DirtyBits mRasterizerDirtyBits;
private:
unsigned int getBlendStateMask(const gl::Framebuffer *framebufferObject,
int samples,
const gl::State &state) const;
};
} // namespace rx
#endif
\ No newline at end of file
...@@ -35,7 +35,6 @@ ...@@ -35,7 +35,6 @@
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h" #include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h" #include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
#include "libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h" #include "libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h"
#include "libANGLE/renderer/d3d/d3d11/StateManager11.h"
#include "libANGLE/renderer/d3d/d3d11/SwapChain11.h" #include "libANGLE/renderer/d3d/d3d11/SwapChain11.h"
#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h" #include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
#include "libANGLE/renderer/d3d/d3d11/TextureStorage11.h" #include "libANGLE/renderer/d3d/d3d11/TextureStorage11.h"
...@@ -195,7 +194,7 @@ ANGLEFeatureLevel GetANGLEFeatureLevel(D3D_FEATURE_LEVEL d3dFeatureLevel) ...@@ -195,7 +194,7 @@ ANGLEFeatureLevel GetANGLEFeatureLevel(D3D_FEATURE_LEVEL d3dFeatureLevel)
} }
} }
} // namespace }
void Renderer11::SRVCache::update(size_t resourceIndex, ID3D11ShaderResourceView *srv) void Renderer11::SRVCache::update(size_t resourceIndex, ID3D11ShaderResourceView *srv)
{ {
...@@ -239,6 +238,7 @@ void Renderer11::SRVCache::clear() ...@@ -239,6 +238,7 @@ void Renderer11::SRVCache::clear()
Renderer11::Renderer11(egl::Display *display) Renderer11::Renderer11(egl::Display *display)
: RendererD3D(display), : RendererD3D(display),
mStateCache(this), mStateCache(this),
mCurStencilSize(0),
mLastHistogramUpdateTime(ANGLEPlatformCurrent()->monotonicallyIncreasingTime()), mLastHistogramUpdateTime(ANGLEPlatformCurrent()->monotonicallyIncreasingTime()),
mDebug(nullptr) mDebug(nullptr)
{ {
...@@ -283,8 +283,6 @@ Renderer11::Renderer11(egl::Display *display) ...@@ -283,8 +283,6 @@ Renderer11::Renderer11(egl::Display *display)
mAppliedNumXFBBindings = static_cast<size_t>(-1); mAppliedNumXFBBindings = static_cast<size_t>(-1);
mStateManager = nullptr;
ZeroMemory(&mAdapterDescription, sizeof(mAdapterDescription)); ZeroMemory(&mAdapterDescription, sizeof(mAdapterDescription));
const auto &attributes = mDisplay->getAttributeMap(); const auto &attributes = mDisplay->getAttributeMap();
...@@ -603,9 +601,6 @@ void Renderer11::initializeDevice() ...@@ -603,9 +601,6 @@ void Renderer11::initializeDevice()
ASSERT(!mPixelTransfer); ASSERT(!mPixelTransfer);
mPixelTransfer = new PixelTransfer11(this); mPixelTransfer = new PixelTransfer11(this);
ASSERT(!mStateManager);
mStateManager = new StateManager11(mDeviceContext, &mStateCache);
const gl::Caps &rendererCaps = getRendererCaps(); const gl::Caps &rendererCaps = getRendererCaps();
mForceSetVertexSamplerStates.resize(rendererCaps.maxVertexTextureImageUnits); mForceSetVertexSamplerStates.resize(rendererCaps.maxVertexTextureImageUnits);
...@@ -1130,11 +1125,117 @@ gl::Error Renderer11::setUniformBuffers(const gl::Data &data, ...@@ -1130,11 +1125,117 @@ gl::Error Renderer11::setUniformBuffers(const gl::Data &data,
return gl::Error(GL_NO_ERROR); return gl::Error(GL_NO_ERROR);
} }
gl::Error Renderer11::setRasterizerState(const gl::RasterizerState &rasterState, gl::Error Renderer11::setRasterizerState(const gl::RasterizerState &rasterState)
const gl::State::DirtyBits &dirtyBits)
{ {
mStateManager->setRasterizerScissorEnabled(mScissorEnabled); if (mForceSetRasterState || memcmp(&rasterState, &mCurRasterState, sizeof(gl::RasterizerState)) != 0)
return mStateManager->setRasterizerState(rasterState, dirtyBits); {
ID3D11RasterizerState *dxRasterState = NULL;
gl::Error error = mStateCache.getRasterizerState(rasterState, mScissorEnabled, &dxRasterState);
if (error.isError())
{
return error;
}
mDeviceContext->RSSetState(dxRasterState);
mCurRasterState = rasterState;
}
mForceSetRasterState = false;
return gl::Error(GL_NO_ERROR);
}
gl::Error Renderer11::setBlendState(const gl::Framebuffer *framebuffer, const gl::BlendState &blendState, const gl::ColorF &blendColor,
unsigned int sampleMask)
{
if (mForceSetBlendState ||
memcmp(&blendState, &mCurBlendState, sizeof(gl::BlendState)) != 0 ||
memcmp(&blendColor, &mCurBlendColor, sizeof(gl::ColorF)) != 0 ||
sampleMask != mCurSampleMask)
{
ID3D11BlendState *dxBlendState = NULL;
gl::Error error = mStateCache.getBlendState(framebuffer, blendState, &dxBlendState);
if (error.isError())
{
return error;
}
ASSERT(dxBlendState != NULL);
float blendColors[4] = {0.0f};
if (blendState.sourceBlendRGB != GL_CONSTANT_ALPHA && blendState.sourceBlendRGB != GL_ONE_MINUS_CONSTANT_ALPHA &&
blendState.destBlendRGB != GL_CONSTANT_ALPHA && blendState.destBlendRGB != GL_ONE_MINUS_CONSTANT_ALPHA)
{
blendColors[0] = blendColor.red;
blendColors[1] = blendColor.green;
blendColors[2] = blendColor.blue;
blendColors[3] = blendColor.alpha;
}
else
{
blendColors[0] = blendColor.alpha;
blendColors[1] = blendColor.alpha;
blendColors[2] = blendColor.alpha;
blendColors[3] = blendColor.alpha;
}
mDeviceContext->OMSetBlendState(dxBlendState, blendColors, sampleMask);
mCurBlendState = blendState;
mCurBlendColor = blendColor;
mCurSampleMask = sampleMask;
}
mForceSetBlendState = false;
return gl::Error(GL_NO_ERROR);
}
gl::Error Renderer11::setDepthStencilState(const gl::DepthStencilState &depthStencilState, int stencilRef,
int stencilBackRef, bool frontFaceCCW)
{
if (mForceSetDepthStencilState ||
memcmp(&depthStencilState, &mCurDepthStencilState, sizeof(gl::DepthStencilState)) != 0 ||
stencilRef != mCurStencilRef || stencilBackRef != mCurStencilBackRef)
{
// get the maximum size of the stencil ref
unsigned int maxStencil = 0;
if (depthStencilState.stencilTest && mCurStencilSize > 0)
{
maxStencil = (1 << mCurStencilSize) - 1;
}
ASSERT((depthStencilState.stencilWritemask & maxStencil) ==
(depthStencilState.stencilBackWritemask & maxStencil));
ASSERT(stencilRef == stencilBackRef);
ASSERT((depthStencilState.stencilMask & maxStencil) ==
(depthStencilState.stencilBackMask & maxStencil));
ID3D11DepthStencilState *dxDepthStencilState = NULL;
gl::Error error = mStateCache.getDepthStencilState(depthStencilState, &dxDepthStencilState);
if (error.isError())
{
return error;
}
ASSERT(dxDepthStencilState);
// Max D3D11 stencil reference value is 0xFF, corresponding to the max 8 bits in a stencil buffer
// GL specifies we should clamp the ref value to the nearest bit depth when doing stencil ops
static_assert(D3D11_DEFAULT_STENCIL_READ_MASK == 0xFF, "Unexpected value of D3D11_DEFAULT_STENCIL_READ_MASK");
static_assert(D3D11_DEFAULT_STENCIL_WRITE_MASK == 0xFF, "Unexpected value of D3D11_DEFAULT_STENCIL_WRITE_MASK");
UINT dxStencilRef = std::min<UINT>(stencilRef, 0xFFu);
mDeviceContext->OMSetDepthStencilState(dxDepthStencilState, dxStencilRef);
mCurDepthStencilState = depthStencilState;
mCurStencilRef = stencilRef;
mCurStencilBackRef = stencilBackRef;
}
mForceSetDepthStencilState = false;
return gl::Error(GL_NO_ERROR);
} }
void Renderer11::setScissorRectangle(const gl::Rectangle &scissor, bool enabled) void Renderer11::setScissorRectangle(const gl::Rectangle &scissor, bool enabled)
...@@ -1155,7 +1256,7 @@ void Renderer11::setScissorRectangle(const gl::Rectangle &scissor, bool enabled) ...@@ -1155,7 +1256,7 @@ void Renderer11::setScissorRectangle(const gl::Rectangle &scissor, bool enabled)
if (enabled != mScissorEnabled) if (enabled != mScissorEnabled)
{ {
mStateManager->forceSetRasterizerState(); mForceSetRasterState = true;
} }
mCurScissor = scissor; mCurScissor = scissor;
...@@ -1410,10 +1511,10 @@ gl::Error Renderer11::applyRenderTarget(const gl::Framebuffer *framebuffer) ...@@ -1410,10 +1511,10 @@ gl::Error Renderer11::applyRenderTarget(const gl::Framebuffer *framebuffer)
} }
unsigned int stencilSize = depthStencil->getStencilSize(); unsigned int stencilSize = depthStencil->getStencilSize();
if (!mDepthStencilInitialized || stencilSize != mStateManager->getCurStencilSize()) if (!mDepthStencilInitialized || stencilSize != mCurStencilSize)
{ {
mStateManager->setCurStencilSize(stencilSize); mCurStencilSize = stencilSize;
mStateManager->forceSetDepthStencilState(); mForceSetDepthStencilState = true;
} }
} }
...@@ -1429,12 +1530,11 @@ gl::Error Renderer11::applyRenderTarget(const gl::Framebuffer *framebuffer) ...@@ -1429,12 +1530,11 @@ gl::Error Renderer11::applyRenderTarget(const gl::Framebuffer *framebuffer)
mRenderTargetDesc.format = renderTargetFormat; mRenderTargetDesc.format = renderTargetFormat;
mForceSetViewport = true; mForceSetViewport = true;
mForceSetScissor = true; mForceSetScissor = true;
mForceSetBlendState = true;
mStateManager->forceSetBlendState();
if (!mDepthStencilInitialized) if (!mDepthStencilInitialized)
{ {
mStateManager->forceSetRasterizerState(); mForceSetRasterState = true;
} }
for (size_t rtIndex = 0; rtIndex < ArraySize(framebufferRTVs); rtIndex++) for (size_t rtIndex = 0; rtIndex < ArraySize(framebufferRTVs); rtIndex++)
...@@ -1994,9 +2094,7 @@ gl::Error Renderer11::applyShadersImpl(const gl::Data &data, GLenum drawMode) ...@@ -1994,9 +2094,7 @@ gl::Error Renderer11::applyShadersImpl(const gl::Data &data, GLenum drawMode)
} }
ID3D11GeometryShader *geometryShader = NULL; ID3D11GeometryShader *geometryShader = NULL;
bool transformFeedbackActive = data.state->isTransformFeedbackActiveUnpaused(); bool transformFeedbackActive = data.state->isTransformFeedbackActiveUnpaused();
if (transformFeedbackActive) if (transformFeedbackActive)
{ {
geometryShader = (vertexExe ? GetAs<ShaderExecutable11>(vertexExe)->getStreamOutShader() : NULL); geometryShader = (vertexExe ? GetAs<ShaderExecutable11>(vertexExe)->getStreamOutShader() : NULL);
...@@ -2245,10 +2343,9 @@ void Renderer11::markAllStateDirty() ...@@ -2245,10 +2343,9 @@ void Renderer11::markAllStateDirty()
mForceSetPixelSamplerStates[fsamplerId] = true; mForceSetPixelSamplerStates[fsamplerId] = true;
} }
mStateManager->forceSetBlendState(); mForceSetBlendState = true;
mStateManager->forceSetDepthStencilState(); mForceSetRasterState = true;
mStateManager->forceSetRasterizerState(); mForceSetDepthStencilState = true;
mForceSetScissor = true; mForceSetScissor = true;
mForceSetViewport = true; mForceSetViewport = true;
...@@ -2303,7 +2400,6 @@ void Renderer11::releaseDeviceResources() ...@@ -2303,7 +2400,6 @@ void Renderer11::releaseDeviceResources()
SafeDelete(mClear); SafeDelete(mClear);
SafeDelete(mTrim); SafeDelete(mTrim);
SafeDelete(mPixelTransfer); SafeDelete(mPixelTransfer);
SafeDelete(mStateManager);
SafeRelease(mDriverConstantBufferVS); SafeRelease(mDriverConstantBufferVS);
SafeRelease(mDriverConstantBufferPS); SafeRelease(mDriverConstantBufferPS);
...@@ -3865,4 +3961,4 @@ gl::Error Renderer11::clearTextures(gl::SamplerType samplerType, size_t rangeSta ...@@ -3865,4 +3961,4 @@ gl::Error Renderer11::clearTextures(gl::SamplerType samplerType, size_t rangeSta
return gl::Error(GL_NO_ERROR); return gl::Error(GL_NO_ERROR);
} }
} // namespace rx }
...@@ -11,14 +11,14 @@ ...@@ -11,14 +11,14 @@
#include "common/angleutils.h" #include "common/angleutils.h"
#include "common/mathutil.h" #include "common/mathutil.h"
#include "libANGLE/angletypes.h"
#include "libANGLE/AttributeMap.h" #include "libANGLE/AttributeMap.h"
#include "libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h" #include "libANGLE/angletypes.h"
#include "libANGLE/renderer/d3d/d3d11/InputLayoutCache.h"
#include "libANGLE/renderer/d3d/d3d11/RenderStateCache.h"
#include "libANGLE/renderer/d3d/HLSLCompiler.h" #include "libANGLE/renderer/d3d/HLSLCompiler.h"
#include "libANGLE/renderer/d3d/RendererD3D.h" #include "libANGLE/renderer/d3d/RendererD3D.h"
#include "libANGLE/renderer/d3d/RenderTargetD3D.h" #include "libANGLE/renderer/d3d/RenderTargetD3D.h"
#include "libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h"
#include "libANGLE/renderer/d3d/d3d11/InputLayoutCache.h"
#include "libANGLE/renderer/d3d/d3d11/RenderStateCache.h"
namespace gl namespace gl
{ {
...@@ -120,11 +120,13 @@ class Renderer11 : public RendererD3D ...@@ -120,11 +120,13 @@ class Renderer11 : public RendererD3D
const std::vector<GLint> &vertexUniformBuffers, const std::vector<GLint> &vertexUniformBuffers,
const std::vector<GLint> &fragmentUniformBuffers) override; const std::vector<GLint> &fragmentUniformBuffers) override;
gl::Error setRasterizerState(const gl::RasterizerState &rasterState, virtual gl::Error setRasterizerState(const gl::RasterizerState &rasterState);
const gl::State::DirtyBits &dirtyBits) override; gl::Error setBlendState(const gl::Framebuffer *framebuffer, const gl::BlendState &blendState, const gl::ColorF &blendColor,
unsigned int sampleMask) override;
void setScissorRectangle(const gl::Rectangle &scissor, bool enabled) override; virtual gl::Error setDepthStencilState(const gl::DepthStencilState &depthStencilState, int stencilRef,
int stencilBackRef, bool frontFaceCCW);
virtual void setScissorRectangle(const gl::Rectangle &scissor, bool enabled);
virtual void setViewport(const gl::Rectangle &viewport, float zNear, float zFar, GLenum drawMode, GLenum frontFace, virtual void setViewport(const gl::Rectangle &viewport, float zNear, float zFar, GLenum drawMode, GLenum frontFace,
bool ignoreViewport); bool ignoreViewport);
...@@ -317,6 +319,7 @@ class Renderer11 : public RendererD3D ...@@ -317,6 +319,7 @@ class Renderer11 : public RendererD3D
uintptr_t mAppliedDSV; uintptr_t mAppliedDSV;
bool mDepthStencilInitialized; bool mDepthStencilInitialized;
bool mRenderTargetDescInitialized; bool mRenderTargetDescInitialized;
unsigned int mCurStencilSize;
struct RenderTargetDesc struct RenderTargetDesc
{ {
...@@ -376,6 +379,27 @@ class Renderer11 : public RendererD3D ...@@ -376,6 +379,27 @@ class Renderer11 : public RendererD3D
// A block of NULL pointers, cached so we don't re-allocate every draw call // A block of NULL pointers, cached so we don't re-allocate every draw call
std::vector<ID3D11ShaderResourceView*> mNullSRVs; std::vector<ID3D11ShaderResourceView*> mNullSRVs;
// Currently applied blend state
bool mForceSetBlendState;
gl::BlendState mCurBlendState;
gl::ColorF mCurBlendColor;
unsigned int mCurSampleMask;
// Currently applied rasterizer state
bool mForceSetRasterState;
gl::RasterizerState mCurRasterState;
// Currently applied depth stencil state
bool mForceSetDepthStencilState;
gl::DepthStencilState mCurDepthStencilState;
int mCurStencilRef;
int mCurStencilBackRef;
// Currently applied scissor rectangle
bool mForceSetScissor;
bool mScissorEnabled;
gl::Rectangle mCurScissor;
// Currently applied viewport // Currently applied viewport
bool mForceSetViewport; bool mForceSetViewport;
gl::Rectangle mCurViewport; gl::Rectangle mCurViewport;
...@@ -462,5 +486,5 @@ class Renderer11 : public RendererD3D ...@@ -462,5 +486,5 @@ class Renderer11 : public RendererD3D
ID3D11Debug *mDebug; ID3D11Debug *mDebug;
}; };
} // namespace rx }
#endif // LIBANGLE_RENDERER_D3D_D3D11_RENDERER11_H_ #endif // LIBANGLE_RENDERER_D3D_D3D11_RENDERER11_H_
//
// Copyright (c) 2015 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// StateManager11.cpp: Defines a class for caching D3D11 state
#include "libANGLE/renderer/d3d/d3d11/StateManager11.h"
namespace rx
{
StateManager11::StateManager11(ID3D11DeviceContext *deviceContext, RenderStateCache *stateCache)
: mDeviceContext(deviceContext), mStateCache(stateCache)
{
}
StateManager11::~StateManager11()
{
}
const gl::RasterizerState &StateManager11::getCurRasterizerState()
{
return mCurRasterizerState;
}
// TODO(dianx) Separate out the blend and stencil states so that each dirty bit
// changes only one thing rather than all for D3D11
gl::Error StateManager11::setBlendState(const gl::Framebuffer *framebuffer,
const gl::BlendState &blendState,
const gl::ColorF &blendColor,
unsigned int sampleMask,
const gl::State::DirtyBits &dirtyBits)
{
if (isForceSetBlendState() ||
(IsBlendStateDirty(dirtyBits) &&
(memcmp(&blendState, &mCurBlendState, sizeof(gl::BlendState)) != 0 ||
memcmp(&blendColor, &mCurBlendColor, sizeof(gl::ColorF)) != 0 ||
sampleMask != mCurSampleMask)))
{
ID3D11BlendState *dxBlendState = NULL;
gl::Error error = mStateCache->getBlendState(framebuffer, blendState, &dxBlendState);
if (error.isError())
{
return error;
}
ASSERT(dxBlendState != NULL);
float blendColors[4] = {0.0f};
if (blendState.sourceBlendRGB != GL_CONSTANT_ALPHA &&
blendState.sourceBlendRGB != GL_ONE_MINUS_CONSTANT_ALPHA &&
blendState.destBlendRGB != GL_CONSTANT_ALPHA &&
blendState.destBlendRGB != GL_ONE_MINUS_CONSTANT_ALPHA)
{
blendColors[0] = blendColor.red;
blendColors[1] = blendColor.green;
blendColors[2] = blendColor.blue;
blendColors[3] = blendColor.alpha;
}
else
{
blendColors[0] = blendColor.alpha;
blendColors[1] = blendColor.alpha;
blendColors[2] = blendColor.alpha;
blendColors[3] = blendColor.alpha;
}
mDeviceContext->OMSetBlendState(dxBlendState, blendColors, sampleMask);
mCurBlendState = blendState;
mCurBlendColor = blendColor;
mCurSampleMask = sampleMask;
}
return gl::Error(GL_NO_ERROR);
}
gl::Error StateManager11::setDepthStencilState(const gl::DepthStencilState &depthStencilState,
int stencilRef,
int stencilBackRef,
bool frontFaceCCW,
const gl::State::DirtyBits &dirtyBits)
{
// TODO(dianx) We are currently not using dirty bits for this, but should in a future patch.
if (isForceSetDepthStencilState() ||
memcmp(&depthStencilState, &mCurDepthStencilState, sizeof(gl::DepthStencilState)) != 0 ||
stencilRef != mCurStencilRef || stencilBackRef != mCurStencilBackRef)
{
// get the maximum size of the stencil ref
unsigned int maxStencil = 0;
if (depthStencilState.stencilTest && mCurStencilSize > 0)
{
maxStencil = (1 << mCurStencilSize) - 1;
}
ASSERT((depthStencilState.stencilWritemask & maxStencil) ==
(depthStencilState.stencilBackWritemask & maxStencil));
ASSERT(stencilRef == stencilBackRef);
ASSERT((depthStencilState.stencilMask & maxStencil) ==
(depthStencilState.stencilBackMask & maxStencil));
ID3D11DepthStencilState *dxDepthStencilState = NULL;
gl::Error error =
mStateCache->getDepthStencilState(depthStencilState, &dxDepthStencilState);
if (error.isError())
{
return error;
}
ASSERT(dxDepthStencilState);
// Max D3D11 stencil reference value is 0xFF, the max 8 bits in a stencil buffer
// GL specifies we should clamp the ref value to nearest bit depth when doing stencil ops
static_assert(D3D11_DEFAULT_STENCIL_READ_MASK == 0xFF,
"Unexpected value of D3D11_DEFAULT_STENCIL_READ_MASK");
static_assert(D3D11_DEFAULT_STENCIL_WRITE_MASK == 0xFF,
"Unexpected value of D3D11_DEFAULT_STENCIL_WRITE_MASK");
UINT dxStencilRef = std::min<UINT>(stencilRef, 0xFFu);
mDeviceContext->OMSetDepthStencilState(dxDepthStencilState, dxStencilRef);
mCurDepthStencilState = depthStencilState;
mCurStencilRef = stencilRef;
mCurStencilBackRef = stencilBackRef;
}
return gl::Error(GL_NO_ERROR);
}
gl::Error StateManager11::setRasterizerState(const gl::RasterizerState &rasterizerState,
const gl::State::DirtyBits &dirtyBits)
{
// TODO(dianx) setRasterizerState is being called after syncRendererState in Context.cpp
// which means the force bits are being cleared before this call is reached.
// We should move the dirtybits back when this is moved to syncState
if (isForceSetRasterizerState() ||
(memcmp(&rasterizerState, &mCurRasterizerState, sizeof(gl::RasterizerState)) != 0))
{
ID3D11RasterizerState *dxRasterState = NULL;
gl::Error error = mStateCache->getRasterizerState(rasterizerState, mCurScissorTestEnabled,
&dxRasterState);
if (error.isError())
{
return error;
}
mDeviceContext->RSSetState(dxRasterState);
mCurRasterizerState = rasterizerState;
resetRasterizerForceBits();
}
return gl::Error(GL_NO_ERROR);
}
} // namespace rx
\ No newline at end of file
//
// Copyright (c) 2015 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// StateManager11.h: Defines a class for caching D3D11 state
#ifndef LIBANGLE_RENDERER_D3D11_STATEMANAGER11_H_
#define LIBANGLE_RENDERER_D3D11_STATEMANAGER11_H_
#include "libANGLE/renderer/d3d/StateManagerD3D.h"
#include "libANGLE/renderer/d3d/d3d11/RenderStateCache.h"
namespace rx
{
class StateManager11 final : public StateManagerD3D
{
public:
StateManager11(ID3D11DeviceContext *deviceContext, RenderStateCache *stateCache);
~StateManager11() override;
gl::Error setBlendState(const gl::Framebuffer *framebuffer,
const gl::BlendState &blendState,
const gl::ColorF &blendColor,
unsigned int sampleMask,
const gl::State::DirtyBits &dirtyBits) override;
gl::Error setDepthStencilState(const gl::DepthStencilState &depthStencilState,
int stencilRef,
int stencilBackRef,
bool frontFaceCCW,
const gl::State::DirtyBits &dirtyBits) override;
gl::Error setRasterizerState(const gl::RasterizerState &rasterizerState,
const gl::State::DirtyBits &dirtyBits) override;
const gl::RasterizerState &getCurRasterizerState();
private:
// TODO(dianx) d3d11 and cached states are not in sync, hence we need to force set things
// but this should not be necessary.
ID3D11DeviceContext *mDeviceContext;
RenderStateCache *mStateCache;
};
} // namespace rx
#endif
\ No newline at end of file
...@@ -11,12 +11,12 @@ ...@@ -11,12 +11,12 @@
#include "common/angleutils.h" #include "common/angleutils.h"
#include "common/mathutil.h" #include "common/mathutil.h"
#include "libANGLE/renderer/d3d/d3d9/DebugAnnotator9.h"
#include "libANGLE/renderer/d3d/d3d9/ShaderCache.h"
#include "libANGLE/renderer/d3d/d3d9/VertexDeclarationCache.h"
#include "libANGLE/renderer/d3d/HLSLCompiler.h" #include "libANGLE/renderer/d3d/HLSLCompiler.h"
#include "libANGLE/renderer/d3d/RendererD3D.h" #include "libANGLE/renderer/d3d/RendererD3D.h"
#include "libANGLE/renderer/d3d/RenderTargetD3D.h" #include "libANGLE/renderer/d3d/RenderTargetD3D.h"
#include "libANGLE/renderer/d3d/d3d9/DebugAnnotator9.h"
#include "libANGLE/renderer/d3d/d3d9/ShaderCache.h"
#include "libANGLE/renderer/d3d/d3d9/VertexDeclarationCache.h"
namespace gl namespace gl
{ {
...@@ -96,11 +96,13 @@ class Renderer9 : public RendererD3D ...@@ -96,11 +96,13 @@ class Renderer9 : public RendererD3D
const std::vector<GLint> &vertexUniformBuffers, const std::vector<GLint> &vertexUniformBuffers,
const std::vector<GLint> &fragmentUniformBuffers) override; const std::vector<GLint> &fragmentUniformBuffers) override;
gl::Error setRasterizerState(const gl::RasterizerState &rasterState, virtual gl::Error setRasterizerState(const gl::RasterizerState &rasterState);
const gl::State::DirtyBits &dirtyBits) override; gl::Error setBlendState(const gl::Framebuffer *framebuffer, const gl::BlendState &blendState, const gl::ColorF &blendColor,
unsigned int sampleMask) override;
virtual gl::Error setDepthStencilState(const gl::DepthStencilState &depthStencilState, int stencilRef,
int stencilBackRef, bool frontFaceCCW);
virtual void setScissorRectangle(const gl::Rectangle &scissor, bool enabled); virtual void setScissorRectangle(const gl::Rectangle &scissor, bool enabled);
virtual void setViewport(const gl::Rectangle &viewport, float zNear, float zFar, GLenum drawMode, GLenum frontFace, virtual void setViewport(const gl::Rectangle &viewport, float zNear, float zFar, GLenum drawMode, GLenum frontFace,
bool ignoreViewport); bool ignoreViewport);
...@@ -310,6 +312,8 @@ class Renderer9 : public RendererD3D ...@@ -310,6 +312,8 @@ class Renderer9 : public RendererD3D
unsigned int mAppliedDepthStencilSerial; unsigned int mAppliedDepthStencilSerial;
bool mDepthStencilInitialized; bool mDepthStencilInitialized;
bool mRenderTargetDescInitialized; bool mRenderTargetDescInitialized;
unsigned int mCurStencilSize;
unsigned int mCurDepthSize;
struct RenderTargetDesc struct RenderTargetDesc
{ {
...@@ -321,12 +325,31 @@ class Renderer9 : public RendererD3D ...@@ -321,12 +325,31 @@ class Renderer9 : public RendererD3D
IDirect3DStateBlock9 *mMaskedClearSavedState; IDirect3DStateBlock9 *mMaskedClearSavedState;
// previously set render states
bool mForceSetDepthStencilState;
gl::DepthStencilState mCurDepthStencilState;
int mCurStencilRef;
int mCurStencilBackRef;
bool mCurFrontFaceCCW;
bool mForceSetRasterState;
gl::RasterizerState mCurRasterState;
bool mForceSetScissor;
gl::Rectangle mCurScissor;
bool mScissorEnabled;
bool mForceSetViewport; bool mForceSetViewport;
gl::Rectangle mCurViewport; gl::Rectangle mCurViewport;
float mCurNear; float mCurNear;
float mCurFar; float mCurFar;
float mCurDepthFront; float mCurDepthFront;
bool mForceSetBlendState;
gl::BlendState mCurBlendState;
gl::ColorF mCurBlendColor;
GLuint mCurSampleMask;
// Currently applied sampler states // Currently applied sampler states
struct CurSamplerState struct CurSamplerState
{ {
...@@ -375,5 +398,5 @@ class Renderer9 : public RendererD3D ...@@ -375,5 +398,5 @@ class Renderer9 : public RendererD3D
UINT mMaxNullColorbufferLRU; UINT mMaxNullColorbufferLRU;
}; };
} // namespace rx }
#endif // LIBANGLE_RENDERER_D3D_D3D9_RENDERER9_H_ #endif // LIBANGLE_RENDERER_D3D_D3D9_RENDERER9_H_
//
// Copyright (c) 2015 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// StateManager9.h: Defines a class for caching D3D9 state
#ifndef LIBANGLE_RENDERER_D3D9_STATEMANAGER9_H_
#define LIBANGLE_RENDERER_D3D9_STATEMANAGER9_H_
#include "libANGLE/renderer/d3d/StateManagerD3D.h"
namespace rx
{
class StateManager9 final : public StateManagerD3D
{
public:
StateManager9(IDirect3DDevice9 *device, D3DADAPTER_IDENTIFIER9 &adapterIdentifier);
~StateManager9() override;
gl::Error setBlendState(const gl::Framebuffer *framebuffer,
const gl::BlendState &blendState,
const gl::ColorF &blendColor,
unsigned int sampleMask,
const gl::State::DirtyBits &dirtyBits) override;
gl::Error setDepthStencilState(const gl::DepthStencilState &depthStencilState,
int stencilRef,
int stencilBackRef,
bool frontFaceCCW,
const gl::State::DirtyBits &dirtyBits) override;
gl::Error setRasterizerState(const gl::RasterizerState &rasterizerState,
const gl::State::DirtyBits &dirtyBits) override;
void setCurDepthSize(unsigned int size);
unsigned int getCurDepthSize() const;
private:
static const D3DRENDERSTATETYPE D3DRS_CCW_STENCILREF = D3DRS_STENCILREF;
static const D3DRENDERSTATETYPE D3DRS_CCW_STENCILMASK = D3DRS_STENCILMASK;
static const D3DRENDERSTATETYPE D3DRS_CCW_STENCILWRITEMASK = D3DRS_STENCILWRITEMASK;
VendorID getVendorId() const;
// Blend state setting functions
void setDepthMask(bool depthMask);
void setDepthTestAndFunc(bool depthTest, GLenum depthFunc);
void setStencilTestEnabled(bool stencilTest);
void setStencilFuncsFront(GLenum stencilFunc,
GLuint stencilMask,
int stencilRef,
unsigned int maxStencil,
bool frontFaceCCW);
void setStencilFuncsBack(GLenum stencilBackFunc,
GLuint stencilBackMask,
int stencilBackRef,
unsigned int maxStencil,
bool frontFaceCCW);
void setStencilWriteMaskFront(GLuint stencilWritemask, bool frontFaceCCW);
void setStencilWriteMaskBack(GLuint stencilBackWritemask, bool frontFaceCCW);
void setStencilOpsFront(GLenum stencilFail,
GLenum stencilPassDepthFail,
GLenum stencilPassDepthPass,
bool frontFaceCCW);
void setStencilOpsBack(GLenum stencilBackFail,
GLenum stencilBackPassDepthFail,
GLenum stencilBackPassDepthPass,
bool frontFaceCCW);
// Depth stencil state setting functions
void setBlendEnableFuncsEquations(const gl::BlendState &blendState,
const gl::ColorF &blendColor);
void setBlendColor(const gl::ColorF &blendColor, const gl::BlendState &blendState);
void setBlendEnabled(bool blendEnabled);
void setSampleAlphaToCoverageEnabled(bool sampleAlphaToCoverage);
void setDitherEnabled(bool ditherEnabled);
void setBlendColorMask(const gl::BlendState &blendState, const gl::Framebuffer *framebuffer);
void setSampleMask(unsigned int sampleMask);
// Rasterizer state setting functions
void setRasterizerMode(bool cullFace, GLenum cullMode, GLenum frontFace);
void setRasterizerPolygonOffset(bool polygonOffsetFill,
GLfloat polygonOffsetFactor,
GLfloat polygonOffsetUnits);
IDirect3DDevice9 *mDevice;
const D3DADAPTER_IDENTIFIER9 &mAdapterIdentifier;
unsigned int mCurDepthSize;
bool mCurFrontFaceCCW;
};
} // namespace rx
#endif
\ No newline at end of file
...@@ -418,8 +418,8 @@ void RendererGL::generateCaps(gl::Caps *outCaps, gl::TextureCapsMap* outTextureC ...@@ -418,8 +418,8 @@ void RendererGL::generateCaps(gl::Caps *outCaps, gl::TextureCapsMap* outTextureC
nativegl_gl::GenerateCaps(mFunctions, outCaps, outTextureCaps, outExtensions, &mMaxSupportedESVersion); nativegl_gl::GenerateCaps(mFunctions, outCaps, outTextureCaps, outExtensions, &mMaxSupportedESVersion);
} }
gl::Error RendererGL::syncState(const gl::Data &data, const gl::State::DirtyBits &dirtyBits) void RendererGL::syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits)
{ {
return mStateManager->syncState(*data.state, dirtyBits); mStateManager->syncState(state, dirtyBits);
} }
} }
...@@ -103,7 +103,7 @@ class RendererGL : public Renderer ...@@ -103,7 +103,7 @@ class RendererGL : public Renderer
std::string getVendorString() const override; std::string getVendorString() const override;
std::string getRendererDescription() const override; std::string getRendererDescription() const override;
gl::Error syncState(const gl::Data &data, const gl::State::DirtyBits &dirtyBits) override; void syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits) override;
const gl::Version &getMaxSupportedESVersion() const; const gl::Version &getMaxSupportedESVersion() const;
const FunctionsGL *getFunctions() const { return mFunctions; } const FunctionsGL *getFunctions() const { return mFunctions; }
......
...@@ -1274,7 +1274,7 @@ void StateManagerGL::setClearStencil(GLint clearStencil) ...@@ -1274,7 +1274,7 @@ void StateManagerGL::setClearStencil(GLint clearStencil)
} }
} }
gl::Error StateManagerGL::syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits) void StateManagerGL::syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits)
{ {
// TODO(jmadill): Investigate only syncing vertex state for active attributes // TODO(jmadill): Investigate only syncing vertex state for active attributes
for (unsigned int dirtyBit : angle::IterateBitSet(dirtyBits | mLocalDirtyBits)) for (unsigned int dirtyBit : angle::IterateBitSet(dirtyBits | mLocalDirtyBits))
...@@ -1507,8 +1507,6 @@ gl::Error StateManagerGL::syncState(const gl::State &state, const gl::State::Dir ...@@ -1507,8 +1507,6 @@ gl::Error StateManagerGL::syncState(const gl::State &state, const gl::State::Dir
mLocalDirtyBits.reset(); mLocalDirtyBits.reset();
} }
return gl::Error(GL_NO_ERROR);
} }
void StateManagerGL::setFramebufferSRGBEnabled(bool enabled) void StateManagerGL::setFramebufferSRGBEnabled(bool enabled)
......
...@@ -135,7 +135,7 @@ class StateManagerGL final : angle::NonCopyable ...@@ -135,7 +135,7 @@ class StateManagerGL final : angle::NonCopyable
GLsizei instanceCount, GLsizei instanceCount,
const GLvoid **outIndices); const GLvoid **outIndices);
gl::Error syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits); void syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits);
private: private:
gl::Error setGenericDrawState(const gl::Data &data); gl::Error setGenericDrawState(const gl::Data &data);
......
...@@ -215,8 +215,6 @@ ...@@ -215,8 +215,6 @@
'libANGLE/renderer/d3d/ShaderD3D.h', 'libANGLE/renderer/d3d/ShaderD3D.h',
'libANGLE/renderer/d3d/ShaderExecutableD3D.cpp', 'libANGLE/renderer/d3d/ShaderExecutableD3D.cpp',
'libANGLE/renderer/d3d/ShaderExecutableD3D.h', 'libANGLE/renderer/d3d/ShaderExecutableD3D.h',
'libANGLe/renderer/d3d/StateManagerD3D.h',
'libANGLE/renderer/d3d/StateManagerD3D.cpp',
'libANGLE/renderer/d3d/SurfaceD3D.cpp', 'libANGLE/renderer/d3d/SurfaceD3D.cpp',
'libANGLE/renderer/d3d/SurfaceD3D.h', 'libANGLE/renderer/d3d/SurfaceD3D.h',
'libANGLE/renderer/d3d/SwapChainD3D.h', 'libANGLE/renderer/d3d/SwapChainD3D.h',
...@@ -265,8 +263,6 @@ ...@@ -265,8 +263,6 @@
'libANGLE/renderer/d3d/d3d9/shaders/compiled/luminanceps.h', 'libANGLE/renderer/d3d/d3d9/shaders/compiled/luminanceps.h',
'libANGLE/renderer/d3d/d3d9/shaders/compiled/passthroughps.h', 'libANGLE/renderer/d3d/d3d9/shaders/compiled/passthroughps.h',
'libANGLE/renderer/d3d/d3d9/shaders/compiled/standardvs.h', 'libANGLE/renderer/d3d/d3d9/shaders/compiled/standardvs.h',
'libANGLE/renderer/d3d/d3d9/StateManager9.h',
'libANGLE/renderer/d3d/d3d9/StateManager9.cpp',
'libANGLE/renderer/d3d/d3d9/SwapChain9.cpp', 'libANGLE/renderer/d3d/d3d9/SwapChain9.cpp',
'libANGLE/renderer/d3d/d3d9/SwapChain9.h', 'libANGLE/renderer/d3d/d3d9/SwapChain9.h',
'libANGLE/renderer/d3d/d3d9/TextureStorage9.cpp', 'libANGLE/renderer/d3d/d3d9/TextureStorage9.cpp',
...@@ -375,8 +371,6 @@ ...@@ -375,8 +371,6 @@
'libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui2darrayps.h', 'libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui2darrayps.h',
'libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui2dps.h', 'libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui2dps.h',
'libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui3dps.h', 'libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui3dps.h',
'libANGLE/renderer/d3d/d3d11/StateManager11.h',
'libANGLE/renderer/d3d/d3d11/StateManager11.cpp',
'libANGLE/renderer/d3d/d3d11/SwapChain11.cpp', 'libANGLE/renderer/d3d/d3d11/SwapChain11.cpp',
'libANGLE/renderer/d3d/d3d11/SwapChain11.h', 'libANGLE/renderer/d3d/d3d11/SwapChain11.h',
'libANGLE/renderer/d3d/d3d11/swizzle_format_info.h', 'libANGLE/renderer/d3d/d3d11/swizzle_format_info.h',
......
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