egldispatchstubs.c revision 01e04c3f
1#include "egldispatchstubs.h" 2#include "g_egldispatchstubs.h" 3 4#include <string.h> 5#include <stdlib.h> 6 7#include "eglcurrent.h" 8 9static const __EGLapiExports *exports; 10 11const int __EGL_DISPATCH_FUNC_COUNT = __EGL_DISPATCH_COUNT; 12int __EGL_DISPATCH_FUNC_INDICES[__EGL_DISPATCH_COUNT + 1]; 13 14static int Compare(const void *l, const void *r) 15{ 16 const char *s = *(const char **)r; 17 return strcmp(l, s); 18} 19 20static int FindProcIndex(const char *name) 21{ 22 const char **match = bsearch(name, __EGL_DISPATCH_FUNC_NAMES, 23 __EGL_DISPATCH_COUNT, sizeof(const char *), Compare); 24 25 if (match == NULL) 26 return __EGL_DISPATCH_COUNT; 27 28 return match - __EGL_DISPATCH_FUNC_NAMES; 29} 30 31void __eglInitDispatchStubs(const __EGLapiExports *exportsTable) 32{ 33 int i; 34 exports = exportsTable; 35 for (i=0; i<__EGL_DISPATCH_FUNC_COUNT; i++) { 36 __EGL_DISPATCH_FUNC_INDICES[i] = -1; 37 } 38} 39 40void __eglSetDispatchIndex(const char *name, int dispatchIndex) 41{ 42 int index = FindProcIndex(name); 43 __EGL_DISPATCH_FUNC_INDICES[index] = dispatchIndex; 44} 45 46void *__eglDispatchFindDispatchFunction(const char *name) 47{ 48 int index = FindProcIndex(name); 49 return (void *) __EGL_DISPATCH_FUNCS[index]; 50} 51 52static __eglMustCastToProperFunctionPointerType FetchVendorFunc(__EGLvendorInfo *vendor, 53 int index, EGLint errorCode) 54{ 55 __eglMustCastToProperFunctionPointerType func = NULL; 56 57 if (vendor != NULL) { 58 func = exports->fetchDispatchEntry(vendor, __EGL_DISPATCH_FUNC_INDICES[index]); 59 } 60 if (func == NULL) { 61 if (errorCode != EGL_SUCCESS) { 62 // Since we have no vendor, the follow-up eglGetError() call will 63 // end up using the GLVND error code. Set it here. 64 if (vendor == NULL) { 65 exports->setEGLError(errorCode); 66 } 67 _eglError(errorCode, __EGL_DISPATCH_FUNC_NAMES[index]); 68 } 69 return NULL; 70 } 71 72 if (!exports->setLastVendor(vendor)) { 73 // Don't bother trying to set an error code in libglvnd. If 74 // setLastVendor failed, then setEGLError would also fail. 75 _eglError(errorCode, __EGL_DISPATCH_FUNC_NAMES[index]); 76 return NULL; 77 } 78 79 return func; 80} 81 82__eglMustCastToProperFunctionPointerType __eglDispatchFetchByCurrent(int index) 83{ 84 __EGLvendorInfo *vendor; 85 86 // Note: This is only used for the eglWait* functions. For those, if 87 // there's no current context, then they're supposed to do nothing but 88 // return success. 89 exports->threadInit(); 90 vendor = exports->getCurrentVendor(); 91 return FetchVendorFunc(vendor, index, EGL_SUCCESS); 92} 93 94__eglMustCastToProperFunctionPointerType __eglDispatchFetchByDisplay(EGLDisplay dpy, int index) 95{ 96 __EGLvendorInfo *vendor; 97 98 exports->threadInit(); 99 vendor = exports->getVendorFromDisplay(dpy); 100 return FetchVendorFunc(vendor, index, EGL_BAD_DISPLAY); 101} 102 103__eglMustCastToProperFunctionPointerType __eglDispatchFetchByDevice(EGLDeviceEXT dev, int index) 104{ 105 __EGLvendorInfo *vendor; 106 107 exports->threadInit(); 108 vendor = exports->getVendorFromDevice(dev); 109 return FetchVendorFunc(vendor, index, EGL_BAD_DEVICE_EXT); 110} 111 112