blob: be4c10206a53bd1b2ba830d0b23b79449a28a576 [file] [log] [blame]
Shannon Woods53a94a82014-06-24 15:20:36 -04001//
2// Copyright (c) 2014 The ANGLE Project Authors. All rights reserved.
3// Use of this source code is governed by a BSD-style license that can be
4// found in the LICENSE file.
5//
6
7// State.cpp: Implements the State class, encapsulating raw GL state.
8
Geoff Lang2b5420c2014-11-19 14:20:15 -05009#include "libANGLE/State.h"
Shannon Woods53a94a82014-06-24 15:20:36 -040010
Sami Väisänene45e53b2016-05-25 10:36:04 +030011#include <limits>
12#include <string.h>
13
Jamie Madillc9d442d2016-01-20 11:17:24 -050014#include "common/BitSetIterator.h"
Sami Väisänene45e53b2016-05-25 10:36:04 +030015#include "common/matrix_utils.h"
16#include "common/mathutil.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050017#include "libANGLE/Context.h"
18#include "libANGLE/Caps.h"
Geoff Lang70d0f492015-12-10 17:45:46 -050019#include "libANGLE/Debug.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050020#include "libANGLE/Framebuffer.h"
21#include "libANGLE/FramebufferAttachment.h"
22#include "libANGLE/Query.h"
23#include "libANGLE/VertexArray.h"
24#include "libANGLE/formatutils.h"
Shannon Woods53a94a82014-06-24 15:20:36 -040025
Olli Etuahobbf1c102016-06-28 13:31:33 +030026namespace
27{
28
29GLenum ActiveQueryType(const GLenum type)
30{
31 return (type == GL_ANY_SAMPLES_PASSED_CONSERVATIVE) ? GL_ANY_SAMPLES_PASSED : type;
32}
33
34} // anonymous namepace
35
Shannon Woods53a94a82014-06-24 15:20:36 -040036namespace gl
37{
Geoff Lang76b10c92014-09-05 16:28:14 -040038
Shannon Woods53a94a82014-06-24 15:20:36 -040039State::State()
Jamie Madille79b1e12015-11-04 16:36:37 -050040 : mMaxDrawBuffers(0),
41 mMaxCombinedTextureImageUnits(0),
42 mDepthClearValue(0),
43 mStencilClearValue(0),
44 mScissorTest(false),
45 mSampleCoverage(false),
46 mSampleCoverageValue(0),
47 mSampleCoverageInvert(false),
48 mStencilRef(0),
49 mStencilBackRef(0),
50 mLineWidth(0),
51 mGenerateMipmapHint(GL_NONE),
52 mFragmentShaderDerivativeHint(GL_NONE),
Geoff Langf41a7152016-09-19 15:11:17 -040053 mBindGeneratesResource(true),
Jamie Madille79b1e12015-11-04 16:36:37 -050054 mNearZ(0),
55 mFarZ(0),
56 mReadFramebuffer(nullptr),
57 mDrawFramebuffer(nullptr),
58 mProgram(nullptr),
59 mVertexArray(nullptr),
60 mActiveSampler(0),
Sami Väisänen74c23472016-05-09 17:30:30 +030061 mPrimitiveRestart(false),
62 mMultiSampling(false),
Geoff Lang1d2c41d2016-10-19 16:14:46 -070063 mSampleAlphaToOne(false),
64 mFramebufferSRGB(true)
Shannon Woods53a94a82014-06-24 15:20:36 -040065{
Geoff Lang76b10c92014-09-05 16:28:14 -040066}
67
68State::~State()
69{
70 reset();
71}
72
Geoff Lang70d0f492015-12-10 17:45:46 -050073void State::initialize(const Caps &caps,
74 const Extensions &extensions,
Geoff Langeb66a6e2016-10-31 13:06:12 -040075 const Version &clientVersion,
Geoff Langf41a7152016-09-19 15:11:17 -040076 bool debug,
77 bool bindGeneratesResource)
Geoff Lang76b10c92014-09-05 16:28:14 -040078{
Shannon Woods2df6a602014-09-26 16:12:07 -040079 mMaxDrawBuffers = caps.maxDrawBuffers;
80 mMaxCombinedTextureImageUnits = caps.maxCombinedTextureImageUnits;
Shannon Woods53a94a82014-06-24 15:20:36 -040081
Jamie Madillf75ab352015-03-16 10:46:52 -040082 setColorClearValue(0.0f, 0.0f, 0.0f, 0.0f);
Shannon Woods53a94a82014-06-24 15:20:36 -040083
84 mDepthClearValue = 1.0f;
85 mStencilClearValue = 0;
86
87 mRasterizer.rasterizerDiscard = false;
88 mRasterizer.cullFace = false;
89 mRasterizer.cullMode = GL_BACK;
90 mRasterizer.frontFace = GL_CCW;
91 mRasterizer.polygonOffsetFill = false;
92 mRasterizer.polygonOffsetFactor = 0.0f;
93 mRasterizer.polygonOffsetUnits = 0.0f;
94 mRasterizer.pointDrawMode = false;
95 mRasterizer.multiSample = false;
96 mScissorTest = false;
97 mScissor.x = 0;
98 mScissor.y = 0;
99 mScissor.width = 0;
100 mScissor.height = 0;
101
102 mBlend.blend = false;
103 mBlend.sourceBlendRGB = GL_ONE;
104 mBlend.sourceBlendAlpha = GL_ONE;
105 mBlend.destBlendRGB = GL_ZERO;
106 mBlend.destBlendAlpha = GL_ZERO;
107 mBlend.blendEquationRGB = GL_FUNC_ADD;
108 mBlend.blendEquationAlpha = GL_FUNC_ADD;
109 mBlend.sampleAlphaToCoverage = false;
110 mBlend.dither = true;
111
112 mBlendColor.red = 0;
113 mBlendColor.green = 0;
114 mBlendColor.blue = 0;
115 mBlendColor.alpha = 0;
116
117 mDepthStencil.depthTest = false;
118 mDepthStencil.depthFunc = GL_LESS;
119 mDepthStencil.depthMask = true;
120 mDepthStencil.stencilTest = false;
121 mDepthStencil.stencilFunc = GL_ALWAYS;
Austin Kinrossb8af7232015-03-16 22:33:25 -0700122 mDepthStencil.stencilMask = static_cast<GLuint>(-1);
123 mDepthStencil.stencilWritemask = static_cast<GLuint>(-1);
Shannon Woods53a94a82014-06-24 15:20:36 -0400124 mDepthStencil.stencilBackFunc = GL_ALWAYS;
Austin Kinrossb8af7232015-03-16 22:33:25 -0700125 mDepthStencil.stencilBackMask = static_cast<GLuint>(-1);
126 mDepthStencil.stencilBackWritemask = static_cast<GLuint>(-1);
Shannon Woods53a94a82014-06-24 15:20:36 -0400127 mDepthStencil.stencilFail = GL_KEEP;
128 mDepthStencil.stencilPassDepthFail = GL_KEEP;
129 mDepthStencil.stencilPassDepthPass = GL_KEEP;
130 mDepthStencil.stencilBackFail = GL_KEEP;
131 mDepthStencil.stencilBackPassDepthFail = GL_KEEP;
132 mDepthStencil.stencilBackPassDepthPass = GL_KEEP;
133
134 mStencilRef = 0;
135 mStencilBackRef = 0;
136
137 mSampleCoverage = false;
138 mSampleCoverageValue = 1.0f;
139 mSampleCoverageInvert = false;
140 mGenerateMipmapHint = GL_DONT_CARE;
141 mFragmentShaderDerivativeHint = GL_DONT_CARE;
142
Geoff Langf41a7152016-09-19 15:11:17 -0400143 mBindGeneratesResource = bindGeneratesResource;
144
Shannon Woods53a94a82014-06-24 15:20:36 -0400145 mLineWidth = 1.0f;
146
147 mViewport.x = 0;
148 mViewport.y = 0;
149 mViewport.width = 0;
150 mViewport.height = 0;
151 mNearZ = 0.0f;
152 mFarZ = 1.0f;
153
154 mBlend.colorMaskRed = true;
155 mBlend.colorMaskGreen = true;
156 mBlend.colorMaskBlue = true;
157 mBlend.colorMaskAlpha = true;
158
Geoff Lang76b10c92014-09-05 16:28:14 -0400159 mActiveSampler = 0;
160
Shannon Woods23e05002014-09-22 19:07:27 -0400161 mVertexAttribCurrentValues.resize(caps.maxVertexAttributes);
Shannon Woods53a94a82014-06-24 15:20:36 -0400162
Geoff Lang4dc3af02016-11-18 14:09:27 -0500163 mUniformBuffers.resize(caps.maxUniformBufferBindings);
Shannon Woodsf3acaf92014-09-23 18:07:11 -0400164
Geoff Lang76b10c92014-09-05 16:28:14 -0400165 mSamplerTextures[GL_TEXTURE_2D].resize(caps.maxCombinedTextureImageUnits);
166 mSamplerTextures[GL_TEXTURE_CUBE_MAP].resize(caps.maxCombinedTextureImageUnits);
Geoff Langeb66a6e2016-10-31 13:06:12 -0400167 if (clientVersion >= Version(3, 0))
Shannon Woods53a94a82014-06-24 15:20:36 -0400168 {
Geoff Lang76b10c92014-09-05 16:28:14 -0400169 // TODO: These could also be enabled via extension
170 mSamplerTextures[GL_TEXTURE_2D_ARRAY].resize(caps.maxCombinedTextureImageUnits);
171 mSamplerTextures[GL_TEXTURE_3D].resize(caps.maxCombinedTextureImageUnits);
Shannon Woods53a94a82014-06-24 15:20:36 -0400172 }
Ian Ewellbda75592016-04-18 17:25:54 -0400173 if (extensions.eglImageExternal || extensions.eglStreamConsumerExternal)
174 {
175 mSamplerTextures[GL_TEXTURE_EXTERNAL_OES].resize(caps.maxCombinedTextureImageUnits);
176 }
Shannon Woods53a94a82014-06-24 15:20:36 -0400177
Geoff Lang76b10c92014-09-05 16:28:14 -0400178 mSamplers.resize(caps.maxCombinedTextureImageUnits);
Shannon Woods53a94a82014-06-24 15:20:36 -0400179
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500180 mActiveQueries[GL_ANY_SAMPLES_PASSED].set(nullptr);
181 mActiveQueries[GL_ANY_SAMPLES_PASSED_CONSERVATIVE].set(nullptr);
182 mActiveQueries[GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN].set(nullptr);
183 mActiveQueries[GL_TIME_ELAPSED_EXT].set(nullptr);
Geoff Lang2b4ce802016-04-28 13:34:50 -0400184 mActiveQueries[GL_COMMANDS_COMPLETED_CHROMIUM].set(nullptr);
Shannon Woods53a94a82014-06-24 15:20:36 -0400185
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500186 mProgram = nullptr;
Shannon Woods53a94a82014-06-24 15:20:36 -0400187
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500188 mReadFramebuffer = nullptr;
189 mDrawFramebuffer = nullptr;
Jamie Madillb4b53c52015-02-03 15:22:48 -0500190
191 mPrimitiveRestart = false;
Geoff Lang70d0f492015-12-10 17:45:46 -0500192
193 mDebug.setOutputEnabled(debug);
194 mDebug.setMaxLoggedMessages(extensions.maxDebugLoggedMessages);
Sami Väisänen74c23472016-05-09 17:30:30 +0300195
196 if (extensions.framebufferMultisample)
197 {
198 mMultiSampling = true;
199 mSampleAlphaToOne = false;
200 }
Sami Väisänena797e062016-05-12 15:23:40 +0300201
202 mCoverageModulation = GL_NONE;
Sami Väisänene45e53b2016-05-25 10:36:04 +0300203
204 angle::Matrix<GLfloat>::setToIdentity(mPathMatrixProj);
205 angle::Matrix<GLfloat>::setToIdentity(mPathMatrixMV);
206 mPathStencilFunc = GL_ALWAYS;
207 mPathStencilRef = 0;
208 mPathStencilMask = std::numeric_limits<GLuint>::max();
Shannon Woods53a94a82014-06-24 15:20:36 -0400209}
210
Geoff Lang76b10c92014-09-05 16:28:14 -0400211void State::reset()
Shannon Woods53a94a82014-06-24 15:20:36 -0400212{
Geoff Lang76b10c92014-09-05 16:28:14 -0400213 for (TextureBindingMap::iterator bindingVec = mSamplerTextures.begin(); bindingVec != mSamplerTextures.end(); bindingVec++)
Shannon Woods53a94a82014-06-24 15:20:36 -0400214 {
Geoff Lang76b10c92014-09-05 16:28:14 -0400215 TextureBindingVector &textureVector = bindingVec->second;
216 for (size_t textureIdx = 0; textureIdx < textureVector.size(); textureIdx++)
Shannon Woods53a94a82014-06-24 15:20:36 -0400217 {
Geoff Lang76b10c92014-09-05 16:28:14 -0400218 textureVector[textureIdx].set(NULL);
Shannon Woods53a94a82014-06-24 15:20:36 -0400219 }
220 }
Geoff Lang76b10c92014-09-05 16:28:14 -0400221 for (size_t samplerIdx = 0; samplerIdx < mSamplers.size(); samplerIdx++)
222 {
223 mSamplers[samplerIdx].set(NULL);
224 }
Shannon Woods53a94a82014-06-24 15:20:36 -0400225
Shannon Woods53a94a82014-06-24 15:20:36 -0400226 mArrayBuffer.set(NULL);
227 mRenderbuffer.set(NULL);
228
Geoff Lang7dd2e102014-11-10 15:19:26 -0500229 if (mProgram)
230 {
231 mProgram->release();
232 }
233 mProgram = NULL;
234
Shannon Woods53a94a82014-06-24 15:20:36 -0400235 mTransformFeedback.set(NULL);
236
237 for (State::ActiveQueryMap::iterator i = mActiveQueries.begin(); i != mActiveQueries.end(); i++)
238 {
239 i->second.set(NULL);
240 }
241
242 mGenericUniformBuffer.set(NULL);
Shannon Woods8299bb02014-09-26 18:55:43 -0400243 for (BufferVector::iterator bufItr = mUniformBuffers.begin(); bufItr != mUniformBuffers.end(); ++bufItr)
Shannon Woods53a94a82014-06-24 15:20:36 -0400244 {
Shannon Woodsf3acaf92014-09-23 18:07:11 -0400245 bufItr->set(NULL);
Shannon Woods53a94a82014-06-24 15:20:36 -0400246 }
247
Shannon Woods53a94a82014-06-24 15:20:36 -0400248 mCopyReadBuffer.set(NULL);
249 mCopyWriteBuffer.set(NULL);
250
251 mPack.pixelBuffer.set(NULL);
252 mUnpack.pixelBuffer.set(NULL);
Geoff Lang7dd2e102014-11-10 15:19:26 -0500253
254 mProgram = NULL;
Jamie Madill1b94d432015-08-07 13:23:23 -0400255
Sami Väisänene45e53b2016-05-25 10:36:04 +0300256 angle::Matrix<GLfloat>::setToIdentity(mPathMatrixProj);
257 angle::Matrix<GLfloat>::setToIdentity(mPathMatrixMV);
258 mPathStencilFunc = GL_ALWAYS;
259 mPathStencilRef = 0;
260 mPathStencilMask = std::numeric_limits<GLuint>::max();
261
Jamie Madill1b94d432015-08-07 13:23:23 -0400262 // TODO(jmadill): Is this necessary?
263 setAllDirtyBits();
Shannon Woods53a94a82014-06-24 15:20:36 -0400264}
265
266const RasterizerState &State::getRasterizerState() const
267{
268 return mRasterizer;
269}
270
271const BlendState &State::getBlendState() const
272{
273 return mBlend;
274}
275
276const DepthStencilState &State::getDepthStencilState() const
277{
278 return mDepthStencil;
279}
280
Jamie Madillf75ab352015-03-16 10:46:52 -0400281void State::setColorClearValue(float red, float green, float blue, float alpha)
Shannon Woods53a94a82014-06-24 15:20:36 -0400282{
283 mColorClearValue.red = red;
284 mColorClearValue.green = green;
285 mColorClearValue.blue = blue;
286 mColorClearValue.alpha = alpha;
Jamie Madill1b94d432015-08-07 13:23:23 -0400287 mDirtyBits.set(DIRTY_BIT_CLEAR_COLOR);
Shannon Woods53a94a82014-06-24 15:20:36 -0400288}
289
Jamie Madillf75ab352015-03-16 10:46:52 -0400290void State::setDepthClearValue(float depth)
Shannon Woods53a94a82014-06-24 15:20:36 -0400291{
292 mDepthClearValue = depth;
Jamie Madill1b94d432015-08-07 13:23:23 -0400293 mDirtyBits.set(DIRTY_BIT_CLEAR_DEPTH);
Shannon Woods53a94a82014-06-24 15:20:36 -0400294}
295
Jamie Madillf75ab352015-03-16 10:46:52 -0400296void State::setStencilClearValue(int stencil)
Shannon Woods53a94a82014-06-24 15:20:36 -0400297{
298 mStencilClearValue = stencil;
Jamie Madill1b94d432015-08-07 13:23:23 -0400299 mDirtyBits.set(DIRTY_BIT_CLEAR_STENCIL);
Shannon Woods53a94a82014-06-24 15:20:36 -0400300}
301
Shannon Woods53a94a82014-06-24 15:20:36 -0400302void State::setColorMask(bool red, bool green, bool blue, bool alpha)
303{
304 mBlend.colorMaskRed = red;
305 mBlend.colorMaskGreen = green;
306 mBlend.colorMaskBlue = blue;
307 mBlend.colorMaskAlpha = alpha;
Jamie Madill1b94d432015-08-07 13:23:23 -0400308 mDirtyBits.set(DIRTY_BIT_COLOR_MASK);
Shannon Woods53a94a82014-06-24 15:20:36 -0400309}
310
311void State::setDepthMask(bool mask)
312{
313 mDepthStencil.depthMask = mask;
Jamie Madill1b94d432015-08-07 13:23:23 -0400314 mDirtyBits.set(DIRTY_BIT_DEPTH_MASK);
Shannon Woods53a94a82014-06-24 15:20:36 -0400315}
316
317bool State::isRasterizerDiscardEnabled() const
318{
319 return mRasterizer.rasterizerDiscard;
320}
321
322void State::setRasterizerDiscard(bool enabled)
323{
324 mRasterizer.rasterizerDiscard = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400325 mDirtyBits.set(DIRTY_BIT_RASTERIZER_DISCARD_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400326}
327
328bool State::isCullFaceEnabled() const
329{
330 return mRasterizer.cullFace;
331}
332
333void State::setCullFace(bool enabled)
334{
335 mRasterizer.cullFace = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400336 mDirtyBits.set(DIRTY_BIT_CULL_FACE_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400337}
338
339void State::setCullMode(GLenum mode)
340{
341 mRasterizer.cullMode = mode;
Jamie Madill1b94d432015-08-07 13:23:23 -0400342 mDirtyBits.set(DIRTY_BIT_CULL_FACE);
Shannon Woods53a94a82014-06-24 15:20:36 -0400343}
344
345void State::setFrontFace(GLenum front)
346{
347 mRasterizer.frontFace = front;
Jamie Madill1b94d432015-08-07 13:23:23 -0400348 mDirtyBits.set(DIRTY_BIT_FRONT_FACE);
Shannon Woods53a94a82014-06-24 15:20:36 -0400349}
350
351bool State::isDepthTestEnabled() const
352{
353 return mDepthStencil.depthTest;
354}
355
356void State::setDepthTest(bool enabled)
357{
358 mDepthStencil.depthTest = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400359 mDirtyBits.set(DIRTY_BIT_DEPTH_TEST_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400360}
361
362void State::setDepthFunc(GLenum depthFunc)
363{
364 mDepthStencil.depthFunc = depthFunc;
Jamie Madill1b94d432015-08-07 13:23:23 -0400365 mDirtyBits.set(DIRTY_BIT_DEPTH_FUNC);
Shannon Woods53a94a82014-06-24 15:20:36 -0400366}
367
368void State::setDepthRange(float zNear, float zFar)
369{
370 mNearZ = zNear;
371 mFarZ = zFar;
Jamie Madill1b94d432015-08-07 13:23:23 -0400372 mDirtyBits.set(DIRTY_BIT_DEPTH_RANGE);
Shannon Woods53a94a82014-06-24 15:20:36 -0400373}
374
Geoff Langd42f5b82015-04-16 14:03:29 -0400375float State::getNearPlane() const
Shannon Woods53a94a82014-06-24 15:20:36 -0400376{
Geoff Langd42f5b82015-04-16 14:03:29 -0400377 return mNearZ;
378}
379
380float State::getFarPlane() const
381{
382 return mFarZ;
Shannon Woods53a94a82014-06-24 15:20:36 -0400383}
384
385bool State::isBlendEnabled() const
386{
387 return mBlend.blend;
388}
389
390void State::setBlend(bool enabled)
391{
392 mBlend.blend = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400393 mDirtyBits.set(DIRTY_BIT_BLEND_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400394}
395
396void State::setBlendFactors(GLenum sourceRGB, GLenum destRGB, GLenum sourceAlpha, GLenum destAlpha)
397{
398 mBlend.sourceBlendRGB = sourceRGB;
399 mBlend.destBlendRGB = destRGB;
400 mBlend.sourceBlendAlpha = sourceAlpha;
401 mBlend.destBlendAlpha = destAlpha;
Jamie Madill1b94d432015-08-07 13:23:23 -0400402 mDirtyBits.set(DIRTY_BIT_BLEND_FUNCS);
Shannon Woods53a94a82014-06-24 15:20:36 -0400403}
404
405void State::setBlendColor(float red, float green, float blue, float alpha)
406{
407 mBlendColor.red = red;
408 mBlendColor.green = green;
409 mBlendColor.blue = blue;
410 mBlendColor.alpha = alpha;
Jamie Madill1b94d432015-08-07 13:23:23 -0400411 mDirtyBits.set(DIRTY_BIT_BLEND_COLOR);
Shannon Woods53a94a82014-06-24 15:20:36 -0400412}
413
414void State::setBlendEquation(GLenum rgbEquation, GLenum alphaEquation)
415{
416 mBlend.blendEquationRGB = rgbEquation;
417 mBlend.blendEquationAlpha = alphaEquation;
Jamie Madill1b94d432015-08-07 13:23:23 -0400418 mDirtyBits.set(DIRTY_BIT_BLEND_EQUATIONS);
Shannon Woods53a94a82014-06-24 15:20:36 -0400419}
420
421const ColorF &State::getBlendColor() const
422{
423 return mBlendColor;
424}
425
426bool State::isStencilTestEnabled() const
427{
428 return mDepthStencil.stencilTest;
429}
430
431void State::setStencilTest(bool enabled)
432{
433 mDepthStencil.stencilTest = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400434 mDirtyBits.set(DIRTY_BIT_STENCIL_TEST_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400435}
436
437void State::setStencilParams(GLenum stencilFunc, GLint stencilRef, GLuint stencilMask)
438{
439 mDepthStencil.stencilFunc = stencilFunc;
440 mStencilRef = (stencilRef > 0) ? stencilRef : 0;
441 mDepthStencil.stencilMask = stencilMask;
Jamie Madill1b94d432015-08-07 13:23:23 -0400442 mDirtyBits.set(DIRTY_BIT_STENCIL_FUNCS_FRONT);
Shannon Woods53a94a82014-06-24 15:20:36 -0400443}
444
445void State::setStencilBackParams(GLenum stencilBackFunc, GLint stencilBackRef, GLuint stencilBackMask)
446{
447 mDepthStencil.stencilBackFunc = stencilBackFunc;
448 mStencilBackRef = (stencilBackRef > 0) ? stencilBackRef : 0;
449 mDepthStencil.stencilBackMask = stencilBackMask;
Jamie Madill1b94d432015-08-07 13:23:23 -0400450 mDirtyBits.set(DIRTY_BIT_STENCIL_FUNCS_BACK);
Shannon Woods53a94a82014-06-24 15:20:36 -0400451}
452
453void State::setStencilWritemask(GLuint stencilWritemask)
454{
455 mDepthStencil.stencilWritemask = stencilWritemask;
Jamie Madill1b94d432015-08-07 13:23:23 -0400456 mDirtyBits.set(DIRTY_BIT_STENCIL_WRITEMASK_FRONT);
Shannon Woods53a94a82014-06-24 15:20:36 -0400457}
458
459void State::setStencilBackWritemask(GLuint stencilBackWritemask)
460{
461 mDepthStencil.stencilBackWritemask = stencilBackWritemask;
Jamie Madill1b94d432015-08-07 13:23:23 -0400462 mDirtyBits.set(DIRTY_BIT_STENCIL_WRITEMASK_BACK);
Shannon Woods53a94a82014-06-24 15:20:36 -0400463}
464
465void State::setStencilOperations(GLenum stencilFail, GLenum stencilPassDepthFail, GLenum stencilPassDepthPass)
466{
467 mDepthStencil.stencilFail = stencilFail;
468 mDepthStencil.stencilPassDepthFail = stencilPassDepthFail;
469 mDepthStencil.stencilPassDepthPass = stencilPassDepthPass;
Jamie Madill1b94d432015-08-07 13:23:23 -0400470 mDirtyBits.set(DIRTY_BIT_STENCIL_OPS_FRONT);
Shannon Woods53a94a82014-06-24 15:20:36 -0400471}
472
473void State::setStencilBackOperations(GLenum stencilBackFail, GLenum stencilBackPassDepthFail, GLenum stencilBackPassDepthPass)
474{
475 mDepthStencil.stencilBackFail = stencilBackFail;
476 mDepthStencil.stencilBackPassDepthFail = stencilBackPassDepthFail;
477 mDepthStencil.stencilBackPassDepthPass = stencilBackPassDepthPass;
Jamie Madill1b94d432015-08-07 13:23:23 -0400478 mDirtyBits.set(DIRTY_BIT_STENCIL_OPS_BACK);
Shannon Woods53a94a82014-06-24 15:20:36 -0400479}
480
481GLint State::getStencilRef() const
482{
483 return mStencilRef;
484}
485
486GLint State::getStencilBackRef() const
487{
488 return mStencilBackRef;
489}
490
491bool State::isPolygonOffsetFillEnabled() const
492{
493 return mRasterizer.polygonOffsetFill;
494}
495
496void State::setPolygonOffsetFill(bool enabled)
497{
Jamie Madill1b94d432015-08-07 13:23:23 -0400498 mRasterizer.polygonOffsetFill = enabled;
499 mDirtyBits.set(DIRTY_BIT_POLYGON_OFFSET_FILL_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400500}
501
502void State::setPolygonOffsetParams(GLfloat factor, GLfloat units)
503{
504 // An application can pass NaN values here, so handle this gracefully
505 mRasterizer.polygonOffsetFactor = factor != factor ? 0.0f : factor;
506 mRasterizer.polygonOffsetUnits = units != units ? 0.0f : units;
Jamie Madill1b94d432015-08-07 13:23:23 -0400507 mDirtyBits.set(DIRTY_BIT_POLYGON_OFFSET);
Shannon Woods53a94a82014-06-24 15:20:36 -0400508}
509
510bool State::isSampleAlphaToCoverageEnabled() const
511{
512 return mBlend.sampleAlphaToCoverage;
513}
514
515void State::setSampleAlphaToCoverage(bool enabled)
516{
517 mBlend.sampleAlphaToCoverage = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400518 mDirtyBits.set(DIRTY_BIT_SAMPLE_ALPHA_TO_COVERAGE_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400519}
520
521bool State::isSampleCoverageEnabled() const
522{
523 return mSampleCoverage;
524}
525
526void State::setSampleCoverage(bool enabled)
527{
528 mSampleCoverage = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400529 mDirtyBits.set(DIRTY_BIT_SAMPLE_COVERAGE_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400530}
531
532void State::setSampleCoverageParams(GLclampf value, bool invert)
533{
534 mSampleCoverageValue = value;
535 mSampleCoverageInvert = invert;
Jamie Madill1b94d432015-08-07 13:23:23 -0400536 mDirtyBits.set(DIRTY_BIT_SAMPLE_COVERAGE);
Shannon Woods53a94a82014-06-24 15:20:36 -0400537}
538
Geoff Lang0fbb6002015-04-16 11:11:53 -0400539GLclampf State::getSampleCoverageValue() const
Shannon Woods53a94a82014-06-24 15:20:36 -0400540{
Geoff Lang0fbb6002015-04-16 11:11:53 -0400541 return mSampleCoverageValue;
542}
Shannon Woods53a94a82014-06-24 15:20:36 -0400543
Geoff Lang0fbb6002015-04-16 11:11:53 -0400544bool State::getSampleCoverageInvert() const
545{
546 return mSampleCoverageInvert;
Shannon Woods53a94a82014-06-24 15:20:36 -0400547}
548
Sami Väisänen74c23472016-05-09 17:30:30 +0300549void State::setSampleAlphaToOne(bool enabled)
550{
551 mSampleAlphaToOne = enabled;
552 mDirtyBits.set(DIRTY_BIT_SAMPLE_ALPHA_TO_ONE);
553}
554
555bool State::isSampleAlphaToOneEnabled() const
556{
557 return mSampleAlphaToOne;
558}
559
560void State::setMultisampling(bool enabled)
561{
562 mMultiSampling = enabled;
563 mDirtyBits.set(DIRTY_BIT_MULTISAMPLING);
564}
565
566bool State::isMultisamplingEnabled() const
567{
568 return mMultiSampling;
569}
570
Shannon Woods53a94a82014-06-24 15:20:36 -0400571bool State::isScissorTestEnabled() const
572{
573 return mScissorTest;
574}
575
576void State::setScissorTest(bool enabled)
577{
578 mScissorTest = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400579 mDirtyBits.set(DIRTY_BIT_SCISSOR_TEST_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400580}
581
582void State::setScissorParams(GLint x, GLint y, GLsizei width, GLsizei height)
583{
584 mScissor.x = x;
585 mScissor.y = y;
586 mScissor.width = width;
587 mScissor.height = height;
Jamie Madill1b94d432015-08-07 13:23:23 -0400588 mDirtyBits.set(DIRTY_BIT_SCISSOR);
Shannon Woods53a94a82014-06-24 15:20:36 -0400589}
590
591const Rectangle &State::getScissor() const
592{
593 return mScissor;
594}
595
596bool State::isDitherEnabled() const
597{
598 return mBlend.dither;
599}
600
601void State::setDither(bool enabled)
602{
603 mBlend.dither = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400604 mDirtyBits.set(DIRTY_BIT_DITHER_ENABLED);
Shannon Woods53a94a82014-06-24 15:20:36 -0400605}
606
Jamie Madillb4b53c52015-02-03 15:22:48 -0500607bool State::isPrimitiveRestartEnabled() const
608{
609 return mPrimitiveRestart;
610}
611
612void State::setPrimitiveRestart(bool enabled)
613{
614 mPrimitiveRestart = enabled;
Jamie Madill1b94d432015-08-07 13:23:23 -0400615 mDirtyBits.set(DIRTY_BIT_PRIMITIVE_RESTART_ENABLED);
Jamie Madillb4b53c52015-02-03 15:22:48 -0500616}
617
Shannon Woods53a94a82014-06-24 15:20:36 -0400618void State::setEnableFeature(GLenum feature, bool enabled)
619{
620 switch (feature)
621 {
Sami Väisänen74c23472016-05-09 17:30:30 +0300622 case GL_MULTISAMPLE_EXT: setMultisampling(enabled); break;
623 case GL_SAMPLE_ALPHA_TO_ONE_EXT: setSampleAlphaToOne(enabled); break;
Shannon Woods53a94a82014-06-24 15:20:36 -0400624 case GL_CULL_FACE: setCullFace(enabled); break;
625 case GL_POLYGON_OFFSET_FILL: setPolygonOffsetFill(enabled); break;
626 case GL_SAMPLE_ALPHA_TO_COVERAGE: setSampleAlphaToCoverage(enabled); break;
627 case GL_SAMPLE_COVERAGE: setSampleCoverage(enabled); break;
628 case GL_SCISSOR_TEST: setScissorTest(enabled); break;
629 case GL_STENCIL_TEST: setStencilTest(enabled); break;
630 case GL_DEPTH_TEST: setDepthTest(enabled); break;
631 case GL_BLEND: setBlend(enabled); break;
632 case GL_DITHER: setDither(enabled); break;
Jamie Madillb4b53c52015-02-03 15:22:48 -0500633 case GL_PRIMITIVE_RESTART_FIXED_INDEX: setPrimitiveRestart(enabled); break;
Shannon Woods53a94a82014-06-24 15:20:36 -0400634 case GL_RASTERIZER_DISCARD: setRasterizerDiscard(enabled); break;
Geoff Lang70d0f492015-12-10 17:45:46 -0500635 case GL_DEBUG_OUTPUT_SYNCHRONOUS:
636 mDebug.setOutputSynchronous(enabled);
637 break;
638 case GL_DEBUG_OUTPUT:
639 mDebug.setOutputEnabled(enabled);
640 break;
Geoff Lang1d2c41d2016-10-19 16:14:46 -0700641 case GL_FRAMEBUFFER_SRGB_EXT:
642 setFramebufferSRGB(enabled);
643 break;
Shannon Woods53a94a82014-06-24 15:20:36 -0400644 default: UNREACHABLE();
645 }
646}
647
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700648bool State::getEnableFeature(GLenum feature) const
Shannon Woods53a94a82014-06-24 15:20:36 -0400649{
650 switch (feature)
651 {
Sami Väisänen74c23472016-05-09 17:30:30 +0300652 case GL_MULTISAMPLE_EXT: return isMultisamplingEnabled();
653 case GL_SAMPLE_ALPHA_TO_ONE_EXT: return isSampleAlphaToOneEnabled();
Shannon Woods53a94a82014-06-24 15:20:36 -0400654 case GL_CULL_FACE: return isCullFaceEnabled();
655 case GL_POLYGON_OFFSET_FILL: return isPolygonOffsetFillEnabled();
656 case GL_SAMPLE_ALPHA_TO_COVERAGE: return isSampleAlphaToCoverageEnabled();
657 case GL_SAMPLE_COVERAGE: return isSampleCoverageEnabled();
658 case GL_SCISSOR_TEST: return isScissorTestEnabled();
659 case GL_STENCIL_TEST: return isStencilTestEnabled();
660 case GL_DEPTH_TEST: return isDepthTestEnabled();
661 case GL_BLEND: return isBlendEnabled();
662 case GL_DITHER: return isDitherEnabled();
Jamie Madillb4b53c52015-02-03 15:22:48 -0500663 case GL_PRIMITIVE_RESTART_FIXED_INDEX: return isPrimitiveRestartEnabled();
Shannon Woods53a94a82014-06-24 15:20:36 -0400664 case GL_RASTERIZER_DISCARD: return isRasterizerDiscardEnabled();
Geoff Lang70d0f492015-12-10 17:45:46 -0500665 case GL_DEBUG_OUTPUT_SYNCHRONOUS:
666 return mDebug.isOutputSynchronous();
667 case GL_DEBUG_OUTPUT:
668 return mDebug.isOutputEnabled();
Geoff Langf41a7152016-09-19 15:11:17 -0400669 case GL_BIND_GENERATES_RESOURCE_CHROMIUM:
670 return isBindGeneratesResourceEnabled();
Geoff Lang1d2c41d2016-10-19 16:14:46 -0700671 case GL_FRAMEBUFFER_SRGB_EXT:
672 return getFramebufferSRGB();
Shannon Woods53a94a82014-06-24 15:20:36 -0400673 default: UNREACHABLE(); return false;
674 }
675}
676
677void State::setLineWidth(GLfloat width)
678{
679 mLineWidth = width;
Jamie Madill1b94d432015-08-07 13:23:23 -0400680 mDirtyBits.set(DIRTY_BIT_LINE_WIDTH);
Shannon Woods53a94a82014-06-24 15:20:36 -0400681}
682
Geoff Lang4b3f4162015-04-16 13:22:05 -0400683float State::getLineWidth() const
684{
685 return mLineWidth;
686}
687
Shannon Woods53a94a82014-06-24 15:20:36 -0400688void State::setGenerateMipmapHint(GLenum hint)
689{
690 mGenerateMipmapHint = hint;
Jamie Madill1b94d432015-08-07 13:23:23 -0400691 mDirtyBits.set(DIRTY_BIT_GENERATE_MIPMAP_HINT);
Shannon Woods53a94a82014-06-24 15:20:36 -0400692}
693
694void State::setFragmentShaderDerivativeHint(GLenum hint)
695{
696 mFragmentShaderDerivativeHint = hint;
Jamie Madill1b94d432015-08-07 13:23:23 -0400697 mDirtyBits.set(DIRTY_BIT_SHADER_DERIVATIVE_HINT);
Shannon Woods53a94a82014-06-24 15:20:36 -0400698 // TODO: Propagate the hint to shader translator so we can write
699 // ddx, ddx_coarse, or ddx_fine depending on the hint.
700 // Ignore for now. It is valid for implementations to ignore hint.
701}
702
Geoff Langf41a7152016-09-19 15:11:17 -0400703bool State::isBindGeneratesResourceEnabled() const
704{
705 return mBindGeneratesResource;
706}
707
Shannon Woods53a94a82014-06-24 15:20:36 -0400708void State::setViewportParams(GLint x, GLint y, GLsizei width, GLsizei height)
709{
710 mViewport.x = x;
711 mViewport.y = y;
712 mViewport.width = width;
713 mViewport.height = height;
Jamie Madill1b94d432015-08-07 13:23:23 -0400714 mDirtyBits.set(DIRTY_BIT_VIEWPORT);
Shannon Woods53a94a82014-06-24 15:20:36 -0400715}
716
717const Rectangle &State::getViewport() const
718{
719 return mViewport;
720}
721
722void State::setActiveSampler(unsigned int active)
723{
724 mActiveSampler = active;
725}
726
727unsigned int State::getActiveSampler() const
728{
Cooper Partin4d61f7e2015-08-12 10:56:50 -0700729 return static_cast<unsigned int>(mActiveSampler);
Shannon Woods53a94a82014-06-24 15:20:36 -0400730}
731
Geoff Lang76b10c92014-09-05 16:28:14 -0400732void State::setSamplerTexture(GLenum type, Texture *texture)
Shannon Woods53a94a82014-06-24 15:20:36 -0400733{
Geoff Lang76b10c92014-09-05 16:28:14 -0400734 mSamplerTextures[type][mActiveSampler].set(texture);
Shannon Woods53a94a82014-06-24 15:20:36 -0400735}
736
Jamie Madillc29968b2016-01-20 11:17:23 -0500737Texture *State::getTargetTexture(GLenum target) const
738{
739 return getSamplerTexture(static_cast<unsigned int>(mActiveSampler), target);
740}
741
Geoff Lang76b10c92014-09-05 16:28:14 -0400742Texture *State::getSamplerTexture(unsigned int sampler, GLenum type) const
Shannon Woods53a94a82014-06-24 15:20:36 -0400743{
Jamie Madill5864ac22015-01-12 14:43:07 -0500744 const auto it = mSamplerTextures.find(type);
745 ASSERT(it != mSamplerTextures.end());
Jamie Madill3d3d2f22015-09-23 16:47:51 -0400746 ASSERT(sampler < it->second.size());
Jamie Madill5864ac22015-01-12 14:43:07 -0500747 return it->second[sampler].get();
Shannon Woods53a94a82014-06-24 15:20:36 -0400748}
749
Geoff Lang76b10c92014-09-05 16:28:14 -0400750GLuint State::getSamplerTextureId(unsigned int sampler, GLenum type) const
Shannon Woods53a94a82014-06-24 15:20:36 -0400751{
Jamie Madill5864ac22015-01-12 14:43:07 -0500752 const auto it = mSamplerTextures.find(type);
753 ASSERT(it != mSamplerTextures.end());
Jamie Madill3d3d2f22015-09-23 16:47:51 -0400754 ASSERT(sampler < it->second.size());
Jamie Madill5864ac22015-01-12 14:43:07 -0500755 return it->second[sampler].id();
Shannon Woods53a94a82014-06-24 15:20:36 -0400756}
757
Jamie Madille6382c32014-11-07 15:05:26 -0500758void State::detachTexture(const TextureMap &zeroTextures, GLuint texture)
Shannon Woods53a94a82014-06-24 15:20:36 -0400759{
760 // Textures have a detach method on State rather than a simple
761 // removeBinding, because the zero/null texture objects are managed
762 // separately, and don't have to go through the Context's maps or
763 // the ResourceManager.
764
765 // [OpenGL ES 2.0.24] section 3.8 page 84:
766 // If a texture object is deleted, it is as if all texture units which are bound to that texture object are
767 // rebound to texture object zero
768
Corentin Walleza2257da2016-04-19 16:43:12 -0400769 for (auto &bindingVec : mSamplerTextures)
Shannon Woods53a94a82014-06-24 15:20:36 -0400770 {
Corentin Walleza2257da2016-04-19 16:43:12 -0400771 GLenum textureType = bindingVec.first;
772 TextureBindingVector &textureVector = bindingVec.second;
Geoff Lang76b10c92014-09-05 16:28:14 -0400773 for (size_t textureIdx = 0; textureIdx < textureVector.size(); textureIdx++)
Shannon Woods53a94a82014-06-24 15:20:36 -0400774 {
Geoff Lang76b10c92014-09-05 16:28:14 -0400775 BindingPointer<Texture> &binding = textureVector[textureIdx];
776 if (binding.id() == texture)
Shannon Woods53a94a82014-06-24 15:20:36 -0400777 {
Jamie Madill5864ac22015-01-12 14:43:07 -0500778 auto it = zeroTextures.find(textureType);
779 ASSERT(it != zeroTextures.end());
Jamie Madille6382c32014-11-07 15:05:26 -0500780 // Zero textures are the "default" textures instead of NULL
Jamie Madill5864ac22015-01-12 14:43:07 -0500781 binding.set(it->second.get());
Shannon Woods53a94a82014-06-24 15:20:36 -0400782 }
783 }
784 }
785
786 // [OpenGL ES 2.0.24] section 4.4 page 112:
787 // If a texture object is deleted while its image is attached to the currently bound framebuffer, then it is
788 // as if Texture2DAttachment had been called, with a texture of 0, for each attachment point to which this
789 // image was attached in the currently bound framebuffer.
790
791 if (mReadFramebuffer)
792 {
793 mReadFramebuffer->detachTexture(texture);
794 }
795
796 if (mDrawFramebuffer)
797 {
798 mDrawFramebuffer->detachTexture(texture);
799 }
800}
801
Jamie Madille6382c32014-11-07 15:05:26 -0500802void State::initializeZeroTextures(const TextureMap &zeroTextures)
803{
804 for (const auto &zeroTexture : zeroTextures)
805 {
806 auto &samplerTextureArray = mSamplerTextures[zeroTexture.first];
807
808 for (size_t textureUnit = 0; textureUnit < samplerTextureArray.size(); ++textureUnit)
809 {
810 samplerTextureArray[textureUnit].set(zeroTexture.second.get());
811 }
812 }
813}
814
Shannon Woods53a94a82014-06-24 15:20:36 -0400815void State::setSamplerBinding(GLuint textureUnit, Sampler *sampler)
816{
817 mSamplers[textureUnit].set(sampler);
818}
819
820GLuint State::getSamplerId(GLuint textureUnit) const
821{
Geoff Lang76b10c92014-09-05 16:28:14 -0400822 ASSERT(textureUnit < mSamplers.size());
Shannon Woods53a94a82014-06-24 15:20:36 -0400823 return mSamplers[textureUnit].id();
824}
825
826Sampler *State::getSampler(GLuint textureUnit) const
827{
828 return mSamplers[textureUnit].get();
829}
830
831void State::detachSampler(GLuint sampler)
832{
833 // [OpenGL ES 3.0.2] section 3.8.2 pages 123-124:
834 // If a sampler object that is currently bound to one or more texture units is
835 // deleted, it is as though BindSampler is called once for each texture unit to
836 // which the sampler is bound, with unit set to the texture unit and sampler set to zero.
Geoff Lang76b10c92014-09-05 16:28:14 -0400837 for (size_t textureUnit = 0; textureUnit < mSamplers.size(); textureUnit++)
Shannon Woods53a94a82014-06-24 15:20:36 -0400838 {
Geoff Lang76b10c92014-09-05 16:28:14 -0400839 BindingPointer<Sampler> &samplerBinding = mSamplers[textureUnit];
840 if (samplerBinding.id() == sampler)
Shannon Woods53a94a82014-06-24 15:20:36 -0400841 {
Geoff Lang76b10c92014-09-05 16:28:14 -0400842 samplerBinding.set(NULL);
Shannon Woods53a94a82014-06-24 15:20:36 -0400843 }
844 }
845}
846
847void State::setRenderbufferBinding(Renderbuffer *renderbuffer)
848{
849 mRenderbuffer.set(renderbuffer);
850}
851
852GLuint State::getRenderbufferId() const
853{
854 return mRenderbuffer.id();
855}
856
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700857Renderbuffer *State::getCurrentRenderbuffer() const
Shannon Woods53a94a82014-06-24 15:20:36 -0400858{
859 return mRenderbuffer.get();
860}
861
862void State::detachRenderbuffer(GLuint renderbuffer)
863{
864 // [OpenGL ES 2.0.24] section 4.4 page 109:
865 // If a renderbuffer that is currently bound to RENDERBUFFER is deleted, it is as though BindRenderbuffer
866 // had been executed with the target RENDERBUFFER and name of zero.
867
868 if (mRenderbuffer.id() == renderbuffer)
869 {
870 mRenderbuffer.set(NULL);
871 }
872
873 // [OpenGL ES 2.0.24] section 4.4 page 111:
874 // If a renderbuffer object is deleted while its image is attached to the currently bound framebuffer,
875 // then it is as if FramebufferRenderbuffer had been called, with a renderbuffer of 0, for each attachment
876 // point to which this image was attached in the currently bound framebuffer.
877
878 Framebuffer *readFramebuffer = mReadFramebuffer;
879 Framebuffer *drawFramebuffer = mDrawFramebuffer;
880
881 if (readFramebuffer)
882 {
883 readFramebuffer->detachRenderbuffer(renderbuffer);
884 }
885
886 if (drawFramebuffer && drawFramebuffer != readFramebuffer)
887 {
888 drawFramebuffer->detachRenderbuffer(renderbuffer);
889 }
890
891}
892
893void State::setReadFramebufferBinding(Framebuffer *framebuffer)
894{
Jamie Madill60ec6ea2016-01-22 15:27:19 -0500895 if (mReadFramebuffer == framebuffer)
896 return;
897
Shannon Woods53a94a82014-06-24 15:20:36 -0400898 mReadFramebuffer = framebuffer;
Jamie Madill60ec6ea2016-01-22 15:27:19 -0500899 mDirtyBits.set(DIRTY_BIT_READ_FRAMEBUFFER_BINDING);
900
901 if (mReadFramebuffer && mReadFramebuffer->hasAnyDirtyBit())
902 {
903 mDirtyObjects.set(DIRTY_OBJECT_READ_FRAMEBUFFER);
904 }
Shannon Woods53a94a82014-06-24 15:20:36 -0400905}
906
907void State::setDrawFramebufferBinding(Framebuffer *framebuffer)
908{
Jamie Madill60ec6ea2016-01-22 15:27:19 -0500909 if (mDrawFramebuffer == framebuffer)
910 return;
911
Shannon Woods53a94a82014-06-24 15:20:36 -0400912 mDrawFramebuffer = framebuffer;
Jamie Madill60ec6ea2016-01-22 15:27:19 -0500913 mDirtyBits.set(DIRTY_BIT_DRAW_FRAMEBUFFER_BINDING);
914
915 if (mDrawFramebuffer && mDrawFramebuffer->hasAnyDirtyBit())
916 {
917 mDirtyObjects.set(DIRTY_OBJECT_DRAW_FRAMEBUFFER);
918 }
Shannon Woods53a94a82014-06-24 15:20:36 -0400919}
920
921Framebuffer *State::getTargetFramebuffer(GLenum target) const
922{
923 switch (target)
924 {
Jamie Madill60ec6ea2016-01-22 15:27:19 -0500925 case GL_READ_FRAMEBUFFER_ANGLE:
926 return mReadFramebuffer;
927 case GL_DRAW_FRAMEBUFFER_ANGLE:
928 case GL_FRAMEBUFFER:
929 return mDrawFramebuffer;
930 default:
931 UNREACHABLE();
932 return NULL;
Shannon Woods53a94a82014-06-24 15:20:36 -0400933 }
934}
935
Jamie Madill51f40ec2016-06-15 14:06:00 -0400936Framebuffer *State::getReadFramebuffer() const
Shannon Woods53a94a82014-06-24 15:20:36 -0400937{
938 return mReadFramebuffer;
939}
940
Jamie Madill51f40ec2016-06-15 14:06:00 -0400941Framebuffer *State::getDrawFramebuffer() const
Shannon Woods53a94a82014-06-24 15:20:36 -0400942{
943 return mDrawFramebuffer;
944}
945
946bool State::removeReadFramebufferBinding(GLuint framebuffer)
947{
Jamie Madill77a72f62015-04-14 11:18:32 -0400948 if (mReadFramebuffer != nullptr &&
949 mReadFramebuffer->id() == framebuffer)
Shannon Woods53a94a82014-06-24 15:20:36 -0400950 {
Jamie Madill60ec6ea2016-01-22 15:27:19 -0500951 setReadFramebufferBinding(nullptr);
Shannon Woods53a94a82014-06-24 15:20:36 -0400952 return true;
953 }
954
955 return false;
956}
957
958bool State::removeDrawFramebufferBinding(GLuint framebuffer)
959{
Jamie Madill77a72f62015-04-14 11:18:32 -0400960 if (mReadFramebuffer != nullptr &&
961 mDrawFramebuffer->id() == framebuffer)
Shannon Woods53a94a82014-06-24 15:20:36 -0400962 {
Jamie Madill60ec6ea2016-01-22 15:27:19 -0500963 setDrawFramebufferBinding(nullptr);
Shannon Woods53a94a82014-06-24 15:20:36 -0400964 return true;
965 }
966
967 return false;
968}
969
970void State::setVertexArrayBinding(VertexArray *vertexArray)
971{
972 mVertexArray = vertexArray;
Jamie Madill0b9e9032015-08-17 11:51:52 +0000973 mDirtyBits.set(DIRTY_BIT_VERTEX_ARRAY_BINDING);
Jamie Madillc9d442d2016-01-20 11:17:24 -0500974
975 if (mVertexArray && mVertexArray->hasAnyDirtyBit())
976 {
977 mDirtyObjects.set(DIRTY_OBJECT_VERTEX_ARRAY);
978 }
Shannon Woods53a94a82014-06-24 15:20:36 -0400979}
980
981GLuint State::getVertexArrayId() const
982{
983 ASSERT(mVertexArray != NULL);
984 return mVertexArray->id();
985}
986
987VertexArray *State::getVertexArray() const
988{
989 ASSERT(mVertexArray != NULL);
990 return mVertexArray;
991}
992
993bool State::removeVertexArrayBinding(GLuint vertexArray)
994{
995 if (mVertexArray->id() == vertexArray)
996 {
997 mVertexArray = NULL;
Jamie Madill0b9e9032015-08-17 11:51:52 +0000998 mDirtyBits.set(DIRTY_BIT_VERTEX_ARRAY_BINDING);
Jamie Madillc9d442d2016-01-20 11:17:24 -0500999 mDirtyObjects.set(DIRTY_OBJECT_VERTEX_ARRAY);
Shannon Woods53a94a82014-06-24 15:20:36 -04001000 return true;
1001 }
1002
1003 return false;
1004}
1005
Geoff Lang7dd2e102014-11-10 15:19:26 -05001006void State::setProgram(Program *newProgram)
Shannon Woods53a94a82014-06-24 15:20:36 -04001007{
Geoff Lang7dd2e102014-11-10 15:19:26 -05001008 if (mProgram != newProgram)
Shannon Woods53a94a82014-06-24 15:20:36 -04001009 {
Geoff Lang7dd2e102014-11-10 15:19:26 -05001010 if (mProgram)
1011 {
1012 mProgram->release();
1013 }
1014
1015 mProgram = newProgram;
1016
1017 if (mProgram)
1018 {
1019 newProgram->addRef();
1020 }
Shannon Woods53a94a82014-06-24 15:20:36 -04001021 }
1022}
1023
Geoff Lang7dd2e102014-11-10 15:19:26 -05001024Program *State::getProgram() const
Shannon Woods53a94a82014-06-24 15:20:36 -04001025{
Geoff Lang7dd2e102014-11-10 15:19:26 -05001026 return mProgram;
Shannon Woods53a94a82014-06-24 15:20:36 -04001027}
1028
1029void State::setTransformFeedbackBinding(TransformFeedback *transformFeedback)
1030{
1031 mTransformFeedback.set(transformFeedback);
1032}
1033
1034TransformFeedback *State::getCurrentTransformFeedback() const
1035{
1036 return mTransformFeedback.get();
1037}
1038
Gregoire Payen de La Garanderie52742022015-02-04 14:55:39 +00001039bool State::isTransformFeedbackActiveUnpaused() const
1040{
1041 gl::TransformFeedback *curTransformFeedback = getCurrentTransformFeedback();
Geoff Langbb0a0bb2015-03-27 12:16:57 -04001042 return curTransformFeedback && curTransformFeedback->isActive() && !curTransformFeedback->isPaused();
Gregoire Payen de La Garanderie52742022015-02-04 14:55:39 +00001043}
1044
Corentin Walleza2257da2016-04-19 16:43:12 -04001045bool State::removeTransformFeedbackBinding(GLuint transformFeedback)
Shannon Woods53a94a82014-06-24 15:20:36 -04001046{
1047 if (mTransformFeedback.id() == transformFeedback)
1048 {
Corentin Walleza2257da2016-04-19 16:43:12 -04001049 mTransformFeedback.set(nullptr);
1050 return true;
Shannon Woods53a94a82014-06-24 15:20:36 -04001051 }
Corentin Walleza2257da2016-04-19 16:43:12 -04001052
1053 return false;
Shannon Woods53a94a82014-06-24 15:20:36 -04001054}
1055
Olli Etuahobbf1c102016-06-28 13:31:33 +03001056bool State::isQueryActive(const GLenum type) const
Shannon Woods53a94a82014-06-24 15:20:36 -04001057{
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001058 for (auto &iter : mActiveQueries)
Shannon Woods53a94a82014-06-24 15:20:36 -04001059 {
Olli Etuahobbf1c102016-06-28 13:31:33 +03001060 const Query *query = iter.second.get();
1061 if (query != nullptr && ActiveQueryType(query->getType()) == ActiveQueryType(type))
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001062 {
1063 return true;
1064 }
1065 }
1066
1067 return false;
1068}
1069
1070bool State::isQueryActive(Query *query) const
1071{
1072 for (auto &iter : mActiveQueries)
1073 {
1074 if (iter.second.get() == query)
Shannon Woods53a94a82014-06-24 15:20:36 -04001075 {
1076 return true;
1077 }
1078 }
1079
1080 return false;
1081}
1082
1083void State::setActiveQuery(GLenum target, Query *query)
1084{
1085 mActiveQueries[target].set(query);
1086}
1087
1088GLuint State::getActiveQueryId(GLenum target) const
1089{
1090 const Query *query = getActiveQuery(target);
1091 return (query ? query->id() : 0u);
1092}
1093
1094Query *State::getActiveQuery(GLenum target) const
1095{
Jamie Madill5864ac22015-01-12 14:43:07 -05001096 const auto it = mActiveQueries.find(target);
Shannon Woods53a94a82014-06-24 15:20:36 -04001097
Jamie Madill5864ac22015-01-12 14:43:07 -05001098 // All query types should already exist in the activeQueries map
1099 ASSERT(it != mActiveQueries.end());
1100
1101 return it->second.get();
Shannon Woods53a94a82014-06-24 15:20:36 -04001102}
1103
1104void State::setArrayBufferBinding(Buffer *buffer)
1105{
1106 mArrayBuffer.set(buffer);
1107}
1108
1109GLuint State::getArrayBufferId() const
1110{
1111 return mArrayBuffer.id();
1112}
1113
Shannon Woods53a94a82014-06-24 15:20:36 -04001114void State::setGenericUniformBufferBinding(Buffer *buffer)
1115{
1116 mGenericUniformBuffer.set(buffer);
1117}
1118
1119void State::setIndexedUniformBufferBinding(GLuint index, Buffer *buffer, GLintptr offset, GLsizeiptr size)
1120{
1121 mUniformBuffers[index].set(buffer, offset, size);
1122}
1123
Geoff Lang5d124a62015-09-15 13:03:27 -04001124const OffsetBindingPointer<Buffer> &State::getIndexedUniformBuffer(size_t index) const
Shannon Woods53a94a82014-06-24 15:20:36 -04001125{
Shannon Woodsf3acaf92014-09-23 18:07:11 -04001126 ASSERT(static_cast<size_t>(index) < mUniformBuffers.size());
Geoff Lang5d124a62015-09-15 13:03:27 -04001127 return mUniformBuffers[index];
Gregoire Payen de La Garanderie68694e92015-03-24 14:03:37 +00001128}
1129
Shannon Woods53a94a82014-06-24 15:20:36 -04001130void State::setCopyReadBufferBinding(Buffer *buffer)
1131{
1132 mCopyReadBuffer.set(buffer);
1133}
1134
1135void State::setCopyWriteBufferBinding(Buffer *buffer)
1136{
1137 mCopyWriteBuffer.set(buffer);
1138}
1139
1140void State::setPixelPackBufferBinding(Buffer *buffer)
1141{
1142 mPack.pixelBuffer.set(buffer);
Corentin Wallezbbd663a2016-04-20 17:49:17 -04001143 mDirtyBits.set(DIRTY_BIT_PACK_BUFFER_BINDING);
Shannon Woods53a94a82014-06-24 15:20:36 -04001144}
1145
1146void State::setPixelUnpackBufferBinding(Buffer *buffer)
1147{
1148 mUnpack.pixelBuffer.set(buffer);
Corentin Wallezbbd663a2016-04-20 17:49:17 -04001149 mDirtyBits.set(DIRTY_BIT_UNPACK_BUFFER_BINDING);
Shannon Woods53a94a82014-06-24 15:20:36 -04001150}
1151
1152Buffer *State::getTargetBuffer(GLenum target) const
1153{
1154 switch (target)
1155 {
1156 case GL_ARRAY_BUFFER: return mArrayBuffer.get();
1157 case GL_COPY_READ_BUFFER: return mCopyReadBuffer.get();
1158 case GL_COPY_WRITE_BUFFER: return mCopyWriteBuffer.get();
Jamie Madill8e344942015-07-09 14:22:07 -04001159 case GL_ELEMENT_ARRAY_BUFFER: return getVertexArray()->getElementArrayBuffer().get();
Shannon Woods53a94a82014-06-24 15:20:36 -04001160 case GL_PIXEL_PACK_BUFFER: return mPack.pixelBuffer.get();
1161 case GL_PIXEL_UNPACK_BUFFER: return mUnpack.pixelBuffer.get();
Geoff Lang045536b2015-03-27 15:17:18 -04001162 case GL_TRANSFORM_FEEDBACK_BUFFER: return mTransformFeedback->getGenericBuffer().get();
Shannon Woods53a94a82014-06-24 15:20:36 -04001163 case GL_UNIFORM_BUFFER: return mGenericUniformBuffer.get();
1164 default: UNREACHABLE(); return NULL;
1165 }
1166}
1167
Yuly Novikov5807a532015-12-03 13:01:22 -05001168void State::detachBuffer(GLuint bufferName)
1169{
1170 BindingPointer<Buffer> *buffers[] = {&mArrayBuffer, &mCopyReadBuffer,
1171 &mCopyWriteBuffer, &mPack.pixelBuffer,
1172 &mUnpack.pixelBuffer, &mGenericUniformBuffer};
1173 for (auto buffer : buffers)
1174 {
1175 if (buffer->id() == bufferName)
1176 {
1177 buffer->set(nullptr);
1178 }
1179 }
1180
1181 TransformFeedback *curTransformFeedback = getCurrentTransformFeedback();
1182 if (curTransformFeedback)
1183 {
1184 curTransformFeedback->detachBuffer(bufferName);
1185 }
1186
1187 getVertexArray()->detachBuffer(bufferName);
1188}
1189
Shannon Woods53a94a82014-06-24 15:20:36 -04001190void State::setEnableVertexAttribArray(unsigned int attribNum, bool enabled)
1191{
1192 getVertexArray()->enableAttribute(attribNum, enabled);
Jamie Madillc9d442d2016-01-20 11:17:24 -05001193 mDirtyObjects.set(DIRTY_OBJECT_VERTEX_ARRAY);
Shannon Woods53a94a82014-06-24 15:20:36 -04001194}
1195
1196void State::setVertexAttribf(GLuint index, const GLfloat values[4])
1197{
Shannon Woods23e05002014-09-22 19:07:27 -04001198 ASSERT(static_cast<size_t>(index) < mVertexAttribCurrentValues.size());
Shannon Woods53a94a82014-06-24 15:20:36 -04001199 mVertexAttribCurrentValues[index].setFloatValues(values);
Jamie Madill1e0bc3a2015-08-11 08:12:21 -04001200 mDirtyBits.set(DIRTY_BIT_CURRENT_VALUE_0 + index);
Shannon Woods53a94a82014-06-24 15:20:36 -04001201}
1202
1203void State::setVertexAttribu(GLuint index, const GLuint values[4])
1204{
Shannon Woods23e05002014-09-22 19:07:27 -04001205 ASSERT(static_cast<size_t>(index) < mVertexAttribCurrentValues.size());
Shannon Woods53a94a82014-06-24 15:20:36 -04001206 mVertexAttribCurrentValues[index].setUnsignedIntValues(values);
Jamie Madill1e0bc3a2015-08-11 08:12:21 -04001207 mDirtyBits.set(DIRTY_BIT_CURRENT_VALUE_0 + index);
Shannon Woods53a94a82014-06-24 15:20:36 -04001208}
1209
1210void State::setVertexAttribi(GLuint index, const GLint values[4])
1211{
Shannon Woods23e05002014-09-22 19:07:27 -04001212 ASSERT(static_cast<size_t>(index) < mVertexAttribCurrentValues.size());
Shannon Woods53a94a82014-06-24 15:20:36 -04001213 mVertexAttribCurrentValues[index].setIntValues(values);
Jamie Madill1e0bc3a2015-08-11 08:12:21 -04001214 mDirtyBits.set(DIRTY_BIT_CURRENT_VALUE_0 + index);
Shannon Woods53a94a82014-06-24 15:20:36 -04001215}
1216
Jamie Madill0b9e9032015-08-17 11:51:52 +00001217void State::setVertexAttribState(unsigned int attribNum,
1218 Buffer *boundBuffer,
1219 GLint size,
1220 GLenum type,
1221 bool normalized,
1222 bool pureInteger,
1223 GLsizei stride,
1224 const void *pointer)
Shannon Woods53a94a82014-06-24 15:20:36 -04001225{
1226 getVertexArray()->setAttributeState(attribNum, boundBuffer, size, type, normalized, pureInteger, stride, pointer);
Jamie Madillc9d442d2016-01-20 11:17:24 -05001227 mDirtyObjects.set(DIRTY_OBJECT_VERTEX_ARRAY);
Jamie Madill0b9e9032015-08-17 11:51:52 +00001228}
1229
1230void State::setVertexAttribDivisor(GLuint index, GLuint divisor)
1231{
1232 getVertexArray()->setVertexAttribDivisor(index, divisor);
Jamie Madillc9d442d2016-01-20 11:17:24 -05001233 mDirtyObjects.set(DIRTY_OBJECT_VERTEX_ARRAY);
Shannon Woods53a94a82014-06-24 15:20:36 -04001234}
1235
Shannon Woods53a94a82014-06-24 15:20:36 -04001236const VertexAttribCurrentValueData &State::getVertexAttribCurrentValue(unsigned int attribNum) const
1237{
Shannon Woods23e05002014-09-22 19:07:27 -04001238 ASSERT(static_cast<size_t>(attribNum) < mVertexAttribCurrentValues.size());
Shannon Woods53a94a82014-06-24 15:20:36 -04001239 return mVertexAttribCurrentValues[attribNum];
1240}
1241
Shannon Woods53a94a82014-06-24 15:20:36 -04001242const void *State::getVertexAttribPointer(unsigned int attribNum) const
1243{
1244 return getVertexArray()->getVertexAttribute(attribNum).pointer;
1245}
1246
1247void State::setPackAlignment(GLint alignment)
1248{
1249 mPack.alignment = alignment;
Jamie Madill1b94d432015-08-07 13:23:23 -04001250 mDirtyBits.set(DIRTY_BIT_PACK_ALIGNMENT);
Shannon Woods53a94a82014-06-24 15:20:36 -04001251}
1252
1253GLint State::getPackAlignment() const
1254{
1255 return mPack.alignment;
1256}
1257
1258void State::setPackReverseRowOrder(bool reverseRowOrder)
1259{
1260 mPack.reverseRowOrder = reverseRowOrder;
Jamie Madill1b94d432015-08-07 13:23:23 -04001261 mDirtyBits.set(DIRTY_BIT_PACK_REVERSE_ROW_ORDER);
Shannon Woods53a94a82014-06-24 15:20:36 -04001262}
1263
1264bool State::getPackReverseRowOrder() const
1265{
1266 return mPack.reverseRowOrder;
1267}
1268
Minmin Gongadff67b2015-10-14 10:34:45 -04001269void State::setPackRowLength(GLint rowLength)
1270{
1271 mPack.rowLength = rowLength;
1272 mDirtyBits.set(DIRTY_BIT_PACK_ROW_LENGTH);
1273}
1274
1275GLint State::getPackRowLength() const
1276{
1277 return mPack.rowLength;
1278}
1279
1280void State::setPackSkipRows(GLint skipRows)
1281{
1282 mPack.skipRows = skipRows;
1283 mDirtyBits.set(DIRTY_BIT_PACK_SKIP_ROWS);
1284}
1285
1286GLint State::getPackSkipRows() const
1287{
1288 return mPack.skipRows;
1289}
1290
1291void State::setPackSkipPixels(GLint skipPixels)
1292{
1293 mPack.skipPixels = skipPixels;
1294 mDirtyBits.set(DIRTY_BIT_PACK_SKIP_PIXELS);
1295}
1296
1297GLint State::getPackSkipPixels() const
1298{
1299 return mPack.skipPixels;
1300}
1301
Shannon Woods53a94a82014-06-24 15:20:36 -04001302const PixelPackState &State::getPackState() const
1303{
1304 return mPack;
1305}
1306
Jamie Madill87de3622015-03-16 10:41:44 -04001307PixelPackState &State::getPackState()
1308{
1309 return mPack;
1310}
1311
Shannon Woods53a94a82014-06-24 15:20:36 -04001312void State::setUnpackAlignment(GLint alignment)
1313{
1314 mUnpack.alignment = alignment;
Jamie Madill1b94d432015-08-07 13:23:23 -04001315 mDirtyBits.set(DIRTY_BIT_UNPACK_ALIGNMENT);
Shannon Woods53a94a82014-06-24 15:20:36 -04001316}
1317
1318GLint State::getUnpackAlignment() const
1319{
1320 return mUnpack.alignment;
1321}
1322
Minmin Gongb8aee3b2015-01-27 14:42:36 -08001323void State::setUnpackRowLength(GLint rowLength)
1324{
1325 mUnpack.rowLength = rowLength;
Jamie Madill1b94d432015-08-07 13:23:23 -04001326 mDirtyBits.set(DIRTY_BIT_UNPACK_ROW_LENGTH);
Minmin Gongb8aee3b2015-01-27 14:42:36 -08001327}
1328
1329GLint State::getUnpackRowLength() const
1330{
1331 return mUnpack.rowLength;
1332}
1333
Minmin Gongadff67b2015-10-14 10:34:45 -04001334void State::setUnpackImageHeight(GLint imageHeight)
1335{
1336 mUnpack.imageHeight = imageHeight;
1337 mDirtyBits.set(DIRTY_BIT_UNPACK_IMAGE_HEIGHT);
1338}
1339
1340GLint State::getUnpackImageHeight() const
1341{
1342 return mUnpack.imageHeight;
1343}
1344
1345void State::setUnpackSkipImages(GLint skipImages)
1346{
1347 mUnpack.skipImages = skipImages;
1348 mDirtyBits.set(DIRTY_BIT_UNPACK_SKIP_IMAGES);
1349}
1350
1351GLint State::getUnpackSkipImages() const
1352{
1353 return mUnpack.skipImages;
1354}
1355
1356void State::setUnpackSkipRows(GLint skipRows)
1357{
1358 mUnpack.skipRows = skipRows;
1359 mDirtyBits.set(DIRTY_BIT_UNPACK_SKIP_ROWS);
1360}
1361
1362GLint State::getUnpackSkipRows() const
1363{
1364 return mUnpack.skipRows;
1365}
1366
1367void State::setUnpackSkipPixels(GLint skipPixels)
1368{
1369 mUnpack.skipPixels = skipPixels;
1370 mDirtyBits.set(DIRTY_BIT_UNPACK_SKIP_PIXELS);
1371}
1372
1373GLint State::getUnpackSkipPixels() const
1374{
1375 return mUnpack.skipPixels;
1376}
1377
Shannon Woods53a94a82014-06-24 15:20:36 -04001378const PixelUnpackState &State::getUnpackState() const
1379{
1380 return mUnpack;
1381}
1382
Jamie Madill67102f02015-03-16 10:41:42 -04001383PixelUnpackState &State::getUnpackState()
1384{
1385 return mUnpack;
1386}
1387
Geoff Lang70d0f492015-12-10 17:45:46 -05001388const Debug &State::getDebug() const
1389{
1390 return mDebug;
1391}
1392
1393Debug &State::getDebug()
1394{
1395 return mDebug;
1396}
1397
Sami Väisänena797e062016-05-12 15:23:40 +03001398void State::setCoverageModulation(GLenum components)
1399{
1400 mCoverageModulation = components;
1401 mDirtyBits.set(DIRTY_BIT_COVERAGE_MODULATION);
1402}
1403
1404GLenum State::getCoverageModulation() const
1405{
1406 return mCoverageModulation;
1407}
1408
Sami Väisänene45e53b2016-05-25 10:36:04 +03001409void State::loadPathRenderingMatrix(GLenum matrixMode, const GLfloat *matrix)
1410{
1411 if (matrixMode == GL_PATH_MODELVIEW_CHROMIUM)
1412 {
1413 memcpy(mPathMatrixMV, matrix, 16 * sizeof(GLfloat));
1414 mDirtyBits.set(DIRTY_BIT_PATH_RENDERING_MATRIX_MV);
1415 }
1416 else if (matrixMode == GL_PATH_PROJECTION_CHROMIUM)
1417 {
1418 memcpy(mPathMatrixProj, matrix, 16 * sizeof(GLfloat));
1419 mDirtyBits.set(DIRTY_BIT_PATH_RENDERING_MATRIX_PROJ);
1420 }
1421 else
1422 {
1423 UNREACHABLE();
1424 }
1425}
1426
1427const GLfloat *State::getPathRenderingMatrix(GLenum which) const
1428{
1429 if (which == GL_PATH_MODELVIEW_MATRIX_CHROMIUM)
1430 {
1431 return mPathMatrixMV;
1432 }
1433 else if (which == GL_PATH_PROJECTION_MATRIX_CHROMIUM)
1434 {
1435 return mPathMatrixProj;
1436 }
1437
1438 UNREACHABLE();
1439 return nullptr;
1440}
1441
1442void State::setPathStencilFunc(GLenum func, GLint ref, GLuint mask)
1443{
1444 mPathStencilFunc = func;
1445 mPathStencilRef = ref;
1446 mPathStencilMask = mask;
1447 mDirtyBits.set(DIRTY_BIT_PATH_RENDERING_STENCIL_STATE);
1448}
1449
1450GLenum State::getPathStencilFunc() const
1451{
1452 return mPathStencilFunc;
1453}
1454
1455GLint State::getPathStencilRef() const
1456{
1457 return mPathStencilRef;
1458}
1459
1460GLuint State::getPathStencilMask() const
1461{
1462 return mPathStencilMask;
1463}
1464
Geoff Lang1d2c41d2016-10-19 16:14:46 -07001465void State::setFramebufferSRGB(bool sRGB)
1466{
1467 mFramebufferSRGB = sRGB;
1468 mDirtyBits.set(DIRTY_BIT_FRAMEBUFFER_SRGB);
1469}
1470
1471bool State::getFramebufferSRGB() const
1472{
1473 return mFramebufferSRGB;
1474}
1475
Shannon Woods53a94a82014-06-24 15:20:36 -04001476void State::getBooleanv(GLenum pname, GLboolean *params)
1477{
1478 switch (pname)
1479 {
1480 case GL_SAMPLE_COVERAGE_INVERT: *params = mSampleCoverageInvert; break;
1481 case GL_DEPTH_WRITEMASK: *params = mDepthStencil.depthMask; break;
1482 case GL_COLOR_WRITEMASK:
1483 params[0] = mBlend.colorMaskRed;
1484 params[1] = mBlend.colorMaskGreen;
1485 params[2] = mBlend.colorMaskBlue;
1486 params[3] = mBlend.colorMaskAlpha;
1487 break;
1488 case GL_CULL_FACE: *params = mRasterizer.cullFace; break;
1489 case GL_POLYGON_OFFSET_FILL: *params = mRasterizer.polygonOffsetFill; break;
1490 case GL_SAMPLE_ALPHA_TO_COVERAGE: *params = mBlend.sampleAlphaToCoverage; break;
1491 case GL_SAMPLE_COVERAGE: *params = mSampleCoverage; break;
1492 case GL_SCISSOR_TEST: *params = mScissorTest; break;
1493 case GL_STENCIL_TEST: *params = mDepthStencil.stencilTest; break;
1494 case GL_DEPTH_TEST: *params = mDepthStencil.depthTest; break;
1495 case GL_BLEND: *params = mBlend.blend; break;
1496 case GL_DITHER: *params = mBlend.dither; break;
Geoff Langbb0a0bb2015-03-27 12:16:57 -04001497 case GL_TRANSFORM_FEEDBACK_ACTIVE: *params = getCurrentTransformFeedback()->isActive() ? GL_TRUE : GL_FALSE; break;
1498 case GL_TRANSFORM_FEEDBACK_PAUSED: *params = getCurrentTransformFeedback()->isPaused() ? GL_TRUE : GL_FALSE; break;
Jamie Madille2cd53d2015-10-27 11:15:46 -04001499 case GL_PRIMITIVE_RESTART_FIXED_INDEX:
1500 *params = mPrimitiveRestart;
1501 break;
Geoff Langab831f02015-12-01 09:39:10 -05001502 case GL_RASTERIZER_DISCARD:
1503 *params = isRasterizerDiscardEnabled() ? GL_TRUE : GL_FALSE;
1504 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001505 case GL_DEBUG_OUTPUT_SYNCHRONOUS:
1506 *params = mDebug.isOutputSynchronous() ? GL_TRUE : GL_FALSE;
1507 break;
1508 case GL_DEBUG_OUTPUT:
1509 *params = mDebug.isOutputEnabled() ? GL_TRUE : GL_FALSE;
1510 break;
Sami Väisänen74c23472016-05-09 17:30:30 +03001511 case GL_MULTISAMPLE_EXT:
1512 *params = mMultiSampling;
1513 break;
1514 case GL_SAMPLE_ALPHA_TO_ONE_EXT:
1515 *params = mSampleAlphaToOne;
1516 break;
Geoff Langf41a7152016-09-19 15:11:17 -04001517 case GL_BIND_GENERATES_RESOURCE_CHROMIUM:
1518 *params = isBindGeneratesResourceEnabled() ? GL_TRUE : GL_FALSE;
1519 break;
Geoff Lang1d2c41d2016-10-19 16:14:46 -07001520 case GL_FRAMEBUFFER_SRGB_EXT:
1521 *params = getFramebufferSRGB() ? GL_TRUE : GL_FALSE;
1522 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001523 default:
1524 UNREACHABLE();
1525 break;
1526 }
1527}
1528
1529void State::getFloatv(GLenum pname, GLfloat *params)
1530{
1531 // Please note: DEPTH_CLEAR_VALUE is included in our internal getFloatv implementation
1532 // because it is stored as a float, despite the fact that the GL ES 2.0 spec names
1533 // GetIntegerv as its native query function. As it would require conversion in any
1534 // case, this should make no difference to the calling application.
1535 switch (pname)
1536 {
1537 case GL_LINE_WIDTH: *params = mLineWidth; break;
1538 case GL_SAMPLE_COVERAGE_VALUE: *params = mSampleCoverageValue; break;
1539 case GL_DEPTH_CLEAR_VALUE: *params = mDepthClearValue; break;
1540 case GL_POLYGON_OFFSET_FACTOR: *params = mRasterizer.polygonOffsetFactor; break;
1541 case GL_POLYGON_OFFSET_UNITS: *params = mRasterizer.polygonOffsetUnits; break;
1542 case GL_DEPTH_RANGE:
1543 params[0] = mNearZ;
1544 params[1] = mFarZ;
1545 break;
1546 case GL_COLOR_CLEAR_VALUE:
1547 params[0] = mColorClearValue.red;
1548 params[1] = mColorClearValue.green;
1549 params[2] = mColorClearValue.blue;
1550 params[3] = mColorClearValue.alpha;
1551 break;
1552 case GL_BLEND_COLOR:
1553 params[0] = mBlendColor.red;
1554 params[1] = mBlendColor.green;
1555 params[2] = mBlendColor.blue;
1556 params[3] = mBlendColor.alpha;
1557 break;
Sami Väisänen74c23472016-05-09 17:30:30 +03001558 case GL_MULTISAMPLE_EXT:
1559 *params = static_cast<GLfloat>(mMultiSampling);
1560 break;
1561 case GL_SAMPLE_ALPHA_TO_ONE_EXT:
1562 *params = static_cast<GLfloat>(mSampleAlphaToOne);
Sami Väisänena797e062016-05-12 15:23:40 +03001563 case GL_COVERAGE_MODULATION_CHROMIUM:
Jamie Madille2e406c2016-06-02 13:04:10 -04001564 params[0] = static_cast<GLfloat>(mCoverageModulation);
1565 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001566 default:
1567 UNREACHABLE();
1568 break;
1569 }
1570}
1571
Jamie Madill9082b982016-04-27 15:21:51 -04001572void State::getIntegerv(const ContextState &data, GLenum pname, GLint *params)
Shannon Woods53a94a82014-06-24 15:20:36 -04001573{
1574 if (pname >= GL_DRAW_BUFFER0_EXT && pname <= GL_DRAW_BUFFER15_EXT)
1575 {
1576 unsigned int colorAttachment = (pname - GL_DRAW_BUFFER0_EXT);
Shannon Woods2df6a602014-09-26 16:12:07 -04001577 ASSERT(colorAttachment < mMaxDrawBuffers);
Shannon Woods53a94a82014-06-24 15:20:36 -04001578 Framebuffer *framebuffer = mDrawFramebuffer;
1579 *params = framebuffer->getDrawBufferState(colorAttachment);
1580 return;
1581 }
1582
1583 // Please note: DEPTH_CLEAR_VALUE is not included in our internal getIntegerv implementation
1584 // because it is stored as a float, despite the fact that the GL ES 2.0 spec names
1585 // GetIntegerv as its native query function. As it would require conversion in any
1586 // case, this should make no difference to the calling application. You may find it in
1587 // State::getFloatv.
1588 switch (pname)
1589 {
1590 case GL_ARRAY_BUFFER_BINDING: *params = mArrayBuffer.id(); break;
Jamie Madill8e344942015-07-09 14:22:07 -04001591 case GL_ELEMENT_ARRAY_BUFFER_BINDING: *params = getVertexArray()->getElementArrayBuffer().id(); break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001592 //case GL_FRAMEBUFFER_BINDING: // now equivalent to GL_DRAW_FRAMEBUFFER_BINDING_ANGLE
1593 case GL_DRAW_FRAMEBUFFER_BINDING_ANGLE: *params = mDrawFramebuffer->id(); break;
1594 case GL_READ_FRAMEBUFFER_BINDING_ANGLE: *params = mReadFramebuffer->id(); break;
1595 case GL_RENDERBUFFER_BINDING: *params = mRenderbuffer.id(); break;
1596 case GL_VERTEX_ARRAY_BINDING: *params = mVertexArray->id(); break;
Geoff Lang7dd2e102014-11-10 15:19:26 -05001597 case GL_CURRENT_PROGRAM: *params = mProgram ? mProgram->id() : 0; break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001598 case GL_PACK_ALIGNMENT: *params = mPack.alignment; break;
1599 case GL_PACK_REVERSE_ROW_ORDER_ANGLE: *params = mPack.reverseRowOrder; break;
Minmin Gongadff67b2015-10-14 10:34:45 -04001600 case GL_PACK_ROW_LENGTH:
1601 *params = mPack.rowLength;
1602 break;
1603 case GL_PACK_SKIP_ROWS:
1604 *params = mPack.skipRows;
1605 break;
1606 case GL_PACK_SKIP_PIXELS:
1607 *params = mPack.skipPixels;
1608 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001609 case GL_UNPACK_ALIGNMENT: *params = mUnpack.alignment; break;
Minmin Gongb8aee3b2015-01-27 14:42:36 -08001610 case GL_UNPACK_ROW_LENGTH: *params = mUnpack.rowLength; break;
Minmin Gongadff67b2015-10-14 10:34:45 -04001611 case GL_UNPACK_IMAGE_HEIGHT:
1612 *params = mUnpack.imageHeight;
1613 break;
1614 case GL_UNPACK_SKIP_IMAGES:
1615 *params = mUnpack.skipImages;
1616 break;
1617 case GL_UNPACK_SKIP_ROWS:
1618 *params = mUnpack.skipRows;
1619 break;
1620 case GL_UNPACK_SKIP_PIXELS:
1621 *params = mUnpack.skipPixels;
1622 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001623 case GL_GENERATE_MIPMAP_HINT: *params = mGenerateMipmapHint; break;
1624 case GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES: *params = mFragmentShaderDerivativeHint; break;
Cooper Partin4d61f7e2015-08-12 10:56:50 -07001625 case GL_ACTIVE_TEXTURE:
1626 *params = (static_cast<GLint>(mActiveSampler) + GL_TEXTURE0);
1627 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001628 case GL_STENCIL_FUNC: *params = mDepthStencil.stencilFunc; break;
1629 case GL_STENCIL_REF: *params = mStencilRef; break;
1630 case GL_STENCIL_VALUE_MASK: *params = clampToInt(mDepthStencil.stencilMask); break;
1631 case GL_STENCIL_BACK_FUNC: *params = mDepthStencil.stencilBackFunc; break;
1632 case GL_STENCIL_BACK_REF: *params = mStencilBackRef; break;
1633 case GL_STENCIL_BACK_VALUE_MASK: *params = clampToInt(mDepthStencil.stencilBackMask); break;
1634 case GL_STENCIL_FAIL: *params = mDepthStencil.stencilFail; break;
1635 case GL_STENCIL_PASS_DEPTH_FAIL: *params = mDepthStencil.stencilPassDepthFail; break;
1636 case GL_STENCIL_PASS_DEPTH_PASS: *params = mDepthStencil.stencilPassDepthPass; break;
1637 case GL_STENCIL_BACK_FAIL: *params = mDepthStencil.stencilBackFail; break;
1638 case GL_STENCIL_BACK_PASS_DEPTH_FAIL: *params = mDepthStencil.stencilBackPassDepthFail; break;
1639 case GL_STENCIL_BACK_PASS_DEPTH_PASS: *params = mDepthStencil.stencilBackPassDepthPass; break;
1640 case GL_DEPTH_FUNC: *params = mDepthStencil.depthFunc; break;
1641 case GL_BLEND_SRC_RGB: *params = mBlend.sourceBlendRGB; break;
1642 case GL_BLEND_SRC_ALPHA: *params = mBlend.sourceBlendAlpha; break;
1643 case GL_BLEND_DST_RGB: *params = mBlend.destBlendRGB; break;
1644 case GL_BLEND_DST_ALPHA: *params = mBlend.destBlendAlpha; break;
1645 case GL_BLEND_EQUATION_RGB: *params = mBlend.blendEquationRGB; break;
1646 case GL_BLEND_EQUATION_ALPHA: *params = mBlend.blendEquationAlpha; break;
1647 case GL_STENCIL_WRITEMASK: *params = clampToInt(mDepthStencil.stencilWritemask); break;
1648 case GL_STENCIL_BACK_WRITEMASK: *params = clampToInt(mDepthStencil.stencilBackWritemask); break;
1649 case GL_STENCIL_CLEAR_VALUE: *params = mStencilClearValue; break;
Geoff Langbce529e2014-12-01 12:48:41 -05001650 case GL_IMPLEMENTATION_COLOR_READ_TYPE: *params = mReadFramebuffer->getImplementationColorReadType(); break;
1651 case GL_IMPLEMENTATION_COLOR_READ_FORMAT: *params = mReadFramebuffer->getImplementationColorReadFormat(); break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001652 case GL_SAMPLE_BUFFERS:
1653 case GL_SAMPLES:
1654 {
1655 gl::Framebuffer *framebuffer = mDrawFramebuffer;
Geoff Lang748f74e2014-12-01 11:25:34 -05001656 if (framebuffer->checkStatus(data) == GL_FRAMEBUFFER_COMPLETE)
Shannon Woods53a94a82014-06-24 15:20:36 -04001657 {
1658 switch (pname)
1659 {
1660 case GL_SAMPLE_BUFFERS:
Jamie Madill48faf802014-11-06 15:27:22 -05001661 if (framebuffer->getSamples(data) != 0)
Shannon Woods53a94a82014-06-24 15:20:36 -04001662 {
1663 *params = 1;
1664 }
1665 else
1666 {
1667 *params = 0;
1668 }
1669 break;
1670 case GL_SAMPLES:
Jamie Madill48faf802014-11-06 15:27:22 -05001671 *params = framebuffer->getSamples(data);
Shannon Woods53a94a82014-06-24 15:20:36 -04001672 break;
1673 }
1674 }
1675 else
1676 {
1677 *params = 0;
1678 }
1679 }
1680 break;
1681 case GL_VIEWPORT:
1682 params[0] = mViewport.x;
1683 params[1] = mViewport.y;
1684 params[2] = mViewport.width;
1685 params[3] = mViewport.height;
1686 break;
1687 case GL_SCISSOR_BOX:
1688 params[0] = mScissor.x;
1689 params[1] = mScissor.y;
1690 params[2] = mScissor.width;
1691 params[3] = mScissor.height;
1692 break;
1693 case GL_CULL_FACE_MODE: *params = mRasterizer.cullMode; break;
1694 case GL_FRONT_FACE: *params = mRasterizer.frontFace; break;
1695 case GL_RED_BITS:
1696 case GL_GREEN_BITS:
1697 case GL_BLUE_BITS:
1698 case GL_ALPHA_BITS:
1699 {
1700 gl::Framebuffer *framebuffer = getDrawFramebuffer();
Jamie Madillb6bda4a2015-04-20 12:53:26 -04001701 const gl::FramebufferAttachment *colorbuffer = framebuffer->getFirstColorbuffer();
Shannon Woods53a94a82014-06-24 15:20:36 -04001702
1703 if (colorbuffer)
1704 {
1705 switch (pname)
1706 {
1707 case GL_RED_BITS: *params = colorbuffer->getRedSize(); break;
1708 case GL_GREEN_BITS: *params = colorbuffer->getGreenSize(); break;
1709 case GL_BLUE_BITS: *params = colorbuffer->getBlueSize(); break;
1710 case GL_ALPHA_BITS: *params = colorbuffer->getAlphaSize(); break;
1711 }
1712 }
1713 else
1714 {
1715 *params = 0;
1716 }
1717 }
1718 break;
1719 case GL_DEPTH_BITS:
1720 {
Jamie Madille3ef7152015-04-28 16:55:17 +00001721 const gl::Framebuffer *framebuffer = getDrawFramebuffer();
1722 const gl::FramebufferAttachment *depthbuffer = framebuffer->getDepthbuffer();
Shannon Woods53a94a82014-06-24 15:20:36 -04001723
1724 if (depthbuffer)
1725 {
1726 *params = depthbuffer->getDepthSize();
1727 }
1728 else
1729 {
1730 *params = 0;
1731 }
1732 }
1733 break;
1734 case GL_STENCIL_BITS:
1735 {
Jamie Madille3ef7152015-04-28 16:55:17 +00001736 const gl::Framebuffer *framebuffer = getDrawFramebuffer();
1737 const gl::FramebufferAttachment *stencilbuffer = framebuffer->getStencilbuffer();
Shannon Woods53a94a82014-06-24 15:20:36 -04001738
1739 if (stencilbuffer)
1740 {
1741 *params = stencilbuffer->getStencilSize();
1742 }
1743 else
1744 {
1745 *params = 0;
1746 }
1747 }
1748 break;
1749 case GL_TEXTURE_BINDING_2D:
Shannon Woods2df6a602014-09-26 16:12:07 -04001750 ASSERT(mActiveSampler < mMaxCombinedTextureImageUnits);
Cooper Partin4d61f7e2015-08-12 10:56:50 -07001751 *params = getSamplerTextureId(static_cast<unsigned int>(mActiveSampler), GL_TEXTURE_2D);
Shannon Woods53a94a82014-06-24 15:20:36 -04001752 break;
1753 case GL_TEXTURE_BINDING_CUBE_MAP:
Shannon Woods2df6a602014-09-26 16:12:07 -04001754 ASSERT(mActiveSampler < mMaxCombinedTextureImageUnits);
Cooper Partin4d61f7e2015-08-12 10:56:50 -07001755 *params =
1756 getSamplerTextureId(static_cast<unsigned int>(mActiveSampler), GL_TEXTURE_CUBE_MAP);
Shannon Woods53a94a82014-06-24 15:20:36 -04001757 break;
1758 case GL_TEXTURE_BINDING_3D:
Shannon Woods2df6a602014-09-26 16:12:07 -04001759 ASSERT(mActiveSampler < mMaxCombinedTextureImageUnits);
Cooper Partin4d61f7e2015-08-12 10:56:50 -07001760 *params = getSamplerTextureId(static_cast<unsigned int>(mActiveSampler), GL_TEXTURE_3D);
Shannon Woods53a94a82014-06-24 15:20:36 -04001761 break;
1762 case GL_TEXTURE_BINDING_2D_ARRAY:
Shannon Woods2df6a602014-09-26 16:12:07 -04001763 ASSERT(mActiveSampler < mMaxCombinedTextureImageUnits);
Cooper Partin4d61f7e2015-08-12 10:56:50 -07001764 *params =
1765 getSamplerTextureId(static_cast<unsigned int>(mActiveSampler), GL_TEXTURE_2D_ARRAY);
Shannon Woods53a94a82014-06-24 15:20:36 -04001766 break;
John Bauman18319182016-09-28 14:22:27 -07001767 case GL_TEXTURE_BINDING_EXTERNAL_OES:
1768 ASSERT(mActiveSampler < mMaxCombinedTextureImageUnits);
1769 *params = getSamplerTextureId(static_cast<unsigned int>(mActiveSampler),
1770 GL_TEXTURE_EXTERNAL_OES);
1771 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001772 case GL_UNIFORM_BUFFER_BINDING:
1773 *params = mGenericUniformBuffer.id();
1774 break;
Frank Henigman22581ff2015-11-06 14:25:54 -05001775 case GL_TRANSFORM_FEEDBACK_BINDING:
Frank Henigmanb0f0b812015-11-21 17:49:29 -05001776 *params = mTransformFeedback.id();
Frank Henigman22581ff2015-11-06 14:25:54 -05001777 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001778 case GL_TRANSFORM_FEEDBACK_BUFFER_BINDING:
Geoff Lang045536b2015-03-27 15:17:18 -04001779 *params = mTransformFeedback->getGenericBuffer().id();
Shannon Woods53a94a82014-06-24 15:20:36 -04001780 break;
1781 case GL_COPY_READ_BUFFER_BINDING:
1782 *params = mCopyReadBuffer.id();
1783 break;
1784 case GL_COPY_WRITE_BUFFER_BINDING:
1785 *params = mCopyWriteBuffer.id();
1786 break;
1787 case GL_PIXEL_PACK_BUFFER_BINDING:
1788 *params = mPack.pixelBuffer.id();
1789 break;
1790 case GL_PIXEL_UNPACK_BUFFER_BINDING:
1791 *params = mUnpack.pixelBuffer.id();
1792 break;
Olli Etuaho86821db2016-03-04 12:05:47 +02001793 case GL_READ_BUFFER:
1794 *params = mReadFramebuffer->getReadBufferState();
1795 break;
1796 case GL_SAMPLER_BINDING:
1797 ASSERT(mActiveSampler < mMaxCombinedTextureImageUnits);
1798 *params = getSamplerId(static_cast<GLuint>(mActiveSampler));
1799 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001800 case GL_DEBUG_LOGGED_MESSAGES:
1801 *params = static_cast<GLint>(mDebug.getMessageCount());
1802 break;
1803 case GL_DEBUG_NEXT_LOGGED_MESSAGE_LENGTH:
1804 *params = static_cast<GLint>(mDebug.getNextMessageLength());
1805 break;
1806 case GL_DEBUG_GROUP_STACK_DEPTH:
1807 *params = static_cast<GLint>(mDebug.getGroupStackDepth());
1808 break;
Sami Väisänen74c23472016-05-09 17:30:30 +03001809 case GL_MULTISAMPLE_EXT:
1810 *params = static_cast<GLint>(mMultiSampling);
1811 break;
1812 case GL_SAMPLE_ALPHA_TO_ONE_EXT:
1813 *params = static_cast<GLint>(mSampleAlphaToOne);
Sami Väisänena797e062016-05-12 15:23:40 +03001814 case GL_COVERAGE_MODULATION_CHROMIUM:
1815 *params = static_cast<GLint>(mCoverageModulation);
Sami Väisänen74c23472016-05-09 17:30:30 +03001816 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001817 default:
1818 UNREACHABLE();
1819 break;
1820 }
1821}
1822
Geoff Lang70d0f492015-12-10 17:45:46 -05001823void State::getPointerv(GLenum pname, void **params) const
1824{
1825 switch (pname)
1826 {
1827 case GL_DEBUG_CALLBACK_FUNCTION:
1828 *params = reinterpret_cast<void *>(mDebug.getCallback());
1829 break;
1830 case GL_DEBUG_CALLBACK_USER_PARAM:
1831 *params = const_cast<void *>(mDebug.getUserParam());
1832 break;
1833 default:
1834 UNREACHABLE();
1835 break;
1836 }
1837}
1838
Martin Radev66fb8202016-07-28 11:45:20 +03001839void State::getIntegeri_v(GLenum target, GLuint index, GLint *data)
Shannon Woods53a94a82014-06-24 15:20:36 -04001840{
1841 switch (target)
1842 {
1843 case GL_TRANSFORM_FEEDBACK_BUFFER_BINDING:
Geoff Lang045536b2015-03-27 15:17:18 -04001844 if (static_cast<size_t>(index) < mTransformFeedback->getIndexedBufferCount())
Shannon Woods53a94a82014-06-24 15:20:36 -04001845 {
Geoff Lang045536b2015-03-27 15:17:18 -04001846 *data = mTransformFeedback->getIndexedBuffer(index).id();
Shannon Woods53a94a82014-06-24 15:20:36 -04001847 }
1848 break;
1849 case GL_UNIFORM_BUFFER_BINDING:
Shannon Woodsf3acaf92014-09-23 18:07:11 -04001850 if (static_cast<size_t>(index) < mUniformBuffers.size())
Shannon Woods53a94a82014-06-24 15:20:36 -04001851 {
1852 *data = mUniformBuffers[index].id();
1853 }
1854 break;
1855 default:
Martin Radev66fb8202016-07-28 11:45:20 +03001856 UNREACHABLE();
1857 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001858 }
Shannon Woods53a94a82014-06-24 15:20:36 -04001859}
1860
Martin Radev66fb8202016-07-28 11:45:20 +03001861void State::getInteger64i_v(GLenum target, GLuint index, GLint64 *data)
Shannon Woods53a94a82014-06-24 15:20:36 -04001862{
1863 switch (target)
1864 {
1865 case GL_TRANSFORM_FEEDBACK_BUFFER_START:
Geoff Lang045536b2015-03-27 15:17:18 -04001866 if (static_cast<size_t>(index) < mTransformFeedback->getIndexedBufferCount())
Shannon Woods53a94a82014-06-24 15:20:36 -04001867 {
Geoff Lang045536b2015-03-27 15:17:18 -04001868 *data = mTransformFeedback->getIndexedBuffer(index).getOffset();
Shannon Woods53a94a82014-06-24 15:20:36 -04001869 }
1870 break;
1871 case GL_TRANSFORM_FEEDBACK_BUFFER_SIZE:
Geoff Lang045536b2015-03-27 15:17:18 -04001872 if (static_cast<size_t>(index) < mTransformFeedback->getIndexedBufferCount())
Shannon Woods53a94a82014-06-24 15:20:36 -04001873 {
Geoff Lang045536b2015-03-27 15:17:18 -04001874 *data = mTransformFeedback->getIndexedBuffer(index).getSize();
Shannon Woods53a94a82014-06-24 15:20:36 -04001875 }
1876 break;
1877 case GL_UNIFORM_BUFFER_START:
Shannon Woodsf3acaf92014-09-23 18:07:11 -04001878 if (static_cast<size_t>(index) < mUniformBuffers.size())
Shannon Woods53a94a82014-06-24 15:20:36 -04001879 {
1880 *data = mUniformBuffers[index].getOffset();
1881 }
1882 break;
1883 case GL_UNIFORM_BUFFER_SIZE:
Shannon Woodsf3acaf92014-09-23 18:07:11 -04001884 if (static_cast<size_t>(index) < mUniformBuffers.size())
Shannon Woods53a94a82014-06-24 15:20:36 -04001885 {
1886 *data = mUniformBuffers[index].getSize();
1887 }
1888 break;
1889 default:
Martin Radev66fb8202016-07-28 11:45:20 +03001890 UNREACHABLE();
1891 break;
Shannon Woods53a94a82014-06-24 15:20:36 -04001892 }
Martin Radev66fb8202016-07-28 11:45:20 +03001893}
Shannon Woods53a94a82014-06-24 15:20:36 -04001894
Martin Radev66fb8202016-07-28 11:45:20 +03001895void State::getBooleani_v(GLenum target, GLuint index, GLboolean *data)
1896{
1897 UNREACHABLE();
Shannon Woods53a94a82014-06-24 15:20:36 -04001898}
1899
Jamie Madilld9ba4f72014-08-04 10:47:59 -04001900bool State::hasMappedBuffer(GLenum target) const
1901{
1902 if (target == GL_ARRAY_BUFFER)
1903 {
Geoff Lang5ead9272015-03-25 12:27:43 -04001904 const VertexArray *vao = getVertexArray();
Jamie Madilleea3a6e2015-04-15 10:02:48 -04001905 const auto &vertexAttribs = vao->getVertexAttributes();
Jamie Madill8e344942015-07-09 14:22:07 -04001906 size_t maxEnabledAttrib = vao->getMaxEnabledAttribute();
Jamie Madillaebf9dd2015-04-28 12:39:07 -04001907 for (size_t attribIndex = 0; attribIndex < maxEnabledAttrib; attribIndex++)
Jamie Madilld9ba4f72014-08-04 10:47:59 -04001908 {
Jamie Madilleea3a6e2015-04-15 10:02:48 -04001909 const gl::VertexAttribute &vertexAttrib = vertexAttribs[attribIndex];
Jamie Madilld9ba4f72014-08-04 10:47:59 -04001910 gl::Buffer *boundBuffer = vertexAttrib.buffer.get();
1911 if (vertexAttrib.enabled && boundBuffer && boundBuffer->isMapped())
1912 {
1913 return true;
1914 }
1915 }
1916
1917 return false;
1918 }
1919 else
1920 {
1921 Buffer *buffer = getTargetBuffer(target);
1922 return (buffer && buffer->isMapped());
1923 }
1924}
1925
Jamie Madillc9d442d2016-01-20 11:17:24 -05001926void State::syncDirtyObjects()
1927{
1928 if (!mDirtyObjects.any())
1929 return;
1930
Jamie Madill60ec6ea2016-01-22 15:27:19 -05001931 syncDirtyObjects(mDirtyObjects);
1932}
1933
1934void State::syncDirtyObjects(const DirtyObjects &bitset)
1935{
1936 for (auto dirtyObject : angle::IterateBitSet(bitset))
Jamie Madillc9d442d2016-01-20 11:17:24 -05001937 {
1938 switch (dirtyObject)
1939 {
1940 case DIRTY_OBJECT_READ_FRAMEBUFFER:
Jamie Madill60ec6ea2016-01-22 15:27:19 -05001941 ASSERT(mReadFramebuffer);
1942 mReadFramebuffer->syncState();
Jamie Madillc9d442d2016-01-20 11:17:24 -05001943 break;
1944 case DIRTY_OBJECT_DRAW_FRAMEBUFFER:
Jamie Madill60ec6ea2016-01-22 15:27:19 -05001945 ASSERT(mDrawFramebuffer);
1946 mDrawFramebuffer->syncState();
Jamie Madillc9d442d2016-01-20 11:17:24 -05001947 break;
1948 case DIRTY_OBJECT_VERTEX_ARRAY:
Jamie Madill60ec6ea2016-01-22 15:27:19 -05001949 ASSERT(mVertexArray);
Jamie Madillc9d442d2016-01-20 11:17:24 -05001950 mVertexArray->syncImplState();
1951 break;
1952 case DIRTY_OBJECT_PROGRAM:
1953 // TODO(jmadill): implement this
1954 break;
1955 default:
1956 UNREACHABLE();
1957 break;
1958 }
1959 }
1960
Jamie Madill60ec6ea2016-01-22 15:27:19 -05001961 mDirtyObjects &= ~bitset;
1962}
1963
1964void State::syncDirtyObject(GLenum target)
1965{
1966 DirtyObjects localSet;
1967
1968 switch (target)
1969 {
1970 case GL_READ_FRAMEBUFFER:
1971 localSet.set(DIRTY_OBJECT_READ_FRAMEBUFFER);
1972 break;
1973 case GL_DRAW_FRAMEBUFFER:
1974 localSet.set(DIRTY_OBJECT_DRAW_FRAMEBUFFER);
1975 break;
1976 case GL_FRAMEBUFFER:
1977 localSet.set(DIRTY_OBJECT_READ_FRAMEBUFFER);
1978 localSet.set(DIRTY_OBJECT_DRAW_FRAMEBUFFER);
1979 break;
1980 case GL_VERTEX_ARRAY:
1981 localSet.set(DIRTY_OBJECT_VERTEX_ARRAY);
1982 break;
1983 case GL_PROGRAM:
1984 localSet.set(DIRTY_OBJECT_PROGRAM);
1985 break;
1986 }
1987
1988 syncDirtyObjects(localSet);
1989}
1990
1991void State::setObjectDirty(GLenum target)
1992{
1993 switch (target)
1994 {
1995 case GL_READ_FRAMEBUFFER:
1996 mDirtyObjects.set(DIRTY_OBJECT_READ_FRAMEBUFFER);
1997 break;
1998 case GL_DRAW_FRAMEBUFFER:
1999 mDirtyObjects.set(DIRTY_OBJECT_DRAW_FRAMEBUFFER);
2000 break;
2001 case GL_FRAMEBUFFER:
2002 mDirtyObjects.set(DIRTY_OBJECT_READ_FRAMEBUFFER);
2003 mDirtyObjects.set(DIRTY_OBJECT_DRAW_FRAMEBUFFER);
2004 break;
2005 case GL_VERTEX_ARRAY:
2006 mDirtyObjects.set(DIRTY_OBJECT_VERTEX_ARRAY);
2007 break;
2008 case GL_PROGRAM:
2009 mDirtyObjects.set(DIRTY_OBJECT_PROGRAM);
2010 break;
2011 }
Shannon Woods53a94a82014-06-24 15:20:36 -04002012}
Jamie Madillc9d442d2016-01-20 11:17:24 -05002013
2014} // namespace gl