VirtualBox

source: vbox/trunk/src/VBox/Devices/Graphics/DevVGA-SVGA3d-glLdr.cpp@ 76254

Last change on this file since 76254 was 76254, checked in by vboxsync, 6 years ago

DevVGA-SVGA3d: enable dynamic loading of opengl: use function pointer type

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 8.7 KB
Line 
1/* $Id: DevVGA-SVGA3d-glLdr.cpp 76254 2018-12-16 15:05:45Z vboxsync $ */
2/** @file
3 * DevVGA - VMWare SVGA device - 3D part, dynamic loading of GL function.
4 */
5
6/*
7 * Copyright (C) 2018 Oracle Corporation
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License (GPL) as published by the Free Software
13 * Foundation, in version 2 as it comes in the "COPYING" file of the
14 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16 */
17
18#define VMSVGA3D_GL_DEFINE_PFN
19#include "DevVGA-SVGA3d-glLdr.h"
20
21#include <iprt/assert.h>
22#include <iprt/cdefs.h>
23#include <iprt/err.h>
24#include <iprt/ldr.h>
25#include <iprt/log.h>
26
27#ifdef RT_OS_WINDOWS
28# define OGLGETPROCADDRESS MyWinGetProcAddress
29DECLINLINE(PFNRT) MyWinGetProcAddress(const char *pszSymbol)
30{
31 int rc;
32
33 static RTLDRMOD s_hOpenGL32 = NULL;
34 if (s_hOpenGL32 == NULL)
35 {
36 rc = RTLdrLoadSystem("opengl32", /* fNoUnload = */ true, &s_hOpenGL32);
37 if (RT_FAILURE(rc))
38 s_hOpenGL32 = NULL;
39 }
40
41 typedef PROC (WINAPI *PFNWGLGETPROCADDRESS)(LPCSTR);
42 static PFNWGLGETPROCADDRESS s_wglGetProcAddress = NULL;
43 if (s_wglGetProcAddress == NULL)
44 {
45 if (s_hOpenGL32 != NULL)
46 {
47 rc = RTLdrGetSymbol(s_hOpenGL32, "wglGetProcAddress", (void **)&s_wglGetProcAddress);
48 if (RT_FAILURE(rc))
49 s_wglGetProcAddress = NULL;
50 }
51 }
52
53 if (s_wglGetProcAddress)
54 {
55 /* Khronos: [on failure] "some implementations will return other values. 1, 2, and 3 are used, as well as -1". */
56 PFNRT p = (PFNRT)s_wglGetProcAddress(pszSymbol);
57 if (RT_VALID_PTR(p))
58 return p;
59
60 /* Might be an exported symbol. */
61 rc = RTLdrGetSymbol(s_hOpenGL32, pszSymbol, (void **)&p);
62 if (RT_SUCCESS(rc))
63 return p;
64 }
65
66 return 0;
67}
68
69#elif defined(RT_OS_DARWIN)
70# include <dlfcn.h>
71# define OGLGETPROCADDRESS MyNSGLGetProcAddress
72/** Resolves an OpenGL symbol. */
73static void *MyNSGLGetProcAddress(const char *pszSymbol)
74{
75 /* Another copy in shaderapi.c. */
76 static void *s_pvImage = NULL;
77 if (s_pvImage == NULL)
78 s_pvImage = dlopen("/System/Library/Frameworks/OpenGL.framework/Versions/Current/OpenGL", RTLD_LAZY);
79 return s_pvImage ? dlsym(s_pvImage, pszSymbol) : NULL;
80}
81
82#else
83# define OGLGETPROCADDRESS MyGLXGetProcAddress
84static PFNRT MyGLXGetProcAddress(const char *pszSymbol)
85{
86 int rc;
87
88 static RTLDRMOD s_hGL = NULL;
89 if (s_hGL == NULL)
90 {
91 static const char s_szLibGL[] = "libGL.so.1";
92 rc = RTLdrLoadEx(s_szLibGL, &s_hGL, RTLDRLOAD_FLAGS_GLOBAL | RTLDRLOAD_FLAGS_NO_UNLOAD, NULL);
93 if (RT_FAILURE(rc))
94 {
95 LogRel(("VMSVGA3d: failed to load %s: %Rrc\n", s_szLibGL, rc));
96 s_hGL = NULL;
97 return NULL;
98 }
99 }
100
101 typedef PFNRT (* PFNGLXGETPROCADDRESS)(const GLubyte * procName);
102 static PFNGLXGETPROCADDRESS s_glXGetProcAddress = NULL;
103 if (s_glXGetProcAddress == NULL)
104 {
105 rc = RTLdrGetSymbol(s_hGL, "glXGetProcAddress", (void **)&s_glXGetProcAddress);
106 if (RT_FAILURE(rc))
107 {
108 LogRel(("VMSVGA3d: failed to get glXGetProcAddress: %Rrc\n", rc));
109 s_glXGetProcAddress = NULL;
110 return NULL;
111 }
112 }
113
114 PFNRT p = s_glXGetProcAddress((const GLubyte *)pszSymbol);
115 if (RT_VALID_PTR(p))
116 return p;
117
118 /* Might be an exported symbol. */
119 rc = RTLdrGetSymbol(s_hGL, pszSymbol, (void **)&p);
120 if (RT_SUCCESS(rc))
121 return p;
122
123 return NULL;
124}
125#endif
126
127#define GLGETPROC_(ProcName, NameSuffix) do { \
128 *(PFNRT *)&pfn_##ProcName = OGLGETPROCADDRESS(#ProcName NameSuffix); \
129 AssertLogRelMsgReturn(pfn_##ProcName, ("%s missing\n", #ProcName NameSuffix), VERR_NOT_IMPLEMENTED); \
130} while(0)
131
132int glLdrInit(void)
133{
134 pfn_glAlphaFunc = 0;
135 pfn_glBindTexture = 0;
136 pfn_glBlendColor = 0;
137 pfn_glBlendEquation = 0;
138 pfn_glBlendFunc = 0;
139 pfn_glClear = 0;
140 pfn_glClearColor = 0;
141 pfn_glClearDepth = 0;
142 pfn_glClearStencil = 0;
143 pfn_glClientActiveTexture = 0;
144 pfn_glClipPlane = 0;
145 pfn_glColorMask = 0;
146 pfn_glColorPointer = 0;
147 pfn_glCullFace = 0;
148 pfn_glDeleteTextures = 0;
149 pfn_glDepthFunc = 0;
150 pfn_glDepthMask = 0;
151 pfn_glDepthRange = 0;
152 pfn_glDisable = 0;
153 pfn_glDisableClientState = 0;
154 pfn_glDrawArrays = 0;
155 pfn_glDrawElements = 0;
156 pfn_glEnable = 0;
157 pfn_glEnableClientState = 0;
158 pfn_glFogf = 0;
159 pfn_glFogfv = 0;
160 pfn_glFogi = 0;
161 pfn_glFrontFace = 0;
162 pfn_glGenTextures = 0;
163 pfn_glGetBooleanv = 0;
164 pfn_glGetError = 0;
165 pfn_glGetFloatv = 0;
166 pfn_glGetIntegerv = 0;
167 pfn_glGetString = 0;
168 pfn_glGetTexImage = 0;
169 pfn_glLightModelfv = 0;
170 pfn_glLightf = 0;
171 pfn_glLightfv = 0;
172 pfn_glLineWidth = 0;
173 pfn_glLoadIdentity = 0;
174 pfn_glLoadMatrixf = 0;
175 pfn_glMaterialfv = 0;
176 pfn_glMatrixMode = 0;
177 pfn_glMultMatrixf = 0;
178 pfn_glNormalPointer = 0;
179 pfn_glPixelStorei = 0;
180 pfn_glPointSize = 0;
181 pfn_glPolygonMode = 0;
182 pfn_glPolygonOffset = 0;
183 pfn_glPopAttrib = 0;
184 pfn_glPopMatrix = 0;
185 pfn_glPushAttrib = 0;
186 pfn_glPushMatrix = 0;
187 pfn_glScissor = 0;
188 pfn_glShadeModel = 0;
189 pfn_glStencilFunc = 0;
190 pfn_glStencilMask = 0;
191 pfn_glStencilOp = 0;
192 pfn_glTexCoordPointer = 0;
193 pfn_glTexImage2D = 0;
194 pfn_glTexParameterf = 0;
195 pfn_glTexParameterfv = 0;
196 pfn_glTexParameteri = 0;
197 pfn_glTexSubImage2D = 0;
198 pfn_glVertexPointer = 0;
199 pfn_glViewport = 0;
200#ifdef RT_OS_WINDOWS
201 pfn_wglCreateContext = 0;
202 pfn_wglDeleteContext = 0;
203 pfn_wglMakeCurrent = 0;
204 pfn_wglShareLists = 0;
205#elif defined(RT_OS_LINUX)
206 pfn_glXQueryVersion = 0;
207 pfn_glXChooseVisual = 0;
208 pfn_glXCreateContext = 0;
209 pfn_glXMakeCurrent = 0;
210 pfn_glXDestroyContext = 0;
211#endif
212
213 GLGETPROC_(glAlphaFunc, "");
214 GLGETPROC_(glBindTexture, "");
215 GLGETPROC_(glBlendFunc, "");
216 GLGETPROC_(glClear, "");
217 GLGETPROC_(glClearColor, "");
218 GLGETPROC_(glClearDepth, "");
219 GLGETPROC_(glClearStencil, "");
220 GLGETPROC_(glClipPlane, "");
221 GLGETPROC_(glColorMask, "");
222 GLGETPROC_(glColorPointer, "");
223 GLGETPROC_(glCullFace, "");
224 GLGETPROC_(glDeleteTextures, "");
225 GLGETPROC_(glDepthFunc, "");
226 GLGETPROC_(glDepthMask, "");
227 GLGETPROC_(glDepthRange, "");
228 GLGETPROC_(glDisable, "");
229 GLGETPROC_(glDisableClientState, "");
230 GLGETPROC_(glDrawArrays, "");
231 GLGETPROC_(glDrawElements, "");
232 GLGETPROC_(glEnable, "");
233 GLGETPROC_(glEnableClientState, "");
234 GLGETPROC_(glFogf, "");
235 GLGETPROC_(glFogfv, "");
236 GLGETPROC_(glFogi, "");
237 GLGETPROC_(glFrontFace, "");
238 GLGETPROC_(glGenTextures, "");
239 GLGETPROC_(glGetBooleanv, "");
240 GLGETPROC_(glGetError, "");
241 GLGETPROC_(glGetFloatv, "");
242 GLGETPROC_(glGetIntegerv, "");
243 GLGETPROC_(glGetString, "");
244 GLGETPROC_(glGetTexImage, "");
245 GLGETPROC_(glLightModelfv, "");
246 GLGETPROC_(glLightf, "");
247 GLGETPROC_(glLightfv, "");
248 GLGETPROC_(glLineWidth, "");
249 GLGETPROC_(glLoadIdentity, "");
250 GLGETPROC_(glLoadMatrixf, "");
251 GLGETPROC_(glMaterialfv, "");
252 GLGETPROC_(glMatrixMode, "");
253 GLGETPROC_(glMultMatrixf, "");
254 GLGETPROC_(glNormalPointer, "");
255 GLGETPROC_(glPixelStorei, "");
256 GLGETPROC_(glPointSize, "");
257 GLGETPROC_(glPolygonMode, "");
258 GLGETPROC_(glPolygonOffset, "");
259 GLGETPROC_(glPopAttrib, "");
260 GLGETPROC_(glPopMatrix, "");
261 GLGETPROC_(glPushAttrib, "");
262 GLGETPROC_(glPushMatrix, "");
263 GLGETPROC_(glScissor, "");
264 GLGETPROC_(glShadeModel, "");
265 GLGETPROC_(glStencilFunc, "");
266 GLGETPROC_(glStencilMask, "");
267 GLGETPROC_(glStencilOp, "");
268 GLGETPROC_(glTexCoordPointer, "");
269 GLGETPROC_(glTexImage2D, "");
270 GLGETPROC_(glTexParameterf, "");
271 GLGETPROC_(glTexParameterfv, "");
272 GLGETPROC_(glTexParameteri, "");
273 GLGETPROC_(glTexSubImage2D, "");
274 GLGETPROC_(glVertexPointer, "");
275 GLGETPROC_(glViewport, "");
276#ifdef RT_OS_WINDOWS
277 GLGETPROC_(wglCreateContext, "");
278 GLGETPROC_(wglDeleteContext, "");
279 GLGETPROC_(wglMakeCurrent, "");
280 GLGETPROC_(wglShareLists, "");
281#elif defined(RT_OS_LINUX)
282 GLGETPROC_(glXQueryVersion, "");
283 GLGETPROC_(glXChooseVisual, "");
284 GLGETPROC_(glXCreateContext, "");
285 GLGETPROC_(glXMakeCurrent, "");
286 GLGETPROC_(glXDestroyContext, "");
287#endif
288 return VINF_SUCCESS;
289}
290
291PFNRT glLdrGetProcAddress(const char *pszSymbol)
292{
293 return OGLGETPROCADDRESS(pszSymbol);
294}
295
296int glLdrGetExtFunctions(void)
297{
298 GLGETPROC_(glBlendColor, "");
299 GLGETPROC_(glBlendEquation, "");
300 GLGETPROC_(glClientActiveTexture, "");
301 return VINF_SUCCESS;
302}
Note: See TracBrowser for help on using the repository browser.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette