You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
1071 lines
40 KiB
1071 lines
40 KiB
/*
|
|
* Copyright (C) 2011 The Android Open Source Project
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
#ifndef _GL_CLIENT_STATE_H_
|
|
#define _GL_CLIENT_STATE_H_
|
|
|
|
#define GL_API
|
|
#ifndef ANDROID
|
|
#define GL_APIENTRY
|
|
#define GL_APIENTRYP
|
|
#endif
|
|
|
|
#ifdef GFXSTREAM
|
|
#include "StateTrackingSupport.h"
|
|
#endif
|
|
|
|
#include "TextureSharedData.h"
|
|
|
|
#include <GLES/gl.h>
|
|
#include <GLES/glext.h>
|
|
#include <GLES2/gl2.h>
|
|
#include <GLES2/gl2ext.h>
|
|
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include "ErrorLog.h"
|
|
#include "codec_defs.h"
|
|
|
|
#include <vector>
|
|
#include <map>
|
|
#include <set>
|
|
#include <string>
|
|
|
|
// Caps of host driver that make it easy to validate stuff
|
|
struct HostDriverCaps {
|
|
// ES 2
|
|
int max_vertex_attribs;
|
|
int max_combined_texture_image_units;
|
|
int max_color_attachments;
|
|
|
|
int max_texture_size;
|
|
int max_texture_size_cube_map;
|
|
int max_renderbuffer_size;
|
|
|
|
// ES 3.0
|
|
int max_draw_buffers;
|
|
|
|
int ubo_offset_alignment;
|
|
int max_uniform_buffer_bindings;
|
|
int max_transform_feedback_separate_attribs;
|
|
|
|
int max_texture_size_3d;
|
|
int max_array_texture_layers;
|
|
|
|
// ES 3.1
|
|
int max_atomic_counter_buffer_bindings;
|
|
int max_shader_storage_buffer_bindings;
|
|
int max_vertex_attrib_bindings;
|
|
int max_vertex_attrib_stride;
|
|
int ssbo_offset_alignment;
|
|
};
|
|
|
|
// Tracking framebuffer objects:
|
|
// which framebuffer is bound,
|
|
// and which texture names
|
|
// are currently bound to which attachment points.
|
|
struct FboProps {
|
|
GLuint name;
|
|
bool previouslyBound;
|
|
bool completenessDirty;
|
|
GLenum cachedCompleteness;
|
|
std::vector<GLuint> colorAttachmenti_textures;
|
|
std::vector<GLint> colorAttachmenti_texture_levels;
|
|
std::vector<GLint> colorAttachmenti_texture_layers;
|
|
|
|
GLint depthAttachment_texture_level;
|
|
GLint depthAttachment_texture_layer;
|
|
GLint stencilAttachment_texture_level;
|
|
GLint stencilAttachment_texture_layer;
|
|
|
|
GLuint depthAttachment_texture;
|
|
GLuint stencilAttachment_texture;
|
|
GLuint depthstencilAttachment_texture;
|
|
|
|
std::vector<bool> colorAttachmenti_hasTex;
|
|
bool depthAttachment_hasTexObj;
|
|
bool stencilAttachment_hasTexObj;
|
|
bool depthstencilAttachment_hasTexObj;
|
|
|
|
std::vector<GLuint> colorAttachmenti_rbos;
|
|
GLuint depthAttachment_rbo;
|
|
GLuint stencilAttachment_rbo;
|
|
GLuint depthstencilAttachment_rbo;
|
|
|
|
std::vector<bool> colorAttachmenti_hasRbo;
|
|
bool depthAttachment_hasRbo;
|
|
bool stencilAttachment_hasRbo;
|
|
bool depthstencilAttachment_hasRbo;
|
|
|
|
GLuint defaultWidth;
|
|
GLuint defaultHeight;
|
|
};
|
|
|
|
// Enum for describing whether a framebuffer attachment
|
|
// is a texture or renderbuffer.
|
|
enum FboAttachmentType {
|
|
FBO_ATTACHMENT_RENDERBUFFER = 0,
|
|
FBO_ATTACHMENT_TEXTURE = 1,
|
|
FBO_ATTACHMENT_NONE = 2
|
|
};
|
|
|
|
// Tracking FBO format
|
|
struct FboFormatInfo {
|
|
FboAttachmentType type;
|
|
GLenum rb_format;
|
|
GLsizei rb_multisamples;
|
|
bool rb_external;
|
|
|
|
GLint tex_internalformat;
|
|
GLenum tex_format;
|
|
GLenum tex_type;
|
|
GLsizei tex_multisamples;
|
|
GLint tex_level;
|
|
GLint tex_layer;
|
|
bool tex_external;
|
|
};
|
|
|
|
class GLClientState {
|
|
public:
|
|
// TODO: Unify everything in here
|
|
typedef enum {
|
|
Buffer,
|
|
TransformFeedback,
|
|
Sampler,
|
|
Query,
|
|
} ObjectType;
|
|
|
|
typedef enum {
|
|
VERTEX_LOCATION = 0,
|
|
NORMAL_LOCATION = 1,
|
|
COLOR_LOCATION = 2,
|
|
POINTSIZE_LOCATION = 3,
|
|
TEXCOORD0_LOCATION = 4,
|
|
TEXCOORD1_LOCATION = 5,
|
|
TEXCOORD2_LOCATION = 6,
|
|
TEXCOORD3_LOCATION = 7,
|
|
TEXCOORD4_LOCATION = 8,
|
|
TEXCOORD5_LOCATION = 9,
|
|
TEXCOORD6_LOCATION = 10,
|
|
TEXCOORD7_LOCATION = 11,
|
|
MATRIXINDEX_LOCATION = 12,
|
|
WEIGHT_LOCATION = 13,
|
|
LAST_LOCATION = 14
|
|
} StateLocation;
|
|
|
|
typedef struct {
|
|
GLint enabled;
|
|
GLint size;
|
|
GLenum type;
|
|
GLsizei stride;
|
|
void *data;
|
|
GLuint reloffset;
|
|
GLuint bufferObject;
|
|
GLenum glConst;
|
|
unsigned int elementSize;
|
|
bool enableDirty; // true if any enable state has changed since last draw
|
|
bool normalized;
|
|
GLuint divisor;
|
|
bool isInt;
|
|
int bindingindex;
|
|
} VertexAttribState;
|
|
|
|
struct BufferBinding {
|
|
GLintptr offset;
|
|
GLintptr stride;
|
|
GLintptr effectiveStride;
|
|
GLsizeiptr size;
|
|
GLuint buffer;
|
|
GLuint divisor;
|
|
GLint vertexAttribLoc;
|
|
};
|
|
|
|
typedef std::vector<VertexAttribState> VertexAttribStateVector;
|
|
typedef std::vector<BufferBinding> VertexAttribBindingVector;
|
|
|
|
struct VAOState {
|
|
VAOState(GLuint ibo, int nLoc, int nBindings) :
|
|
attribState(nLoc),
|
|
bindingState(nBindings),
|
|
element_array_buffer_binding(ibo),
|
|
element_array_buffer_binding_lastEncode(ibo) { }
|
|
VertexAttribStateVector attribState;
|
|
VertexAttribBindingVector bindingState;
|
|
GLuint element_array_buffer_binding;
|
|
GLuint element_array_buffer_binding_lastEncode;
|
|
int attributesNeedingUpdateForDraw[CODEC_MAX_VERTEX_ATTRIBUTES];
|
|
int numAttributesNeedingUpdateForDraw;
|
|
};
|
|
|
|
typedef std::map<GLuint, VAOState> VAOStateMap;
|
|
struct VAOStateRef {
|
|
VAOStateRef() { }
|
|
VAOStateRef(
|
|
VAOStateMap::iterator iter) : it(iter) { }
|
|
VAOState& vaoState() { return it->second; }
|
|
VertexAttribState& operator[](size_t k) { return it->second.attribState[k]; }
|
|
BufferBinding& bufferBinding(size_t k) { return it->second.bindingState[k]; }
|
|
VertexAttribBindingVector& bufferBindings() { return it->second.bindingState; }
|
|
const VertexAttribBindingVector& bufferBindings_const() const { return it->second.bindingState; }
|
|
GLuint vaoId() const { return it->first; }
|
|
GLuint& iboId() { return it->second.element_array_buffer_binding; }
|
|
GLuint& iboIdLastEncode() { return it->second.element_array_buffer_binding_lastEncode; }
|
|
VAOStateMap::iterator it;
|
|
};
|
|
|
|
typedef struct {
|
|
int unpack_alignment;
|
|
|
|
int unpack_row_length;
|
|
int unpack_image_height;
|
|
int unpack_skip_pixels;
|
|
int unpack_skip_rows;
|
|
int unpack_skip_images;
|
|
|
|
int pack_alignment;
|
|
|
|
int pack_row_length;
|
|
int pack_skip_pixels;
|
|
int pack_skip_rows;
|
|
} PixelStoreState;
|
|
|
|
enum {
|
|
MAX_TEXTURE_UNITS = 256,
|
|
};
|
|
|
|
public:
|
|
GLClientState();
|
|
GLClientState(int majorVersion, int minorVersion);
|
|
~GLClientState();
|
|
int nLocations() { return CODEC_MAX_VERTEX_ATTRIBUTES; }
|
|
const PixelStoreState *pixelStoreState() { return &m_pixelStore; }
|
|
int setPixelStore(GLenum param, GLint value);
|
|
GLuint currentVertexArrayObject() const { return m_currVaoState.vaoId(); }
|
|
const VertexAttribBindingVector& currentVertexBufferBindings() const {
|
|
return m_currVaoState.bufferBindings_const();
|
|
}
|
|
|
|
GLuint currentArrayVbo() { return m_arrayBuffer; }
|
|
GLuint currentIndexVbo() { return m_currVaoState.iboId(); }
|
|
void enable(int location, int state);
|
|
// Vertex array objects and vertex attributes
|
|
void addVertexArrayObjects(GLsizei n, GLuint* arrays);
|
|
void removeVertexArrayObjects(GLsizei n, const GLuint* arrays);
|
|
void addVertexArrayObject(GLuint name);
|
|
void removeVertexArrayObject(GLuint name);
|
|
void setVertexArrayObject(GLuint vao);
|
|
bool isVertexArrayObject(GLuint vao) const;
|
|
void setVertexAttribState(int location, int size, GLenum type, GLboolean normalized, GLsizei stride, const void *data, bool isInt = false);
|
|
void setVertexBindingDivisor(int bindingindex, GLuint divisor);
|
|
const BufferBinding& getCurrAttributeBindingInfo(int attribindex);
|
|
void setVertexAttribBinding(int attribindex, int bindingindex);
|
|
void setVertexAttribFormat(int location, int size, GLenum type, GLboolean normalized, GLuint reloffset, bool isInt = false);
|
|
void getVBOUsage(bool* hasClientArrays, bool* hasVBOs);
|
|
const VertexAttribState& getState(int location);
|
|
const VertexAttribState& getStateAndEnableDirty(int location, bool *enableChanged);
|
|
void updateEnableDirtyArrayForDraw();
|
|
VAOState& currentVaoState();
|
|
int getLocation(GLenum loc);
|
|
void setActiveTexture(int texUnit) {m_activeTexture = texUnit; };
|
|
int getActiveTexture() const { return m_activeTexture; }
|
|
|
|
void addBuffer(GLuint id);
|
|
void removeBuffer(GLuint id);
|
|
bool bufferIdExists(GLuint id) const;
|
|
void unBindBuffer(GLuint id);
|
|
|
|
void setBufferHostMapDirty(GLuint id, bool dirty);
|
|
bool isBufferHostMapDirty(GLuint id) const;
|
|
|
|
void setExistence(ObjectType type, bool exists, GLsizei count, const GLuint* ids);
|
|
bool queryExistence(ObjectType type, GLuint id) const;
|
|
bool samplerExists(GLuint id) const;
|
|
bool tryBind(GLenum target, GLuint id);
|
|
bool isBoundTargetValid(GLenum target);
|
|
bool isQueryBound(GLenum target);
|
|
bool isQueryObjectActive(GLuint id);
|
|
void setLastQueryTarget(GLenum target, GLuint id);
|
|
GLenum getLastQueryTarget(GLuint id);
|
|
|
|
static void onFenceCreated(GLsync sync);
|
|
static void onFenceDestroyed(GLsync sync);
|
|
static bool fenceExists(GLsync sync);
|
|
|
|
void setBoundPixelPackBufferDirtyForHostMap();
|
|
void setBoundTransformFeedbackBuffersDirtyForHostMap();
|
|
void setBoundShaderStorageBuffersDirtyForHostMap();
|
|
void setBoundAtomicCounterBuffersDirtyForHostMap();
|
|
|
|
int bindBuffer(GLenum target, GLuint id);
|
|
void bindIndexedBuffer(GLenum target, GLuint index, GLuint buffer, GLintptr offset, GLsizeiptr size, GLintptr stride, GLintptr effectiveStride);
|
|
int getMaxIndexedBufferBindings(GLenum target) const;
|
|
bool isNonIndexedBindNoOp(GLenum target, GLuint buffer);
|
|
bool isIndexedBindNoOp(GLenum target, GLuint index, GLuint buffer, GLintptr offset, GLsizeiptr size, GLintptr stride, GLintptr effectiveStride);
|
|
|
|
int getMaxTextureSize() const;
|
|
int getMaxTextureSize3D() const;
|
|
int getMaxTextureSizeCubeMap() const;
|
|
int getLog2MaxTextureSize() const;
|
|
|
|
void postDraw();
|
|
void postReadPixels();
|
|
void postDispatchCompute();
|
|
|
|
bool shouldSkipHostMapBuffer(GLenum target);
|
|
void onHostMappedBuffer(GLenum target);
|
|
|
|
int getBuffer(GLenum target);
|
|
GLuint getLastEncodedBufferBind(GLenum target);
|
|
void setLastEncodedBufferBind(GLenum target, GLuint id);
|
|
|
|
size_t pixelDataSize(GLsizei width, GLsizei height, GLsizei depth, GLenum format, GLenum type, int pack) const;
|
|
size_t pboNeededDataSize(GLsizei width, GLsizei height, GLsizei depth, GLenum format, GLenum type, int pack) const;
|
|
size_t clearBufferNumElts(GLenum buffer) const;
|
|
void getPackingOffsets2D(GLsizei width, GLsizei height, GLenum format, GLenum type, int* bpp, int* startOffset, int* pixelRowSize, int* totalRowSize, int* skipRows) const;
|
|
void getUnpackingOffsets2D(GLsizei width, GLsizei height, GLenum format, GLenum type, int* bpp, int* startOffset, int* pixelRowSize, int* totalRowSize, int* skipRows) const;
|
|
void getUnpackingOffsets3D(GLsizei width, GLsizei height, GLsizei depth, GLenum format, GLenum type, int* bpp, int* startOffset, int* pixelRowSize, int* totalRowSize, int* pixelImageSize, int* totalImageSize, int* skipRows, int* skipImages) const;
|
|
|
|
void setCurrentProgram(GLint program) { m_currentProgram = program; }
|
|
void setCurrentShaderProgram(GLint program) { m_currentShaderProgram = program; }
|
|
GLint currentProgram() const { return m_currentProgram; }
|
|
GLint currentShaderProgram() const { return m_currentShaderProgram; }
|
|
|
|
struct UniformBlockInfoKey {
|
|
GLuint program;
|
|
GLuint uniformBlockIndex;
|
|
};
|
|
struct UniformBlockInfoKeyCompare {
|
|
bool operator() (const UniformBlockInfoKey& a,
|
|
const UniformBlockInfoKey& b) const {
|
|
if (a.program != b.program) return a.program < b.program;
|
|
if (a.uniformBlockIndex != b.uniformBlockIndex) return a.uniformBlockIndex < b.uniformBlockIndex;
|
|
return false;
|
|
}
|
|
};
|
|
struct UniformBlockUniformInfo {
|
|
size_t numActiveUniforms;
|
|
};
|
|
|
|
typedef std::map<UniformBlockInfoKey, UniformBlockUniformInfo, UniformBlockInfoKeyCompare> UniformBlockInfoMap;
|
|
UniformBlockInfoMap m_uniformBlockInfoMap;
|
|
|
|
void setNumActiveUniformsInUniformBlock(GLuint program, GLuint uniformBlockIndex, GLint numActiveUniforms);
|
|
size_t numActiveUniformsInUniformBlock(GLuint program, GLuint uniformBlockIndex) const;
|
|
|
|
typedef std::map<GLuint, GLuint> ProgramPipelineMap;
|
|
typedef ProgramPipelineMap::iterator ProgramPipelineIterator;
|
|
void associateProgramWithPipeline(GLuint program, GLuint pipeline);
|
|
ProgramPipelineIterator programPipelineBegin();
|
|
ProgramPipelineIterator programPipelineEnd();
|
|
|
|
/* OES_EGL_image_external
|
|
*
|
|
* These functions manipulate GL state which interacts with the
|
|
* OES_EGL_image_external extension, to support client-side emulation on
|
|
* top of host implementations that don't have it.
|
|
*
|
|
* Most of these calls should only be used with TEXTURE_2D or
|
|
* TEXTURE_EXTERNAL_OES texture targets; TEXTURE_CUBE_MAP or other extension
|
|
* targets should bypass this. An exception is bindTexture(), which should
|
|
* see all glBindTexture() calls for any target.
|
|
*/
|
|
|
|
// glActiveTexture(GL_TEXTURE0 + i)
|
|
// Sets the active texture unit. Up to MAX_TEXTURE_UNITS are supported.
|
|
GLenum setActiveTextureUnit(GLenum texture);
|
|
GLenum getActiveTextureUnit() const;
|
|
|
|
// glEnable(GL_TEXTURE_(2D|EXTERNAL_OES))
|
|
void enableTextureTarget(GLenum target);
|
|
|
|
// glDisable(GL_TEXTURE_(2D|EXTERNAL_OES))
|
|
void disableTextureTarget(GLenum target);
|
|
|
|
bool bindSampler(GLuint unit, GLuint sampler);
|
|
bool isSamplerBindNoOp(GLuint unit, GLuint sampler);
|
|
void onDeleteSamplers(GLsizei n, const GLuint* samplers);
|
|
|
|
// Implements the target priority logic:
|
|
// * Return GL_TEXTURE_EXTERNAL_OES if enabled, else
|
|
// * Return GL_TEXTURE_2D if enabled, else
|
|
// * Return the allDisabled value.
|
|
// For some cases passing GL_TEXTURE_2D for allDisabled makes callee code
|
|
// simpler; for other cases passing a recognizable enum like GL_ZERO or
|
|
// GL_INVALID_ENUM is appropriate.
|
|
GLenum getPriorityEnabledTarget(GLenum allDisabled) const;
|
|
|
|
// glBindTexture(GL_TEXTURE_*, ...)
|
|
// Set the target binding of the active texture unit to texture. Returns
|
|
// GL_NO_ERROR on success or GL_INVALID_OPERATION if the texture has
|
|
// previously been bound to a different target. If firstUse is not NULL,
|
|
// it is set to indicate whether this is the first use of the texture.
|
|
// For accurate error detection, bindTexture should be called for *all*
|
|
// targets, not just 2D and EXTERNAL_OES.
|
|
GLenum bindTexture(GLenum target, GLuint texture, GLboolean* firstUse);
|
|
void setBoundEGLImage(GLenum target, GLeglImageOES image, int width, int height);
|
|
|
|
// Return the texture currently bound to GL_TEXTURE_(2D|EXTERNAL_OES).
|
|
GLuint getBoundTexture(GLenum target) const;
|
|
// Return bound framebuffer for target
|
|
GLuint getBoundFramebuffer(GLenum target) const;
|
|
|
|
// Check framebuffer completeness
|
|
GLenum checkFramebufferCompleteness(GLenum target);
|
|
// |currentSamples|: threads through the current sample count of attachments so far,
|
|
// for validating consistent number of samples across attachments
|
|
GLenum checkFramebufferAttachmentCompleteness(GLenum target, GLenum attachment, int* currentSamples) const;
|
|
|
|
// Other publicly-visible texture queries
|
|
GLenum queryTexLastBoundTarget(GLuint name) const;
|
|
GLenum queryTexFormat(GLuint name) const;
|
|
GLint queryTexInternalFormat(GLuint name) const;
|
|
GLsizei queryTexWidth(GLsizei level, GLuint name) const;
|
|
GLsizei queryTexHeight(GLsizei level, GLuint name) const;
|
|
GLsizei queryTexDepth(GLsizei level, GLuint name) const;
|
|
bool queryTexEGLImageBacked(GLuint name) const;
|
|
|
|
// For AMD GPUs, it is easy for the emulator to segfault
|
|
// (esp. in dEQP) when a cube map is defined using glCopyTexImage2D
|
|
// and uses GL_LUMINANCE as internal format.
|
|
// In particular, the segfault happens when negative components of
|
|
// cube maps are defined before positive ones,
|
|
// This procedure checks internal state to see if we have defined
|
|
// the positive component of a cube map already. If not, it returns
|
|
// which positive component needs to be defined first.
|
|
// If there is no need for the extra definition, 0 is returned.
|
|
GLenum copyTexImageLuminanceCubeMapAMDWorkaround(GLenum target, GLint level,
|
|
GLenum internalformat);
|
|
|
|
// Tracks the format of the currently bound texture.
|
|
// This is to pass dEQP tests for fbo completeness.
|
|
void setBoundTextureInternalFormat(GLenum target, GLint format);
|
|
void setBoundTextureFormat(GLenum target, GLenum format);
|
|
void setBoundTextureType(GLenum target, GLenum type);
|
|
void setBoundTextureDims(GLenum target, GLenum cubetarget, GLsizei level, GLsizei width, GLsizei height, GLsizei depth);
|
|
void setBoundTextureSamples(GLenum target, GLsizei samples);
|
|
void addTextureCubeMapImage(GLenum stateTarget, GLenum cubeTarget);
|
|
|
|
// glTexStorage2D disallows any change in texture format after it is set for a particular texture.
|
|
void setBoundTextureImmutableFormat(GLenum target);
|
|
bool isBoundTextureImmutableFormat(GLenum target) const;
|
|
bool isBoundTextureComplete(GLenum target) const;
|
|
|
|
// glDeleteTextures(...)
|
|
// Remove references to the to-be-deleted textures.
|
|
void deleteTextures(GLsizei n, const GLuint* textures);
|
|
|
|
// Render buffer objects
|
|
void addRenderbuffers(GLsizei n, GLuint* renderbuffers);
|
|
void removeRenderbuffers(GLsizei n, const GLuint* renderbuffers);
|
|
bool usedRenderbufferName(GLuint name) const;
|
|
void bindRenderbuffer(GLenum target, GLuint name);
|
|
GLuint boundRenderbuffer() const;
|
|
void setBoundRenderbufferFormat(GLenum format);
|
|
void setBoundRenderbufferSamples(GLsizei samples);
|
|
void setBoundRenderbufferDimensions(GLsizei width, GLsizei height);
|
|
void setBoundRenderbufferEGLImageBacked();
|
|
|
|
// Frame buffer objects
|
|
void addFramebuffers(GLsizei n, GLuint* framebuffers);
|
|
void removeFramebuffers(GLsizei n, const GLuint* framebuffers);
|
|
bool usedFramebufferName(GLuint name) const;
|
|
void bindFramebuffer(GLenum target, GLuint name);
|
|
void setCheckFramebufferStatus(GLenum target, GLenum status);
|
|
void setFramebufferParameter(GLenum target, GLenum pname, GLint param);
|
|
GLenum getCheckFramebufferStatus(GLenum target) const;
|
|
GLuint boundFramebuffer(GLenum target) const;
|
|
|
|
// Texture object -> FBO
|
|
void attachTextureObject(GLenum target, GLenum attachment, GLuint texture, GLint level, GLint layer);
|
|
GLuint getFboAttachmentTextureId(GLenum target, GLenum attachment) const;
|
|
|
|
// RBO -> FBO
|
|
void detachRbo(GLuint renderbuffer);
|
|
void detachRboFromFbo(GLenum target, GLenum attachment, GLuint renderbuffer);
|
|
void attachRbo(GLenum target, GLenum attachment, GLuint renderbuffer);
|
|
GLuint getFboAttachmentRboId(GLenum target, GLenum attachment) const;
|
|
|
|
// FBO attachments in general
|
|
bool attachmentHasObject(GLenum target, GLenum attachment) const;
|
|
GLuint objectOfAttachment(GLenum target, GLenum attachment) const;
|
|
|
|
// Dirty FBO completeness
|
|
void setFboCompletenessDirtyForTexture(GLuint texture);
|
|
void setFboCompletenessDirtyForRbo(GLuint rbo_name);
|
|
|
|
// Transform feedback state
|
|
void setTransformFeedbackActive(bool active);
|
|
void setTransformFeedbackUnpaused(bool unpaused);
|
|
void setTransformFeedbackVaryingsCountForLinking(uint32_t count);
|
|
bool getTransformFeedbackActive() const;
|
|
bool getTransformFeedbackUnpaused() const;
|
|
bool getTransformFeedbackActiveUnpaused() const;
|
|
uint32_t getTransformFeedbackVaryingsCountForLinking() const;
|
|
|
|
// Stencil state
|
|
void stencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask);
|
|
void stencilMaskSeparate(GLenum face, GLuint mask);
|
|
void stencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass);
|
|
|
|
void setTextureData(SharedTextureDataMap* sharedTexData);
|
|
void setRenderbufferInfo(RenderbufferInfo* rbInfo);
|
|
void setSamplerInfo(SamplerInfo* samplerInfo);
|
|
|
|
bool compressedTexImageSizeCompatible(GLenum internalformat, GLsizei width, GLsizei height, GLsizei depth, GLsizei imageSize);
|
|
// set eglsurface property on default framebuffer
|
|
// if coming from eglMakeCurrent
|
|
void fromMakeCurrent();
|
|
// set indexed buffer state.
|
|
// We need to query the underlying OpenGL to get
|
|
// accurate values for indexed buffers
|
|
// and # render targets.
|
|
void initFromCaps(
|
|
const HostDriverCaps& caps);
|
|
bool needsInitFromCaps() const;
|
|
void setExtensions(const std::string& extensions);
|
|
bool hasExtension(const char* ext) const;
|
|
|
|
// Queries the format backing the current framebuffer.
|
|
// Type differs depending on whether the attachment
|
|
// is a texture or renderbuffer.
|
|
void getBoundFramebufferFormat(
|
|
GLenum target,
|
|
GLenum attachment,
|
|
FboFormatInfo* res_info) const;
|
|
FboAttachmentType getBoundFramebufferAttachmentType(
|
|
GLenum target,
|
|
GLenum attachment) const;
|
|
int getMaxColorAttachments() const;
|
|
int getMaxDrawBuffers() const;
|
|
|
|
// Uniform/attribute validation info
|
|
UniformValidationInfo currentUniformValidationInfo;
|
|
AttribValidationInfo currentAttribValidationInfo;;
|
|
|
|
// Uniform validation api
|
|
void validateUniform(bool isFloat, bool isUnsigned, GLint columns, GLint rows, GLint location, GLsizei count, GLenum* err);
|
|
// Attrib validation
|
|
bool isAttribIndexUsedByProgram(int attribIndex);
|
|
|
|
// Fast access to some enables and stencil related glGet's
|
|
bool state_GL_STENCIL_TEST;
|
|
GLenum state_GL_STENCIL_FUNC;
|
|
unsigned int state_GL_STENCIL_VALUE_MASK;
|
|
int state_GL_STENCIL_REF;
|
|
GLenum state_GL_STENCIL_FAIL;
|
|
GLenum state_GL_STENCIL_PASS_DEPTH_FAIL;
|
|
GLenum state_GL_STENCIL_PASS_DEPTH_PASS;
|
|
GLenum state_GL_STENCIL_BACK_FUNC;
|
|
unsigned int state_GL_STENCIL_BACK_VALUE_MASK;
|
|
int state_GL_STENCIL_BACK_REF;
|
|
GLenum state_GL_STENCIL_BACK_FAIL;
|
|
GLenum state_GL_STENCIL_BACK_PASS_DEPTH_FAIL;
|
|
GLenum state_GL_STENCIL_BACK_PASS_DEPTH_PASS;
|
|
unsigned int state_GL_STENCIL_WRITEMASK;
|
|
unsigned int state_GL_STENCIL_BACK_WRITEMASK;
|
|
int state_GL_STENCIL_CLEAR_VALUE;
|
|
private:
|
|
void init();
|
|
bool m_initialized;
|
|
PixelStoreState m_pixelStore;
|
|
|
|
#ifdef GFXSTREAM
|
|
using DirtyMap = PredicateMap<uint32_t, true>;
|
|
|
|
ExistenceMap mBufferIds;
|
|
ExistenceMap mTransformFeedbackIds;
|
|
SamplerInfo* mSamplerInfo;
|
|
ExistenceMap mQueryIds;
|
|
LastQueryTargetInfo mLastQueryTargets;
|
|
|
|
// Bound query target validity and tracking
|
|
struct BoundTargetInfo {
|
|
GLuint id;
|
|
bool valid;
|
|
};
|
|
|
|
// Transform feedback
|
|
BoundTargetInfo mBoundTransformFeedbackValidity;
|
|
|
|
// Queries
|
|
// GL_ANY_SAMPLES_PASSED
|
|
BoundTargetInfo mBoundQueryValidity_AnySamplesPassed;
|
|
// GL_ANY_SAMPLES_PASSED_CONSERVATIVE
|
|
BoundTargetInfo mBoundQueryValidity_AnySamplesPassedConservative;
|
|
// GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN
|
|
BoundTargetInfo mBoundQueryValidity_TransformFeedbackPrimitivesWritten;
|
|
|
|
// Dirty maps
|
|
DirtyMap mHostMappedBufferDirty;
|
|
#else
|
|
std::set<GLuint> mBufferIds;
|
|
#endif
|
|
|
|
// GL_ARRAY_BUFFER_BINDING is separate from VAO state
|
|
GLuint m_arrayBuffer;
|
|
GLuint m_arrayBuffer_lastEncode;
|
|
VAOStateMap m_vaoMap;
|
|
VAOStateRef m_currVaoState;
|
|
|
|
uint16_t m_attribEnableCache;
|
|
uint16_t m_vaoAttribBindingCacheInvalid;
|
|
uint16_t m_vaoAttribBindingHasClientArrayCache;
|
|
uint16_t m_vaoAttribBindingHasVboCache;
|
|
uint8_t m_noClientArraysCache;
|
|
|
|
// Other buffer id's, other targets
|
|
GLuint m_copyReadBuffer;
|
|
GLuint m_copyWriteBuffer;
|
|
|
|
GLuint m_pixelPackBuffer;
|
|
GLuint m_pixelUnpackBuffer;
|
|
|
|
GLuint m_transformFeedbackBuffer;
|
|
GLuint m_uniformBuffer;
|
|
|
|
GLuint m_atomicCounterBuffer;
|
|
GLuint m_dispatchIndirectBuffer;
|
|
GLuint m_drawIndirectBuffer;
|
|
GLuint m_shaderStorageBuffer;
|
|
|
|
bool m_transformFeedbackActive;
|
|
bool m_transformFeedbackUnpaused;
|
|
uint32_t m_transformFeedbackVaryingsCountForLinking;
|
|
|
|
HostDriverCaps m_hostDriverCaps;
|
|
bool m_extensions_set;
|
|
std::string m_extensions;
|
|
bool m_has_color_buffer_float_extension;
|
|
bool m_has_color_buffer_half_float_extension;
|
|
std::vector<BufferBinding> m_indexedTransformFeedbackBuffers;
|
|
std::vector<BufferBinding> m_indexedUniformBuffers;
|
|
std::vector<BufferBinding> m_indexedAtomicCounterBuffers;
|
|
std::vector<BufferBinding> m_indexedShaderStorageBuffers;
|
|
int m_log2MaxTextureSize;
|
|
|
|
int m_glesMajorVersion;
|
|
int m_glesMinorVersion;
|
|
int m_activeTexture;
|
|
GLint m_currentProgram;
|
|
GLint m_currentShaderProgram;
|
|
ProgramPipelineMap m_programPipelines;
|
|
|
|
enum TextureTarget {
|
|
TEXTURE_2D = 0,
|
|
TEXTURE_EXTERNAL = 1,
|
|
TEXTURE_CUBE_MAP = 2,
|
|
TEXTURE_2D_ARRAY = 3,
|
|
TEXTURE_3D = 4,
|
|
TEXTURE_2D_MULTISAMPLE = 5,
|
|
TEXTURE_TARGET_COUNT
|
|
};
|
|
struct TextureUnit {
|
|
unsigned int enables;
|
|
GLuint texture[TEXTURE_TARGET_COUNT];
|
|
GLuint boundSampler;
|
|
};
|
|
struct TextureState {
|
|
TextureUnit unit[MAX_TEXTURE_UNITS];
|
|
TextureUnit* activeUnit;
|
|
// Initialized from shared group.
|
|
SharedTextureDataMap* textureRecs;
|
|
};
|
|
TextureState m_tex;
|
|
|
|
// State tracking of cube map definitions.
|
|
// Currently used only for driver workarounds
|
|
// when using GL_LUMINANCE and defining cube maps with
|
|
// glCopyTexImage2D.
|
|
struct CubeMapDef {
|
|
GLuint id;
|
|
GLenum target;
|
|
GLint level;
|
|
GLenum internalformat;
|
|
};
|
|
struct CubeMapDefCompare {
|
|
bool operator() (const CubeMapDef& a,
|
|
const CubeMapDef& b) const {
|
|
if (a.id != b.id) return a.id < b.id;
|
|
if (a.target != b.target) return a.target < b.target;
|
|
if (a.level != b.level) return a.level < b.level;
|
|
if (a.internalformat != b.internalformat)
|
|
return a.internalformat < b.internalformat;
|
|
return false;
|
|
}
|
|
};
|
|
std::set<CubeMapDef, CubeMapDefCompare> m_cubeMapDefs;
|
|
void writeCopyTexImageState(GLenum target, GLint level,
|
|
GLenum internalformat);
|
|
GLenum copyTexImageNeededTarget(GLenum target, GLint level,
|
|
GLenum internalformat);
|
|
|
|
struct RboState {
|
|
GLuint boundRenderbuffer;
|
|
// Connects to share group.
|
|
// Expected that share group lifetime outlives this context.
|
|
RenderbufferInfo* rboData;
|
|
};
|
|
RboState mRboState;
|
|
void addFreshRenderbuffer(GLuint name);
|
|
|
|
struct FboState {
|
|
GLuint boundDrawFramebuffer;
|
|
GLuint boundReadFramebuffer;
|
|
size_t boundFramebufferIndex;
|
|
std::map<GLuint, FboProps> fboData;
|
|
GLenum drawFboCheckStatus;
|
|
GLenum readFboCheckStatus;
|
|
};
|
|
FboState mFboState;
|
|
void addFreshFramebuffer(GLuint name);
|
|
FboProps& boundFboProps(GLenum target);
|
|
const FboProps& boundFboProps_const(GLenum target) const;
|
|
|
|
// Querying framebuffer format
|
|
GLenum queryRboFormat(GLuint name) const;
|
|
GLsizei queryRboSamples(GLuint name) const;
|
|
GLsizei queryRboWidth(GLuint name) const;
|
|
GLsizei queryRboHeight(GLuint name) const;
|
|
bool queryRboEGLImageBacked(GLuint name) const;
|
|
GLenum queryTexType(GLuint name) const;
|
|
GLsizei queryTexSamples(GLuint name) const;
|
|
|
|
static int compareTexId(const void* pid, const void* prec);
|
|
TextureRec* addTextureRec(GLuint id, GLenum target);
|
|
TextureRec* getTextureRec(GLuint id) const;
|
|
|
|
public:
|
|
bool isTexture(GLuint name) const;
|
|
bool isTextureWithStorage(GLuint name) const;
|
|
bool isTextureWithTarget(GLuint name) const;
|
|
bool isTextureCubeMap(GLuint name) const;
|
|
bool isRenderbuffer(GLuint name) const;
|
|
bool isRenderbufferThatWasBound(GLuint name) const;
|
|
|
|
void getClientStatePointer(GLenum pname, GLvoid** params);
|
|
|
|
template <class T>
|
|
int getVertexAttribParameter(GLuint index, GLenum param, T *ptr)
|
|
{
|
|
bool handled = true;
|
|
const VertexAttribState& vertexAttrib = getState(index);
|
|
const BufferBinding& vertexAttribBufferBinding =
|
|
m_currVaoState.bufferBindings_const()[vertexAttrib.bindingindex];
|
|
|
|
switch(param) {
|
|
#define GL_VERTEX_ATTRIB_BINDING 0x82D4
|
|
case GL_VERTEX_ATTRIB_BINDING:
|
|
*ptr = (T)vertexAttrib.bindingindex;
|
|
break;
|
|
#define GL_VERTEX_ATTRIB_RELATIVE_OFFSET 0x82D5
|
|
case GL_VERTEX_ATTRIB_RELATIVE_OFFSET:
|
|
*ptr = (T)vertexAttrib.reloffset;
|
|
break;
|
|
case GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING:
|
|
*ptr = (T)(vertexAttribBufferBinding.buffer);
|
|
break;
|
|
case GL_VERTEX_ATTRIB_ARRAY_ENABLED:
|
|
*ptr = (T)(vertexAttrib.enabled);
|
|
break;
|
|
#define GL_VERTEX_ATTRIB_ARRAY_INTEGER 0x88FD
|
|
case GL_VERTEX_ATTRIB_ARRAY_INTEGER:
|
|
*ptr = (T)(vertexAttrib.isInt);
|
|
break;
|
|
case GL_VERTEX_ATTRIB_ARRAY_SIZE:
|
|
*ptr = (T)(vertexAttrib.size);
|
|
break;
|
|
case GL_VERTEX_ATTRIB_ARRAY_STRIDE:
|
|
*ptr = (T)(vertexAttribBufferBinding.stride);
|
|
break;
|
|
case GL_VERTEX_ATTRIB_ARRAY_TYPE:
|
|
*ptr = (T)(vertexAttrib.type);
|
|
break;
|
|
case GL_VERTEX_ATTRIB_ARRAY_NORMALIZED:
|
|
*ptr = (T)(vertexAttrib.normalized);
|
|
break;
|
|
case GL_CURRENT_VERTEX_ATTRIB:
|
|
handled = false;
|
|
break;
|
|
default:
|
|
handled = false;
|
|
ERR("unknown vertex-attrib parameter param %d\n", param);
|
|
}
|
|
return handled;
|
|
}
|
|
|
|
template <class T>
|
|
bool getClientStateParameter(GLenum param, T* out)
|
|
{
|
|
bool isClientStateParam = false;
|
|
switch (param) {
|
|
case GL_CLIENT_ACTIVE_TEXTURE: {
|
|
GLint tex = getActiveTexture() + GL_TEXTURE0;
|
|
*out = tex;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_VERTEX_ARRAY_SIZE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::VERTEX_LOCATION);
|
|
*out = state.size;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_VERTEX_ARRAY_TYPE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::VERTEX_LOCATION);
|
|
*out = state.type;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_VERTEX_ARRAY_STRIDE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::VERTEX_LOCATION);
|
|
*out = state.stride;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_COLOR_ARRAY_SIZE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::COLOR_LOCATION);
|
|
*out = state.size;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_COLOR_ARRAY_TYPE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::COLOR_LOCATION);
|
|
*out = state.type;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_COLOR_ARRAY_STRIDE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::COLOR_LOCATION);
|
|
*out = state.stride;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_NORMAL_ARRAY_TYPE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::NORMAL_LOCATION);
|
|
*out = state.type;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_NORMAL_ARRAY_STRIDE: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::NORMAL_LOCATION);
|
|
*out = state.stride;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_TEXTURE_COORD_ARRAY_SIZE: {
|
|
const GLClientState::VertexAttribState& state = getState(getActiveTexture() + GLClientState::TEXCOORD0_LOCATION);
|
|
*out = state.size;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_TEXTURE_COORD_ARRAY_TYPE: {
|
|
const GLClientState::VertexAttribState& state = getState(getActiveTexture() + GLClientState::TEXCOORD0_LOCATION);
|
|
*out = state.type;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_TEXTURE_COORD_ARRAY_STRIDE: {
|
|
const GLClientState::VertexAttribState& state = getState(getActiveTexture() + GLClientState::TEXCOORD0_LOCATION);
|
|
*out = state.stride;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_POINT_SIZE_ARRAY_TYPE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::POINTSIZE_LOCATION);
|
|
*out = state.type;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_POINT_SIZE_ARRAY_STRIDE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::POINTSIZE_LOCATION);
|
|
*out = state.stride;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_MATRIX_INDEX_ARRAY_SIZE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::MATRIXINDEX_LOCATION);
|
|
*out = state.size;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_MATRIX_INDEX_ARRAY_TYPE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::MATRIXINDEX_LOCATION);
|
|
*out = state.type;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_MATRIX_INDEX_ARRAY_STRIDE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::MATRIXINDEX_LOCATION);
|
|
*out = state.stride;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_WEIGHT_ARRAY_SIZE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::WEIGHT_LOCATION);
|
|
*out = state.size;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_WEIGHT_ARRAY_TYPE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::WEIGHT_LOCATION);
|
|
*out = state.type;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_WEIGHT_ARRAY_STRIDE_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::WEIGHT_LOCATION);
|
|
*out = state.stride;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_VERTEX_ARRAY_BUFFER_BINDING: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::VERTEX_LOCATION);
|
|
*out = state.bufferObject;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_NORMAL_ARRAY_BUFFER_BINDING: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::NORMAL_LOCATION);
|
|
*out = state.bufferObject;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_COLOR_ARRAY_BUFFER_BINDING: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::COLOR_LOCATION);
|
|
*out = state.bufferObject;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_TEXTURE_COORD_ARRAY_BUFFER_BINDING: {
|
|
const GLClientState::VertexAttribState& state = getState(getActiveTexture()+GLClientState::TEXCOORD0_LOCATION);
|
|
*out = state.bufferObject;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_POINT_SIZE_ARRAY_BUFFER_BINDING_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::POINTSIZE_LOCATION);
|
|
*out = state.bufferObject;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_MATRIX_INDEX_ARRAY_BUFFER_BINDING_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::MATRIXINDEX_LOCATION);
|
|
*out = state.bufferObject;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_WEIGHT_ARRAY_BUFFER_BINDING_OES: {
|
|
const GLClientState::VertexAttribState& state = getState(GLClientState::WEIGHT_LOCATION);
|
|
*out = state.bufferObject;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_ARRAY_BUFFER_BINDING: {
|
|
int buffer = getBuffer(GL_ARRAY_BUFFER);
|
|
*out = buffer;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_ELEMENT_ARRAY_BUFFER_BINDING: {
|
|
int buffer = getBuffer(GL_ELEMENT_ARRAY_BUFFER);
|
|
*out = buffer;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_MAX_VERTEX_ATTRIBS: {
|
|
*out = CODEC_MAX_VERTEX_ATTRIBUTES;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
case GL_FRAMEBUFFER_BINDING:
|
|
// also case GL_DRAW_FRAMEBUFFER_BINDING:
|
|
*out = (T)mFboState.boundDrawFramebuffer;
|
|
isClientStateParam = true;
|
|
break;
|
|
case 0x8CAA: // GL_READ_FRAMEBUFFER_BINDING
|
|
*out = (T)mFboState.boundReadFramebuffer;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_TEST:
|
|
*out = (T)state_GL_STENCIL_TEST;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_FUNC:
|
|
*out = (T)state_GL_STENCIL_FUNC;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_VALUE_MASK:
|
|
*out = (T)state_GL_STENCIL_VALUE_MASK;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_REF:
|
|
*out = (T)state_GL_STENCIL_REF;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_FAIL:
|
|
*out = (T)state_GL_STENCIL_FAIL;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_PASS_DEPTH_FAIL:
|
|
*out = (T)state_GL_STENCIL_PASS_DEPTH_FAIL;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_PASS_DEPTH_PASS:
|
|
*out = (T)state_GL_STENCIL_PASS_DEPTH_PASS;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_BACK_FUNC:
|
|
*out = (T)state_GL_STENCIL_BACK_FUNC;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_BACK_VALUE_MASK:
|
|
*out = (T)state_GL_STENCIL_BACK_VALUE_MASK;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_BACK_REF:
|
|
*out = (T)state_GL_STENCIL_BACK_REF;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_BACK_FAIL:
|
|
*out = (T)state_GL_STENCIL_BACK_FAIL;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_BACK_PASS_DEPTH_FAIL:
|
|
*out = (T)state_GL_STENCIL_BACK_PASS_DEPTH_FAIL;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_BACK_PASS_DEPTH_PASS:
|
|
*out = (T)state_GL_STENCIL_BACK_PASS_DEPTH_PASS;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_WRITEMASK:
|
|
*out = (T)state_GL_STENCIL_WRITEMASK;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_BACK_WRITEMASK:
|
|
*out = (T)state_GL_STENCIL_BACK_WRITEMASK;
|
|
isClientStateParam = true;
|
|
break;
|
|
case GL_STENCIL_CLEAR_VALUE:
|
|
*out = (T)state_GL_STENCIL_CLEAR_VALUE;
|
|
isClientStateParam = true;
|
|
break;
|
|
}
|
|
return isClientStateParam;
|
|
}
|
|
|
|
};
|
|
#endif
|