blob: 641961f3a822e4ef5cd51d20155dffb834915694 [file] [log] [blame]
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -08001/*
2 * Copyright (C) 2006 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
17#ifndef ANDROID_OPENGLES_CONTEXT_H
18#define ANDROID_OPENGLES_CONTEXT_H
19
20#include <stdint.h>
21#include <stddef.h>
22#include <sys/types.h>
23#include <pthread.h>
24#ifdef HAVE_ANDROID_OS
25#include <bionic_tls.h>
26#endif
27
28#include <private/pixelflinger/ggl_context.h>
Mathias Agopianb1514c92009-04-10 14:24:30 -070029#include <hardware/copybit.h>
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -080030
31#include <GLES/gl.h>
32#include <GLES/glext.h>
33
34namespace android {
35
36const unsigned int OGLES_NUM_COMPRESSED_TEXTURE_FORMATS = 10;
37
38class EGLTextureObject;
39class EGLSurfaceManager;
40class EGLBufferObjectManager;
41
42namespace gl {
Mathias Agopianb1514c92009-04-10 14:24:30 -070043
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -080044struct ogles_context_t;
45struct matrixx_t;
46struct transform_t;
47struct buffer_t;
48
49ogles_context_t* getGlContext();
50
51template<typename T>
52static inline void swap(T& a, T& b) {
53 T t(a); a = b; b = t;
54}
55template<typename T>
56inline T max(T a, T b) {
57 return a<b ? b : a;
58}
59template<typename T>
60inline T max(T a, T b, T c) {
61 return max(a, max(b, c));
62}
63template<typename T>
64inline T min(T a, T b) {
65 return a<b ? a : b;
66}
67template<typename T>
68inline T min(T a, T b, T c) {
69 return min(a, min(b, c));
70}
71template<typename T>
72inline T min(T a, T b, T c, T d) {
73 return min(min(a,b), min(c,d));
74}
75
76// ----------------------------------------------------------------------------
77// vertices
78// ----------------------------------------------------------------------------
79
80struct vec3_t {
81 union {
82 struct { GLfixed x, y, z; };
83 struct { GLfixed r, g, b; };
84 struct { GLfixed S, T, R; };
85 GLfixed v[3];
86 };
87};
88
89struct vec4_t {
90 union {
91 struct { GLfixed x, y, z, w; };
92 struct { GLfixed r, g, b, a; };
93 struct { GLfixed S, T, R, Q; };
94 GLfixed v[4];
95 };
96};
97
98struct vertex_t {
99 enum {
Mathias Agopianb1514c92009-04-10 14:24:30 -0700100 // these constant matter for our clipping
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800101 CLIP_L = 0x0001, // clipping flags
102 CLIP_R = 0x0002,
103 CLIP_B = 0x0004,
104 CLIP_T = 0x0008,
105 CLIP_N = 0x0010,
106 CLIP_F = 0x0020,
107
108 EYE = 0x0040,
109 RESERVED = 0x0080,
Mathias Agopianb1514c92009-04-10 14:24:30 -0700110
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800111 USER_CLIP_0 = 0x0100, // user clipping flags
112 USER_CLIP_1 = 0x0200,
113 USER_CLIP_2 = 0x0400,
114 USER_CLIP_3 = 0x0800,
115 USER_CLIP_4 = 0x1000,
116 USER_CLIP_5 = 0x2000,
117
118 LIT = 0x4000, // lighting has been applied
119 TT = 0x8000, // texture coords transformed
120
121 FRUSTUM_CLIP_ALL= 0x003F,
122 USER_CLIP_ALL = 0x3F00,
123 CLIP_ALL = 0x3F3F,
124 };
Mathias Agopianb1514c92009-04-10 14:24:30 -0700125
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800126 // the fields below are arranged to minimize d-cache usage
127 // we group together, by cache-line, the fields most likely to be used
128
129 union {
130 vec4_t obj;
131 vec4_t eye;
132 };
133 vec4_t clip;
Mathias Agopianb1514c92009-04-10 14:24:30 -0700134
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800135 uint32_t flags;
136 size_t index; // cache tag, and vertex index
137 GLfixed fog;
138 uint8_t locked;
139 uint8_t mru;
140 uint8_t reserved[2];
141 vec4_t window;
142
143 vec4_t color;
144 vec4_t texture[GGL_TEXTURE_UNIT_COUNT];
145 uint32_t reserved1[4];
Mathias Agopianb1514c92009-04-10 14:24:30 -0700146
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800147 inline void clear() {
148 flags = index = locked = mru = 0;
149 }
150};
151
152struct point_size_t {
153 GGLcoord size;
154 GLboolean smooth;
155};
156
157struct line_width_t {
158 GGLcoord width;
159 GLboolean smooth;
160};
161
162struct polygon_offset_t {
163 GLfixed factor;
164 GLfixed units;
165 GLboolean enable;
166};
167
168// ----------------------------------------------------------------------------
169// arrays
170// ----------------------------------------------------------------------------
171
172struct array_t {
173 typedef void (*fetcher_t)(ogles_context_t*, GLfixed*, const GLvoid*);
174 fetcher_t fetch;
175 GLvoid const* physical_pointer;
176 GLint size;
177 GLsizei stride;
178 GLvoid const* pointer;
179 buffer_t const* bo;
180 uint16_t type;
181 GLboolean enable;
182 GLboolean pad;
183 GLsizei bounds;
184 void init(GLint, GLenum, GLsizei, const GLvoid *, const buffer_t*, GLsizei);
185 inline void resolve();
186 inline const GLubyte* element(GLint i) const {
187 return (const GLubyte*)physical_pointer + i * stride;
188 }
189};
190
191struct array_machine_t {
192 array_t vertex;
193 array_t normal;
194 array_t color;
195 array_t texture[GGL_TEXTURE_UNIT_COUNT];
196 uint8_t activeTexture;
197 uint8_t tmu;
198 uint16_t cull;
199 uint32_t flags;
200 GLenum indicesType;
201 buffer_t const* array_buffer;
202 buffer_t const* element_array_buffer;
Mathias Agopianb1514c92009-04-10 14:24:30 -0700203
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800204 void (*compileElements)(ogles_context_t*, vertex_t*, GLint, GLsizei);
205 void (*compileElement)(ogles_context_t*, vertex_t*, GLint);
206
207 void (*mvp_transform)(transform_t const*, vec4_t*, vec4_t const*);
208 void (*mv_transform)(transform_t const*, vec4_t*, vec4_t const*);
209 void (*tex_transform[2])(transform_t const*, vec4_t*, vec4_t const*);
210 void (*perspective)(ogles_context_t*c, vertex_t* v);
211 void (*clipVertex)(ogles_context_t* c, vertex_t* nv,
212 GGLfixed t, const vertex_t* s, const vertex_t* p);
213 void (*clipEye)(ogles_context_t* c, vertex_t* nv,
214 GGLfixed t, const vertex_t* s, const vertex_t* p);
215};
216
217struct vertex_cache_t {
218 enum {
219 // must be at least 4
220 // 3 vertice for triangles
221 // or 2 + 2 for indexed triangles w/ cache contention
222 VERTEX_BUFFER_SIZE = 8,
223 // must be a power of two and at least 3
224 VERTEX_CACHE_SIZE = 64, // 8 KB
225
226 INDEX_BITS = 16,
227 INDEX_MASK = ((1LU<<INDEX_BITS)-1),
228 INDEX_SEQ = 1LU<<INDEX_BITS,
229 };
230 vertex_t* vBuffer;
231 vertex_t* vCache;
232 uint32_t sequence;
233 void* base;
234 uint32_t total;
235 uint32_t misses;
236 int64_t startTime;
237 void init();
238 void uninit();
239 void clear();
240 void dump_stats(GLenum mode);
241};
242
243// ----------------------------------------------------------------------------
244// fog
245// ----------------------------------------------------------------------------
246
247struct fog_t {
248 GLfixed density;
249 GLfixed start;
250 GLfixed end;
251 GLfixed invEndMinusStart;
252 GLenum mode;
253 GLfixed (*fog)(ogles_context_t* c, GLfixed z);
254};
255
256// ----------------------------------------------------------------------------
257// user clip planes
258// ----------------------------------------------------------------------------
259
260const unsigned int OGLES_MAX_CLIP_PLANES = 6;
261
262struct clip_plane_t {
263 vec4_t equation;
264};
265
266struct user_clip_planes_t {
267 clip_plane_t plane[OGLES_MAX_CLIP_PLANES];
268 uint32_t enable;
269};
270
271// ----------------------------------------------------------------------------
272// lighting
273// ----------------------------------------------------------------------------
274
275const unsigned int OGLES_MAX_LIGHTS = 8;
276
277struct light_t {
278 vec4_t ambient;
279 vec4_t diffuse;
280 vec4_t specular;
281 vec4_t implicitAmbient;
282 vec4_t implicitDiffuse;
283 vec4_t implicitSpecular;
284 vec4_t position; // position in eye space
285 vec4_t objPosition;
286 vec4_t normalizedObjPosition;
287 vec4_t spotDir;
288 vec4_t normalizedSpotDir;
289 GLfixed spotExp;
290 GLfixed spotCutoff;
291 GLfixed spotCutoffCosine;
292 GLfixed attenuation[3];
293 GLfixed rConstAttenuation;
294 GLboolean enable;
295};
296
297struct material_t {
298 vec4_t ambient;
299 vec4_t diffuse;
300 vec4_t specular;
301 vec4_t emission;
302 GLfixed shininess;
303};
304
305struct light_model_t {
306 vec4_t ambient;
307 GLboolean twoSide;
308};
309
310struct color_material_t {
311 GLenum face;
312 GLenum mode;
313 GLboolean enable;
314};
315
316struct lighting_t {
317 light_t lights[OGLES_MAX_LIGHTS];
318 material_t front;
319 light_model_t lightModel;
320 color_material_t colorMaterial;
321 uint32_t enabledLights;
322 GLboolean enable;
323 vec4_t implicitSceneEmissionAndAmbient;
324 GLenum shadeModel;
325 typedef void (*light_fct_t)(ogles_context_t*, vertex_t*);
326 void (*lightVertex)(ogles_context_t* c, vertex_t* v);
327 void (*lightTriangle)(ogles_context_t* c,
328 vertex_t* v0, vertex_t* v1, vertex_t* v2);
329};
330
331struct culling_t {
332 GLenum cullFace;
333 GLenum frontFace;
334 GLboolean enable;
335};
336
337// ----------------------------------------------------------------------------
338// textures
339// ----------------------------------------------------------------------------
340
341struct texture_unit_t {
342 GLuint name;
343 EGLTextureObject* texture;
344 uint8_t dirty;
345};
346
347struct texture_state_t
348{
349 texture_unit_t tmu[GGL_TEXTURE_UNIT_COUNT];
350 int active; // active tmu
351 EGLTextureObject* defaultTexture;
352 GGLContext* ggl;
353 uint8_t packAlignment;
354 uint8_t unpackAlignment;
355};
356
357// ----------------------------------------------------------------------------
358// transformation and matrices
359// ----------------------------------------------------------------------------
360
361struct matrixf_t;
362
363struct matrixx_t {
364 GLfixed m[16];
365 void load(const matrixf_t& rhs);
366};
367
368struct matrix_stack_t;
369
370
371struct matrixf_t {
372 void loadIdentity();
373 void load(const matrixf_t& rhs);
374
375 inline GLfloat* editElements() { return m; }
376 inline GLfloat const* elements() const { return m; }
377
378 void set(const GLfixed* rhs);
379 void set(const GLfloat* rhs);
380
381 static void multiply(matrixf_t& r,
382 const matrixf_t& lhs, const matrixf_t& rhs);
383
384 void dump(const char* what);
385
386private:
387 friend struct matrix_stack_t;
388 GLfloat m[16];
389 void load(const GLfixed* rhs);
390 void load(const GLfloat* rhs);
391 void multiply(const matrixf_t& rhs);
392 void translate(GLfloat x, GLfloat y, GLfloat z);
393 void scale(GLfloat x, GLfloat y, GLfloat z);
394 void rotate(GLfloat a, GLfloat x, GLfloat y, GLfloat z);
395};
396
397enum {
398 OP_IDENTITY = 0x00,
399 OP_TRANSLATE = 0x01,
400 OP_UNIFORM_SCALE = 0x02,
401 OP_SCALE = 0x05,
402 OP_ROTATE = 0x08,
403 OP_SKEW = 0x10,
404 OP_ALL = 0x1F
405};
406
407struct transform_t {
408 enum {
409 FLAGS_2D_PROJECTION = 0x1
410 };
411 matrixx_t matrix;
412 uint32_t flags;
413 uint32_t ops;
Mathias Agopianb1514c92009-04-10 14:24:30 -0700414
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800415 union {
416 struct {
417 void (*point2)(transform_t const* t, vec4_t*, vec4_t const*);
418 void (*point3)(transform_t const* t, vec4_t*, vec4_t const*);
419 void (*point4)(transform_t const* t, vec4_t*, vec4_t const*);
420 };
421 void (*pointv[3])(transform_t const* t, vec4_t*, vec4_t const*);
422 };
423
424 void loadIdentity();
425 void picker();
426 void dump(const char* what);
427};
428
429struct mvui_transform_t : public transform_t
430{
431 void picker();
432};
433
434struct matrix_stack_t {
435 enum {
436 DO_PICKER = 0x1,
437 DO_FLOAT_TO_FIXED = 0x2
438 };
439 transform_t transform;
440 uint8_t maxDepth;
441 uint8_t depth;
442 uint8_t dirty;
443 uint8_t reserved;
444 matrixf_t *stack;
445 uint8_t *ops;
446 void init(int depth);
447 void uninit();
448 void loadIdentity();
449 void load(const GLfixed* rhs);
450 void load(const GLfloat* rhs);
451 void multiply(const matrixf_t& rhs);
452 void translate(GLfloat x, GLfloat y, GLfloat z);
453 void scale(GLfloat x, GLfloat y, GLfloat z);
454 void rotate(GLfloat a, GLfloat x, GLfloat y, GLfloat z);
455 GLint push();
456 GLint pop();
457 void validate();
458 matrixf_t& top() { return stack[depth]; }
459 const matrixf_t& top() const { return stack[depth]; }
460 const uint32_t top_ops() const { return ops[depth]; }
461 inline bool isRigidBody() const {
462 return !(ops[depth] & ~(OP_TRANSLATE|OP_UNIFORM_SCALE|OP_ROTATE));
463 }
464};
465
466struct vp_transform_t {
467 transform_t transform;
468 matrixf_t matrix;
469 GLfloat zNear;
470 GLfloat zFar;
471 void loadIdentity();
472};
473
474struct transform_state_t {
475 enum {
476 MODELVIEW = 0x01,
477 PROJECTION = 0x02,
478 VIEWPORT = 0x04,
479 TEXTURE = 0x08,
480 MVUI = 0x10,
481 MVIT = 0x20,
482 MVP = 0x40,
483 };
484 matrix_stack_t *current;
485 matrix_stack_t modelview;
486 matrix_stack_t projection;
487 matrix_stack_t texture[GGL_TEXTURE_UNIT_COUNT];
488
489 // modelview * projection
490 transform_t mvp __attribute__((aligned(32)));
491 // viewport transformation
492 vp_transform_t vpt __attribute__((aligned(32)));
493 // same for 4-D vertices
494 transform_t mvp4;
495 // full modelview inverse transpose
496 transform_t mvit4;
497 // upper 3x3 of mv-inverse-transpose (for normals)
498 mvui_transform_t mvui;
499
500 GLenum matrixMode;
501 GLenum rescaleNormals;
502 uint32_t dirty;
503 void invalidate();
504 void update_mvp();
505 void update_mvit();
506 void update_mvui();
507};
508
509struct viewport_t {
510 GLint x;
511 GLint y;
512 GLsizei w;
Mathias Agopianb1514c92009-04-10 14:24:30 -0700513 GLsizei h;
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800514 struct {
515 GLint x;
516 GLint y;
Mathias Agopianb1514c92009-04-10 14:24:30 -0700517 } surfaceport;
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800518 struct {
519 GLint x;
520 GLint y;
521 GLsizei w;
Mathias Agopianb1514c92009-04-10 14:24:30 -0700522 GLsizei h;
523 } scissor;
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800524};
525
526// ----------------------------------------------------------------------------
527// Lerping
528// ----------------------------------------------------------------------------
529
530struct compute_iterators_t
531{
532 void initTriangle(
533 vertex_t const* v0,
534 vertex_t const* v1,
535 vertex_t const* v2);
536
537 void initLine(
538 vertex_t const* v0,
539 vertex_t const* v1);
540
541 inline void initLerp(vertex_t const* v0, uint32_t enables);
542
543 int iteratorsScale(int32_t it[3],
544 int32_t c0, int32_t c1, int32_t c2) const;
545
546 void iterators1616(GGLfixed it[3],
547 GGLfixed c0, GGLfixed c1, GGLfixed c2) const;
548
549 void iterators0032(int32_t it[3],
550 int32_t c0, int32_t c1, int32_t c2) const;
551
552 void iterators0032(int64_t it[3],
553 int32_t c0, int32_t c1, int32_t c2) const;
554
555 GGLcoord area() const { return m_area; }
556
557private:
558 // don't change order of members here -- used by iterators.S
559 GGLcoord m_dx01, m_dy10, m_dx20, m_dy02;
560 GGLcoord m_x0, m_y0;
561 GGLcoord m_area;
562 uint8_t m_scale;
563 uint8_t m_area_scale;
564 uint8_t m_reserved[2];
565
566};
567
568// ----------------------------------------------------------------------------
569// state
570// ----------------------------------------------------------------------------
571
572#ifdef HAVE_ANDROID_OS
573 // We have a dedicated TLS slot in bionic
574 inline void setGlThreadSpecific(ogles_context_t *value) {
575 ((uint32_t *)__get_tls())[TLS_SLOT_OPENGL] = (uint32_t)value;
576 }
577 inline ogles_context_t* getGlThreadSpecific() {
578 return (ogles_context_t *)(((unsigned *)__get_tls())[TLS_SLOT_OPENGL]);
579 }
580#else
581 extern pthread_key_t gGLKey;
582 inline void setGlThreadSpecific(ogles_context_t *value) {
583 pthread_setspecific(gGLKey, value);
584 }
585 inline ogles_context_t* getGlThreadSpecific() {
586 return static_cast<ogles_context_t*>(pthread_getspecific(gGLKey));
587 }
588#endif
589
590
591struct prims_t {
592 typedef ogles_context_t* GL;
593 void (*renderPoint)(GL, vertex_t*);
594 void (*renderLine)(GL, vertex_t*, vertex_t*);
595 void (*renderTriangle)(GL, vertex_t*, vertex_t*, vertex_t*);
596};
597
Mathias Agopianb1514c92009-04-10 14:24:30 -0700598struct copybits_context_t {
599 // A handle to the blit engine, if it exists, else NULL.
600 copybit_device_t* blitEngine;
601 int32_t minScale;
602 int32_t maxScale;
603 // File descriptor of current drawing surface, if it's suitable for use as
604 // a copybits destination, else -1.
605 int drawSurfaceFd;
606};
607
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800608struct ogles_context_t {
609 context_t rasterizer;
610 array_machine_t arrays __attribute__((aligned(32)));
611 texture_state_t textures;
612 transform_state_t transforms;
613 vertex_cache_t vc;
614 prims_t prims;
615 culling_t cull;
616 lighting_t lighting;
617 user_clip_planes_t clipPlanes;
618 compute_iterators_t lerp; __attribute__((aligned(32)));
619 vertex_t current;
620 vec4_t currentColorClamped;
621 vec3_t currentNormal;
622 viewport_t viewport;
623 point_size_t point;
624 line_width_t line;
625 polygon_offset_t polygonOffset;
626 fog_t fog;
627 uint32_t perspective : 1;
628 uint32_t transformTextures : 1;
629 EGLSurfaceManager* surfaceManager;
630 EGLBufferObjectManager* bufferObjectManager;
Mathias Agopianb1514c92009-04-10 14:24:30 -0700631
632 // copybits is only used if LIBAGL_USE_GRALLOC_COPYBITS is
633 // defined, but it is always present because ogles_context_t is a public
634 // struct that is used by clients of libagl. We want the size and offsets
635 // to stay the same, whether or not LIBAGL_USE_GRALLOC_COPYBITS is defined.
636
637 copybits_context_t copybits;
638
The Android Open Source Project89fa4ad2009-03-03 19:31:44 -0800639 GLenum error;
640
641 static inline ogles_context_t* get() {
642 return getGlThreadSpecific();
643 }
644
645};
646
647}; // namespace gl
648}; // namespace android
649
650#endif // ANDROID_OPENGLES_CONTEXT_H
651