OSDN Git Service

Merge "Allow glGetProgramInfoLog_enc to have empty length"
[android-x86/device-generic-goldfish-opengl.git] / shared / OpenglCodecCommon / GLClientState.h
1 /*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16 #ifndef _GL_CLIENT_STATE_H_
17 #define _GL_CLIENT_STATE_H_
18
19 #define GL_API
20 #ifndef ANDROID
21 #define GL_APIENTRY
22 #define GL_APIENTRYP
23 #endif
24
25 #include <GLES/gl.h>
26 #include <GLES/glext.h>
27 #include <GLES2/gl2.h>
28 #include <GLES2/gl2ext.h>
29
30 #include <stdio.h>
31 #include <stdlib.h>
32 #include "ErrorLog.h"
33 #include "codec_defs.h"
34
35 class GLClientState {
36 public:
37     typedef enum {
38         VERTEX_LOCATION = 0,
39         NORMAL_LOCATION = 1,
40         COLOR_LOCATION = 2,
41         POINTSIZE_LOCATION = 3,
42         TEXCOORD0_LOCATION = 4,
43         TEXCOORD1_LOCATION = 5,
44         TEXCOORD2_LOCATION = 6,
45         TEXCOORD3_LOCATION = 7,
46         TEXCOORD4_LOCATION = 8,
47         TEXCOORD5_LOCATION = 9,
48         TEXCOORD6_LOCATION = 10,
49         TEXCOORD7_LOCATION = 11,
50         MATRIXINDEX_LOCATION = 12,
51         WEIGHT_LOCATION = 13,
52         LAST_LOCATION = 14
53     } StateLocation;
54
55     typedef struct {
56         GLint enabled;
57         GLint size;
58         GLenum type;
59         GLsizei stride;
60         void *data;
61         GLuint bufferObject;
62         GLenum glConst;
63         unsigned int elementSize;
64         bool enableDirty;  // true if any enable state has changed since last draw
65         bool normalized;
66     } VertexAttribState;
67
68     typedef struct {
69         int unpack_alignment;
70         int pack_alignment;
71     } PixelStoreState;
72
73     enum {
74         MAX_TEXTURE_UNITS = 32,
75     };
76
77 public:
78     GLClientState(int nLocations = CODEC_MAX_VERTEX_ATTRIBUTES);
79     ~GLClientState();
80     int nLocations() { return m_nLocations; }
81     const PixelStoreState *pixelStoreState() { return &m_pixelStore; }
82     int setPixelStore(GLenum param, GLint value);
83     GLuint currentArrayVbo() { return m_currentArrayVbo; }
84     GLuint currentIndexVbo() { return m_currentIndexVbo; }
85     void enable(int location, int state);
86     void setState(int  location, int size, GLenum type, GLboolean normalized, GLsizei stride, const void *data);
87     void setBufferObject(int location, GLuint id);
88     const VertexAttribState  *getState(int location);
89     const VertexAttribState  *getStateAndEnableDirty(int location, bool *enableChanged);
90     int getLocation(GLenum loc);
91     void setActiveTexture(int texUnit) {m_activeTexture = texUnit; };
92     int getActiveTexture() const { return m_activeTexture; }
93
94     int bindBuffer(GLenum target, GLuint id)
95     {
96         int err = 0;
97         switch(target) {
98         case GL_ARRAY_BUFFER:
99             m_currentArrayVbo = id;
100             break;
101         case GL_ELEMENT_ARRAY_BUFFER:
102             m_currentIndexVbo = id;
103             break;
104         default:
105             err = -1;
106         }
107         return err;
108     }
109
110     int getBuffer(GLenum target)
111     {
112       int ret=0;
113       switch (target) {
114       case GL_ARRAY_BUFFER:
115           ret = m_currentArrayVbo;
116           break;
117       case GL_ELEMENT_ARRAY_BUFFER:
118           ret = m_currentIndexVbo;
119           break;
120       default:
121           ret = -1;
122       }
123       return ret;
124     }
125     size_t pixelDataSize(GLsizei width, GLsizei height, GLenum format, GLenum type, int pack) const;
126
127     void setCurrentProgram(GLint program) { m_currentProgram = program; }
128     GLint currentProgram() const { return m_currentProgram; }
129
130     /* OES_EGL_image_external
131      *
132      * These functions manipulate GL state which interacts with the
133      * OES_EGL_image_external extension, to support client-side emulation on
134      * top of host implementations that don't have it.
135      *
136      * Most of these calls should only be used with TEXTURE_2D or
137      * TEXTURE_EXTERNAL_OES texture targets; TEXTURE_CUBE_MAP or other extension
138      * targets should bypass this. An exception is bindTexture(), which should
139      * see all glBindTexture() calls for any target.
140      */
141
142     // glActiveTexture(GL_TEXTURE0 + i)
143     // Sets the active texture unit. Up to MAX_TEXTURE_UNITS are supported.
144     GLenum setActiveTextureUnit(GLenum texture);
145     GLenum getActiveTextureUnit() const;
146
147     // glEnable(GL_TEXTURE_(2D|EXTERNAL_OES))
148     void enableTextureTarget(GLenum target);
149
150     // glDisable(GL_TEXTURE_(2D|EXTERNAL_OES))
151     void disableTextureTarget(GLenum target);
152
153     // Implements the target priority logic:
154     // * Return GL_TEXTURE_EXTERNAL_OES if enabled, else
155     // * Return GL_TEXTURE_2D if enabled, else
156     // * Return the allDisabled value.
157     // For some cases passing GL_TEXTURE_2D for allDisabled makes callee code
158     // simpler; for other cases passing a recognizable enum like GL_ZERO or
159     // GL_INVALID_ENUM is appropriate.
160     GLenum getPriorityEnabledTarget(GLenum allDisabled) const;
161
162     // glBindTexture(GL_TEXTURE_*, ...)
163     // Set the target binding of the active texture unit to texture. Returns
164     // GL_NO_ERROR on success or GL_INVALID_OPERATION if the texture has
165     // previously been bound to a different target. If firstUse is not NULL,
166     // it is set to indicate whether this is the first use of the texture.
167     // For accurate error detection, bindTexture should be called for *all*
168     // targets, not just 2D and EXTERNAL_OES.
169     GLenum bindTexture(GLenum target, GLuint texture, GLboolean* firstUse);
170
171     // Return the texture currently bound to GL_TEXTURE_(2D|EXTERNAL_OES).
172     GLuint getBoundTexture(GLenum target) const;
173
174     // glDeleteTextures(...)
175     // Remove references to the to-be-deleted textures.
176     void deleteTextures(GLsizei n, const GLuint* textures);
177
178 private:
179     PixelStoreState m_pixelStore;
180     VertexAttribState *m_states;
181     int m_nLocations;
182     GLuint m_currentArrayVbo;
183     GLuint m_currentIndexVbo;
184     int m_activeTexture;
185     GLint m_currentProgram;
186
187     bool validLocation(int location) { return (location >= 0 && location < m_nLocations); }
188
189     enum TextureTarget {
190         TEXTURE_2D = 0,
191         TEXTURE_EXTERNAL = 1,
192         TEXTURE_TARGET_COUNT
193     };
194     struct TextureUnit {
195         unsigned int enables;
196         GLuint texture[TEXTURE_TARGET_COUNT];
197     };
198     struct TextureRec {
199         GLuint id;
200         GLenum target;
201     };
202     struct TextureState {
203         TextureUnit unit[MAX_TEXTURE_UNITS];
204         TextureUnit* activeUnit;
205         TextureRec* textures;
206         GLuint numTextures;
207         GLuint allocTextures;
208     };
209     TextureState m_tex;
210
211     static int compareTexId(const void* pid, const void* prec);
212     TextureRec* addTextureRec(GLuint id, GLenum target);
213
214 public:
215     void getClientStatePointer(GLenum pname, GLvoid** params);
216
217     template <class T>
218     int getVertexAttribParameter(GLuint index, GLenum param, T *ptr)
219     {
220         bool handled = true;
221         const VertexAttribState *vertexAttrib = getState(index);
222         if (vertexAttrib == NULL) {
223             ERR("getVeterxAttriParameter for non existant index %d\n", index);
224             // set gl error;
225             return handled;
226         }
227
228         switch(param) {
229         case GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING:
230             *ptr = (T)(vertexAttrib->bufferObject);
231             break;
232         case GL_VERTEX_ATTRIB_ARRAY_ENABLED:
233             *ptr = (T)(vertexAttrib->enabled);
234             break;
235         case GL_VERTEX_ATTRIB_ARRAY_SIZE:
236             *ptr = (T)(vertexAttrib->size);
237             break;
238         case GL_VERTEX_ATTRIB_ARRAY_STRIDE:
239             *ptr = (T)(vertexAttrib->stride);
240             break;
241         case GL_VERTEX_ATTRIB_ARRAY_TYPE:
242             *ptr = (T)(vertexAttrib->type);
243             break;
244         case GL_VERTEX_ATTRIB_ARRAY_NORMALIZED:
245             *ptr = (T)(vertexAttrib->normalized);
246             break;
247         case GL_CURRENT_VERTEX_ATTRIB:
248             handled = false;
249             break;
250         default:
251             handled = false;
252             ERR("unknown vertex-attrib parameter param %d\n", param);
253         }
254         return handled;
255     }
256
257     template <class T>
258     bool getClientStateParameter(GLenum param, T* ptr)
259     {
260         bool isClientStateParam = false;
261         switch (param) {
262         case GL_CLIENT_ACTIVE_TEXTURE: {
263             GLint tex = getActiveTexture() + GL_TEXTURE0;
264             *ptr = tex;
265             isClientStateParam = true;
266             break;
267             }
268         case GL_VERTEX_ARRAY_SIZE: {
269             const GLClientState::VertexAttribState *state = getState(GLClientState::VERTEX_LOCATION);
270             *ptr = state->size;
271             isClientStateParam = true;
272             break;
273             }
274         case GL_VERTEX_ARRAY_TYPE: {
275             const GLClientState::VertexAttribState *state = getState(GLClientState::VERTEX_LOCATION);
276             *ptr = state->type;
277             isClientStateParam = true;
278             break;
279             }
280         case GL_VERTEX_ARRAY_STRIDE: {
281             const GLClientState::VertexAttribState *state = getState(GLClientState::VERTEX_LOCATION);
282             *ptr = state->stride;
283             isClientStateParam = true;
284             break;
285             }
286         case GL_COLOR_ARRAY_SIZE: {
287             const GLClientState::VertexAttribState *state = getState(GLClientState::COLOR_LOCATION);
288             *ptr = state->size;
289             isClientStateParam = true;
290             break;
291             }
292         case GL_COLOR_ARRAY_TYPE: {
293             const GLClientState::VertexAttribState *state = getState(GLClientState::COLOR_LOCATION);
294             *ptr = state->type;
295             isClientStateParam = true;
296             break;
297             }
298         case GL_COLOR_ARRAY_STRIDE: {
299             const GLClientState::VertexAttribState *state = getState(GLClientState::COLOR_LOCATION);
300             *ptr = state->stride;
301             isClientStateParam = true;
302             break;
303             }
304         case GL_NORMAL_ARRAY_TYPE: {
305             const GLClientState::VertexAttribState *state = getState(GLClientState::NORMAL_LOCATION);
306             *ptr = state->type;
307             isClientStateParam = true;
308             break;
309             }
310         case GL_NORMAL_ARRAY_STRIDE: {
311             const GLClientState::VertexAttribState *state = getState(GLClientState::NORMAL_LOCATION);
312             *ptr = state->stride;
313             isClientStateParam = true;
314             break;
315             }
316         case GL_TEXTURE_COORD_ARRAY_SIZE: {
317             const GLClientState::VertexAttribState *state = getState(getActiveTexture() + GLClientState::TEXCOORD0_LOCATION);
318             *ptr = state->size;
319             isClientStateParam = true;
320             break;
321             }
322         case GL_TEXTURE_COORD_ARRAY_TYPE: {
323             const GLClientState::VertexAttribState *state = getState(getActiveTexture() + GLClientState::TEXCOORD0_LOCATION);
324             *ptr = state->type;
325             isClientStateParam = true;
326             break;
327             }
328         case GL_TEXTURE_COORD_ARRAY_STRIDE: {
329             const GLClientState::VertexAttribState *state = getState(getActiveTexture() + GLClientState::TEXCOORD0_LOCATION);
330             *ptr = state->stride;
331             isClientStateParam = true;
332             break;
333             }
334         case GL_POINT_SIZE_ARRAY_TYPE_OES: {
335             const GLClientState::VertexAttribState *state = getState(GLClientState::POINTSIZE_LOCATION);
336             *ptr = state->type;
337             isClientStateParam = true;
338             break;
339             }
340         case GL_POINT_SIZE_ARRAY_STRIDE_OES: {
341             const GLClientState::VertexAttribState *state = getState(GLClientState::POINTSIZE_LOCATION);
342             *ptr = state->stride;
343             isClientStateParam = true;
344             break;
345             }
346         case GL_MATRIX_INDEX_ARRAY_SIZE_OES: {
347             const GLClientState::VertexAttribState *state = getState(GLClientState::MATRIXINDEX_LOCATION);
348             *ptr = state->size;
349             isClientStateParam = true;
350             break;
351             }
352         case GL_MATRIX_INDEX_ARRAY_TYPE_OES: {
353             const GLClientState::VertexAttribState *state = getState(GLClientState::MATRIXINDEX_LOCATION);
354             *ptr = state->type;
355             isClientStateParam = true;
356             break;
357             }
358         case GL_MATRIX_INDEX_ARRAY_STRIDE_OES: {
359             const GLClientState::VertexAttribState *state = getState(GLClientState::MATRIXINDEX_LOCATION);
360             *ptr = state->stride;
361             isClientStateParam = true;
362             break;
363             }
364         case GL_WEIGHT_ARRAY_SIZE_OES: {
365             const GLClientState::VertexAttribState *state = getState(GLClientState::WEIGHT_LOCATION);
366             *ptr = state->size;
367             isClientStateParam = true;
368             break;
369             }
370         case GL_WEIGHT_ARRAY_TYPE_OES: {
371             const GLClientState::VertexAttribState *state = getState(GLClientState::WEIGHT_LOCATION);
372             *ptr = state->type;
373             isClientStateParam = true;
374             break;
375             }
376         case GL_WEIGHT_ARRAY_STRIDE_OES: {
377             const GLClientState::VertexAttribState *state = getState(GLClientState::WEIGHT_LOCATION);
378             *ptr = state->stride;
379             isClientStateParam = true;
380             break;
381             }
382         case GL_VERTEX_ARRAY_BUFFER_BINDING: {
383             const GLClientState::VertexAttribState *state = getState(GLClientState::VERTEX_LOCATION);
384             *ptr = state->bufferObject;
385             isClientStateParam = true;
386             break;
387             }
388         case GL_NORMAL_ARRAY_BUFFER_BINDING: {
389             const GLClientState::VertexAttribState *state = getState(GLClientState::NORMAL_LOCATION);
390             *ptr = state->bufferObject;
391             isClientStateParam = true;
392             break;
393             }
394         case GL_COLOR_ARRAY_BUFFER_BINDING: {
395             const GLClientState::VertexAttribState *state = getState(GLClientState::COLOR_LOCATION);
396             *ptr = state->bufferObject;
397             isClientStateParam = true;
398             break;
399             }
400         case GL_TEXTURE_COORD_ARRAY_BUFFER_BINDING: {
401             const GLClientState::VertexAttribState *state = getState(getActiveTexture()+GLClientState::TEXCOORD0_LOCATION);
402             *ptr = state->bufferObject;
403             isClientStateParam = true;
404             break;
405             }
406         case GL_POINT_SIZE_ARRAY_BUFFER_BINDING_OES: {
407             const GLClientState::VertexAttribState *state = getState(GLClientState::POINTSIZE_LOCATION);
408             *ptr = state->bufferObject;
409             isClientStateParam = true;
410             break;
411             }
412         case GL_MATRIX_INDEX_ARRAY_BUFFER_BINDING_OES: {
413             const GLClientState::VertexAttribState *state = getState(GLClientState::MATRIXINDEX_LOCATION);
414             *ptr = state->bufferObject;
415             isClientStateParam = true;
416             break;
417             }
418         case GL_WEIGHT_ARRAY_BUFFER_BINDING_OES: {
419             const GLClientState::VertexAttribState *state = getState(GLClientState::WEIGHT_LOCATION);
420             *ptr = state->bufferObject;
421             isClientStateParam = true;
422             break;
423             }
424         case GL_ARRAY_BUFFER_BINDING: {
425             int buffer = getBuffer(GL_ARRAY_BUFFER);
426             *ptr = buffer;
427             isClientStateParam = true;
428             break;
429             }
430         case GL_ELEMENT_ARRAY_BUFFER_BINDING: {
431             int buffer = getBuffer(GL_ELEMENT_ARRAY_BUFFER);
432             *ptr = buffer;
433             isClientStateParam = true;
434             break;
435             }
436         }
437         return isClientStateParam;
438     }
439
440 };
441 #endif