1 #include "coregl_fastpath.h"
7 #define _COREGL_SYMBOL(IS_EXTENSION, RET_TYPE, FUNC_NAME, PARAM_LIST) RET_TYPE (*_orig_fastpath_##FUNC_NAME) PARAM_LIST = NULL;
8 #include "../../headers/sym.h"
11 Fastpath_Opt_Flag fp_opt = FP_UNKNOWN_PATH;
14 FILE *trace_fp = NULL;
16 GLenum FPGL_Error = GL_NO_ERROR;
18 GLGlueContext_List *gctx_list = NULL;
20 Mutex init_context_mutex = MUTEX_INITIALIZER;
21 GLGlueContext *initial_ctx = NULL;
23 Mutex ctx_list_access_mutex = MUTEX_INITIALIZER;
25 GLContext_List *glctx_list = NULL;
28 _get_texture_states(GLenum pname, GLint *params)
30 GLuint cur_active_tex = 0;
32 AST(initial_ctx != NULL);
34 _sym_glGetIntegerv(GL_ACTIVE_TEXTURE, (GLint *)&cur_active_tex);
36 for (i = 0; i < initial_ctx->gl_num_tex_units[0]; i++)
38 _sym_glActiveTexture(GL_TEXTURE0 + i);
39 _sym_glGetIntegerv(pname, &(((GLint *)params)[i]));
41 _sym_glActiveTexture(cur_active_tex);
45 _get_stencil_max_mask()
47 GLuint stencil_bit = 0;
49 _sym_glGetIntegerv(GL_STENCIL_BITS, (GLint *)&stencil_bit);
50 return (1 << stencil_bit) - 1;
54 init_modules_fastpath()
58 LOG("[CoreGL] <Fastpath> : ");
60 fastpath_opt = atoi(get_env_setting("COREGL_FASTPATH"));
65 LOG("(%d) Fastpath enabled...\n", fastpath_opt);
66 fp_opt = FP_FAST_PATH;
69 LOG("(%d) Default API path enabled...\n", fastpath_opt);
70 fp_opt = FP_NORMAL_PATH;
74 debug_nofp = atoi(get_env_setting("COREGL_DEBUG_NOFP"));
76 fastpath_apply_overrides();
81 deinit_modules_fastpath()
83 GLContext_List *current = NULL;
85 AST(mutex_lock(&ctx_list_access_mutex) == 1);
87 // Destroy remained context & Detect leaks
88 int retry_destroy = 0;
96 if (current->cstate != NULL)
98 ERR("\E[0;31;1mWARNING : Context attached to [dpy=%p|rctx=%p] has not been completely destroyed.(leak)\E[0m\n", current->cstate->rdpy, current->cstate->rctx);
100 _sym_eglMakeCurrent(current->cstate->rdpy, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
101 _sym_eglDestroyContext(current->cstate->rdpy, current->cstate->rctx);
103 fastpath_remove_context_states_from_list(current->cstate, NULL);
108 glctx_list = current->next;
110 current = glctx_list;
112 if (retry_destroy == 0) break;
117 AST(mutex_unlock(&ctx_list_access_mutex) == 1);
121 init_modules_tstate_fastpath(GLThreadState *tstate)
123 MY_MODULE_TSTATE *tstate_mt = NULL;
125 tstate_mt = (MY_MODULE_TSTATE *)calloc(1, sizeof(MY_MODULE_TSTATE));
127 tstate_mt->binded_api = EGL_OPENGL_ES_API;
129 tstate->module_data[MY_MODULE_ID] = tstate_mt;
133 deinit_modules_tstate_fastpath(GLThreadState *tstate)
135 if (tstate->module_data[MY_MODULE_ID] != NULL)
137 free(tstate->module_data[MY_MODULE_ID]);
138 tstate->module_data[MY_MODULE_ID] = NULL;
143 fastpath_apply_overrides()
148 fastpath_apply_overrides_egl(1);
149 fastpath_apply_overrides_gl(1);
154 ERR("Invalide GL Override Option!!!\n");
159 #define OVERRIDE(f) \
162 COREGL_OVERRIDE_API(_orig_fastpath_, f, ovr_); \
163 COREGL_OVERRIDE_API(ovr_, f, fastpath_); \
167 AST(ovr_##f != NULL); \
168 COREGL_OVERRIDE_API(ovr_, f, _orig_fastpath_); \
169 _orig_fastpath_##f = NULL; \
173 fastpath_apply_overrides_egl(int enable)
175 // Fast-Path Core Functions
176 OVERRIDE(eglGetProcAddress);
178 OVERRIDE(eglBindAPI);
179 OVERRIDE(eglQueryAPI);
181 OVERRIDE(eglCreateContext);
182 OVERRIDE(eglCreateImageKHR);
183 OVERRIDE(eglMakeCurrent);
184 OVERRIDE(eglDestroyContext);
185 OVERRIDE(eglQueryContext);
186 OVERRIDE(eglGetCurrentContext);
187 OVERRIDE(eglReleaseThread);
188 OVERRIDE(eglGetCurrentSurface);
189 OVERRIDE(eglTerminate);
194 fastpath_apply_overrides_gl(int enable)
196 // Fast-Path Functions
199 OVERRIDE(glGetError);
201 OVERRIDE(glGetIntegerv);
202 OVERRIDE(glGetFloatv);
203 OVERRIDE(glGetBooleanv);
205 OVERRIDE(glActiveTexture);
206 OVERRIDE(glGenTextures);
207 OVERRIDE(glBindTexture);
208 OVERRIDE(glIsTexture);
209 OVERRIDE(glDeleteTextures);
210 OVERRIDE(glFramebufferTexture2D);
211 OVERRIDE(glFramebufferTexture2DMultisampleEXT);
213 OVERRIDE(glGenBuffers);
214 OVERRIDE(glBindBuffer);
215 OVERRIDE(glIsBuffer);
216 OVERRIDE(glDeleteBuffers);
218 OVERRIDE(glGenFramebuffers);
219 OVERRIDE(glBindFramebuffer);
220 OVERRIDE(glIsFramebuffer);
221 OVERRIDE(glDeleteFramebuffers);
223 OVERRIDE(glGenRenderbuffers);
224 OVERRIDE(glBindRenderbuffer);
225 OVERRIDE(glFramebufferRenderbuffer);
226 OVERRIDE(glIsRenderbuffer);
227 OVERRIDE(glDeleteRenderbuffers);
229 OVERRIDE(glCreateShader);
230 OVERRIDE(glCreateProgram);
231 OVERRIDE(glAttachShader);
232 OVERRIDE(glCompileShader);
233 OVERRIDE(glShaderBinary);
234 OVERRIDE(glDeleteShader);
235 OVERRIDE(glDetachShader);
236 OVERRIDE(glGetShaderiv);
237 OVERRIDE(glGetShaderInfoLog);
238 OVERRIDE(glGetShaderSource);
239 OVERRIDE(glIsShader);
240 OVERRIDE(glShaderSource);
241 OVERRIDE(glBindAttribLocation);
242 OVERRIDE(glDeleteProgram);
243 OVERRIDE(glDetachShader);
244 OVERRIDE(glGetActiveAttrib);
245 OVERRIDE(glGetActiveUniform);
246 OVERRIDE(glGetAttachedShaders);
247 OVERRIDE(glGetAttribLocation);
248 OVERRIDE(glGetProgramiv);
249 OVERRIDE(glGetProgramInfoLog);
250 OVERRIDE(glGetUniformfv);
251 OVERRIDE(glGetUniformiv);
252 OVERRIDE(glGetUniformLocation);
253 OVERRIDE(glIsProgram);
254 OVERRIDE(glLinkProgram);
255 OVERRIDE(glUseProgram);
256 OVERRIDE(glValidateProgram);
257 OVERRIDE(glGetProgramBinary);
258 OVERRIDE(glProgramBinary);
260 OVERRIDE(glBlendColor);
261 OVERRIDE(glBlendEquation);
262 OVERRIDE(glBlendEquationSeparate);
263 OVERRIDE(glBlendFunc);
264 OVERRIDE(glBlendFuncSeparate);
265 OVERRIDE(glClearColor);
266 OVERRIDE(glClearDepthf);
267 OVERRIDE(glClearStencil);
268 OVERRIDE(glColorMask);
269 OVERRIDE(glCullFace);
270 OVERRIDE(glDepthFunc);
271 OVERRIDE(glDepthMask);
272 OVERRIDE(glDepthRangef);
274 OVERRIDE(glDisableVertexAttribArray);
275 OVERRIDE(glDrawArrays);
276 OVERRIDE(glDrawElements);
278 OVERRIDE(glEnableVertexAttribArray);
279 OVERRIDE(glFrontFace);
280 OVERRIDE(glGetVertexAttribfv);
281 OVERRIDE(glGetVertexAttribiv);
282 OVERRIDE(glGetVertexAttribPointerv);
284 OVERRIDE(glLineWidth);
285 OVERRIDE(glPixelStorei);
286 OVERRIDE(glPolygonOffset);
287 OVERRIDE(glSampleCoverage);
289 OVERRIDE(glStencilFunc);
290 OVERRIDE(glStencilFuncSeparate);
291 OVERRIDE(glStencilMask);
292 OVERRIDE(glStencilMaskSeparate);
293 OVERRIDE(glStencilOp);
294 OVERRIDE(glStencilOpSeparate);
295 OVERRIDE(glVertexAttrib1f);
296 OVERRIDE(glVertexAttrib1fv);
297 OVERRIDE(glVertexAttrib2f);
298 OVERRIDE(glVertexAttrib2fv);
299 OVERRIDE(glVertexAttrib3f);
300 OVERRIDE(glVertexAttrib3fv);
301 OVERRIDE(glVertexAttrib4f);
302 OVERRIDE(glVertexAttrib4fv);
303 OVERRIDE(glVertexAttribPointer);
304 OVERRIDE(glViewport);
306 OVERRIDE(glEGLImageTargetTexture2DOES);
311 LOG("\E[0;35;1m[CoreGL] SKIP GL FASTPATH...\E[0m\n");
318 _get_shared_object(GL_Shared_Object_State *sostate, GL_Object_Type type)
322 case GL_OBJECT_TYPE_TEXTURE:
323 return sostate->texture;
324 case GL_OBJECT_TYPE_BUFFER:
325 return sostate->buffer;
326 case GL_OBJECT_TYPE_FRAMEBUFFER:
327 return sostate->framebuffer;
328 case GL_OBJECT_TYPE_RENDERBUFFER:
329 return sostate->renderbuffer;
330 case GL_OBJECT_TYPE_PROGRAM:
331 return sostate->program;
338 fastpath_add_context_state_to_list(const void *option, const int option_len, GLContextState *cstate, Mutex *mtx)
342 GLContext_List *current = NULL;
343 GLContext_List *newitm = NULL;
345 if (mtx != NULL) AST(mutex_lock(mtx) == 1);
349 tid = get_current_thread();
351 current = glctx_list;
352 while (current != NULL)
354 if (current->option_len == option_len &&
355 memcmp(current->option, option, option_len) == 0 &&
356 current->thread_id == tid)
358 AST(current->cstate == cstate);
361 current = current->next;
364 newitm = (GLContext_List *)calloc(1, sizeof(GLContext_List));
367 ERR("Failed to create context list.\n");
371 newitm->cstate = cstate;
372 newitm->thread_id = tid;
373 newitm->option_len = option_len;
374 newitm->option = (void *)malloc(option_len);
375 memcpy(newitm->option, option, option_len);
377 if (glctx_list != NULL)
378 newitm->next = glctx_list;
399 if (mtx != NULL) AST(mutex_unlock(mtx) == 1);
405 fastpath_get_context_state_from_list(const void *option, const int option_len, Mutex *mtx)
407 GLContextState *ret = NULL;
408 GLContext_List *current = NULL;
411 if (mtx != NULL) AST(mutex_lock(mtx) == 1);
413 tid = get_current_thread();
415 current = glctx_list;
416 while (current != NULL)
418 if (current->option_len == option_len &&
419 memcmp(current->option, option, option_len) == 0 &&
420 current->thread_id == tid)
422 ret = current->cstate;
425 current = current->next;
430 if (mtx != NULL) AST(mutex_unlock(mtx) == 1);
435 fastpath_remove_context_states_from_list(GLContextState *cstate, Mutex *mtx)
439 GLContext_List *olditm = NULL;
440 GLContext_List *current = NULL;
442 if (mtx != NULL) AST(mutex_lock(mtx) == 1);
446 tid = get_current_thread();
447 current = glctx_list;
449 while (current != NULL)
451 if (current->cstate == cstate)
453 GLContext_List *nextitm = NULL;
456 olditm->next = current->next;
457 nextitm = olditm->next;
461 glctx_list = current->next;
462 nextitm = glctx_list;
470 current = current->next;
475 if (mtx != NULL) AST(mutex_unlock(mtx) == 1);
480 fastpath_sostate_create_object(GL_Shared_Object_State *sostate, GL_Object_Type type, GLuint real_name)
482 GL_Object **object = NULL;
483 GLuint ret = _COREGL_INT_INIT_VALUE;
486 object = _get_shared_object(sostate, type);
488 for (i = 1; i < MAX_GL_OBJECT_SIZE; i++)
490 if (object[i] == NULL)
492 GL_Object *newobj = (GL_Object *)calloc(1, sizeof(GL_Object));
493 newobj->id = (int)type + i;
494 newobj->real_id = real_name;
507 fastpath_sostate_remove_object(GL_Shared_Object_State *sostate, GL_Object_Type type, GLuint glue_name)
509 GL_Object **object = NULL;
510 GLuint ret = _COREGL_INT_INIT_VALUE;
511 int hash = _COREGL_INT_INIT_VALUE;
513 object = _get_shared_object(sostate, type);
515 hash = glue_name - (int)type;
517 hash > MAX_GL_OBJECT_SIZE ||
518 object[hash] == NULL ||
519 object[hash]->id != glue_name)
535 fastpath_sostate_get_object(GL_Shared_Object_State *sostate, GL_Object_Type type, GLuint glue_name)
537 GL_Object **object = NULL;
538 GLuint ret = _COREGL_INT_INIT_VALUE;
539 int hash = _COREGL_INT_INIT_VALUE;
541 object = _get_shared_object(sostate, type);
543 hash = glue_name - (int)type;
545 hash > MAX_GL_OBJECT_SIZE ||
546 object[hash] == NULL ||
547 object[hash]->id != glue_name)
552 ret = object[hash]->real_id;
560 fastpath_sostate_find_object(GL_Shared_Object_State *sostate, GL_Object_Type type, GLuint real_name)
562 GL_Object **object = NULL;
563 GLuint ret = _COREGL_INT_INIT_VALUE;
566 object = _get_shared_object(sostate, type);
568 for (i = 1; i < MAX_GL_OBJECT_SIZE; i++)
570 if (object[i] != NULL && object[i]->real_id == real_name)
584 fastpath_dump_context_states(GLGlueContext *ctx, int force_output)
586 static struct timeval tv_last = { 0, 0 };
588 if (unlikely(trace_state_flag != 1)) return;
592 struct timeval tv_now = { 0, 0 };
593 AST(gettimeofday(&tv_now, NULL) == 0);
594 if (tv_now.tv_sec - tv_last.tv_sec < _COREGL_TRACE_OUTPUT_INTERVAL_SEC)
602 TRACE("\E[0;40;34m========================================================================================================================\E[0m\n");
603 TRACE("\E[0;32;1m State info \E[1;37;1m: GlueCTX = %p\E[0m\n", ctx);
604 TRACE("\E[0;40;34m========================================================================================================================\E[0m\n");
606 #define PRINTF_CHAR_GLenum "%10d"
607 #define PRINTF_CHAR_GLboolean "%10d"
608 #define PRINTF_CHAR_GLint "%10d"
609 #define PRINTF_CHAR_GLsizei "%10u"
610 #define PRINTF_CHAR_GLuint "%10u"
611 #define PRINTF_CHAR_GLuintmask "0x%8X"
613 #define PRINTF_CHAR_GLclampf "%10.6f"
614 #define PRINTF_CHAR_GLfloat "%10.6f"
616 #define PRINTF_CHAR_GLvoidptr "%10p"
618 #define PRINTF_CHAR(type) PRINTF_CHAR_##type
620 #define INITIAL_CTX initial_ctx
621 #define GLUE_STATE(TYPE, NAME, SIZE, ARRAY_SIZE, DEFAULT_STMT, GET_STMT) \
623 TYPE valuedata[SIZE]; \
624 TYPE *value = NULL; \
625 value = valuedata; GET_STMT; value = valuedata; \
626 TRACE("\E[0;37;1m %-30.30s : (\E[0m ", #NAME); \
627 for (int i = 0; i < SIZE; i++) \
631 TRACE("\n %-30.30s ", "");\
635 TRACE(PRINTF_CHAR(TYPE), ctx->NAME[i]); \
636 TRACE("["PRINTF_CHAR(TYPE)"]", value[i]); \
638 TRACE(" \E[0;37;1m)\E[0m\n"); \
640 # include "coregl_fastpath_state.h"
644 TRACE("\E[0;40;34m========================================================================================================================\E[0m\n");
654 fastpath_init_context_states(GLGlueContext *ctx)
658 AST(mutex_lock(&init_context_mutex) == 1);
662 ERR("Context NULL\n");
667 AST(ctx->initialized == 0);
668 AST(ctx->sostate != NULL);
670 if (initial_ctx == NULL)
672 initial_ctx = (GLGlueContext *)calloc(1, sizeof(GLGlueContext));
673 AST(initial_ctx != NULL);
675 //#define FORCE_DEFAULT_VALUE
676 #ifdef FORCE_DEFAULT_VALUE
677 # define INITIAL_CTX initial_ctx
678 # define GLUE_STATE(TYPE, NAME, SIZE, ARRAY_SIZE, DEFAULT_STMT, GET_STMT) \
681 TYPE valuedata[SIZE]; \
682 TYPE *value = NULL; \
683 memset(valuedata, 0xcc, sizeof(TYPE) * SIZE); \
684 value = valuedata; DEFAULT_STMT; value = valuedata; \
685 for (i = 0; i < SIZE; i++) \
687 if (*((char *)(&value[i])) == 0xcc) \
689 memset(&value[i], 0xaa, sizeof(TYPE)); \
690 value = valuedata; DEFAULT_STMT; value = valuedata; \
691 if (*((char *)(&value[i])) == 0xaa) \
693 ERR("\E[0;31;1mWARNING : GL-state '"#NAME"' cannot be retrieved\E[0m\n"); \
697 initial_ctx->NAME[i] = value[i]; \
700 # include "coregl_fastpath_state.h"
704 # define INITIAL_CTX initial_ctx
705 # define SET_GLUE_VALUE(DEFAULT_STMT, FALLBACK_STMT) \
708 value = valuedata; DEFAULT_STMT; value = valuedata; \
712 value = valuedata; FALLBACK_STMT; value = valuedata; \
715 # define GLUE_STATE(TYPE, NAME, SIZE, ARRAY_SIZE, DEFAULT_STMT, GET_STMT) \
719 TYPE valuedata[SIZE]; \
720 TYPE *value = NULL; \
721 memset(valuedata, 0xcc, sizeof(TYPE) * SIZE); \
724 SET_GLUE_VALUE(GET_STMT, DEFAULT_STMT); \
725 for (i = 0; i < SIZE; i++) \
727 if (*((char *)(&value[i])) == 0xcc) \
729 memset(&value[i], 0xaa, sizeof(TYPE)); \
730 SET_GLUE_VALUE(GET_STMT, DEFAULT_STMT); \
731 if (*((char *)(&value[i])) == 0xaa) \
736 ERR("\E[0;31;1mWARNING : GL-state '"#NAME"' cannot be retrieved\E[0m\n"); \
741 initial_ctx->NAME[i] = value[i]; \
745 value = valuedata; DEFAULT_STMT; value = valuedata; \
746 for (i = 0; i < SIZE; i++) \
748 if (initial_ctx->NAME[i] != value[i]) \
750 ERR("WARNING : GL-state '"#NAME"'[%d] value ["PRINTF_CHAR(TYPE)"] is different from SPEC-DEFAULT ["PRINTF_CHAR(TYPE)"]\n", i, ctx->NAME[i], value[i]); \
755 while (try_step == 2); \
757 # include "coregl_fastpath_state.h"
758 # undef SET_GLUE_VALUE
763 if (initial_ctx->gl_num_vertex_attribs[0] > MAX_VERTEX_ATTRIBS)
765 ERR("\E[0;31;1mWARNING : Number of vertex attrib is too big! (%d-%d)\E[0m\n", MAX_VERTEX_ATTRIBS, initial_ctx->gl_num_vertex_attribs[0]);
767 if (initial_ctx->gl_num_tex_units[0] > MAX_TEXTURE_UNITS)
769 ERR("\E[0;31;1mWARNING : Number of texture unit is too big! (%d-%d)\E[0m\n", MAX_TEXTURE_UNITS, initial_ctx->gl_num_tex_units[0]);
775 #define INITIAL_CTX initial_ctx
776 #define GLUE_STATE(TYPE, NAME, SIZE, ARRAY_SIZE, DEFAULT_STMT, GET_STMT) \
777 for (i = 0; i < SIZE; i++) \
779 ctx->NAME[i] = initial_ctx->NAME[i]; \
781 # include "coregl_fastpath_state.h"
786 ctx->initialized = 1;
791 AST(mutex_unlock(&init_context_mutex) == 1);
796 #ifdef COREGL_USE_MODULE_TRACEPATH
797 extern void *tracepath_api_trace_begin(const char *name, void *hint, int trace_total_time);
798 extern void *tracepath_api_trace_end(const char *name, void *hint, int trace_total_time);
802 fastpath_make_context_current(GLGlueContext *oldctx, GLGlueContext *newctx)
804 unsigned char flag = 0;
807 if (debug_nofp == 1) goto finish;
809 // Return if they're the same
810 if (oldctx == newctx) goto finish;
812 #define STATE_COMPARE(state) \
813 if ((oldctx->state) != (newctx->state))
815 #define STATES_COMPARE(state_ptr, bytes) \
816 if ((memcmp((oldctx->state_ptr), (newctx->state_ptr), (bytes))) != 0)
819 #ifdef COREGL_USE_MODULE_TRACEPATH
820 static void *trace_hint_glfinish = NULL;
821 trace_hint_glfinish = tracepath_api_trace_begin("eglMakeCurrent(FP glFinish)", trace_hint_glfinish, 0);
822 #endif // COREGL_USE_MODULE_TRACEPATH
826 #ifdef COREGL_USE_MODULE_TRACEPATH
827 tracepath_api_trace_end("eglMakeCurrent(FP glFinish)", trace_hint_glfinish, 0);
828 #endif // COREGL_USE_MODULE_TRACEPATH
830 #ifdef COREGL_USE_MODULE_TRACEPATH
831 static void *trace_hint_bindbuffers = NULL;
832 trace_hint_bindbuffers = tracepath_api_trace_begin("eglMakeCurrent(FP bind buffers)", trace_hint_bindbuffers, 0);
833 #endif // COREGL_USE_MODULE_TRACEPATH
835 //------------------//
837 flag = oldctx->_bind_flag | newctx->_bind_flag;
840 STATE_COMPARE(gl_array_buffer_binding[0])
842 _sym_glBindBuffer(GL_ARRAY_BUFFER, newctx->gl_array_buffer_binding[0]);
844 STATE_COMPARE(gl_element_array_buffer_binding[0])
846 _sym_glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, newctx->gl_element_array_buffer_binding[0]);
848 STATE_COMPARE(gl_framebuffer_binding[0])
850 _sym_glBindFramebuffer(GL_FRAMEBUFFER, newctx->gl_framebuffer_binding[0]);
852 STATE_COMPARE(gl_renderbuffer_binding[0])
854 _sym_glBindRenderbuffer(GL_RENDERBUFFER, newctx->gl_renderbuffer_binding[0]);
858 #ifdef COREGL_USE_MODULE_TRACEPATH
859 tracepath_api_trace_end("eglMakeCurrent(FP bind buffers)", trace_hint_bindbuffers, 0);
860 #endif // COREGL_USE_MODULE_TRACEPATH
863 //------------------//
866 #ifdef COREGL_USE_MODULE_TRACEPATH
867 static void *trace_hint_enable_states = NULL;
868 trace_hint_enable_states = tracepath_api_trace_begin("eglMakeCurrent(FP enable states)", trace_hint_enable_states, 0);
869 #endif // COREGL_USE_MODULE_TRACEPATH
871 flag = oldctx->_enable_flag1 | newctx->_enable_flag1;
874 STATE_COMPARE(gl_blend[0])
876 if (newctx->gl_blend[0])
877 _sym_glEnable(GL_BLEND);
879 _sym_glDisable(GL_BLEND);
881 STATE_COMPARE(gl_cull_face[0])
883 if (newctx->gl_cull_face[0])
884 _sym_glEnable(GL_CULL_FACE);
886 _sym_glDisable(GL_CULL_FACE);
888 STATE_COMPARE(gl_depth_test[0])
890 if (newctx->gl_depth_test[0])
891 _sym_glEnable(GL_DEPTH_TEST);
893 _sym_glDisable(GL_DEPTH_TEST);
895 STATE_COMPARE(gl_dither[0])
897 if (newctx->gl_dither[0])
898 _sym_glEnable(GL_DITHER);
900 _sym_glDisable(GL_DITHER);
905 flag = oldctx->_enable_flag2 | newctx->_enable_flag2;
908 STATE_COMPARE(gl_polygon_offset_fill[0])
910 if (newctx->gl_polygon_offset_fill[0])
911 _sym_glEnable(GL_POLYGON_OFFSET_FILL);
913 _sym_glDisable(GL_POLYGON_OFFSET_FILL);
915 STATE_COMPARE(gl_sample_alpha_to_coverage[0])
917 if (newctx->gl_sample_alpha_to_coverage[0])
918 _sym_glEnable(GL_SAMPLE_ALPHA_TO_COVERAGE);
920 _sym_glDisable(GL_SAMPLE_ALPHA_TO_COVERAGE);
922 STATE_COMPARE(gl_sample_coverage[0])
924 if (newctx->gl_sample_coverage[0])
925 _sym_glEnable(GL_SAMPLE_COVERAGE);
927 _sym_glDisable(GL_SAMPLE_COVERAGE);
929 STATE_COMPARE(gl_scissor_test[0])
931 if (newctx->gl_scissor_test[0])
932 _sym_glEnable(GL_SCISSOR_TEST);
934 _sym_glDisable(GL_SCISSOR_TEST);
936 STATE_COMPARE(gl_stencil_test[0])
938 if (newctx->gl_stencil_test[0])
939 _sym_glEnable(GL_STENCIL_TEST);
941 _sym_glDisable(GL_STENCIL_TEST);
945 #ifdef COREGL_USE_MODULE_TRACEPATH
946 tracepath_api_trace_end("eglMakeCurrent(FP enable states)", trace_hint_enable_states, 0);
947 #endif // COREGL_USE_MODULE_TRACEPATH
949 //------------------//
951 #ifdef COREGL_USE_MODULE_TRACEPATH
952 static void *trace_hint_clear_viewport = NULL;
953 trace_hint_clear_viewport = tracepath_api_trace_begin("eglMakeCurrent(FP clear/viewport)", trace_hint_clear_viewport, 0);
954 #endif // COREGL_USE_MODULE_TRACEPATH
956 flag = oldctx->_clear_flag1 | newctx->_clear_flag1;
960 STATES_COMPARE(gl_viewport, 4 * sizeof(GLint))
962 _sym_glViewport(newctx->gl_viewport[0],
963 newctx->gl_viewport[1],
964 newctx->gl_viewport[2],
965 newctx->gl_viewport[3]);
968 STATE_COMPARE(gl_current_program[0])
970 _sym_glUseProgram(newctx->gl_current_program[0]);
972 STATES_COMPARE(gl_color_clear_value, 4 * sizeof(GLclampf))
974 _sym_glClearColor(newctx->gl_color_clear_value[0],
975 newctx->gl_color_clear_value[1],
976 newctx->gl_color_clear_value[2],
977 newctx->gl_color_clear_value[3]);
983 flag = oldctx->_clear_flag2 | newctx->_clear_flag2;
986 STATES_COMPARE(gl_color_writemask, 4 * sizeof(GLboolean))
988 _sym_glColorMask(newctx->gl_color_writemask[0],
989 newctx->gl_color_writemask[1],
990 newctx->gl_color_writemask[2],
991 newctx->gl_color_writemask[3]);
993 STATES_COMPARE(gl_depth_range, 2 * sizeof(GLclampf))
995 _sym_glDepthRangef(newctx->gl_depth_range[0],
996 newctx->gl_depth_range[1]);
998 STATE_COMPARE(gl_depth_clear_value[0])
1000 _sym_glClearDepthf(newctx->gl_depth_clear_value[0]);
1002 STATE_COMPARE(gl_depth_func[0])
1004 _sym_glDepthFunc(newctx->gl_depth_func[0]);
1006 STATE_COMPARE(gl_depth_writemask[0])
1008 _sym_glDepthMask(newctx->gl_depth_writemask[0]);
1010 STATE_COMPARE(gl_cull_face_mode[0])
1012 _sym_glCullFace(newctx->gl_cull_face_mode[0]);
1017 #ifdef COREGL_USE_MODULE_TRACEPATH
1018 tracepath_api_trace_end("eglMakeCurrent(FP clear/viewport)", trace_hint_clear_viewport, 0);
1019 #endif // COREGL_USE_MODULE_TRACEPATH
1021 //------------------//
1023 #ifdef COREGL_USE_MODULE_TRACEPATH
1024 static void *trace_hint_bind_textures = NULL;
1025 trace_hint_bind_textures = tracepath_api_trace_begin("eglMakeCurrent(FP bind textures)", trace_hint_bind_textures, 0);
1026 #endif // COREGL_USE_MODULE_TRACEPATH
1028 flag = oldctx->_tex_flag1 | newctx->_tex_flag1;
1032 for (i = 0; i < oldctx->gl_num_tex_units[0]; i++)
1034 STATE_COMPARE(gl_tex_2d_state[i])
1036 _sym_glActiveTexture(GL_TEXTURE0 + i);
1037 _sym_glBindTexture(GL_TEXTURE_2D, newctx->gl_tex_2d_state[i]);
1040 STATE_COMPARE(gl_tex_cube_state[i])
1042 _sym_glActiveTexture(GL_TEXTURE0 + i);
1043 _sym_glBindTexture(GL_TEXTURE_CUBE_MAP, newctx->gl_tex_cube_state[i]);
1047 // Restore active texture
1048 _sym_glActiveTexture(newctx->gl_active_texture[0]);
1050 STATE_COMPARE(gl_generate_mipmap_hint[0])
1052 _sym_glHint(GL_GENERATE_MIPMAP_HINT, newctx->gl_generate_mipmap_hint[0]);
1055 #ifdef COREGL_USE_MODULE_TRACEPATH
1056 tracepath_api_trace_end("eglMakeCurrent(FP bind textures)", trace_hint_bind_textures, 0);
1057 #endif // COREGL_USE_MODULE_TRACEPATH
1059 //------------------//
1060 #ifdef COREGL_USE_MODULE_TRACEPATH
1061 static void *trace_hint_etc = NULL;
1062 trace_hint_etc = tracepath_api_trace_begin("eglMakeCurrent(FP etc.)", trace_hint_etc, 0);
1063 #endif // COREGL_USE_MODULE_TRACEPATH
1065 flag = oldctx->_blend_flag | newctx->_blend_flag;
1068 STATES_COMPARE(gl_blend_color, 4 * sizeof(GLclampf))
1070 _sym_glBlendColor(newctx->gl_blend_color[0],
1071 newctx->gl_blend_color[1],
1072 newctx->gl_blend_color[2],
1073 newctx->gl_blend_color[3]);
1075 if ((oldctx->gl_blend_src_rgb[0] != newctx->gl_blend_src_rgb[0]) ||
1076 (oldctx->gl_blend_dst_rgb[0] != newctx->gl_blend_dst_rgb[0]) ||
1077 (oldctx->gl_blend_src_alpha[0] != newctx->gl_blend_src_alpha[0]) ||
1078 (oldctx->gl_blend_dst_alpha[0] != newctx->gl_blend_dst_alpha[0]))
1080 _sym_glBlendFuncSeparate(newctx->gl_blend_src_rgb[0],
1081 newctx->gl_blend_dst_rgb[0],
1082 newctx->gl_blend_src_alpha[0],
1083 newctx->gl_blend_dst_alpha[0]);
1085 if ((oldctx->gl_blend_equation_rgb[0] != newctx->gl_blend_equation_rgb[0]) ||
1086 (oldctx->gl_blend_equation_alpha[0] != newctx->gl_blend_equation_alpha[0]))
1088 _sym_glBlendEquationSeparate(newctx->gl_blend_equation_rgb[0], newctx->gl_blend_equation_alpha[0]);
1093 //------------------//
1095 flag = oldctx->_stencil_flag1 | newctx->_stencil_flag1;
1098 if ((oldctx->gl_stencil_func[0] != newctx->gl_stencil_func[0]) ||
1099 (oldctx->gl_stencil_ref[0] != newctx->gl_stencil_ref[0]) ||
1100 (oldctx->gl_stencil_value_mask[0] != newctx->gl_stencil_value_mask[0]))
1102 _sym_glStencilFuncSeparate(GL_FRONT,
1103 newctx->gl_stencil_func[0],
1104 newctx->gl_stencil_ref[0],
1105 newctx->gl_stencil_value_mask[0]);
1107 if ((oldctx->gl_stencil_fail[0] != newctx->gl_stencil_fail[0]) ||
1108 (oldctx->gl_stencil_pass_depth_fail[0] != newctx->gl_stencil_pass_depth_fail[0]) ||
1109 (oldctx->gl_stencil_pass_depth_pass[0] != newctx->gl_stencil_pass_depth_pass[0]))
1111 _sym_glStencilOpSeparate(GL_FRONT,
1112 newctx->gl_stencil_fail[0],
1113 newctx->gl_stencil_pass_depth_fail[0],
1114 newctx->gl_stencil_pass_depth_pass[0]);
1117 STATE_COMPARE(gl_stencil_writemask[0])
1119 _sym_glStencilMaskSeparate(GL_FRONT, newctx->gl_stencil_writemask[0]);
1125 flag = oldctx->_stencil_flag2 | newctx->_stencil_flag2;
1128 if ((oldctx->gl_stencil_back_func[0] != newctx->gl_stencil_back_func[0]) ||
1129 (oldctx->gl_stencil_back_ref[0] != newctx->gl_stencil_back_ref[0]) ||
1130 (oldctx->gl_stencil_back_value_mask[0] != newctx->gl_stencil_back_value_mask[0]))
1132 _sym_glStencilFuncSeparate(GL_BACK,
1133 newctx->gl_stencil_back_func[0],
1134 newctx->gl_stencil_back_ref[0],
1135 newctx->gl_stencil_back_value_mask[0]);
1137 if ((oldctx->gl_stencil_back_fail[0] != newctx->gl_stencil_back_fail[0]) ||
1138 (oldctx->gl_stencil_back_pass_depth_fail[0] != newctx->gl_stencil_back_pass_depth_fail[0]) ||
1139 (oldctx->gl_stencil_back_pass_depth_pass[0] != newctx->gl_stencil_back_pass_depth_pass[0]))
1141 _sym_glStencilOpSeparate(GL_BACK,
1142 newctx->gl_stencil_back_fail[0],
1143 newctx->gl_stencil_back_pass_depth_fail[0],
1144 newctx->gl_stencil_back_pass_depth_pass[0]);
1147 STATE_COMPARE(gl_stencil_back_writemask[0])
1149 _sym_glStencilMaskSeparate(GL_BACK, newctx->gl_stencil_back_writemask[0]);
1151 STATE_COMPARE(gl_stencil_clear_value[0])
1153 _sym_glClearStencil(newctx->gl_stencil_clear_value[0]);
1157 //------------------//
1159 flag = oldctx->_misc_flag1 | newctx->_misc_flag1;
1162 STATE_COMPARE(gl_front_face[0])
1164 _sym_glFrontFace(newctx->gl_front_face[0]);
1166 STATE_COMPARE(gl_line_width[0])
1168 _sym_glLineWidth(newctx->gl_line_width[0]);
1170 if ((oldctx->gl_polygon_offset_factor[0] != newctx->gl_polygon_offset_factor[0]) ||
1171 (oldctx->gl_polygon_offset_units[0] != newctx->gl_polygon_offset_units[0]))
1173 _sym_glPolygonOffset(newctx->gl_polygon_offset_factor[0],
1174 newctx->gl_polygon_offset_units[0]);
1176 if ((oldctx->gl_sample_coverage_value[0] != newctx->gl_sample_coverage_value[0]) ||
1177 (oldctx->gl_sample_coverage_invert[0] != newctx->gl_sample_coverage_invert[0]))
1179 _sym_glSampleCoverage(newctx->gl_sample_coverage_value[0],
1180 newctx->gl_sample_coverage_invert[0]);
1185 flag = oldctx->_misc_flag2 | newctx->_misc_flag2;
1188 STATES_COMPARE(gl_scissor_box, 4 * sizeof(GLint))
1190 _sym_glScissor(newctx->gl_scissor_box[0],
1191 newctx->gl_scissor_box[1],
1192 newctx->gl_scissor_box[2],
1193 newctx->gl_scissor_box[3]);
1195 STATE_COMPARE(gl_pack_alignment[0])
1197 _sym_glPixelStorei(GL_PACK_ALIGNMENT, newctx->gl_pack_alignment[0]);
1199 STATE_COMPARE(gl_unpack_alignment[0])
1201 _sym_glPixelStorei(GL_UNPACK_ALIGNMENT, newctx->gl_unpack_alignment[0]);
1204 #ifdef COREGL_USE_MODULE_TRACEPATH
1205 tracepath_api_trace_end("eglMakeCurrent(FP etc.)", trace_hint_etc, 0);
1206 #endif // COREGL_USE_MODULE_TRACEPATH
1209 #ifdef COREGL_USE_MODULE_TRACEPATH
1210 static void *trace_hint_vertex_attrib = NULL;
1211 trace_hint_vertex_attrib = tracepath_api_trace_begin("eglMakeCurrent(FP vertex attrib)", trace_hint_vertex_attrib, 0);
1212 #endif // COREGL_USE_MODULE_TRACEPATH
1214 flag = oldctx->_vattrib_flag | newctx->_vattrib_flag;
1217 for (i = 0; i < oldctx->gl_num_vertex_attribs[0]; i++)
1219 if (newctx->gl_vertex_array_buf_id[i] != oldctx->gl_vertex_array_buf_id[i])
1221 _sym_glBindBuffer(GL_ARRAY_BUFFER, newctx->gl_vertex_array_buf_id[i]);
1223 else _sym_glBindBuffer(GL_ARRAY_BUFFER, 0);
1225 _sym_glVertexAttribPointer(i,
1226 newctx->gl_vertex_array_size[i],
1227 newctx->gl_vertex_array_type[i],
1228 newctx->gl_vertex_array_normalized[i],
1229 newctx->gl_vertex_array_stride[i],
1230 newctx->gl_vertex_array_pointer[i]);
1232 STATES_COMPARE(gl_vertex_attrib_value + 4 * i, 4 * sizeof(GLfloat))
1234 _sym_glVertexAttrib4fv(i, &newctx->gl_vertex_attrib_value[4 * i]);
1237 if (newctx->gl_vertex_array_enabled[i] == GL_TRUE)
1239 _sym_glEnableVertexAttribArray(i);
1243 _sym_glDisableVertexAttribArray(i);
1247 STATE_COMPARE(gl_array_buffer_binding[0])
1249 _sym_glBindBuffer(GL_ARRAY_BUFFER, newctx->gl_array_buffer_binding[0]);
1251 STATE_COMPARE(gl_element_array_buffer_binding[0])
1253 _sym_glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, newctx->gl_element_array_buffer_binding[0]);
1258 #ifdef COREGL_USE_MODULE_TRACEPATH
1259 tracepath_api_trace_end("eglMakeCurrent(FP vertex attrib)", trace_hint_vertex_attrib, 0);
1260 #endif // COREGL_USE_MODULE_TRACEPATH
1266 #ifdef COREGL_FASTPATH_TRACE_STATE_INFO
1267 if (unlikely(trace_state_flag == 1))
1268 fastpath_dump_context_states(newctx, 0);
1269 #endif // COREGL_FASTPATH_TRACE_STATE_INFO
1271 #undef STATE_COMPARE
1272 #undef STATES_COMPARE