Context.cpp revision 9f6e888f3d86e9bc8cd07d7315211db3be15fb16
1// SwiftShader Software Renderer
2//
3// Copyright(c) 2005-2013 TransGaming Inc.
4//
5// All rights reserved. No part of this software may be copied, distributed, transmitted,
6// transcribed, stored in a retrieval system, translated into any human or computer
7// language by any means, or disclosed to third parties without the explicit written
8// agreement of TransGaming Inc. Without such an agreement, no rights or licenses, express
9// or implied, including but not limited to any patent rights, are granted to you.
10//
11
12// Context.cpp: Implements the es1::Context class, managing all GL state and performing
13// rendering operations. It is the GLES2 specific implementation of EGLContext.
14
15#include "Context.h"
16
17#include "main.h"
18#include "mathutil.h"
19#include "utilities.h"
20#include "ResourceManager.h"
21#include "Buffer.h"
22#include "Framebuffer.h"
23#include "Renderbuffer.h"
24#include "Texture.h"
25#include "VertexDataManager.h"
26#include "IndexDataManager.h"
27#include "libEGL/Display.h"
28#include "libEGL/Surface.h"
29#include "Common/Half.hpp"
30
31#include <EGL/eglext.h>
32
33#undef near
34#undef far
35
36namespace es1
37{
38Context::Context(const egl::Config *config, const Context *shareContext)
39    : modelViewStack(MAX_MODELVIEW_STACK_DEPTH),
40      projectionStack(MAX_PROJECTION_STACK_DEPTH),
41	  textureStack0(MAX_TEXTURE_STACK_DEPTH),
42	  textureStack1(MAX_TEXTURE_STACK_DEPTH)
43{
44	sw::Context *context = new sw::Context();
45	device = new es1::Device(context);
46
47	mVertexDataManager = new VertexDataManager(this);
48    mIndexDataManager = new IndexDataManager();
49
50    setClearColor(0.0f, 0.0f, 0.0f, 0.0f);
51
52    mState.depthClearValue = 1.0f;
53    mState.stencilClearValue = 0;
54
55    mState.cullFace = false;
56    mState.cullMode = GL_BACK;
57    mState.frontFace = GL_CCW;
58    mState.depthTest = false;
59    mState.depthFunc = GL_LESS;
60    mState.blend = false;
61    mState.sourceBlendRGB = GL_ONE;
62    mState.sourceBlendAlpha = GL_ONE;
63    mState.destBlendRGB = GL_ZERO;
64    mState.destBlendAlpha = GL_ZERO;
65    mState.blendEquationRGB = GL_FUNC_ADD_OES;
66    mState.blendEquationAlpha = GL_FUNC_ADD_OES;
67    mState.stencilTest = false;
68    mState.stencilFunc = GL_ALWAYS;
69    mState.stencilRef = 0;
70    mState.stencilMask = -1;
71    mState.stencilWritemask = -1;
72    mState.stencilFail = GL_KEEP;
73    mState.stencilPassDepthFail = GL_KEEP;
74    mState.stencilPassDepthPass = GL_KEEP;
75    mState.polygonOffsetFill = false;
76    mState.polygonOffsetFactor = 0.0f;
77    mState.polygonOffsetUnits = 0.0f;
78    mState.sampleAlphaToCoverage = false;
79    mState.sampleCoverage = false;
80    mState.sampleCoverageValue = 1.0f;
81    mState.sampleCoverageInvert = false;
82    mState.scissorTest = false;
83    mState.dither = true;
84    mState.generateMipmapHint = GL_DONT_CARE;
85
86    mState.lineWidth = 1.0f;
87
88    mState.viewportX = 0;
89    mState.viewportY = 0;
90    mState.viewportWidth = config->mDisplayMode.width;
91    mState.viewportHeight = config->mDisplayMode.height;
92    mState.zNear = 0.0f;
93    mState.zFar = 1.0f;
94
95    mState.scissorX = 0;
96    mState.scissorY = 0;
97    mState.scissorWidth = config->mDisplayMode.width;
98    mState.scissorHeight = config->mDisplayMode.height;
99
100    mState.colorMaskRed = true;
101    mState.colorMaskGreen = true;
102    mState.colorMaskBlue = true;
103    mState.colorMaskAlpha = true;
104    mState.depthMask = true;
105
106    if(shareContext != NULL)
107    {
108        mResourceManager = shareContext->mResourceManager;
109        mResourceManager->addRef();
110    }
111    else
112    {
113        mResourceManager = new ResourceManager();
114    }
115
116    // [OpenGL ES 2.0.24] section 3.7 page 83:
117    // In the initial state, TEXTURE_2D and TEXTURE_CUBE_MAP have twodimensional
118    // and cube map texture state vectors respectively associated with them.
119    // In order that access to these initial textures not be lost, they are treated as texture
120    // objects all of whose names are 0.
121
122    mTexture2DZero.set(new Texture2D(0));
123    mTextureExternalZero.set(new TextureExternal(0));
124
125    mState.activeSampler = 0;
126    bindArrayBuffer(0);
127    bindElementArrayBuffer(0);
128    bindTexture2D(0);
129    bindFramebuffer(0);
130    bindRenderbuffer(0);
131
132    mState.packAlignment = 4;
133    mState.unpackAlignment = 4;
134
135    mInvalidEnum = false;
136    mInvalidValue = false;
137    mInvalidOperation = false;
138    mOutOfMemory = false;
139    mInvalidFramebufferOperation = false;
140
141	lighting = false;
142
143	for(int i = 0; i < MAX_LIGHTS; i++)
144	{
145		light[i].enable = false;
146		light[i].ambient = {0.0f, 0.0f, 0.0f, 1.0f};
147		light[i].diffuse = {0.0f, 0.0f, 0.0f, 1.0f};
148		light[i].specular = {0.0f, 0.0f, 0.0f, 1.0f};
149		light[i].position = {0.0f, 0.0f, 1.0f, 0.0f};
150		light[i].direction = {0.0f, 0.0f, -1.0f};
151		light[i].attenuation = {1.0f, 0.0f, 0.0f};
152	}
153
154	light[0].diffuse = {1.0f, 1.0f, 1.0f, 1.0f};
155	light[0].specular = {1.0f, 1.0f, 1.0f, 1.0f};
156
157	globalAmbient = {0.2f, 0.2f, 0.2f, 1.0f};
158	materialAmbient = {0.2f, 0.2f, 0.2f, 1.0f};
159	materialDiffuse = {0.8f, 0.8f, 0.8f, 1.0f};
160	materialSpecular = {0.0f, 0.0f, 0.0f, 1.0f};
161	materialEmission = {0.0f, 0.0f, 0.0f, 1.0f};
162
163	matrixMode = GL_MODELVIEW;
164    texture2D = false;
165	clientTexture = GL_TEXTURE0;
166
167	setVertexAttrib(sw::Color0, 1.0f, 1.0f, 1.0f, 1.0f);
168
169	for(int i = 0; i < MAX_TEXTURE_UNITS; i++)
170	{
171		setVertexAttrib(sw::TexCoord0 + i, 0.0f, 0.0f, 0.0f, 1.0f);
172	}
173
174	setVertexAttrib(sw::Normal, 0.0f, 0.0f, 1.0f, 1.0f);
175
176    mHasBeenCurrent = false;
177
178    markAllStateDirty();
179}
180
181Context::~Context()
182{
183    while(!mFramebufferMap.empty())
184    {
185        deleteFramebuffer(mFramebufferMap.begin()->first);
186    }
187
188    for(int type = 0; type < TEXTURE_TYPE_COUNT; type++)
189    {
190        for(int sampler = 0; sampler < MAX_TEXTURE_UNITS; sampler++)
191        {
192            mState.samplerTexture[type][sampler].set(NULL);
193        }
194    }
195
196    for(int i = 0; i < MAX_VERTEX_ATTRIBS; i++)
197    {
198        mState.vertexAttribute[i].mBoundBuffer.set(NULL);
199    }
200
201    mState.arrayBuffer.set(NULL);
202    mState.elementArrayBuffer.set(NULL);
203    mState.renderbuffer.set(NULL);
204
205    mTexture2DZero.set(NULL);
206    mTextureExternalZero.set(NULL);
207
208    delete mVertexDataManager;
209    delete mIndexDataManager;
210
211    mResourceManager->release();
212	delete device;
213}
214
215void Context::makeCurrent(egl::Surface *surface)
216{
217    if(!mHasBeenCurrent)
218    {
219        mState.viewportX = 0;
220        mState.viewportY = 0;
221        mState.viewportWidth = surface->getWidth();
222        mState.viewportHeight = surface->getHeight();
223
224        mState.scissorX = 0;
225        mState.scissorY = 0;
226        mState.scissorWidth = surface->getWidth();
227        mState.scissorHeight = surface->getHeight();
228
229        mHasBeenCurrent = true;
230    }
231
232    // Wrap the existing resources into GL objects and assign them to the '0' names
233    egl::Image *defaultRenderTarget = surface->getRenderTarget();
234    egl::Image *depthStencil = surface->getDepthStencil();
235
236    Colorbuffer *colorbufferZero = new Colorbuffer(defaultRenderTarget);
237    DepthStencilbuffer *depthStencilbufferZero = new DepthStencilbuffer(depthStencil);
238    Framebuffer *framebufferZero = new DefaultFramebuffer(colorbufferZero, depthStencilbufferZero);
239
240    setFramebufferZero(framebufferZero);
241
242    if(defaultRenderTarget)
243    {
244        defaultRenderTarget->release();
245    }
246
247    if(depthStencil)
248    {
249        depthStencil->release();
250    }
251
252    markAllStateDirty();
253}
254
255void Context::destroy()
256{
257	delete this;
258}
259
260int Context::getClientVersion()
261{
262	return 1;
263}
264
265// This function will set all of the state-related dirty flags, so that all state is set during next pre-draw.
266void Context::markAllStateDirty()
267{
268    mDepthStateDirty = true;
269    mMaskStateDirty = true;
270    mBlendStateDirty = true;
271    mStencilStateDirty = true;
272    mPolygonOffsetStateDirty = true;
273    mSampleStateDirty = true;
274    mDitherStateDirty = true;
275    mFrontFaceDirty = true;
276}
277
278void Context::setClearColor(float red, float green, float blue, float alpha)
279{
280    mState.colorClearValue.red = red;
281    mState.colorClearValue.green = green;
282    mState.colorClearValue.blue = blue;
283    mState.colorClearValue.alpha = alpha;
284}
285
286void Context::setClearDepth(float depth)
287{
288    mState.depthClearValue = depth;
289}
290
291void Context::setClearStencil(int stencil)
292{
293    mState.stencilClearValue = stencil;
294}
295
296void Context::setCullFace(bool enabled)
297{
298    mState.cullFace = enabled;
299}
300
301bool Context::isCullFaceEnabled() const
302{
303    return mState.cullFace;
304}
305
306void Context::setCullMode(GLenum mode)
307{
308   mState.cullMode = mode;
309}
310
311void Context::setFrontFace(GLenum front)
312{
313    if(mState.frontFace != front)
314    {
315        mState.frontFace = front;
316        mFrontFaceDirty = true;
317    }
318}
319
320void Context::setDepthTest(bool enabled)
321{
322    if(mState.depthTest != enabled)
323    {
324        mState.depthTest = enabled;
325        mDepthStateDirty = true;
326    }
327}
328
329bool Context::isDepthTestEnabled() const
330{
331    return mState.depthTest;
332}
333
334void Context::setDepthFunc(GLenum depthFunc)
335{
336    if(mState.depthFunc != depthFunc)
337    {
338        mState.depthFunc = depthFunc;
339        mDepthStateDirty = true;
340    }
341}
342
343void Context::setDepthRange(float zNear, float zFar)
344{
345    mState.zNear = zNear;
346    mState.zFar = zFar;
347}
348
349void Context::setBlend(bool enabled)
350{
351    if(mState.blend != enabled)
352    {
353        mState.blend = enabled;
354        mBlendStateDirty = true;
355    }
356}
357
358bool Context::isBlendEnabled() const
359{
360    return mState.blend;
361}
362
363void Context::setBlendFactors(GLenum sourceRGB, GLenum destRGB, GLenum sourceAlpha, GLenum destAlpha)
364{
365    if(mState.sourceBlendRGB != sourceRGB ||
366       mState.sourceBlendAlpha != sourceAlpha ||
367       mState.destBlendRGB != destRGB ||
368       mState.destBlendAlpha != destAlpha)
369    {
370        mState.sourceBlendRGB = sourceRGB;
371        mState.destBlendRGB = destRGB;
372        mState.sourceBlendAlpha = sourceAlpha;
373        mState.destBlendAlpha = destAlpha;
374        mBlendStateDirty = true;
375    }
376}
377
378void Context::setBlendEquation(GLenum rgbEquation, GLenum alphaEquation)
379{
380    if(mState.blendEquationRGB != rgbEquation ||
381       mState.blendEquationAlpha != alphaEquation)
382    {
383        mState.blendEquationRGB = rgbEquation;
384        mState.blendEquationAlpha = alphaEquation;
385        mBlendStateDirty = true;
386    }
387}
388
389void Context::setStencilTest(bool enabled)
390{
391    if(mState.stencilTest != enabled)
392    {
393        mState.stencilTest = enabled;
394        mStencilStateDirty = true;
395    }
396}
397
398bool Context::isStencilTestEnabled() const
399{
400    return mState.stencilTest;
401}
402
403void Context::setStencilParams(GLenum stencilFunc, GLint stencilRef, GLuint stencilMask)
404{
405    if(mState.stencilFunc != stencilFunc ||
406        mState.stencilRef != stencilRef ||
407        mState.stencilMask != stencilMask)
408    {
409        mState.stencilFunc = stencilFunc;
410        mState.stencilRef = (stencilRef > 0) ? stencilRef : 0;
411        mState.stencilMask = stencilMask;
412        mStencilStateDirty = true;
413    }
414}
415
416void Context::setStencilWritemask(GLuint stencilWritemask)
417{
418    if(mState.stencilWritemask != stencilWritemask)
419    {
420        mState.stencilWritemask = stencilWritemask;
421        mStencilStateDirty = true;
422    }
423}
424
425void Context::setStencilOperations(GLenum stencilFail, GLenum stencilPassDepthFail, GLenum stencilPassDepthPass)
426{
427    if(mState.stencilFail != stencilFail ||
428        mState.stencilPassDepthFail != stencilPassDepthFail ||
429        mState.stencilPassDepthPass != stencilPassDepthPass)
430    {
431        mState.stencilFail = stencilFail;
432        mState.stencilPassDepthFail = stencilPassDepthFail;
433        mState.stencilPassDepthPass = stencilPassDepthPass;
434        mStencilStateDirty = true;
435    }
436}
437
438void Context::setPolygonOffsetFill(bool enabled)
439{
440    if(mState.polygonOffsetFill != enabled)
441    {
442        mState.polygonOffsetFill = enabled;
443        mPolygonOffsetStateDirty = true;
444    }
445}
446
447bool Context::isPolygonOffsetFillEnabled() const
448{
449    return mState.polygonOffsetFill;
450}
451
452void Context::setPolygonOffsetParams(GLfloat factor, GLfloat units)
453{
454    if(mState.polygonOffsetFactor != factor ||
455        mState.polygonOffsetUnits != units)
456    {
457        mState.polygonOffsetFactor = factor;
458        mState.polygonOffsetUnits = units;
459        mPolygonOffsetStateDirty = true;
460    }
461}
462
463void Context::setSampleAlphaToCoverage(bool enabled)
464{
465    if(mState.sampleAlphaToCoverage != enabled)
466    {
467        mState.sampleAlphaToCoverage = enabled;
468        mSampleStateDirty = true;
469    }
470}
471
472bool Context::isSampleAlphaToCoverageEnabled() const
473{
474    return mState.sampleAlphaToCoverage;
475}
476
477void Context::setSampleCoverage(bool enabled)
478{
479    if(mState.sampleCoverage != enabled)
480    {
481        mState.sampleCoverage = enabled;
482        mSampleStateDirty = true;
483    }
484}
485
486bool Context::isSampleCoverageEnabled() const
487{
488    return mState.sampleCoverage;
489}
490
491void Context::setSampleCoverageParams(GLclampf value, bool invert)
492{
493    if(mState.sampleCoverageValue != value ||
494        mState.sampleCoverageInvert != invert)
495    {
496        mState.sampleCoverageValue = value;
497        mState.sampleCoverageInvert = invert;
498        mSampleStateDirty = true;
499    }
500}
501
502void Context::setScissorTest(bool enabled)
503{
504    mState.scissorTest = enabled;
505}
506
507bool Context::isScissorTestEnabled() const
508{
509    return mState.scissorTest;
510}
511
512void Context::setDither(bool enabled)
513{
514    if(mState.dither != enabled)
515    {
516        mState.dither = enabled;
517        mDitherStateDirty = true;
518    }
519}
520
521bool Context::isDitherEnabled() const
522{
523    return mState.dither;
524}
525
526void Context::setLighting(bool enable)
527{
528    lighting = enable;
529}
530
531void Context::setLight(int index, bool enable)
532{
533    light[index].enable = enable;
534}
535
536void Context::setLightAmbient(int index, float r, float g, float b, float a)
537{
538	light[index].ambient = {r, g, b, a};
539}
540
541void Context::setLightDiffuse(int index, float r, float g, float b, float a)
542{
543	light[index].diffuse = {r, g, b, a};
544}
545
546void Context::setLightSpecular(int index, float r, float g, float b, float a)
547{
548	light[index].specular = {r, g, b, a};
549}
550
551void Context::setLightPosition(int index, float x, float y, float z, float w)
552{
553	light[index].position = {x, y, z, w};
554}
555
556void Context::setLightDirection(int index, float x, float y, float z)
557{
558	light[index].direction = {x, y, z};
559}
560
561void Context::setLightAttenuationConstant(int index, float constant)
562{
563	light[index].attenuation.constant = constant;
564}
565
566void Context::setLightAttenuationLinear(int index, float linear)
567{
568	light[index].attenuation.linear = linear;
569}
570
571void Context::setLightAttenuationQuadratic(int index, float quadratic)
572{
573	light[index].attenuation.quadratic = quadratic;
574}
575
576void Context::setTexture2D(bool enable)
577{
578    texture2D = enable;
579}
580
581void Context::setLineWidth(GLfloat width)
582{
583    mState.lineWidth = width;
584}
585
586void Context::setGenerateMipmapHint(GLenum hint)
587{
588    mState.generateMipmapHint = hint;
589}
590
591void Context::setViewportParams(GLint x, GLint y, GLsizei width, GLsizei height)
592{
593    mState.viewportX = x;
594    mState.viewportY = y;
595    mState.viewportWidth = width;
596    mState.viewportHeight = height;
597}
598
599void Context::setScissorParams(GLint x, GLint y, GLsizei width, GLsizei height)
600{
601    mState.scissorX = x;
602    mState.scissorY = y;
603    mState.scissorWidth = width;
604    mState.scissorHeight = height;
605}
606
607void Context::setColorMask(bool red, bool green, bool blue, bool alpha)
608{
609    if(mState.colorMaskRed != red || mState.colorMaskGreen != green ||
610       mState.colorMaskBlue != blue || mState.colorMaskAlpha != alpha)
611    {
612        mState.colorMaskRed = red;
613        mState.colorMaskGreen = green;
614        mState.colorMaskBlue = blue;
615        mState.colorMaskAlpha = alpha;
616        mMaskStateDirty = true;
617    }
618}
619
620void Context::setDepthMask(bool mask)
621{
622    if(mState.depthMask != mask)
623    {
624        mState.depthMask = mask;
625        mMaskStateDirty = true;
626    }
627}
628
629void Context::setActiveSampler(unsigned int active)
630{
631    mState.activeSampler = active;
632}
633
634GLuint Context::getFramebufferHandle() const
635{
636    return mState.framebuffer;
637}
638
639GLuint Context::getRenderbufferHandle() const
640{
641    return mState.renderbuffer.id();
642}
643
644GLuint Context::getArrayBufferHandle() const
645{
646    return mState.arrayBuffer.id();
647}
648
649void Context::setEnableVertexAttribArray(unsigned int attribNum, bool enabled)
650{
651    mState.vertexAttribute[attribNum].mArrayEnabled = enabled;
652}
653
654const VertexAttribute &Context::getVertexAttribState(unsigned int attribNum)
655{
656    return mState.vertexAttribute[attribNum];
657}
658
659void Context::setVertexAttribState(unsigned int attribNum, Buffer *boundBuffer, GLint size, GLenum type, bool normalized,
660                                   GLsizei stride, const void *pointer)
661{
662    mState.vertexAttribute[attribNum].mBoundBuffer.set(boundBuffer);
663    mState.vertexAttribute[attribNum].mSize = size;
664    mState.vertexAttribute[attribNum].mType = type;
665    mState.vertexAttribute[attribNum].mNormalized = normalized;
666    mState.vertexAttribute[attribNum].mStride = stride;
667    mState.vertexAttribute[attribNum].mPointer = pointer;
668}
669
670const void *Context::getVertexAttribPointer(unsigned int attribNum) const
671{
672    return mState.vertexAttribute[attribNum].mPointer;
673}
674
675const VertexAttributeArray &Context::getVertexAttributes()
676{
677    return mState.vertexAttribute;
678}
679
680void Context::setPackAlignment(GLint alignment)
681{
682    mState.packAlignment = alignment;
683}
684
685GLint Context::getPackAlignment() const
686{
687    return mState.packAlignment;
688}
689
690void Context::setUnpackAlignment(GLint alignment)
691{
692    mState.unpackAlignment = alignment;
693}
694
695GLint Context::getUnpackAlignment() const
696{
697    return mState.unpackAlignment;
698}
699
700GLuint Context::createBuffer()
701{
702    return mResourceManager->createBuffer();
703}
704
705GLuint Context::createTexture()
706{
707    return mResourceManager->createTexture();
708}
709
710GLuint Context::createRenderbuffer()
711{
712    return mResourceManager->createRenderbuffer();
713}
714
715// Returns an unused framebuffer name
716GLuint Context::createFramebuffer()
717{
718    GLuint handle = mFramebufferHandleAllocator.allocate();
719
720    mFramebufferMap[handle] = NULL;
721
722    return handle;
723}
724
725void Context::deleteBuffer(GLuint buffer)
726{
727    if(mResourceManager->getBuffer(buffer))
728    {
729        detachBuffer(buffer);
730    }
731
732    mResourceManager->deleteBuffer(buffer);
733}
734
735void Context::deleteTexture(GLuint texture)
736{
737    if(mResourceManager->getTexture(texture))
738    {
739        detachTexture(texture);
740    }
741
742    mResourceManager->deleteTexture(texture);
743}
744
745void Context::deleteRenderbuffer(GLuint renderbuffer)
746{
747    if(mResourceManager->getRenderbuffer(renderbuffer))
748    {
749        detachRenderbuffer(renderbuffer);
750    }
751
752    mResourceManager->deleteRenderbuffer(renderbuffer);
753}
754
755void Context::deleteFramebuffer(GLuint framebuffer)
756{
757    FramebufferMap::iterator framebufferObject = mFramebufferMap.find(framebuffer);
758
759    if(framebufferObject != mFramebufferMap.end())
760    {
761        detachFramebuffer(framebuffer);
762
763        mFramebufferHandleAllocator.release(framebufferObject->first);
764        delete framebufferObject->second;
765        mFramebufferMap.erase(framebufferObject);
766    }
767}
768
769Buffer *Context::getBuffer(GLuint handle)
770{
771    return mResourceManager->getBuffer(handle);
772}
773
774Texture *Context::getTexture(GLuint handle)
775{
776    return mResourceManager->getTexture(handle);
777}
778
779Renderbuffer *Context::getRenderbuffer(GLuint handle)
780{
781    return mResourceManager->getRenderbuffer(handle);
782}
783
784Framebuffer *Context::getFramebuffer()
785{
786    return getFramebuffer(mState.framebuffer);
787}
788
789void Context::bindArrayBuffer(unsigned int buffer)
790{
791    mResourceManager->checkBufferAllocation(buffer);
792
793    mState.arrayBuffer.set(getBuffer(buffer));
794}
795
796void Context::bindElementArrayBuffer(unsigned int buffer)
797{
798    mResourceManager->checkBufferAllocation(buffer);
799
800    mState.elementArrayBuffer.set(getBuffer(buffer));
801}
802
803void Context::bindTexture2D(GLuint texture)
804{
805    mResourceManager->checkTextureAllocation(texture, TEXTURE_2D);
806
807    mState.samplerTexture[TEXTURE_2D][mState.activeSampler].set(getTexture(texture));
808}
809
810void Context::bindTextureExternal(GLuint texture)
811{
812    mResourceManager->checkTextureAllocation(texture, TEXTURE_EXTERNAL);
813
814    mState.samplerTexture[TEXTURE_EXTERNAL][mState.activeSampler].set(getTexture(texture));
815}
816
817void Context::bindFramebuffer(GLuint framebuffer)
818{
819    if(!getFramebuffer(framebuffer))
820    {
821        mFramebufferMap[framebuffer] = new Framebuffer();
822    }
823
824    mState.framebuffer = framebuffer;
825}
826
827void Context::bindRenderbuffer(GLuint renderbuffer)
828{
829    mState.renderbuffer.set(getRenderbuffer(renderbuffer));
830}
831
832void Context::setFramebufferZero(Framebuffer *buffer)
833{
834    delete mFramebufferMap[0];
835    mFramebufferMap[0] = buffer;
836}
837
838void Context::setRenderbufferStorage(RenderbufferStorage *renderbuffer)
839{
840    Renderbuffer *renderbufferObject = mState.renderbuffer.get();
841    renderbufferObject->setStorage(renderbuffer);
842}
843
844Framebuffer *Context::getFramebuffer(unsigned int handle)
845{
846    FramebufferMap::iterator framebuffer = mFramebufferMap.find(handle);
847
848    if(framebuffer == mFramebufferMap.end())
849    {
850        return NULL;
851    }
852    else
853    {
854        return framebuffer->second;
855    }
856}
857
858Buffer *Context::getArrayBuffer()
859{
860    return mState.arrayBuffer.get();
861}
862
863Buffer *Context::getElementArrayBuffer()
864{
865    return mState.elementArrayBuffer.get();
866}
867
868Texture2D *Context::getTexture2D()
869{
870    return static_cast<Texture2D*>(getSamplerTexture(mState.activeSampler, TEXTURE_2D));
871}
872
873TextureExternal *Context::getTextureExternal()
874{
875    return static_cast<TextureExternal*>(getSamplerTexture(mState.activeSampler, TEXTURE_EXTERNAL));
876}
877
878Texture *Context::getSamplerTexture(unsigned int sampler, TextureType type)
879{
880    GLuint texid = mState.samplerTexture[type][sampler].id();
881
882    if(texid == 0)   // Special case: 0 refers to different initial textures based on the target
883    {
884        switch (type)
885        {
886        case TEXTURE_2D: return mTexture2DZero.get();
887        case TEXTURE_EXTERNAL: return mTextureExternalZero.get();
888        default: UNREACHABLE();
889        }
890    }
891
892    return mState.samplerTexture[type][sampler].get();
893}
894
895bool Context::getBooleanv(GLenum pname, GLboolean *params)
896{
897    switch (pname)
898    {
899      case GL_SAMPLE_COVERAGE_INVERT:   *params = mState.sampleCoverageInvert;      break;
900      case GL_DEPTH_WRITEMASK:          *params = mState.depthMask;                 break;
901      case GL_COLOR_WRITEMASK:
902        params[0] = mState.colorMaskRed;
903        params[1] = mState.colorMaskGreen;
904        params[2] = mState.colorMaskBlue;
905        params[3] = mState.colorMaskAlpha;
906        break;
907      case GL_CULL_FACE:                *params = mState.cullFace;                  break;
908      case GL_POLYGON_OFFSET_FILL:      *params = mState.polygonOffsetFill;         break;
909      case GL_SAMPLE_ALPHA_TO_COVERAGE: *params = mState.sampleAlphaToCoverage;     break;
910      case GL_SAMPLE_COVERAGE:          *params = mState.sampleCoverage;            break;
911      case GL_SCISSOR_TEST:             *params = mState.scissorTest;               break;
912      case GL_STENCIL_TEST:             *params = mState.stencilTest;               break;
913      case GL_DEPTH_TEST:               *params = mState.depthTest;                 break;
914      case GL_BLEND:                    *params = mState.blend;                     break;
915      case GL_DITHER:                   *params = mState.dither;                    break;
916      default:
917        return false;
918    }
919
920    return true;
921}
922
923bool Context::getFloatv(GLenum pname, GLfloat *params)
924{
925    // Please note: DEPTH_CLEAR_VALUE is included in our internal getFloatv implementation
926    // because it is stored as a float, despite the fact that the GL ES 2.0 spec names
927    // GetIntegerv as its native query function. As it would require conversion in any
928    // case, this should make no difference to the calling application.
929    switch (pname)
930    {
931      case GL_LINE_WIDTH:               *params = mState.lineWidth;            break;
932      case GL_SAMPLE_COVERAGE_VALUE:    *params = mState.sampleCoverageValue;  break;
933      case GL_DEPTH_CLEAR_VALUE:        *params = mState.depthClearValue;      break;
934      case GL_POLYGON_OFFSET_FACTOR:    *params = mState.polygonOffsetFactor;  break;
935      case GL_POLYGON_OFFSET_UNITS:     *params = mState.polygonOffsetUnits;   break;
936      case GL_ALIASED_LINE_WIDTH_RANGE:
937        params[0] = ALIASED_LINE_WIDTH_RANGE_MIN;
938        params[1] = ALIASED_LINE_WIDTH_RANGE_MAX;
939        break;
940      case GL_ALIASED_POINT_SIZE_RANGE:
941        params[0] = ALIASED_POINT_SIZE_RANGE_MIN;
942        params[1] = ALIASED_POINT_SIZE_RANGE_MAX;
943        break;
944      case GL_DEPTH_RANGE:
945        params[0] = mState.zNear;
946        params[1] = mState.zFar;
947        break;
948      case GL_COLOR_CLEAR_VALUE:
949        params[0] = mState.colorClearValue.red;
950        params[1] = mState.colorClearValue.green;
951        params[2] = mState.colorClearValue.blue;
952        params[3] = mState.colorClearValue.alpha;
953        break;
954	  case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:
955        *params = MAX_TEXTURE_MAX_ANISOTROPY;
956		break;
957	  case GL_MODELVIEW_MATRIX:
958		for(int i = 0; i < 16; i++)
959		{
960			params[i] = modelViewStack.current()[i % 4][i / 4];
961		}
962		break;
963	  case GL_PROJECTION_MATRIX:
964		for(int i = 0; i < 16; i++)
965		{
966			params[i] = projectionStack.current()[i % 4][i / 4];
967		}
968		break;
969      default:
970        return false;
971    }
972
973    return true;
974}
975
976bool Context::getIntegerv(GLenum pname, GLint *params)
977{
978    // Please note: DEPTH_CLEAR_VALUE is not included in our internal getIntegerv implementation
979    // because it is stored as a float, despite the fact that the GL ES 2.0 spec names
980    // GetIntegerv as its native query function. As it would require conversion in any
981    // case, this should make no difference to the calling application. You may find it in
982    // Context::getFloatv.
983    switch (pname)
984    {
985    case GL_ARRAY_BUFFER_BINDING:             *params = mState.arrayBuffer.id();              break;
986    case GL_ELEMENT_ARRAY_BUFFER_BINDING:     *params = mState.elementArrayBuffer.id();       break;
987	case GL_FRAMEBUFFER_BINDING_OES:          *params = mState.framebuffer;                   break;
988    case GL_RENDERBUFFER_BINDING_OES:         *params = mState.renderbuffer.id();             break;
989    case GL_PACK_ALIGNMENT:                   *params = mState.packAlignment;                 break;
990    case GL_UNPACK_ALIGNMENT:                 *params = mState.unpackAlignment;               break;
991    case GL_GENERATE_MIPMAP_HINT:             *params = mState.generateMipmapHint;            break;
992    case GL_ACTIVE_TEXTURE:                   *params = (mState.activeSampler + GL_TEXTURE0); break;
993    case GL_STENCIL_FUNC:                     *params = mState.stencilFunc;                   break;
994    case GL_STENCIL_REF:                      *params = mState.stencilRef;                    break;
995    case GL_STENCIL_VALUE_MASK:               *params = mState.stencilMask;                   break;
996    case GL_STENCIL_FAIL:                     *params = mState.stencilFail;                   break;
997    case GL_STENCIL_PASS_DEPTH_FAIL:          *params = mState.stencilPassDepthFail;          break;
998    case GL_STENCIL_PASS_DEPTH_PASS:          *params = mState.stencilPassDepthPass;          break;
999    case GL_DEPTH_FUNC:                       *params = mState.depthFunc;                     break;
1000    case GL_BLEND_SRC_RGB_OES:                *params = mState.sourceBlendRGB;                break;
1001    case GL_BLEND_SRC_ALPHA_OES:              *params = mState.sourceBlendAlpha;              break;
1002    case GL_BLEND_DST_RGB_OES:                *params = mState.destBlendRGB;                  break;
1003    case GL_BLEND_DST_ALPHA_OES:              *params = mState.destBlendAlpha;                break;
1004    case GL_BLEND_EQUATION_RGB_OES:           *params = mState.blendEquationRGB;              break;
1005    case GL_BLEND_EQUATION_ALPHA_OES:         *params = mState.blendEquationAlpha;            break;
1006    case GL_STENCIL_WRITEMASK:                *params = mState.stencilWritemask;              break;
1007    case GL_STENCIL_CLEAR_VALUE:              *params = mState.stencilClearValue;             break;
1008    case GL_SUBPIXEL_BITS:                    *params = 4;                                    break;
1009	case GL_MAX_TEXTURE_SIZE:                 *params = IMPLEMENTATION_MAX_TEXTURE_SIZE;      break;
1010	case GL_NUM_COMPRESSED_TEXTURE_FORMATS:   *params = NUM_COMPRESSED_TEXTURE_FORMATS;       break;
1011	case GL_SAMPLE_BUFFERS:
1012    case GL_SAMPLES:
1013        {
1014            Framebuffer *framebuffer = getFramebuffer();
1015			int width, height, samples;
1016
1017            if(framebuffer->completeness(width, height, samples) == GL_FRAMEBUFFER_COMPLETE_OES)
1018            {
1019                switch(pname)
1020                {
1021                case GL_SAMPLE_BUFFERS:
1022                    if(samples > 1)
1023                    {
1024                        *params = 1;
1025                    }
1026                    else
1027                    {
1028                        *params = 0;
1029                    }
1030                    break;
1031                case GL_SAMPLES:
1032                    *params = samples & ~1;
1033                    break;
1034                }
1035            }
1036            else
1037            {
1038                *params = 0;
1039            }
1040        }
1041        break;
1042    case GL_IMPLEMENTATION_COLOR_READ_TYPE:
1043		{
1044			Framebuffer *framebuffer = getFramebuffer();
1045			*params = framebuffer->getImplementationColorReadType();
1046		}
1047		break;
1048    case GL_IMPLEMENTATION_COLOR_READ_FORMAT:
1049		{
1050			Framebuffer *framebuffer = getFramebuffer();
1051			*params = framebuffer->getImplementationColorReadFormat();
1052		}
1053		break;
1054    case GL_MAX_VIEWPORT_DIMS:
1055        {
1056			int maxDimension = IMPLEMENTATION_MAX_RENDERBUFFER_SIZE;
1057            params[0] = maxDimension;
1058            params[1] = maxDimension;
1059        }
1060        break;
1061    case GL_COMPRESSED_TEXTURE_FORMATS:
1062        {
1063			for(int i = 0; i < NUM_COMPRESSED_TEXTURE_FORMATS; i++)
1064			{
1065				params[i] = compressedTextureFormats[i];
1066			}
1067        }
1068        break;
1069    case GL_VIEWPORT:
1070        params[0] = mState.viewportX;
1071        params[1] = mState.viewportY;
1072        params[2] = mState.viewportWidth;
1073        params[3] = mState.viewportHeight;
1074        break;
1075    case GL_SCISSOR_BOX:
1076        params[0] = mState.scissorX;
1077        params[1] = mState.scissorY;
1078        params[2] = mState.scissorWidth;
1079        params[3] = mState.scissorHeight;
1080        break;
1081    case GL_CULL_FACE_MODE:                   *params = mState.cullMode;                 break;
1082    case GL_FRONT_FACE:                       *params = mState.frontFace;                break;
1083    case GL_RED_BITS:
1084    case GL_GREEN_BITS:
1085    case GL_BLUE_BITS:
1086    case GL_ALPHA_BITS:
1087        {
1088            Framebuffer *framebuffer = getFramebuffer();
1089            Renderbuffer *colorbuffer = framebuffer->getColorbuffer();
1090
1091            if(colorbuffer)
1092            {
1093                switch (pname)
1094                {
1095                  case GL_RED_BITS:   *params = colorbuffer->getRedSize();   break;
1096                  case GL_GREEN_BITS: *params = colorbuffer->getGreenSize(); break;
1097                  case GL_BLUE_BITS:  *params = colorbuffer->getBlueSize();  break;
1098                  case GL_ALPHA_BITS: *params = colorbuffer->getAlphaSize(); break;
1099                }
1100            }
1101            else
1102            {
1103                *params = 0;
1104            }
1105        }
1106        break;
1107    case GL_DEPTH_BITS:
1108        {
1109            Framebuffer *framebuffer = getFramebuffer();
1110            Renderbuffer *depthbuffer = framebuffer->getDepthbuffer();
1111
1112            if(depthbuffer)
1113            {
1114                *params = depthbuffer->getDepthSize();
1115            }
1116            else
1117            {
1118                *params = 0;
1119            }
1120        }
1121        break;
1122    case GL_STENCIL_BITS:
1123        {
1124            Framebuffer *framebuffer = getFramebuffer();
1125            Renderbuffer *stencilbuffer = framebuffer->getStencilbuffer();
1126
1127            if(stencilbuffer)
1128            {
1129                *params = stencilbuffer->getStencilSize();
1130            }
1131            else
1132            {
1133                *params = 0;
1134            }
1135        }
1136        break;
1137    case GL_TEXTURE_BINDING_2D:
1138        {
1139            if(mState.activeSampler < 0 || mState.activeSampler > MAX_TEXTURE_UNITS - 1)
1140            {
1141                error(GL_INVALID_OPERATION);
1142                return false;
1143            }
1144
1145            *params = mState.samplerTexture[TEXTURE_2D][mState.activeSampler].id();
1146        }
1147        break;
1148    case GL_TEXTURE_BINDING_CUBE_MAP_OES:
1149        {
1150            if(mState.activeSampler < 0 || mState.activeSampler > MAX_TEXTURE_UNITS - 1)
1151            {
1152                error(GL_INVALID_OPERATION);
1153                return false;
1154            }
1155
1156            *params = mState.samplerTexture[TEXTURE_CUBE][mState.activeSampler].id();
1157        }
1158        break;
1159    case GL_TEXTURE_BINDING_EXTERNAL_OES:
1160        {
1161            if(mState.activeSampler < 0 || mState.activeSampler > MAX_TEXTURE_UNITS - 1)
1162            {
1163                error(GL_INVALID_OPERATION);
1164                return false;
1165            }
1166
1167            *params = mState.samplerTexture[TEXTURE_EXTERNAL][mState.activeSampler].id();
1168        }
1169        break;
1170	case GL_MAX_LIGHTS:                 *params = MAX_LIGHTS;                 break;
1171    case GL_MAX_MODELVIEW_STACK_DEPTH:  *params = MAX_MODELVIEW_STACK_DEPTH;  break;
1172	case GL_MAX_PROJECTION_STACK_DEPTH: *params = MAX_PROJECTION_STACK_DEPTH; break;
1173	case GL_MAX_TEXTURE_STACK_DEPTH:    *params = MAX_TEXTURE_STACK_DEPTH;    break;
1174	case GL_MAX_TEXTURE_UNITS:          *params = MAX_TEXTURE_UNITS;          break;
1175    default:
1176        return false;
1177    }
1178
1179    return true;
1180}
1181
1182int Context::getQueryParameterNum(GLenum pname)
1183{
1184    // Please note: the query type returned for DEPTH_CLEAR_VALUE in this implementation
1185    // is FLOAT rather than INT, as would be suggested by the GL ES 2.0 spec. This is due
1186    // to the fact that it is stored internally as a float, and so would require conversion
1187    // if returned from Context::getIntegerv. Since this conversion is already implemented
1188    // in the case that one calls glGetIntegerv to retrieve a float-typed state variable, we
1189    // place DEPTH_CLEAR_VALUE with the floats. This should make no difference to the calling
1190    // application.
1191    switch (pname)
1192    {
1193    case GL_COMPRESSED_TEXTURE_FORMATS:
1194		return NUM_COMPRESSED_TEXTURE_FORMATS;
1195    case GL_NUM_COMPRESSED_TEXTURE_FORMATS:
1196    case GL_ARRAY_BUFFER_BINDING:
1197    case GL_FRAMEBUFFER_BINDING_OES:
1198    case GL_RENDERBUFFER_BINDING_OES:
1199    case GL_PACK_ALIGNMENT:
1200    case GL_UNPACK_ALIGNMENT:
1201    case GL_GENERATE_MIPMAP_HINT:
1202    case GL_RED_BITS:
1203    case GL_GREEN_BITS:
1204    case GL_BLUE_BITS:
1205    case GL_ALPHA_BITS:
1206    case GL_DEPTH_BITS:
1207    case GL_STENCIL_BITS:
1208    case GL_ELEMENT_ARRAY_BUFFER_BINDING:
1209    case GL_CULL_FACE_MODE:
1210    case GL_FRONT_FACE:
1211    case GL_ACTIVE_TEXTURE:
1212    case GL_STENCIL_FUNC:
1213    case GL_STENCIL_VALUE_MASK:
1214    case GL_STENCIL_REF:
1215    case GL_STENCIL_FAIL:
1216    case GL_STENCIL_PASS_DEPTH_FAIL:
1217    case GL_STENCIL_PASS_DEPTH_PASS:
1218    case GL_DEPTH_FUNC:
1219    case GL_BLEND_SRC_RGB_OES:
1220    case GL_BLEND_SRC_ALPHA_OES:
1221    case GL_BLEND_DST_RGB_OES:
1222    case GL_BLEND_DST_ALPHA_OES:
1223    case GL_BLEND_EQUATION_RGB_OES:
1224    case GL_BLEND_EQUATION_ALPHA_OES:
1225    case GL_STENCIL_WRITEMASK:
1226    case GL_STENCIL_CLEAR_VALUE:
1227    case GL_SUBPIXEL_BITS:
1228    case GL_MAX_TEXTURE_SIZE:
1229    case GL_MAX_CUBE_MAP_TEXTURE_SIZE_OES:
1230    case GL_SAMPLE_BUFFERS:
1231    case GL_SAMPLES:
1232    case GL_IMPLEMENTATION_COLOR_READ_TYPE_OES:
1233    case GL_IMPLEMENTATION_COLOR_READ_FORMAT_OES:
1234    case GL_TEXTURE_BINDING_2D:
1235    case GL_TEXTURE_BINDING_CUBE_MAP_OES:
1236    case GL_TEXTURE_BINDING_EXTERNAL_OES:
1237        return 1;
1238    case GL_MAX_VIEWPORT_DIMS:
1239        return 2;
1240    case GL_VIEWPORT:
1241    case GL_SCISSOR_BOX:
1242        return 4;
1243    case GL_SAMPLE_COVERAGE_INVERT:
1244    case GL_DEPTH_WRITEMASK:
1245    case GL_CULL_FACE:                // CULL_FACE through DITHER are natural to IsEnabled,
1246    case GL_POLYGON_OFFSET_FILL:      // but can be retrieved through the Get{Type}v queries.
1247    case GL_SAMPLE_ALPHA_TO_COVERAGE: // For this purpose, they are treated here as bool-natural
1248    case GL_SAMPLE_COVERAGE:
1249    case GL_SCISSOR_TEST:
1250    case GL_STENCIL_TEST:
1251    case GL_DEPTH_TEST:
1252    case GL_BLEND:
1253    case GL_DITHER:
1254        return 1;
1255    case GL_COLOR_WRITEMASK:
1256        return 4;
1257    case GL_POLYGON_OFFSET_FACTOR:
1258    case GL_POLYGON_OFFSET_UNITS:
1259    case GL_SAMPLE_COVERAGE_VALUE:
1260    case GL_DEPTH_CLEAR_VALUE:
1261    case GL_LINE_WIDTH:
1262        return 1;
1263    case GL_ALIASED_LINE_WIDTH_RANGE:
1264    case GL_ALIASED_POINT_SIZE_RANGE:
1265    case GL_DEPTH_RANGE:
1266        return 2;
1267    case GL_COLOR_CLEAR_VALUE:
1268        return 4;
1269	case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:
1270	case GL_MAX_LIGHTS:
1271	case GL_MAX_MODELVIEW_STACK_DEPTH:
1272	case GL_MAX_PROJECTION_STACK_DEPTH:
1273	case GL_MAX_TEXTURE_STACK_DEPTH:
1274	case GL_MAX_TEXTURE_UNITS:
1275        return 1;
1276	default:
1277		UNREACHABLE();
1278    }
1279
1280    return -1;
1281}
1282
1283bool Context::isQueryParameterInt(GLenum pname)
1284{
1285    // Please note: the query type returned for DEPTH_CLEAR_VALUE in this implementation
1286    // is FLOAT rather than INT, as would be suggested by the GL ES 2.0 spec. This is due
1287    // to the fact that it is stored internally as a float, and so would require conversion
1288    // if returned from Context::getIntegerv. Since this conversion is already implemented
1289    // in the case that one calls glGetIntegerv to retrieve a float-typed state variable, we
1290    // place DEPTH_CLEAR_VALUE with the floats. This should make no difference to the calling
1291    // application.
1292    switch(pname)
1293    {
1294    case GL_COMPRESSED_TEXTURE_FORMATS:
1295    case GL_NUM_COMPRESSED_TEXTURE_FORMATS:
1296    case GL_ARRAY_BUFFER_BINDING:
1297    case GL_FRAMEBUFFER_BINDING_OES:
1298    case GL_RENDERBUFFER_BINDING_OES:
1299    case GL_PACK_ALIGNMENT:
1300    case GL_UNPACK_ALIGNMENT:
1301    case GL_GENERATE_MIPMAP_HINT:
1302    case GL_RED_BITS:
1303    case GL_GREEN_BITS:
1304    case GL_BLUE_BITS:
1305    case GL_ALPHA_BITS:
1306    case GL_DEPTH_BITS:
1307    case GL_STENCIL_BITS:
1308    case GL_ELEMENT_ARRAY_BUFFER_BINDING:
1309    case GL_CULL_FACE_MODE:
1310    case GL_FRONT_FACE:
1311    case GL_ACTIVE_TEXTURE:
1312    case GL_STENCIL_FUNC:
1313    case GL_STENCIL_VALUE_MASK:
1314    case GL_STENCIL_REF:
1315    case GL_STENCIL_FAIL:
1316    case GL_STENCIL_PASS_DEPTH_FAIL:
1317    case GL_STENCIL_PASS_DEPTH_PASS:
1318    case GL_DEPTH_FUNC:
1319    case GL_BLEND_SRC_RGB_OES:
1320    case GL_BLEND_SRC_ALPHA_OES:
1321    case GL_BLEND_DST_RGB_OES:
1322    case GL_BLEND_DST_ALPHA_OES:
1323    case GL_BLEND_EQUATION_RGB_OES:
1324    case GL_BLEND_EQUATION_ALPHA_OES:
1325    case GL_STENCIL_WRITEMASK:
1326    case GL_STENCIL_CLEAR_VALUE:
1327    case GL_SUBPIXEL_BITS:
1328    case GL_MAX_TEXTURE_SIZE:
1329    case GL_MAX_CUBE_MAP_TEXTURE_SIZE_OES:
1330    case GL_SAMPLE_BUFFERS:
1331    case GL_SAMPLES:
1332    case GL_IMPLEMENTATION_COLOR_READ_TYPE_OES:
1333    case GL_IMPLEMENTATION_COLOR_READ_FORMAT_OES:
1334    case GL_TEXTURE_BINDING_2D:
1335    case GL_TEXTURE_BINDING_CUBE_MAP_OES:
1336    case GL_TEXTURE_BINDING_EXTERNAL_OES:
1337    case GL_MAX_VIEWPORT_DIMS:
1338    case GL_VIEWPORT:
1339    case GL_SCISSOR_BOX:
1340	case GL_MAX_LIGHTS:
1341	case GL_MAX_MODELVIEW_STACK_DEPTH:
1342	case GL_MAX_PROJECTION_STACK_DEPTH:
1343	case GL_MAX_TEXTURE_STACK_DEPTH:
1344	case GL_MAX_TEXTURE_UNITS:
1345        return true;
1346	default:
1347		ASSERT(isQueryParameterFloat(pname) || isQueryParameterBool(pname));
1348    }
1349
1350    return false;
1351}
1352
1353bool Context::isQueryParameterFloat(GLenum pname)
1354{
1355    // Please note: the query type returned for DEPTH_CLEAR_VALUE in this implementation
1356    // is FLOAT rather than INT, as would be suggested by the GL ES 2.0 spec. This is due
1357    // to the fact that it is stored internally as a float, and so would require conversion
1358    // if returned from Context::getIntegerv. Since this conversion is already implemented
1359    // in the case that one calls glGetIntegerv to retrieve a float-typed state variable, we
1360    // place DEPTH_CLEAR_VALUE with the floats. This should make no difference to the calling
1361    // application.
1362    switch(pname)
1363    {
1364    case GL_POLYGON_OFFSET_FACTOR:
1365    case GL_POLYGON_OFFSET_UNITS:
1366    case GL_SAMPLE_COVERAGE_VALUE:
1367    case GL_DEPTH_CLEAR_VALUE:
1368    case GL_LINE_WIDTH:
1369    case GL_ALIASED_LINE_WIDTH_RANGE:
1370    case GL_ALIASED_POINT_SIZE_RANGE:
1371    case GL_DEPTH_RANGE:
1372    case GL_COLOR_CLEAR_VALUE:
1373	case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:
1374        return true;
1375    default:
1376        ASSERT(isQueryParameterInt(pname) || isQueryParameterBool(pname));
1377    }
1378
1379    return false;
1380}
1381
1382bool Context::isQueryParameterBool(GLenum pname)
1383{
1384    switch(pname)
1385    {
1386    case GL_SAMPLE_COVERAGE_INVERT:
1387    case GL_DEPTH_WRITEMASK:
1388    case GL_CULL_FACE:                // CULL_FACE through DITHER are natural to IsEnabled,
1389    case GL_POLYGON_OFFSET_FILL:      // but can be retrieved through the Get{Type}v queries.
1390    case GL_SAMPLE_ALPHA_TO_COVERAGE: // For this purpose, they are treated here as bool-natural
1391    case GL_SAMPLE_COVERAGE:
1392    case GL_SCISSOR_TEST:
1393    case GL_STENCIL_TEST:
1394    case GL_DEPTH_TEST:
1395    case GL_BLEND:
1396    case GL_DITHER:
1397    case GL_COLOR_WRITEMASK:
1398        return true;
1399    default:
1400        ASSERT(isQueryParameterInt(pname) || isQueryParameterFloat(pname));
1401    }
1402
1403    return false;
1404}
1405
1406// Applies the render target surface, depth stencil surface, viewport rectangle and scissor rectangle
1407bool Context::applyRenderTarget()
1408{
1409    Framebuffer *framebuffer = getFramebuffer();
1410	int width, height, samples;
1411
1412    if(!framebuffer || framebuffer->completeness(width, height, samples) != GL_FRAMEBUFFER_COMPLETE_OES)
1413    {
1414        return error(GL_INVALID_FRAMEBUFFER_OPERATION_OES, false);
1415    }
1416
1417    egl::Image *renderTarget = framebuffer->getRenderTarget();
1418	device->setRenderTarget(renderTarget);
1419	if(renderTarget) renderTarget->release();
1420
1421    egl::Image *depthStencil = framebuffer->getDepthStencil();
1422    device->setDepthStencilSurface(depthStencil);
1423	if(depthStencil) depthStencil->release();
1424
1425    Viewport viewport;
1426    float zNear = clamp01(mState.zNear);
1427    float zFar = clamp01(mState.zFar);
1428
1429    viewport.x0 = mState.viewportX;
1430    viewport.y0 = mState.viewportY;
1431    viewport.width = mState.viewportWidth;
1432    viewport.height = mState.viewportHeight;
1433    viewport.minZ = zNear;
1434    viewport.maxZ = zFar;
1435
1436    device->setViewport(viewport);
1437
1438    if(mState.scissorTest)
1439    {
1440		sw::Rect scissor = {mState.scissorX, mState.scissorY, mState.scissorX + mState.scissorWidth, mState.scissorY + mState.scissorHeight};
1441		scissor.clip(0, 0, width, height);
1442
1443		device->setScissorRect(scissor);
1444        device->setScissorEnable(true);
1445    }
1446    else
1447    {
1448        device->setScissorEnable(false);
1449    }
1450
1451    return true;
1452}
1453
1454// Applies the fixed-function state (culling, depth test, alpha blending, stenciling, etc)
1455void Context::applyState(GLenum drawMode)
1456{
1457    Framebuffer *framebuffer = getFramebuffer();
1458
1459    if(mState.cullFace)
1460    {
1461        device->setCullMode(es2sw::ConvertCullMode(mState.cullMode, mState.frontFace));
1462    }
1463    else
1464    {
1465		device->setCullMode(sw::CULL_NONE);
1466    }
1467
1468    if(mDepthStateDirty)
1469    {
1470        if(mState.depthTest)
1471        {
1472			device->setDepthBufferEnable(true);
1473			device->setDepthCompare(es2sw::ConvertDepthComparison(mState.depthFunc));
1474        }
1475        else
1476        {
1477            device->setDepthBufferEnable(false);
1478        }
1479
1480        mDepthStateDirty = false;
1481    }
1482
1483    if(mBlendStateDirty)
1484    {
1485        if(mState.blend)
1486        {
1487			device->setAlphaBlendEnable(true);
1488			device->setSeparateAlphaBlendEnable(true);
1489
1490			device->setSourceBlendFactor(es2sw::ConvertBlendFunc(mState.sourceBlendRGB));
1491			device->setDestBlendFactor(es2sw::ConvertBlendFunc(mState.destBlendRGB));
1492			device->setBlendOperation(es2sw::ConvertBlendOp(mState.blendEquationRGB));
1493
1494            device->setSourceBlendFactorAlpha(es2sw::ConvertBlendFunc(mState.sourceBlendAlpha));
1495			device->setDestBlendFactorAlpha(es2sw::ConvertBlendFunc(mState.destBlendAlpha));
1496			device->setBlendOperationAlpha(es2sw::ConvertBlendOp(mState.blendEquationAlpha));
1497        }
1498        else
1499        {
1500			device->setAlphaBlendEnable(false);
1501        }
1502
1503        mBlendStateDirty = false;
1504    }
1505
1506    if(mStencilStateDirty || mFrontFaceDirty)
1507    {
1508        if(mState.stencilTest && framebuffer->hasStencil())
1509        {
1510			device->setStencilEnable(true);
1511			device->setTwoSidedStencil(true);
1512
1513            // get the maximum size of the stencil ref
1514            Renderbuffer *stencilbuffer = framebuffer->getStencilbuffer();
1515            GLuint maxStencil = (1 << stencilbuffer->getStencilSize()) - 1;
1516
1517			device->setStencilWriteMask(mState.stencilWritemask);
1518			device->setStencilCompare(es2sw::ConvertStencilComparison(mState.stencilFunc));
1519
1520			device->setStencilReference((mState.stencilRef < (GLint)maxStencil) ? mState.stencilRef : maxStencil);
1521			device->setStencilMask(mState.stencilMask);
1522
1523			device->setStencilFailOperation(es2sw::ConvertStencilOp(mState.stencilFail));
1524			device->setStencilZFailOperation(es2sw::ConvertStencilOp(mState.stencilPassDepthFail));
1525			device->setStencilPassOperation(es2sw::ConvertStencilOp(mState.stencilPassDepthPass));
1526
1527			device->setStencilWriteMaskCCW(mState.stencilWritemask);
1528			device->setStencilCompareCCW(es2sw::ConvertStencilComparison(mState.stencilFunc));
1529
1530			device->setStencilReferenceCCW((mState.stencilRef < (GLint)maxStencil) ? mState.stencilRef : maxStencil);
1531			device->setStencilMaskCCW(mState.stencilMask);
1532
1533			device->setStencilFailOperationCCW(es2sw::ConvertStencilOp(mState.stencilFail));
1534			device->setStencilZFailOperationCCW(es2sw::ConvertStencilOp(mState.stencilPassDepthFail));
1535			device->setStencilPassOperationCCW(es2sw::ConvertStencilOp(mState.stencilPassDepthPass));
1536        }
1537        else
1538        {
1539			device->setStencilEnable(false);
1540        }
1541
1542        mStencilStateDirty = false;
1543        mFrontFaceDirty = false;
1544    }
1545
1546    if(mMaskStateDirty)
1547    {
1548		device->setColorWriteMask(0, es2sw::ConvertColorMask(mState.colorMaskRed, mState.colorMaskGreen, mState.colorMaskBlue, mState.colorMaskAlpha));
1549		device->setDepthWriteEnable(mState.depthMask);
1550
1551        mMaskStateDirty = false;
1552    }
1553
1554    if(mPolygonOffsetStateDirty)
1555    {
1556        if(mState.polygonOffsetFill)
1557        {
1558            Renderbuffer *depthbuffer = framebuffer->getDepthbuffer();
1559            if(depthbuffer)
1560            {
1561				device->setSlopeDepthBias(mState.polygonOffsetFactor);
1562                float depthBias = ldexp(mState.polygonOffsetUnits, -(int)(depthbuffer->getDepthSize()));
1563				device->setDepthBias(depthBias);
1564            }
1565        }
1566        else
1567        {
1568            device->setSlopeDepthBias(0);
1569            device->setDepthBias(0);
1570        }
1571
1572        mPolygonOffsetStateDirty = false;
1573    }
1574
1575    if(mSampleStateDirty)
1576    {
1577        if(mState.sampleAlphaToCoverage)
1578        {
1579            device->setTransparencyAntialiasing(sw::TRANSPARENCY_ALPHA_TO_COVERAGE);
1580        }
1581		else
1582		{
1583			device->setTransparencyAntialiasing(sw::TRANSPARENCY_NONE);
1584		}
1585
1586        if(mState.sampleCoverage)
1587        {
1588            unsigned int mask = 0;
1589            if(mState.sampleCoverageValue != 0)
1590            {
1591				int width, height, samples;
1592				framebuffer->completeness(width, height, samples);
1593
1594                float threshold = 0.5f;
1595
1596                for(int i = 0; i < samples; i++)
1597                {
1598                    mask <<= 1;
1599
1600                    if((i + 1) * mState.sampleCoverageValue >= threshold)
1601                    {
1602                        threshold += 1.0f;
1603                        mask |= 1;
1604                    }
1605                }
1606            }
1607
1608            if(mState.sampleCoverageInvert)
1609            {
1610                mask = ~mask;
1611            }
1612
1613			device->setMultiSampleMask(mask);
1614        }
1615        else
1616        {
1617			device->setMultiSampleMask(0xFFFFFFFF);
1618        }
1619
1620        mSampleStateDirty = false;
1621    }
1622
1623    if(mDitherStateDirty)
1624    {
1625    //	UNIMPLEMENTED();   // FIXME
1626
1627        mDitherStateDirty = false;
1628    }
1629
1630	device->setLightingEnable(lighting);
1631	device->setGlobalAmbient(sw::Color<float>(globalAmbient.red, globalAmbient.green, globalAmbient.blue, globalAmbient.alpha));
1632
1633	for(int i = 0; i < MAX_LIGHTS; i++)
1634	{
1635		device->setLightEnable(i, light[i].enable);
1636		device->setLightAmbient(i, sw::Color<float>(light[i].ambient.red, light[i].ambient.green, light[i].ambient.blue, light[i].ambient.alpha));
1637		device->setLightDiffuse(i, sw::Color<float>(light[i].diffuse.red, light[i].diffuse.green, light[i].diffuse.blue, light[i].diffuse.alpha));
1638		device->setLightSpecular(i, sw::Color<float>(light[i].specular.red, light[i].specular.green, light[i].specular.blue, light[i].specular.alpha));
1639		device->setLightAttenuation(i, light[i].attenuation.constant, light[i].attenuation.linear, light[i].attenuation.quadratic);
1640
1641		if(light[i].position.w != 0.0f)
1642		{
1643			device->setLightPosition(i, sw::Point(light[i].position.x / light[i].position.w, light[i].position.y / light[i].position.w, light[i].position.z / light[i].position.w));
1644		}
1645		else   // Hack: set the position far way
1646		{
1647			device->setLightPosition(i, sw::Point(1e10f * light[i].position.x, 1e10f * light[i].position.y, 1e10f * light[i].position.z));
1648		}
1649	}
1650
1651	device->setMaterialAmbient(sw::Color<float>(materialAmbient.red, materialAmbient.green, materialAmbient.blue, materialAmbient.alpha));
1652	device->setMaterialDiffuse(sw::Color<float>(materialDiffuse.red, materialDiffuse.green, materialDiffuse.blue, materialDiffuse.alpha));
1653	device->setMaterialSpecular(sw::Color<float>(materialSpecular.red, materialSpecular.green, materialSpecular.blue, materialSpecular.alpha));
1654	device->setMaterialEmission(sw::Color<float>(materialEmission.red, materialEmission.green, materialEmission.blue, materialEmission.alpha));
1655
1656    device->setDiffuseMaterialSource(sw::MATERIAL_MATERIAL);
1657	device->setSpecularMaterialSource(sw::MATERIAL_MATERIAL);
1658	device->setAmbientMaterialSource(sw::MATERIAL_MATERIAL);
1659	device->setEmissiveMaterialSource(sw::MATERIAL_MATERIAL);
1660
1661    device->setProjectionMatrix(projectionStack.current());
1662    device->setModelMatrix(modelViewStack.current());
1663    device->setTextureMatrix(0, textureStack0.current());
1664	device->setTextureMatrix(1, textureStack1.current());
1665	device->setTextureTransform(0, textureStack0.isIdentity() ? 0 : 4, false);
1666	device->setTextureTransform(1, textureStack1.isIdentity() ? 0 : 4, false);
1667}
1668
1669GLenum Context::applyVertexBuffer(GLint base, GLint first, GLsizei count)
1670{
1671    TranslatedAttribute attributes[MAX_VERTEX_ATTRIBS];
1672
1673    GLenum err = mVertexDataManager->prepareVertexData(first, count, attributes);
1674    if(err != GL_NO_ERROR)
1675    {
1676        return err;
1677    }
1678
1679	device->resetInputStreams(false);
1680
1681    for(int i = 0; i < MAX_VERTEX_ATTRIBS; i++)
1682	{
1683		sw::Resource *resource = attributes[i].vertexBuffer;
1684		const void *buffer = (char*)resource->data() + attributes[i].offset;
1685
1686		int stride = attributes[i].stride;
1687
1688		buffer = (char*)buffer + stride * base;
1689
1690		sw::Stream attribute(resource, buffer, stride);
1691
1692		attribute.type = attributes[i].type;
1693		attribute.count = attributes[i].count;
1694		attribute.normalized = attributes[i].normalized;
1695
1696		device->setInputStream(i, attribute);
1697	}
1698
1699	return GL_NO_ERROR;
1700}
1701
1702// Applies the indices and element array bindings
1703GLenum Context::applyIndexBuffer(const void *indices, GLsizei count, GLenum mode, GLenum type, TranslatedIndexData *indexInfo)
1704{
1705    GLenum err = mIndexDataManager->prepareIndexData(type, count, mState.elementArrayBuffer.get(), indices, indexInfo);
1706
1707    if(err == GL_NO_ERROR)
1708    {
1709        device->setIndexBuffer(indexInfo->indexBuffer);
1710    }
1711
1712    return err;
1713}
1714
1715void Context::applyTextures()
1716{
1717    for(int samplerIndex = 0; samplerIndex < MAX_TEXTURE_UNITS; samplerIndex++)
1718    {
1719        Texture *texture = getSamplerTexture(samplerIndex, TEXTURE_2D);
1720
1721		if(texture2D && texture->isSamplerComplete())
1722        {
1723            GLenum wrapS = texture->getWrapS();
1724            GLenum wrapT = texture->getWrapT();
1725            GLenum texFilter = texture->getMinFilter();
1726            GLenum magFilter = texture->getMagFilter();
1727			GLfloat maxAnisotropy = texture->getMaxAnisotropy();
1728
1729			device->setAddressingModeU(sw::SAMPLER_PIXEL, samplerIndex, es2sw::ConvertTextureWrap(wrapS));
1730            device->setAddressingModeV(sw::SAMPLER_PIXEL, samplerIndex, es2sw::ConvertTextureWrap(wrapT));
1731
1732			sw::FilterType minFilter;
1733			sw::MipmapType mipFilter;
1734            es2sw::ConvertMinFilter(texFilter, &minFilter, &mipFilter, maxAnisotropy);
1735		//	ASSERT(minFilter == es2sw::ConvertMagFilter(magFilter));
1736
1737			device->setTextureFilter(sw::SAMPLER_PIXEL, samplerIndex, minFilter);
1738		//	device->setTextureFilter(sw::SAMPLER_PIXEL, samplerIndex, es2sw::ConvertMagFilter(magFilter));
1739			device->setMipmapFilter(sw::SAMPLER_PIXEL, samplerIndex, mipFilter);
1740			device->setMaxAnisotropy(sw::SAMPLER_PIXEL, samplerIndex, maxAnisotropy);
1741
1742			applyTexture(samplerIndex, texture);
1743
1744			device->setStageOperation(samplerIndex, sw::TextureStage::STAGE_MODULATE);
1745            device->setFirstArgument(samplerIndex, sw::TextureStage::SOURCE_TEXTURE);
1746            device->setSecondArgument(samplerIndex, sw::TextureStage::SOURCE_CURRENT);
1747
1748            device->setStageOperationAlpha(samplerIndex, sw::TextureStage::STAGE_MODULATE);
1749            device->setFirstArgumentAlpha(samplerIndex, sw::TextureStage::SOURCE_TEXTURE);
1750            device->setSecondArgumentAlpha(samplerIndex, sw::TextureStage::SOURCE_CURRENT);
1751        }
1752        else
1753        {
1754            applyTexture(samplerIndex, 0);
1755
1756			device->setStageOperation(samplerIndex, sw::TextureStage::STAGE_SELECTARG1);
1757            device->setFirstArgument(samplerIndex, sw::TextureStage::SOURCE_CURRENT);
1758            device->setSecondArgument(samplerIndex, sw::TextureStage::SOURCE_CURRENT);
1759
1760            device->setStageOperationAlpha(samplerIndex, sw::TextureStage::STAGE_SELECTARG1);
1761            device->setFirstArgumentAlpha(samplerIndex, sw::TextureStage::SOURCE_CURRENT);
1762            device->setSecondArgumentAlpha(samplerIndex, sw::TextureStage::SOURCE_CURRENT);
1763        }
1764    }
1765}
1766
1767void Context::applyTexture(int index, Texture *baseTexture)
1768{
1769	sw::Resource *resource = 0;
1770
1771	if(baseTexture)
1772	{
1773		resource = baseTexture->getResource();
1774	}
1775
1776	device->setTextureResource(index, resource);
1777
1778	if(baseTexture)
1779	{
1780		int levelCount = baseTexture->getLevelCount();
1781
1782		if(baseTexture->getTarget() == GL_TEXTURE_2D || baseTexture->getTarget() == GL_TEXTURE_EXTERNAL_OES)
1783		{
1784			Texture2D *texture = static_cast<Texture2D*>(baseTexture);
1785
1786			for(int mipmapLevel = 0; mipmapLevel < MIPMAP_LEVELS; mipmapLevel++)
1787			{
1788				int surfaceLevel = mipmapLevel;
1789
1790				if(surfaceLevel < 0)
1791				{
1792					surfaceLevel = 0;
1793				}
1794				else if(surfaceLevel >= levelCount)
1795				{
1796					surfaceLevel = levelCount - 1;
1797				}
1798
1799				egl::Image *surface = texture->getImage(surfaceLevel);
1800				device->setTextureLevel(index, 0, mipmapLevel, surface, sw::TEXTURE_2D);
1801			}
1802		}
1803		else UNIMPLEMENTED();
1804	}
1805	else
1806	{
1807		device->setTextureLevel(index, 0, 0, 0, sw::TEXTURE_NULL);
1808	}
1809}
1810
1811void Context::readPixels(GLint x, GLint y, GLsizei width, GLsizei height,
1812                         GLenum format, GLenum type, GLsizei *bufSize, void* pixels)
1813{
1814    Framebuffer *framebuffer = getFramebuffer();
1815	int framebufferWidth, framebufferHeight, framebufferSamples;
1816
1817    if(framebuffer->completeness(framebufferWidth, framebufferHeight, framebufferSamples) != GL_FRAMEBUFFER_COMPLETE_OES)
1818    {
1819        return error(GL_INVALID_FRAMEBUFFER_OPERATION_OES);
1820    }
1821
1822    if(getFramebufferHandle() != 0 && framebufferSamples != 0)
1823    {
1824        return error(GL_INVALID_OPERATION);
1825    }
1826
1827	if(format != GL_RGBA || type != GL_UNSIGNED_BYTE)
1828	{
1829		if(format != framebuffer->getImplementationColorReadFormat() || type != framebuffer->getImplementationColorReadType())
1830		{
1831			return error(GL_INVALID_OPERATION);
1832		}
1833	}
1834
1835	GLsizei outputPitch = ComputePitch(width, format, type, mState.packAlignment);
1836
1837	// Sized query sanity check
1838    if(bufSize)
1839    {
1840        int requiredSize = outputPitch * height;
1841        if(requiredSize > *bufSize)
1842        {
1843            return error(GL_INVALID_OPERATION);
1844        }
1845    }
1846
1847    egl::Image *renderTarget = framebuffer->getRenderTarget();
1848
1849    if(!renderTarget)
1850    {
1851        return error(GL_OUT_OF_MEMORY);
1852    }
1853
1854	sw::Rect rect = {x, y, x + width, y + height};
1855	rect.clip(0, 0, renderTarget->getWidth(), renderTarget->getHeight());
1856
1857    unsigned char *source = (unsigned char*)renderTarget->lock(rect.x0, rect.y0, sw::LOCK_READONLY);
1858    unsigned char *dest = (unsigned char*)pixels;
1859    int inputPitch = (int)renderTarget->getPitch();
1860
1861    for(int j = 0; j < rect.y1 - rect.y0; j++)
1862    {
1863		unsigned short *dest16 = (unsigned short*)dest;
1864		unsigned int *dest32 = (unsigned int*)dest;
1865
1866		if(renderTarget->getInternalFormat() == sw::FORMAT_A8R8G8B8 &&
1867           format == GL_RGBA && type == GL_UNSIGNED_BYTE)
1868        {
1869            for(int i = 0; i < rect.x1 - rect.x0; i++)
1870			{
1871				unsigned int argb = *(unsigned int*)(source + 4 * i);
1872
1873				dest32[i] = (argb & 0xFF00FF00) | ((argb & 0x000000FF) << 16) | ((argb & 0x00FF0000) >> 16);
1874			}
1875        }
1876        else if(renderTarget->getInternalFormat() == sw::FORMAT_A8R8G8B8 &&
1877                format == GL_BGRA_EXT && type == GL_UNSIGNED_BYTE)
1878        {
1879            memcpy(dest, source, (rect.x1 - rect.x0) * 4);
1880        }
1881		else
1882		{
1883			for(int i = 0; i < rect.x1 - rect.x0; i++)
1884			{
1885				float r;
1886				float g;
1887				float b;
1888				float a;
1889
1890				switch(renderTarget->getInternalFormat())
1891				{
1892				case sw::FORMAT_R5G6B5:
1893					{
1894						unsigned short rgb = *(unsigned short*)(source + 2 * i);
1895
1896						a = 1.0f;
1897						b = (rgb & 0x001F) * (1.0f / 0x001F);
1898						g = (rgb & 0x07E0) * (1.0f / 0x07E0);
1899						r = (rgb & 0xF800) * (1.0f / 0xF800);
1900					}
1901					break;
1902				case sw::FORMAT_A1R5G5B5:
1903					{
1904						unsigned short argb = *(unsigned short*)(source + 2 * i);
1905
1906						a = (argb & 0x8000) ? 1.0f : 0.0f;
1907						b = (argb & 0x001F) * (1.0f / 0x001F);
1908						g = (argb & 0x03E0) * (1.0f / 0x03E0);
1909						r = (argb & 0x7C00) * (1.0f / 0x7C00);
1910					}
1911					break;
1912				case sw::FORMAT_A8R8G8B8:
1913					{
1914						unsigned int argb = *(unsigned int*)(source + 4 * i);
1915
1916						a = (argb & 0xFF000000) * (1.0f / 0xFF000000);
1917						b = (argb & 0x000000FF) * (1.0f / 0x000000FF);
1918						g = (argb & 0x0000FF00) * (1.0f / 0x0000FF00);
1919						r = (argb & 0x00FF0000) * (1.0f / 0x00FF0000);
1920					}
1921					break;
1922				case sw::FORMAT_X8R8G8B8:
1923					{
1924						unsigned int xrgb = *(unsigned int*)(source + 4 * i);
1925
1926						a = 1.0f;
1927						b = (xrgb & 0x000000FF) * (1.0f / 0x000000FF);
1928						g = (xrgb & 0x0000FF00) * (1.0f / 0x0000FF00);
1929						r = (xrgb & 0x00FF0000) * (1.0f / 0x00FF0000);
1930					}
1931					break;
1932				case sw::FORMAT_A2R10G10B10:
1933					{
1934						unsigned int argb = *(unsigned int*)(source + 4 * i);
1935
1936						a = (argb & 0xC0000000) * (1.0f / 0xC0000000);
1937						b = (argb & 0x000003FF) * (1.0f / 0x000003FF);
1938						g = (argb & 0x000FFC00) * (1.0f / 0x000FFC00);
1939						r = (argb & 0x3FF00000) * (1.0f / 0x3FF00000);
1940					}
1941					break;
1942				case sw::FORMAT_A32B32G32R32F:
1943					{
1944						r = *((float*)(source + 16 * i) + 0);
1945						g = *((float*)(source + 16 * i) + 1);
1946						b = *((float*)(source + 16 * i) + 2);
1947						a = *((float*)(source + 16 * i) + 3);
1948					}
1949					break;
1950				case sw::FORMAT_A16B16G16R16F:
1951					{
1952						r = (float)*((sw::half*)(source + 8 * i) + 0);
1953						g = (float)*((sw::half*)(source + 8 * i) + 1);
1954						b = (float)*((sw::half*)(source + 8 * i) + 2);
1955						a = (float)*((sw::half*)(source + 8 * i) + 3);
1956					}
1957					break;
1958				default:
1959					UNIMPLEMENTED();   // FIXME
1960					UNREACHABLE();
1961				}
1962
1963				switch(format)
1964				{
1965				case GL_RGBA:
1966					switch(type)
1967					{
1968					case GL_UNSIGNED_BYTE:
1969						dest[4 * i + 0] = (unsigned char)(255 * r + 0.5f);
1970						dest[4 * i + 1] = (unsigned char)(255 * g + 0.5f);
1971						dest[4 * i + 2] = (unsigned char)(255 * b + 0.5f);
1972						dest[4 * i + 3] = (unsigned char)(255 * a + 0.5f);
1973						break;
1974					default: UNREACHABLE();
1975					}
1976					break;
1977				case GL_BGRA_EXT:
1978					switch(type)
1979					{
1980					case GL_UNSIGNED_BYTE:
1981						dest[4 * i + 0] = (unsigned char)(255 * b + 0.5f);
1982						dest[4 * i + 1] = (unsigned char)(255 * g + 0.5f);
1983						dest[4 * i + 2] = (unsigned char)(255 * r + 0.5f);
1984						dest[4 * i + 3] = (unsigned char)(255 * a + 0.5f);
1985						break;
1986					case GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT:
1987						// According to the desktop GL spec in the "Transfer of Pixel Rectangles" section
1988						// this type is packed as follows:
1989						//   15   14   13   12   11   10    9    8    7    6    5    4    3    2    1    0
1990						//  --------------------------------------------------------------------------------
1991						// |       4th         |        3rd         |        2nd        |   1st component   |
1992						//  --------------------------------------------------------------------------------
1993						// in the case of BGRA_EXT, B is the first component, G the second, and so forth.
1994						dest16[i] =
1995							((unsigned short)(15 * a + 0.5f) << 12)|
1996							((unsigned short)(15 * r + 0.5f) << 8) |
1997							((unsigned short)(15 * g + 0.5f) << 4) |
1998							((unsigned short)(15 * b + 0.5f) << 0);
1999						break;
2000					case GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT:
2001						// According to the desktop GL spec in the "Transfer of Pixel Rectangles" section
2002						// this type is packed as follows:
2003						//   15   14   13   12   11   10    9    8    7    6    5    4    3    2    1    0
2004						//  --------------------------------------------------------------------------------
2005						// | 4th |          3rd           |           2nd          |      1st component     |
2006						//  --------------------------------------------------------------------------------
2007						// in the case of BGRA_EXT, B is the first component, G the second, and so forth.
2008						dest16[i] =
2009							((unsigned short)(     a + 0.5f) << 15) |
2010							((unsigned short)(31 * r + 0.5f) << 10) |
2011							((unsigned short)(31 * g + 0.5f) << 5) |
2012							((unsigned short)(31 * b + 0.5f) << 0);
2013						break;
2014					default: UNREACHABLE();
2015					}
2016					break;
2017				case GL_RGB:
2018					switch(type)
2019					{
2020					case GL_UNSIGNED_SHORT_5_6_5:
2021						dest16[i] =
2022							((unsigned short)(31 * b + 0.5f) << 0) |
2023							((unsigned short)(63 * g + 0.5f) << 5) |
2024							((unsigned short)(31 * r + 0.5f) << 11);
2025						break;
2026					default: UNREACHABLE();
2027					}
2028					break;
2029				default: UNREACHABLE();
2030				}
2031			}
2032        }
2033
2034		source += inputPitch;
2035		dest += outputPitch;
2036    }
2037
2038	renderTarget->unlock();
2039	renderTarget->release();
2040}
2041
2042void Context::clear(GLbitfield mask)
2043{
2044    Framebuffer *framebuffer = getFramebuffer();
2045
2046    if(!framebuffer || framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE_OES)
2047    {
2048        return error(GL_INVALID_FRAMEBUFFER_OPERATION_OES);
2049    }
2050
2051    if(!applyRenderTarget())
2052    {
2053        return;
2054    }
2055
2056	unsigned int color = (unorm<8>(mState.colorClearValue.alpha) << 24) |
2057                         (unorm<8>(mState.colorClearValue.red) << 16) |
2058                         (unorm<8>(mState.colorClearValue.green) << 8) |
2059                         (unorm<8>(mState.colorClearValue.blue) << 0);
2060    float depth = clamp01(mState.depthClearValue);
2061    int stencil = mState.stencilClearValue & 0x000000FF;
2062
2063	if(mask & GL_COLOR_BUFFER_BIT)
2064	{
2065		unsigned int rgbaMask = (mState.colorMaskRed ? 0x1 : 0) |
2066		                        (mState.colorMaskGreen ? 0x2 : 0) |
2067		                        (mState.colorMaskBlue ? 0x4 : 0) |
2068		                        (mState.colorMaskAlpha ? 0x8 : 0);
2069
2070		if(rgbaMask != 0)
2071		{
2072			device->clearColor(color, rgbaMask);
2073		}
2074	}
2075
2076	if(mask & GL_DEPTH_BUFFER_BIT)
2077	{
2078		if(mState.depthMask != 0)
2079		{
2080			device->clearDepth(depth);
2081		}
2082	}
2083
2084	if(mask & GL_STENCIL_BUFFER_BIT)
2085	{
2086		if(mState.stencilWritemask != 0)
2087		{
2088			device->clearStencil(stencil, mState.stencilWritemask);
2089		}
2090	}
2091}
2092
2093void Context::drawArrays(GLenum mode, GLint first, GLsizei count)
2094{
2095    PrimitiveType primitiveType;
2096    int primitiveCount;
2097
2098    if(!es2sw::ConvertPrimitiveType(mode, count, primitiveType, primitiveCount))
2099        return error(GL_INVALID_ENUM);
2100
2101    if(primitiveCount <= 0)
2102    {
2103        return;
2104    }
2105
2106    if(!applyRenderTarget())
2107    {
2108        return;
2109    }
2110
2111    applyState(mode);
2112
2113    GLenum err = applyVertexBuffer(0, first, count);
2114    if(err != GL_NO_ERROR)
2115    {
2116        return error(err);
2117    }
2118
2119    applyTextures();
2120
2121    if(!cullSkipsDraw(mode))
2122    {
2123        device->drawPrimitive(primitiveType, primitiveCount);
2124    }
2125}
2126
2127void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices)
2128{
2129    if(!indices && !mState.elementArrayBuffer)
2130    {
2131        return error(GL_INVALID_OPERATION);
2132    }
2133
2134    PrimitiveType primitiveType;
2135    int primitiveCount;
2136
2137    if(!es2sw::ConvertPrimitiveType(mode, count, primitiveType, primitiveCount))
2138        return error(GL_INVALID_ENUM);
2139
2140    if(primitiveCount <= 0)
2141    {
2142        return;
2143    }
2144
2145    if(!applyRenderTarget())
2146    {
2147        return;
2148    }
2149
2150    applyState(mode);
2151
2152    TranslatedIndexData indexInfo;
2153    GLenum err = applyIndexBuffer(indices, count, mode, type, &indexInfo);
2154    if(err != GL_NO_ERROR)
2155    {
2156        return error(err);
2157    }
2158
2159    GLsizei vertexCount = indexInfo.maxIndex - indexInfo.minIndex + 1;
2160    err = applyVertexBuffer(-(int)indexInfo.minIndex, indexInfo.minIndex, vertexCount);
2161    if(err != GL_NO_ERROR)
2162    {
2163        return error(err);
2164    }
2165
2166    applyTextures();
2167
2168    if(!cullSkipsDraw(mode))
2169    {
2170		device->drawIndexedPrimitive(primitiveType, indexInfo.indexOffset, primitiveCount, IndexDataManager::typeSize(type));
2171    }
2172}
2173
2174void Context::finish()
2175{
2176	device->finish();
2177}
2178
2179void Context::flush()
2180{
2181    // We don't queue anything without processing it as fast as possible
2182}
2183
2184void Context::recordInvalidEnum()
2185{
2186    mInvalidEnum = true;
2187}
2188
2189void Context::recordInvalidValue()
2190{
2191    mInvalidValue = true;
2192}
2193
2194void Context::recordInvalidOperation()
2195{
2196    mInvalidOperation = true;
2197}
2198
2199void Context::recordOutOfMemory()
2200{
2201    mOutOfMemory = true;
2202}
2203
2204void Context::recordInvalidFramebufferOperation()
2205{
2206    mInvalidFramebufferOperation = true;
2207}
2208
2209// Get one of the recorded errors and clear its flag, if any.
2210// [OpenGL ES 2.0.24] section 2.5 page 13.
2211GLenum Context::getError()
2212{
2213    if(mInvalidEnum)
2214    {
2215        mInvalidEnum = false;
2216
2217        return GL_INVALID_ENUM;
2218    }
2219
2220    if(mInvalidValue)
2221    {
2222        mInvalidValue = false;
2223
2224        return GL_INVALID_VALUE;
2225    }
2226
2227    if(mInvalidOperation)
2228    {
2229        mInvalidOperation = false;
2230
2231        return GL_INVALID_OPERATION;
2232    }
2233
2234    if(mOutOfMemory)
2235    {
2236        mOutOfMemory = false;
2237
2238        return GL_OUT_OF_MEMORY;
2239    }
2240
2241    if(mInvalidFramebufferOperation)
2242    {
2243        mInvalidFramebufferOperation = false;
2244
2245        return GL_INVALID_FRAMEBUFFER_OPERATION_OES;
2246    }
2247
2248    return GL_NO_ERROR;
2249}
2250
2251int Context::getSupportedMultiSampleDepth(sw::Format format, int requested)
2252{
2253    if(requested <= 1)
2254    {
2255        return 1;
2256    }
2257
2258	if(requested == 2)
2259	{
2260		return 2;
2261	}
2262
2263	return 4;
2264}
2265
2266void Context::detachBuffer(GLuint buffer)
2267{
2268    // [OpenGL ES 2.0.24] section 2.9 page 22:
2269    // If a buffer object is deleted while it is bound, all bindings to that object in the current context
2270    // (i.e. in the thread that called Delete-Buffers) are reset to zero.
2271
2272    if(mState.arrayBuffer.id() == buffer)
2273    {
2274        mState.arrayBuffer.set(NULL);
2275    }
2276
2277    if(mState.elementArrayBuffer.id() == buffer)
2278    {
2279        mState.elementArrayBuffer.set(NULL);
2280    }
2281
2282    for(int attribute = 0; attribute < MAX_VERTEX_ATTRIBS; attribute++)
2283    {
2284        if(mState.vertexAttribute[attribute].mBoundBuffer.id() == buffer)
2285        {
2286            mState.vertexAttribute[attribute].mBoundBuffer.set(NULL);
2287        }
2288    }
2289}
2290
2291void Context::detachTexture(GLuint texture)
2292{
2293    // [OpenGL ES 2.0.24] section 3.8 page 84:
2294    // If a texture object is deleted, it is as if all texture units which are bound to that texture object are
2295    // rebound to texture object zero
2296
2297    for(int type = 0; type < TEXTURE_TYPE_COUNT; type++)
2298    {
2299        for(int sampler = 0; sampler < MAX_TEXTURE_UNITS; sampler++)
2300        {
2301            if(mState.samplerTexture[type][sampler].id() == texture)
2302            {
2303                mState.samplerTexture[type][sampler].set(NULL);
2304            }
2305        }
2306    }
2307
2308    // [OpenGL ES 2.0.24] section 4.4 page 112:
2309    // If a texture object is deleted while its image is attached to the currently bound framebuffer, then it is
2310    // as if FramebufferTexture2D had been called, with a texture of 0, for each attachment point to which this
2311    // image was attached in the currently bound framebuffer.
2312
2313    Framebuffer *framebuffer = getFramebuffer();
2314
2315    if(framebuffer)
2316    {
2317        framebuffer->detachTexture(texture);
2318    }
2319}
2320
2321void Context::detachFramebuffer(GLuint framebuffer)
2322{
2323    // [OpenGL ES 2.0.24] section 4.4 page 107:
2324    // If a framebuffer that is currently bound to the target FRAMEBUFFER is deleted, it is as though
2325    // BindFramebuffer had been executed with the target of FRAMEBUFFER and framebuffer of zero.
2326
2327    if(mState.framebuffer == framebuffer)
2328    {
2329        bindFramebuffer(0);
2330    }
2331}
2332
2333void Context::detachRenderbuffer(GLuint renderbuffer)
2334{
2335    // [OpenGL ES 2.0.24] section 4.4 page 109:
2336    // If a renderbuffer that is currently bound to RENDERBUFFER is deleted, it is as though BindRenderbuffer
2337    // had been executed with the target RENDERBUFFER and name of zero.
2338
2339    if(mState.renderbuffer.id() == renderbuffer)
2340    {
2341        bindRenderbuffer(0);
2342    }
2343
2344    // [OpenGL ES 2.0.24] section 4.4 page 111:
2345    // If a renderbuffer object is deleted while its image is attached to the currently bound framebuffer,
2346    // then it is as if FramebufferRenderbuffer had been called, with a renderbuffer of 0, for each attachment
2347    // point to which this image was attached in the currently bound framebuffer.
2348
2349    Framebuffer *framebuffer = getFramebuffer();
2350
2351    if(framebuffer)
2352    {
2353        framebuffer->detachRenderbuffer(renderbuffer);
2354    }
2355}
2356
2357bool Context::cullSkipsDraw(GLenum drawMode)
2358{
2359    return mState.cullFace && mState.cullMode == GL_FRONT_AND_BACK && isTriangleMode(drawMode);
2360}
2361
2362bool Context::isTriangleMode(GLenum drawMode)
2363{
2364    switch (drawMode)
2365    {
2366      case GL_TRIANGLES:
2367      case GL_TRIANGLE_FAN:
2368      case GL_TRIANGLE_STRIP:
2369        return true;
2370      case GL_POINTS:
2371      case GL_LINES:
2372      case GL_LINE_LOOP:
2373      case GL_LINE_STRIP:
2374        return false;
2375      default: UNREACHABLE();
2376    }
2377
2378    return false;
2379}
2380
2381void Context::setVertexAttrib(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
2382{
2383    ASSERT(index < MAX_VERTEX_ATTRIBS);
2384
2385    mState.vertexAttribute[index].mCurrentValue[0] = x;
2386    mState.vertexAttribute[index].mCurrentValue[1] = y;
2387    mState.vertexAttribute[index].mCurrentValue[2] = z;
2388    mState.vertexAttribute[index].mCurrentValue[3] = w;
2389
2390    mVertexDataManager->dirtyCurrentValue(index);
2391}
2392
2393void Context::bindTexImage(egl::Surface *surface)
2394{
2395	es1::Texture2D *textureObject = getTexture2D();
2396
2397    if(textureObject)
2398    {
2399		textureObject->bindTexImage(surface);
2400	}
2401}
2402
2403EGLenum Context::validateSharedImage(EGLenum target, GLuint name, GLuint textureLevel)
2404{
2405    switch(target)
2406    {
2407    case EGL_GL_TEXTURE_2D_KHR:
2408        break;
2409    case EGL_GL_RENDERBUFFER_KHR:
2410        break;
2411    default:
2412        return EGL_BAD_PARAMETER;
2413    }
2414
2415    if(textureLevel >= IMPLEMENTATION_MAX_TEXTURE_LEVELS)
2416    {
2417        return EGL_BAD_MATCH;
2418    }
2419
2420	if(target == EGL_GL_TEXTURE_2D_KHR)
2421    {
2422        Texture *texture = getTexture(name);
2423
2424        if(!texture || texture->getTarget() != GL_TEXTURE_2D)
2425        {
2426            return EGL_BAD_PARAMETER;
2427        }
2428
2429        if(texture->isShared(GL_TEXTURE_2D, textureLevel))   // Bound to an EGLSurface or already an EGLImage sibling
2430        {
2431            return EGL_BAD_ACCESS;
2432        }
2433
2434        if(textureLevel != 0 && !texture->isSamplerComplete())
2435        {
2436            return EGL_BAD_PARAMETER;
2437        }
2438
2439        if(textureLevel == 0 && !(texture->isSamplerComplete() && texture->getLevelCount() == 1))
2440        {
2441            return EGL_BAD_PARAMETER;
2442        }
2443    }
2444    else if(target == EGL_GL_RENDERBUFFER_KHR)
2445    {
2446        Renderbuffer *renderbuffer = getRenderbuffer(name);
2447
2448        if(!renderbuffer)
2449        {
2450            return EGL_BAD_PARAMETER;
2451        }
2452
2453        if(renderbuffer->isShared())   // Already an EGLImage sibling
2454        {
2455            return EGL_BAD_ACCESS;
2456        }
2457    }
2458    else UNREACHABLE();
2459
2460	return EGL_SUCCESS;
2461}
2462
2463egl::Image *Context::createSharedImage(EGLenum target, GLuint name, GLuint textureLevel)
2464{
2465    if(target == EGL_GL_TEXTURE_2D_KHR)
2466    {
2467        es1::Texture *texture = getTexture(name);
2468
2469        return texture->createSharedImage(GL_TEXTURE_2D, textureLevel);
2470    }
2471    else if(target == EGL_GL_RENDERBUFFER_KHR)
2472    {
2473        es1::Renderbuffer *renderbuffer = getRenderbuffer(name);
2474
2475        return renderbuffer->createSharedImage();
2476    }
2477    else UNREACHABLE();
2478
2479	return 0;
2480}
2481
2482Device *Context::getDevice()
2483{
2484	return device;
2485}
2486
2487void Context::setMatrixMode(GLenum mode)
2488{
2489    matrixMode = mode;
2490}
2491
2492sw::MatrixStack &Context::currentMatrixStack()
2493{
2494	switch(matrixMode)
2495	{
2496	case GL_MODELVIEW:
2497		return modelViewStack;
2498	case GL_PROJECTION:
2499		return projectionStack;
2500	case GL_TEXTURE:
2501		switch(mState.activeSampler)
2502		{
2503		case 0: return textureStack0;
2504		case 1: return textureStack1;
2505		}
2506		break;
2507	}
2508
2509	UNREACHABLE();
2510	return textureStack0;
2511}
2512
2513void Context::loadIdentity()
2514{
2515	currentMatrixStack().identity();
2516}
2517
2518void Context::load(const GLfloat *m)
2519{
2520    currentMatrixStack().load(m);
2521}
2522
2523void Context::pushMatrix()
2524{
2525	if(!currentMatrixStack().push())
2526	{
2527		return error(GL_STACK_OVERFLOW);
2528	}
2529}
2530
2531void Context::popMatrix()
2532{
2533    if(!currentMatrixStack().pop())
2534	{
2535		return error(GL_STACK_OVERFLOW);
2536	}
2537}
2538
2539void Context::rotate(GLfloat angle, GLfloat x, GLfloat y, GLfloat z)
2540{
2541    currentMatrixStack().rotate(angle, x, y, z);
2542}
2543
2544void Context::translate(GLfloat x, GLfloat y, GLfloat z)
2545{
2546    currentMatrixStack().translate(x, y, z);
2547}
2548
2549void Context::scale(GLfloat x, GLfloat y, GLfloat z)
2550{
2551    currentMatrixStack().scale(x, y, z);
2552}
2553
2554void Context::multiply(const GLfloat *m)
2555{
2556    currentMatrixStack().multiply(m);
2557}
2558
2559void Context::ortho(GLfloat left, GLfloat right, GLfloat bottom, GLfloat top, GLfloat zNear, GLfloat zFar)
2560{
2561	currentMatrixStack().ortho(left, right, bottom, top, zNear, zFar);
2562}
2563
2564void Context::clientActiveTexture(GLenum texture)
2565{
2566	clientTexture = texture;
2567}
2568
2569GLenum Context::getClientActiveTexture() const
2570{
2571	return clientTexture;
2572}
2573
2574unsigned int Context::getActiveTexture() const
2575{
2576	return mState.activeSampler;
2577}
2578
2579}
2580
2581// Exported functions for use by EGL
2582extern "C"
2583{
2584	es1::Context *glCreateContext(const egl::Config *config, const es1::Context *shareContext)
2585	{
2586		return new es1::Context(config, shareContext);
2587	}
2588}
2589