VirtualBox

source: vbox/trunk/src/VBox/HostServices/SharedOpenGL/gllindrv.cpp@ 3858

Last change on this file since 3858 was 3858, checked in by vboxsync, 17 years ago

OpenGL update by Alexander Eichner

File size: 20.8 KB
Line 
1/** @file
2 *
3 * VBox OpenGL
4 *
5 * Simple buffered OpenGL functions
6 *
7 * Contributor: Alexander Eichner
8 */
9
10/*
11 * Copyright (C) 2006-2007 innotek GmbH
12 *
13 * This file is part of VirtualBox Open Source Edition (OSE), as
14 * available from http://www.virtualbox.org. This file is free software;
15 * you can redistribute it and/or modify it under the terms of the GNU
16 * General Public License as published by the Free Software Foundation,
17 * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE
18 * distribution. VirtualBox OSE is distributed in the hope that it will
19 * be useful, but WITHOUT ANY WARRANTY of any kind.
20 *
21 * If you received this file as part of a commercial VirtualBox
22 * distribution, then only the terms of your commercial VirtualBox
23 * license agreement apply instead of the previous paragraph.
24 *
25 */
26#define GLX_GLXEXT_PROTOTYPES
27
28#include "vboxgl.h"
29#define LOG_GROUP LOG_GROUP_SHARED_OPENGL
30#include <VBox/log.h>
31#include <string.h>
32#include <stdio.h>
33#include <GL/gl.h>
34#include <GL/glx.h>
35#include <GL/glxext.h>
36
37
38/* X11 server connection for all OpenGL clients.
39 * Neccessary because Mesa and DRI cannot handle more than one
40 * connection per thread (only hardware acceleration, software rendering
41 * runs fine with more than one connection).
42 * Would crash in vboxglDisconnect if on every vboxglConnect
43 * a new Display is created */
44Display *glXDisplay = NULL;
45
46static Bool WaitForNotify( Display *dpy, XEvent *event, XPointer arg ) {
47 return (event->type == MapNotify) && (event->xmap.window == (Window) arg);
48}
49
50/* from http://www.mesa3d.org/brianp/sig97/exten.htm */
51GLboolean vboxglCheckExtension(Display *dpy, int screenNum, const char *extName )
52{
53 /*
54 ** Search for extName in the extensions string. Use of strstr()
55 ** is not sufficient because extension names can be prefixes of
56 ** other extension names. Could use strtok() but the constant
57 ** string returned by glGetString can be in read-only memory.
58 */
59 char *p = (char *) glXQueryExtensionsString(dpy, screenNum);
60 char *end;
61 int extNameLen;
62
63 extNameLen = strlen(extName);
64 end = p + strlen(p);
65
66 while (p < end) {
67 int n = strcspn(p, " ");
68 if ((extNameLen == n) && (strncmp(extName, p, n) == 0)) {
69 return GL_TRUE;
70 }
71 p += (n + 1);
72 }
73 return GL_FALSE;
74}
75
76/**
77 * Global init of VBox OpenGL
78 *
79 * @returns VBox error code
80 */
81int vboxglGlobalInit()
82{
83 Log(("vboxglGlobalInit\n"));
84
85 /*vboxInitOpenGLExtensions();*/
86 return VINF_SUCCESS;
87}
88
89/**
90 * Global deinit of VBox OpenGL
91 *
92 * @returns VBox error code
93 */
94int vboxglGlobalUnload()
95{
96 Log(("vboxglGlobalUnload"));
97
98 if (glXDisplay)
99 XCloseDisplay(glXDisplay);
100
101 return VINF_SUCCESS;
102}
103
104/**
105 * Enable OpenGL
106 *
107 * @returns VBox error code
108 * @param pClient Client context
109 */
110int vboxglEnableOpenGL(PVBOXOGLCTX pClient)
111{
112 static int attribs[] = {
113 GLX_DRAWABLE_TYPE, GLX_WINDOW_BIT,
114 GLX_RENDER_TYPE, GLX_RGBA_BIT,
115 GLX_DOUBLEBUFFER, GL_TRUE, /* Request a double-buffered color buffer with */
116 GLX_RED_SIZE, 1, /* the maximum number of bits per component */
117 GLX_GREEN_SIZE, 1,
118 GLX_BLUE_SIZE, 1,
119 None
120 };
121 int screen_num;
122 XSetWindowAttributes attr;
123 unsigned long mask;
124 int returnedFBConfigs;
125
126 /* we have to set up a rendering context to be able to use glGetString
127 * a window is created but is not mapped to screen (so it's not visible')
128 * and a GLXContext is bound to it */
129 screen_num = DefaultScreen(pClient->dpy);
130 pClient->enable.fbConfig = pClient->glxChooseFBConfig(pClient->dpy, screen_num, attribs, &returnedFBConfigs);
131 Log(("vboxglGetString: returned FBConfigs: %d\n", returnedFBConfigs));
132 pClient->enable.visinfo = pClient->glxGetVisualFromFBConfig(pClient->dpy, pClient->enable.fbConfig[0]);
133 /* Create Window */
134 attr.background_pixel = 0;
135 attr.border_pixel = 0;
136 attr.colormap = XCreateColormap(pClient->dpy, RootWindow(pClient->dpy, screen_num), pClient->enable.visinfo->visual, AllocNone);
137 attr.event_mask = StructureNotifyMask | ExposureMask;
138 mask = CWBackPixel | CWBorderPixel | CWColormap | CWEventMask;
139 pClient->enable.win = XCreateWindow(pClient->dpy, RootWindow(pClient->dpy, screen_num), 0, 0, 100, 100,
140 0, pClient->enable.visinfo->depth, InputOutput,
141 pClient->enable.visinfo->visual, mask, &attr);
142 /* Create Context */
143 pClient->enable.ctx = pClient->glxCreateNewContext(pClient->dpy, pClient->enable.fbConfig[0], GLX_RGBA_TYPE, NULL, GL_TRUE);
144 glXMakeCurrent(pClient->dpy, pClient->enable.win, pClient->enable.ctx);
145
146 return VINF_SUCCESS;
147}
148
149/**
150 * Disable OpenGL
151 *
152 * @returns VBox error code
153 * @param pClient Client context
154 */
155int vboxglDisableOpenGL(PVBOXOGLCTX pClient)
156{
157 /* Free all data */
158 if (pClient->enable.ctx)
159 {
160 glFlush();
161 glXMakeCurrent(pClient->dpy, None, NULL);
162 XDestroyWindow(pClient->dpy, pClient->enable.win);
163 glXDestroyContext(pClient->dpy, pClient->enable.ctx);
164 XFree(pClient->enable.visinfo);
165 XFree(pClient->enable.fbConfig);
166 }
167
168 return VINF_SUCCESS;
169}
170
171/**
172 * Client connect init
173 *
174 * @returns VBox error code
175 * @param pClient Client context
176 */
177int vboxglConnect(PVBOXOGLCTX pClient)
178{
179 int rc = VERR_NOT_IMPLEMENTED;
180 Log(("vboxglConnect\n"));
181
182 pClient->PixelFormatToFBConfigMapper = NULL;
183 pClient->xWindow = 0;
184
185 if (!glXDisplay)
186 glXDisplay = XOpenDisplay(NULL);
187
188 pClient->dpy = glXDisplay;
189
190 if (pClient->dpy) {
191 int screenNum, major, minor;
192
193 screenNum = DefaultScreen(pClient->dpy);
194 glXQueryVersion(pClient->dpy, &major, &minor);
195
196 if ((major == 1) && (minor >= 3)) {
197 Log(("Server GLX 1.3 supported\n"));
198 pClient->glxChooseFBConfig = (PFNGLXCHOOSEFBCONFIGSGIXPROC) glXGetProcAddressARB(
199 (GLubyte *) "glXChooseFBConfig");
200 pClient->glxGetVisualFromFBConfig = (PFNGLXGETVISUALFROMFBCONFIGSGIXPROC) glXGetProcAddressARB(
201 (GLubyte *) "glXGetVisualFromFBConfig");
202 pClient->glxCreateNewContext = (PFNGLXCREATECONTEXTWITHCONFIGSGIXPROC) glXGetProcAddressARB(
203 (GLubyte *) "glXCreateNewContext");
204 } else if (vboxglCheckExtension(pClient->dpy, screenNum, "GLX_SGIX_fbconfig")) {
205 Log(("GLX_SGIX_fbconfig extension supported\n"));
206 pClient->glxChooseFBConfig = (PFNGLXCHOOSEFBCONFIGSGIXPROC) glXGetProcAddressARB(
207 (GLubyte *) "glXChooseFBConfigSGIX");
208 pClient->glxGetVisualFromFBConfig = (PFNGLXGETVISUALFROMFBCONFIGSGIXPROC) glXGetProcAddressARB(
209 (GLubyte *) "glXGetVisualFromFBConfigSGIX");
210 pClient->glxCreateNewContext = (PFNGLXCREATECONTEXTWITHCONFIGSGIXPROC) glXGetProcAddressARB(
211 (GLubyte *) "glXCreateContextWithConfigSGIX");
212 } else {
213 Log(("Error no FBConfig supported\n"));
214 rc = VERR_NOT_IMPLEMENTED;
215 }
216 if (pClient->glxChooseFBConfig && pClient->glxGetVisualFromFBConfig && pClient->glxCreateNewContext)
217 rc = VINF_SUCCESS;
218 }
219
220 return rc;
221}
222
223/**
224 * Client disconnect cleanup
225 *
226 * @returns VBox error code
227 * @param pClient Client context
228 */
229int vboxglDisconnect(PVBOXOGLCTX pClient)
230{
231 Log(("vboxglDisconnect\n"));
232
233#ifdef VBOX_OGL_DEBUG_WINDOW_OUTPUT
234 if (pClient->xWindow != 0) {
235 XUnmapWindow(pClient->dpy, pClient->xWindow);
236 XDestroyWindow(pClient->dpy, pClient->xWindow);
237 }
238 if (pClient->PixelFormatToFBConfigMapper) {
239 XFree(pClient->PixelFormatToFBConfigMapper);
240 }
241
242 pClient->dpy = NULL;
243 pClient->xWindow = 0;
244 pClient->actFBConfig = NULL;
245#endif
246 return VINF_SUCCESS;
247}
248
249/* Driver functions */
250void vboxglDrvCreateContext(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
251{
252 XSetWindowAttributes attr;
253 XVisualInfo *visinfo = NULL;
254 unsigned long mask;
255 GLXFBConfig fbConfig;
256 GLXContextID glrc;
257 int screen_num;
258 XEvent event;
259 OGL_CMD(DrvCreateContext, 1);
260 OGL_PARAM(HDC, hdc);
261
262 Log(("DrvCreateContext %x\n", hdc));
263#ifdef VBOX_OGL_DEBUG_WINDOW_OUTPUT
264
265 screen_num = DefaultScreen(pClient->dpy);
266 fbConfig = pClient->actFBConfig;
267
268 visinfo = pClient->glxGetVisualFromFBConfig(pClient->dpy, fbConfig);
269
270 if (pClient->xWindow == 0) {
271
272 /* window attributes */
273 attr.background_pixel = 0;
274 attr.border_pixel = 0;
275 attr.colormap = XCreateColormap(pClient->dpy, RootWindow(pClient->dpy, screen_num ), visinfo->visual, AllocNone);
276 attr.event_mask = StructureNotifyMask | ExposureMask;
277 mask = CWBackPixel | CWBorderPixel | CWColormap | CWEventMask;
278 pClient->xWindow = XCreateWindow(pClient->dpy,
279 RootWindow(pClient->dpy, screen_num),
280 0, 0, pClient->winWidth, pClient->winHeight, 0,
281 visinfo->depth, InputOutput,
282 visinfo->visual, mask, &attr);
283 }
284 XResizeWindow(pClient->dpy, pClient->xWindow, pClient->winWidth, pClient->winHeight);
285 pClient->glxContext = pClient->glxCreateNewContext(pClient->dpy, fbConfig, GLX_RGBA_TYPE, NULL, GL_TRUE);
286
287 XMapWindow(pClient->dpy, pClient->xWindow);
288 XIfEvent(pClient->dpy, &event, WaitForNotify, (XPointer)pClient->xWindow );
289
290 glrc = 1;
291 Assert(glrc);
292#else
293 AssertFailed();
294 glrc = 0;
295#endif
296
297 pClient->lastretval = (uint64_t)glrc;
298 pClient->fHasLastError = true;
299 pClient->ulLastError = glGetError();
300}
301
302void vboxglDrvDeleteContext(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
303{
304 OGL_CMD(DrvDeleteContext, 1);
305 OGL_PARAM(HGLRC, hglrc);
306 Log(("DrvDeleteContext %x\n", hglrc));
307
308 glXDestroyContext(pClient->dpy, VBOX_OGL_GUEST_TO_HOST_HDC(hglrc));
309 pClient->lastretval = 1;
310 pClient->fHasLastError = true;
311 pClient->ulLastError = glGetError();
312}
313
314void vboxglDrvSetContext(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
315{
316 OGL_CMD(DrvSetContext, 2);
317 OGL_PARAM(HDC, hdc);
318 OGL_PARAM(HGLRC, hglrc);
319 Log(("DrvSetContext %x %x\n", hdc, hglrc));
320#ifdef VBOX_OGL_DEBUG_WINDOW_OUTPUT
321
322 pClient->lastretval = glXMakeCurrent(pClient->dpy, pClient->xWindow,
323 VBOX_OGL_GUEST_TO_HOST_HDC(hglrc));
324 if (!pClient->lastretval)
325 Log(("glXMakeCurrent failed\n"));
326 pClient->fHasLastError = true;
327 pClient->ulLastError = glGetError();
328#else
329 AssertFailed();
330#endif
331}
332
333void vboxglDrvCopyContext(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
334{
335 OGL_CMD(DrvDeleteContext, 3);
336 OGL_PARAM(HGLRC, hglrcSrc);
337 OGL_PARAM(HGLRC, hglrcDst);
338 OGL_PARAM(UINT, mask);
339 Log(("DrvCopyContext %x %x %x\n", hglrcSrc, hglrcDst, mask));
340
341 glXCopyContext(pClient->dpy, VBOX_OGL_GUEST_TO_HOST_HDC(hglrc), VBOX_OGL_GUEST_TO_HOST_HDC(hglrc), mask);
342 pClient->lastretval = 1;
343 pClient->fHasLastError = true;
344 pClient->ulLastError = glGetError();
345}
346
347void vboxglDrvReleaseContext(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
348{
349 OGL_CMD(DrvReleaseContext, 1);
350 OGL_PARAM(HGLRC, hglrc);
351 Log(("DrvReleaseContext %x\n", hglrc));
352 /* clear current selection */
353 pClient->lastretval = glXMakeCurrent(pClient->dpy, None, NULL);
354
355 if (!pClient->lastretval)
356 Log(("glXMakeCurrent failed\n"));
357 pClient->fHasLastError = true;
358 pClient->ulLastError = glGetError();
359}
360
361void vboxglDrvCreateLayerContext(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
362{
363 XSetWindowAttributes attr;
364 XVisualInfo *visinfo = NULL;
365 unsigned long mask;
366 GLXFBConfig fbConfig;
367 GLXContextID glrc;
368 int screen_num;
369 XEvent event;
370 OGL_CMD(DrvCreateLayerContext, 2);
371 OGL_PARAM(HDC, hdc);
372 OGL_PARAM(int, iLayerPlane);
373
374 Log(("DrvCreateLayerContext %x\n", hdc));
375#ifdef VBOX_OGL_DEBUG_WINDOW_OUTPUT
376
377 screen_num = DefaultScreen(pClient->dpy);
378 fbConfig = pClient->actFBConfig;
379 visinfo = pClient->glxGetVisualFromFBConfig(pClient->dpy, fbConfig);
380
381 if (pClient->xWindow == 0) {
382
383 /* window attributes */
384 attr.background_pixel = 0;
385 attr.border_pixel = 0;
386 attr.colormap = XCreateColormap(pClient->dpy, RootWindow(pClient->dpy, screen_num ), visinfo->visual, AllocNone);
387 attr.event_mask = StructureNotifyMask | ExposureMask;
388 mask = CWBackPixel | CWBorderPixel | CWColormap | CWEventMask;
389 pClient->xWindow = XCreateWindow(pClient->dpy,
390 RootWindow(pClient->dpy, screen_num),
391 0, 0, pClient->winWidth, pClient->winHeight, 0,
392 visinfo->depth, InputOutput,
393 visinfo->visual, mask, &attr);
394 }
395 XResizeWindow(pClient->dpy, pClient->xWindow, pClient->winWidth, pClient->winHeight);
396 pClient->glxContext = pClient->glxCreateNewContext(pClient->dpy, fbConfig, GLX_RGBA_TYPE, NULL, GL_TRUE);
397 XMapWindow(pClient->dpy, pClient->xWindow);
398 XIfEvent(pClient->dpy, &event, WaitForNotify, (XPointer)pClient->xWindow );
399
400 glrc = 1;
401 Assert(glrc);
402
403 pClient->lastretval = glrc;
404 pClient->fHasLastError = true;
405 pClient->ulLastError = glGetError();
406#else
407 AssertFailed();
408#endif
409}
410
411void vboxglDrvShareLists(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
412{
413 OGL_CMD(DrvShareLists, 3);
414 OGL_PARAM(HGLRC, hglrc1);
415 OGL_PARAM(HGLRC, hglrc2);
416 pClient->lastretval = 0; /** @todo */
417 pClient->fHasLastError = true;
418 pClient->ulLastError = glGetError();
419}
420
421
422void vboxglDrvRealizeLayerPalette(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
423{
424 OGL_CMD(DrvRealizeLayerPalette, 3);
425 OGL_PARAM(HDC, hdc);
426 OGL_PARAM(int, iLayerPlane);
427 OGL_PARAM(BOOL, bRealize);
428 pClient->lastretval = 0; /** @todo */
429 pClient->fHasLastError = true;
430 pClient->ulLastError = glGetError();
431}
432
433void vboxglDrvSwapLayerBuffers(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
434{
435 OGL_CMD(DrvSwapLayerBuffers, 2);
436 OGL_PARAM(HDC, hdc);
437 OGL_PARAM(UINT, fuPlanes);
438 pClient->lastretval = 0; /** @todo */
439 pClient->fHasLastError = true;
440 pClient->ulLastError = glGetError();
441}
442
443void vboxglDrvSetPixelFormat(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
444{
445 int screen_num;
446 OGL_CMD(DrvSetPixelFormat, 4);
447 OGL_PARAM(HDC, hdc);
448 OGL_PARAM(int, iPixelFormat);
449 OGL_PARAM(uint32_t, cx);
450 OGL_PARAM(uint32_t, cy);
451
452 Log(("vboxDrvSetPixelFormat %d\n", iPixelFormat));
453
454 /* Get GLXFBConfig based on the given ID */
455 pClient->actFBConfig = pClient->PixelFormatToFBConfigMapper[iPixelFormat-1];
456 screen_num = DefaultScreen(pClient->dpy);
457
458 pClient->winWidth = cx;
459 pClient->winHeight = cy;
460 pClient->lastretval = true;
461 pClient->fHasLastError = true;
462 pClient->ulLastError = glGetError();
463}
464
465void vboxglDrvSwapBuffers(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
466{
467 OGL_CMD(DrvSwapBuffers, 1);
468 OGL_PARAM(HDC, hdc);
469
470 glXSwapBuffers(pClient->dpy, pClient->xWindow);
471 pClient->lastretval = 1;
472 pClient->fHasLastError = true;
473 pClient->ulLastError = glGetError();
474}
475
476void vboxglDrvDescribeLayerPlane(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
477{
478 PLAYERPLANEDESCRIPTOR plpd;
479
480 OGL_CMD(DrvDescribeLayerPlane, 4);
481 OGL_PARAM(HDC, hdc);
482 OGL_PARAM(int, iPixelFormat);
483 OGL_PARAM(int, iLayerPlane);
484 OGL_PARAM(UINT, nBytes);
485 Assert(pClient->cbLastParam == nBytes);
486 plpd = (PLAYERPLANEDESCRIPTOR)pClient->pLastParam;
487
488 pClient->lastretval = 0; /** @todo */
489 pClient->fHasLastError = true;
490 pClient->ulLastError = glGetError();
491}
492
493void vboxglDrvSetLayerPaletteEntries(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
494{
495 OGL_CMD(DrvSetLayerPaletteEntries, 5);
496 OGL_PARAM(HDC, hdc);
497 OGL_PARAM(int, iLayerPlane);
498 OGL_PARAM(int, iStart);
499 OGL_PARAM(int, cEntries);
500 OGL_MEMPARAM(COLORREF, pcr);
501 pClient->lastretval = 0; /** @todo */
502 pClient->fHasLastError = true;
503 pClient->ulLastError = glGetError();
504}
505
506void vboxglDrvGetLayerPaletteEntries(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
507{
508 COLORREF *pcr;
509
510 OGL_CMD(DrvGetLayerPaletteEntries, 4);
511 OGL_PARAM(HDC, hdc);
512 OGL_PARAM(int, iLayerPlane);
513 OGL_PARAM(int, iStart);
514 OGL_PARAM(int, cEntries);
515
516 Assert(pClient->cbLastParam == sizeof(COLORREF)*cEntries);
517 pcr = (COLORREF *)pClient->pLastParam;
518 pClient->lastretval = 0; /** @todo */
519 pClient->fHasLastError = true;
520 pClient->ulLastError = glGetError();
521}
522
523void vboxglDrvDescribePixelFormat(VBOXOGLCTX *pClient, uint8_t *pCmdBuffer)
524{
525 LPPIXELFORMATDESCRIPTOR ppfd;
526 GLXFBConfig *allFBConfigs, matchingFBConfig;
527 int screenNum, glxReturnValue;
528
529 OGL_CMD(DrvDescribePixelFormat, 3);
530 OGL_PARAM(HDC, hdc);
531 OGL_PARAM(int, iPixelFormat);
532 OGL_PARAM(UINT, nBytes);
533 Assert(pClient->cbLastParam == nBytes);
534 ppfd = (LPPIXELFORMATDESCRIPTOR)pClient->pLastParam;
535
536 Log(("iPixelFormat: %d\n", iPixelFormat));
537
538 if (!pClient->PixelFormatToFBConfigMapper) {
539 /* First get number of all visuals for the return value */
540 screenNum = DefaultScreen(pClient->dpy);
541 allFBConfigs = glXGetFBConfigs(pClient->dpy, screenNum,
542 &pClient->numFBConfigs);
543 pClient->PixelFormatToFBConfigMapper = allFBConfigs;
544 }
545
546 if (nBytes == sizeof(PIXELFORMATDESCRIPTOR)) {
547 int redSize, greenSize, blueSize, alphaSize, xVisual, xRenderable;
548 /* Get GLXFBConfig which matches iPixelFormat */
549 matchingFBConfig = pClient->PixelFormatToFBConfigMapper[iPixelFormat-1];
550
551 Log(("Filling values into PIXELFORMATDESCRIPTOR\n"));
552 /* translate all values to theire corresponding Windows ones */
553 ppfd->nSize = sizeof(PIXELFORMATDESCRIPTOR);
554 ppfd->nVersion = 1;
555 ppfd->iLayerType = PFD_MAIN_PLANE;
556 ppfd->dwFlags = 0;
557
558 /* Set cColorBits */
559 glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_RED_SIZE, &redSize);
560 glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_GREEN_SIZE, &greenSize);
561 glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_BLUE_SIZE, &blueSize);
562 glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_ALPHA_SIZE, &alphaSize);
563 ppfd->cColorBits = redSize + greenSize + blueSize;
564 ppfd->cRedBits = redSize;
565 ppfd->cBlueBits = blueSize;
566 ppfd->cGreenBits = greenSize;
567 ppfd->cAlphaBits = alphaSize;
568
569 /* Set dwFlags */
570 if (!glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_DRAWABLE_TYPE, &glxReturnValue)) {
571 glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_VISUAL_ID, &xVisual);
572 glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_X_RENDERABLE, &xRenderable);
573 if ((glxReturnValue & GLX_WINDOW_BIT) && xVisual)
574 ppfd->dwFlags |= (PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL);
575 }
576 if (!glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_DOUBLEBUFFER, &glxReturnValue)) {
577 if (glxReturnValue)
578 ppfd->dwFlags |= PFD_DOUBLEBUFFER;
579 }
580 /* Set iPixelType */
581 if (!glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_RENDER_TYPE, &glxReturnValue)) {
582 if (glxReturnValue & GLX_RGBA_BIT)
583 ppfd->iPixelType = PFD_TYPE_RGBA;
584 else if ((glxReturnValue & GLX_COLOR_INDEX_BIT) & !(glxReturnValue & GLX_RGBA_BIT))
585 ppfd->iPixelType = PFD_TYPE_COLORINDEX;
586 }
587 /* Set cDepthBits */
588 if (!glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_DEPTH_SIZE, &glxReturnValue)) {
589 ppfd->cDepthBits = glxReturnValue;
590 } else {
591 ppfd->cDepthBits = 0;
592 }
593 /* Set cStencilBits */
594 if (!glXGetFBConfigAttrib(pClient->dpy, matchingFBConfig, GLX_STENCIL_SIZE, &glxReturnValue)) {
595 ppfd->cStencilBits = glxReturnValue;
596 } else {
597 ppfd->cStencilBits = 0;
598 }
599 /** @todo Fill in the rest */
600 }
601
602 pClient->lastretval = pClient->numFBConfigs;
603 pClient->fHasLastError = true;
604 pClient->ulLastError = glGetError();
605}
606
607RTUINTPTR vboxDrvIsExtensionAvailable(char *pszExtFunctionName)
608{
609 RTUINTPTR pfnProc = (RTUINTPTR)glXGetProcAddress((const GLubyte *)pszExtFunctionName);
610 Log(("vboxDrvIsExtensionAvailable %s -> %d\n", pszExtFunctionName, !!pfnProc));
611 return pfnProc;
612}
613
Note: See TracBrowser for help on using the repository browser.

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