diff --git a/src/dispatch_common.h b/src/dispatch_common.h index a0722ff..aa8d04e 100644 --- a/src/dispatch_common.h +++ b/src/dispatch_common.h @@ -27,15 +27,18 @@ #define PLATFORM_HAS_EGL 0 #define PLATFORM_HAS_GLX 0 #define PLATFORM_HAS_WGL 1 -#define EPOXYAPIENTRY __declspec(dllexport) __stdcall +#define EPOXYCALL __stdcall +#define EPOXYAPIENTRY __declspec(dllexport) EPOXYCALL #elif defined(__APPLE__) #define PLATFORM_HAS_EGL 0 #define PLATFORM_HAS_GLX 1 #define PLATFORM_HAS_WGL 0 +#define EPOXYCALL #else #define PLATFORM_HAS_EGL 1 #define PLATFORM_HAS_GLX 1 #define PLATFORM_HAS_WGL 0 +#define EPOXYCALL #endif #include "epoxy/gl.h" @@ -73,6 +76,76 @@ #define WRAPPER_VISIBILITY static GLAPIENTRY #define WRAPPER(x) x ## _wrapped +#if USING_DISPATCH_TABLE +#define GEN_GLOBAL_REWRITE_PTR(name, args, passthrough) +#define GEN_GLOBAL_REWRITE_PTR_RET(ret, name, args, passthrough) + +#define GEN_DISPATCH_TABLE_REWRITE_PTR(name, args, passthrough) \ + static EPOXYCALL void \ + name##_dispatch_table_rewrite_ptr args \ + { \ + struct dispatch_table *dispatch_table = get_dispatch_table(); \ + \ + dispatch_table->name = (void *)name##_resolver(); \ + dispatch_table->name passthrough; \ + } + +#define GEN_DISPATCH_TABLE_REWRITE_PTR_RET(ret, name, args, passthrough) \ + static EPOXYCALL ret \ + name##_dispatch_table_rewrite_ptr args \ + { \ + struct dispatch_table *dispatch_table = get_dispatch_table(); \ + \ + dispatch_table->name = (void *)name##_resolver(); \ + return dispatch_table->name passthrough; \ + } + +#define GEN_DISPATCH_TABLE_THUNK(name, args, passthrough) \ + static EPOXYCALL void \ + name##_dispatch_table_thunk args \ + { \ + get_dispatch_table()->name passthrough; \ + } + +#define GEN_DISPATCH_TABLE_THUNK_RET(ret, name, args, passthrough) \ + static EPOXYCALL ret \ + name##_dispatch_table_thunk args \ + { \ + return get_dispatch_table()->name passthrough; \ + } + +#else +#define GEN_GLOBAL_REWRITE_PTR(name, args, passthrough) \ + static EPOXYCALL void \ + name##_global_rewrite_ptr args \ + { \ + name = (void *)name##_resolver(); \ + name passthrough; \ + } + +#define GEN_GLOBAL_REWRITE_PTR_RET(ret, name, args, passthrough) \ + static EPOXYCALL ret \ + name##_global_rewrite_ptr args \ + { \ + name = (void *)name##_resolver(); \ + return name passthrough; \ + } +#define GEN_DISPATCH_TABLE_REWRITE_PTR(name, args, passthrough) +#define GEN_DISPATCH_TABLE_REWRITE_PTR_RET(ret, name, args, passthrough) +#define GEN_DISPATCH_TABLE_THUNK(name, args, passthrough) +#define GEN_DISPATCH_TABLE_THUNK_RET(ret, name, args, passthrough) +#endif + +#define GEN_THUNKS(name, args, passthrough) \ + GEN_GLOBAL_REWRITE_PTR(name, args, passthrough) \ + GEN_DISPATCH_TABLE_REWRITE_PTR(name, args, passthrough) \ + GEN_DISPATCH_TABLE_THUNK(name, args, passthrough) + +#define GEN_THUNKS_RET(ret, name, args, passthrough) \ + GEN_GLOBAL_REWRITE_PTR_RET(ret, name, args, passthrough) \ + GEN_DISPATCH_TABLE_REWRITE_PTR_RET(ret, name, args, passthrough) \ + GEN_DISPATCH_TABLE_THUNK_RET(ret, name, args, passthrough) + void *epoxy_egl_dlsym(const char *name); void *epoxy_glx_dlsym(const char *name); void *epoxy_gl_dlsym(const char *name); @@ -96,16 +169,22 @@ void epoxy_print_failure_reasons(const char *name, bool epoxy_extension_in_string(const char *extension_list, const char *ext); -extern void UNWRAPPED_PROTO(epoxy_glBegin_unwrapped)(GLenum primtype); -extern void UNWRAPPED_PROTO(epoxy_glEnd_unwrapped)(void); +#define glBegin_unwrapped epoxy_glBegin_unwrapped +#define glEnd_unwrapped epoxy_glEnd_unwrapped +extern void UNWRAPPED_PROTO(glBegin_unwrapped)(GLenum primtype); +extern void UNWRAPPED_PROTO(glEnd_unwrapped)(void); #if USING_DISPATCH_TABLE void gl_init_dispatch_table(void); void wgl_init_dispatch_table(void); extern uint32_t gl_tls_index, gl_tls_size; extern uint32_t wgl_tls_index, wgl_tls_size; -extern BOOL UNWRAPPED_PROTO(epoxy_wglMakeCurrent_unwrapped)(HDC hdc, HGLRC hglrc); -extern BOOL UNWRAPPED_PROTO(epoxy_wglMakeContextCurrentARB_unwrapped)(HDC hDrawDC, HDC hReadDC, HGLRC hglrc); -extern BOOL UNWRAPPED_PROTO(epoxy_wglMakeContextCurrentEXT_unwrapped)(HDC hDrawDC, HDC hReadDC, HGLRC hglrc); -extern BOOL UNWRAPPED_PROTO(epoxy_wglMakeAssociatedContextCurrentAMD_unwrapped)(HGLRC hglrc); +#define wglMakeCurrent_unwrapped epoxy_wglMakeCurrent_unwrapped +#define wglMakeContextCurrentARB_unwrapped epoxy_wglMakeContextCurrentARB_unwrapped +#define wglMakeContextCurrentEXT_unwrapped epoxy_wglMakeContextCurrentEXT_unwrapped +#define wglMakeAssociatedContextCurrentAMD_unwrapped epoxy_wglMakeAssociatedContextCurrentAMD_unwrapped +extern BOOL UNWRAPPED_PROTO(wglMakeCurrent_unwrapped)(HDC hdc, HGLRC hglrc); +extern BOOL UNWRAPPED_PROTO(wglMakeContextCurrentARB_unwrapped)(HDC hDrawDC, HDC hReadDC, HGLRC hglrc); +extern BOOL UNWRAPPED_PROTO(wglMakeContextCurrentEXT_unwrapped)(HDC hDrawDC, HDC hReadDC, HGLRC hglrc); +extern BOOL UNWRAPPED_PROTO(wglMakeAssociatedContextCurrentAMD_unwrapped)(HGLRC hglrc); #endif diff --git a/src/gen_dispatch.py b/src/gen_dispatch.py index aee4308..5af23d6 100755 --- a/src/gen_dispatch.py +++ b/src/gen_dispatch.py @@ -535,7 +535,7 @@ class Generator(object): def write_function_ptr_resolver(self, func): self.outln('static {0}'.format(func.ptr_type)) - self.outln('epoxy_{0}_resolver(void)'.format(func.name)) + self.outln('epoxy_{0}_resolver(void)'.format(func.wrapped_name)) self.outln('{') providers = [] @@ -594,70 +594,27 @@ class Generator(object): self.outln('}') self.outln('') - def write_dispatch_table_thunk(self, func): - # Writes out the thunk that fetches the (win32) dispatch table - # and calls through its entrypoint. - - dispatch_table_entry = 'dispatch_table->p{0}'.format(func.name) - - self.outln('static __stdcall {0}'.format(func.ret_type)) - self.outln('epoxy_{0}_dispatch_table_thunk({1})'.format(func.wrapped_name, func.args_decl)) - self.outln('{') - self.outln(' struct dispatch_table *dispatch_table = get_dispatch_table();') - self.outln('') - if func.ret_type == 'void': - self.outln(' {0}({1});'.format(dispatch_table_entry, func.args_list)) - else: - self.outln(' return {0}({1});'.format(dispatch_table_entry, func.args_list)) - self.outln('}') - self.outln('') - - def write_dispatch_table_rewrite_stub(self, func): - # Writes out the initial dispatch table function pointer value - # that that resolves, writes the resolved value into the - # dispatch table, and calls down to it. - - dispatch_table_entry = 'dispatch_table->p{0}'.format(func.name) - - self.outln('static GLAPIENTRY {0}'.format(func.ret_type)) - self.outln('epoxy_{0}_rewrite_stub({1})'.format(func.name, func.args_decl)) - self.outln('{') - self.outln(' struct dispatch_table *dispatch_table = get_dispatch_table();') - self.outln('') - self.outln(' dispatch_table->p{0} = epoxy_{0}_resolver();'.format(func.name)) - self.outln('') - + def write_thunks(self, func): + # Writes out the function that's initially plugged into the + # global function pointer, which resolves, updates the global + # function pointer, and calls down to it. + # + # It also writes out the actual initialized global function + # pointer. if func.ret_type == 'void': - self.outln(' dispatch_table->p{0}({1});'.format(func.name, func.args_list)) + self.outln('GEN_THUNKS({0}, ({1}), ({2}))'.format(func.wrapped_name, + func.args_decl, + func.args_list)) else: - self.outln(' return dispatch_table->p{0}({1});'.format(func.name, func.args_list)) - self.outln('}') - self.outln('') + self.outln('GEN_THUNKS_RET({0}, {1}, ({2}), ({3}))'.format(func.ret_type, + func.wrapped_name, + func.args_decl, + func.args_list)) def write_linux_function_pointer(self, func): - # Writes out the function for resolving and updating the - # global function pointer, plus the actual global function - # pointer initializer. - - self.outln('static {0}'.format(func.ret_type)) - self.outln('epoxy_{0}_rewrite_ptr({1})'.format(func.wrapped_name, - func.args_decl)) - self.outln('{') - self.outln(' epoxy_{0} = (void *)epoxy_{1}_resolver();'.format(func.wrapped_name, - func.name)) - - if func.ret_type == 'void': - self.outln(' epoxy_{0}({1});'.format(func.wrapped_name, - func.args_list)) - else: - self.outln(' return epoxy_{0}({1});'.format(func.wrapped_name, - func.args_list)) - - self.outln('}') - - self.outln('{0}{1} epoxy_{2} = epoxy_{2}_rewrite_ptr;'.format(func.public, - func.ptr_type, - func.wrapped_name)) + self.outln('{0}{1} epoxy_{2} = epoxy_{2}_global_rewrite_ptr;'.format(func.public, + func.ptr_type, + func.wrapped_name)) self.outln('') def write_win32_function_pointer(self, func): @@ -779,7 +736,7 @@ class Generator(object): self.outln('struct dispatch_table {') for func in self.sorted_functions: - self.outln(' {0} p{1};'.format(func.ptr_type, func.name)) + self.outln(' {0} epoxy_{1};'.format(func.ptr_type, func.wrapped_name)) self.outln('};') self.outln('') @@ -801,17 +758,14 @@ class Generator(object): for func in self.sorted_functions: self.write_function_ptr_resolver(func) - self.outln('#if USING_DISPATCH_TABLE') - for func in self.sorted_functions: - self.write_dispatch_table_rewrite_stub(func) + self.write_thunks(func) - for func in self.sorted_functions: - self.write_dispatch_table_thunk(func) + self.outln('#if USING_DISPATCH_TABLE') self.outln('static struct dispatch_table resolver_table = {') for func in self.sorted_functions: - self.outln(' .p{0} = epoxy_{0}_rewrite_stub,'.format(func.name)) + self.outln(' .{0} = epoxy_{0}_dispatch_table_rewrite_ptr,'.format(func.wrapped_name)) self.outln('};') self.outln('')