1/* 2 * Copyright (c) 2004, 2012, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26#ifndef OGLFuncs_md_h_Included 27#define OGLFuncs_md_h_Included 28 29#include <stdlib.h> 30#ifndef MACOSX 31#include <dlfcn.h> 32#endif 33#include "jvm_md.h" 34#include "J2D_GL/glx.h" 35#include "OGLFuncMacros.h" 36 37/** 38 * GLX 1.2 functions 39 */ 40typedef void (GLAPIENTRY *glXDestroyContextType)(Display *dpy, GLXContext ctx); 41typedef GLXContext (GLAPIENTRY *glXGetCurrentContextType)(void); 42typedef GLXDrawable (GLAPIENTRY *glXGetCurrentDrawableType)(void); 43typedef Bool (GLAPIENTRY *glXIsDirectType)(Display *dpy, GLXContext ctx); 44typedef Bool (GLAPIENTRY *glXQueryExtensionType)(Display *dpy, int *errorBase, int *eventBase); 45typedef Bool (GLAPIENTRY *glXQueryVersionType)(Display *dpy, int *major, int *minor); 46typedef void (GLAPIENTRY *glXSwapBuffersType)(Display *dpy, GLXDrawable drawable); 47typedef const char * (GLAPIENTRY *glXGetClientStringType)(Display *dpy, int name); 48typedef const char * (GLAPIENTRY *glXQueryServerStringType)(Display *dpy, int screen, int name); 49typedef const char * (GLAPIENTRY *glXQueryExtensionsStringType)(Display *dpy, int screen); 50typedef void (GLAPIENTRY *glXWaitGLType)(void); 51 52/** 53 * GLX 1.3 functions 54 */ 55typedef GLXFBConfig * (GLAPIENTRY *glXGetFBConfigsType)(Display *dpy, int screen, int *nelements); 56typedef GLXFBConfig * (GLAPIENTRY *glXChooseFBConfigType)(Display *dpy, int screen, const int *attrib_list, int *nelements); 57typedef int (GLAPIENTRY *glXGetFBConfigAttribType)(Display *dpy, GLXFBConfig config, int attribute, int *value); 58typedef XVisualInfo * (GLAPIENTRY *glXGetVisualFromFBConfigType)(Display *dpy, GLXFBConfig config); 59typedef GLXWindow (GLAPIENTRY *glXCreateWindowType)(Display *dpy, GLXFBConfig config, Window win, const int *attrib_list); 60typedef void (GLAPIENTRY *glXDestroyWindowType)(Display *dpy, GLXWindow win); 61typedef GLXPbuffer (GLAPIENTRY *glXCreatePbufferType)(Display *dpy, GLXFBConfig config, const int *attrib_list); 62typedef void (GLAPIENTRY *glXDestroyPbufferType)(Display *dpy, GLXPbuffer pbuffer); 63typedef void (GLAPIENTRY *glXQueryDrawableType)(Display *dpy, GLXDrawable draw, int attribute, unsigned int *value); 64typedef GLXContext (GLAPIENTRY *glXCreateNewContextType)(Display *dpy, GLXFBConfig config, int render_type, GLXContext share_list, Bool direct); 65typedef Bool (GLAPIENTRY *glXMakeContextCurrentType)(Display *dpy, GLXDrawable draw, GLXDrawable read, GLXContext ctx); 66typedef GLXDrawable (GLAPIENTRY *glXGetCurrentReadDrawableType)(void); 67typedef int (GLAPIENTRY *glXQueryContextType)(Display *dpy, GLXContext ctx, int attribute, int *value); 68typedef void (GLAPIENTRY *glXSelectEventType)(Display *dpy, GLXDrawable draw, unsigned long event_mask); 69typedef void (GLAPIENTRY *glXGetSelectedEventType)(Display *dpy, GLXDrawable draw, unsigned long *event_mask); 70 71/** 72 * GLX extension functions 73 */ 74typedef void * (GLAPIENTRY *glXGetProcAddressType)(const char *); 75 76/* 77 * Note: Historically we have used dlopen/dlsym() to load function pointers 78 * from libgl.so, and things have worked fine. However, we have run into at 79 * least one case (on ATI's Linux drivers) where dlsym() will return NULL 80 * when trying to load functions from the GL_ARB_fragment_shader extension. 81 * Plausibly this is a bug in their drivers (other extension functions load 82 * just fine on those same drivers), but for a number of years there has been 83 * a glXGetProcAddressARB() extension available that is intended to be the 84 * primary means for an application to load extension functions in a reliable 85 * manner. So while dlsym() will return NULL for those shader-related 86 * functions, glXGetProcAddressARB() works just fine. 87 * 88 * I haven't used the glXGetProcAddress() approach in the past because it 89 * seemed unnecessary (i.e. dlsym() was working fine), but upon further 90 * reading I think we should use glXGetProcAddress() in favor of dlsym(), 91 * not only to work around this "bug", but also to be safer going forward. 92 * 93 * Just to complicate matters, glXGetProcAddress() was proposed to be added 94 * into the GLX 1.4 spec, which is still (as yet) unfinalized. Sun's OGL 1.3 95 * implementation reports its GLX version as 1.4, and therefore includes 96 * the glXGetProcAddress() entrypoint, but does not include 97 * GLX_ARB_get_proc_address in its extension string nor does it export the 98 * glXGetProcAddressARB() entrypoint. On the other hand, ATI's Linux drivers 99 * (as well as Nvidia's Linux and Solaris drivers) currently report their 100 * GLX version as 1.3, but they do export the glXGetProcAddressARB() 101 * entrypoint and its associated extension string. So to make this work 102 * everywhere, we first try to load the glXGetProcAddress() entrypoint, 103 * failing that we try the glXGetProcAddressARB() entrypoint, and if that 104 * fails too, then we close libGL.so and do not bother trying to initialize 105 * the rest of the OGL pipeline. 106 */ 107 108#define OGL_LIB_HANDLE pLibGL 109#define OGL_DECLARE_LIB_HANDLE() \ 110 static glXGetProcAddressType j2d_glXGetProcAddress; \ 111 static void *OGL_LIB_HANDLE = NULL 112#define OGL_LIB_IS_UNINITIALIZED() \ 113 (OGL_LIB_HANDLE == NULL) 114#define OGL_OPEN_LIB() \ 115do { \ 116 { \ 117 char *libGLPath = getenv("J2D_ALT_LIBGL_PATH"); \ 118 if (libGLPath == NULL) { \ 119 libGLPath = VERSIONED_JNI_LIB_NAME("GL", "1"); \ 120 } \ 121 OGL_LIB_HANDLE = dlopen(libGLPath, RTLD_LAZY | RTLD_LOCAL); \ 122 } \ 123 if (OGL_LIB_HANDLE) { \ 124 j2d_glXGetProcAddress = (glXGetProcAddressType) \ 125 dlsym(OGL_LIB_HANDLE, "glXGetProcAddress"); \ 126 if (j2d_glXGetProcAddress == NULL) { \ 127 j2d_glXGetProcAddress = (glXGetProcAddressType) \ 128 dlsym(OGL_LIB_HANDLE, "glXGetProcAddressARB"); \ 129 if (j2d_glXGetProcAddress == NULL) { \ 130 dlclose(OGL_LIB_HANDLE); \ 131 OGL_LIB_HANDLE = NULL; \ 132 } \ 133 } \ 134 } \ 135} while (0) 136#define OGL_CLOSE_LIB() \ 137 dlclose(OGL_LIB_HANDLE) 138#define OGL_GET_PROC_ADDRESS(f) \ 139 j2d_glXGetProcAddress(#f) 140#define OGL_GET_EXT_PROC_ADDRESS(f) \ 141 OGL_GET_PROC_ADDRESS(f) 142 143#define OGL_EXPRESS_PLATFORM_FUNCS(action) \ 144 OGL_##action##_FUNC(glXDestroyContext); \ 145 OGL_##action##_FUNC(glXGetCurrentContext); \ 146 OGL_##action##_FUNC(glXGetCurrentDrawable); \ 147 OGL_##action##_FUNC(glXIsDirect); \ 148 OGL_##action##_FUNC(glXQueryExtension); \ 149 OGL_##action##_FUNC(glXQueryVersion); \ 150 OGL_##action##_FUNC(glXSwapBuffers); \ 151 OGL_##action##_FUNC(glXGetClientString); \ 152 OGL_##action##_FUNC(glXQueryServerString); \ 153 OGL_##action##_FUNC(glXQueryExtensionsString); \ 154 OGL_##action##_FUNC(glXWaitGL); \ 155 OGL_##action##_FUNC(glXGetFBConfigs); \ 156 OGL_##action##_FUNC(glXChooseFBConfig); \ 157 OGL_##action##_FUNC(glXGetFBConfigAttrib); \ 158 OGL_##action##_FUNC(glXGetVisualFromFBConfig); \ 159 OGL_##action##_FUNC(glXCreateWindow); \ 160 OGL_##action##_FUNC(glXDestroyWindow); \ 161 OGL_##action##_FUNC(glXCreatePbuffer); \ 162 OGL_##action##_FUNC(glXDestroyPbuffer); \ 163 OGL_##action##_FUNC(glXQueryDrawable); \ 164 OGL_##action##_FUNC(glXCreateNewContext); \ 165 OGL_##action##_FUNC(glXMakeContextCurrent); \ 166 OGL_##action##_FUNC(glXGetCurrentReadDrawable); \ 167 OGL_##action##_FUNC(glXQueryContext); \ 168 OGL_##action##_FUNC(glXSelectEvent); \ 169 OGL_##action##_FUNC(glXGetSelectedEvent); 170 171#define OGL_EXPRESS_PLATFORM_EXT_FUNCS(action) 172 173#endif /* OGLFuncs_md_h_Included */ 174