Bug Summary

File:glx/glxcmds.c
Location:line 1178, column 13
Description:Assigned value is garbage or undefined

Annotated Source Code

1/*
2 * SGI FREE SOFTWARE LICENSE B (Version 2.0, Sept. 18, 2008)
3 * Copyright (C) 1991-2000 Silicon Graphics, Inc. All Rights Reserved.
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the "Software"),
7 * to deal in the Software without restriction, including without limitation
8 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9 * and/or sell copies of the Software, and to permit persons to whom the
10 * Software is furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice including the dates of first publication and
13 * either this permission notice or a reference to
14 * http://oss.sgi.com/projects/FreeB/
15 * shall be included in all copies or substantial portions of the Software.
16 *
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
18 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
20 * SILICON GRAPHICS, INC. BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
21 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
22 * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23 * SOFTWARE.
24 *
25 * Except as contained in this notice, the name of Silicon Graphics, Inc.
26 * shall not be used in advertising or otherwise to promote the sale, use or
27 * other dealings in this Software without prior written authorization from
28 * Silicon Graphics, Inc.
29 */
30
31#ifdef HAVE_DIX_CONFIG_H1
32#include <dix-config.h>
33#endif
34
35#include <string.h>
36#include <assert.h>
37
38#include "glxserver.h"
39#include <GL/glxtokens.h>
40#include <unpack.h>
41#include <pixmapstr.h>
42#include <windowstr.h>
43#include "glxutil.h"
44#include "glxext.h"
45#include "indirect_dispatch.h"
46#include "indirect_table.h"
47#include "indirect_util.h"
48
49static char GLXServerVendorName[] = "SGI";
50
51_X_HIDDEN__attribute__((visibility("hidden"))) int
52validGlxScreen(ClientPtr client, int screen, __GLXscreen ** pGlxScreen,
53 int *err)
54{
55 /*
56 ** Check if screen exists.
57 */
58 if (screen < 0 || screen >= screenInfo.numScreens) {
59 client->errorValue = screen;
60 *err = BadValue2;
61 return FALSE0;
62 }
63 *pGlxScreen = glxGetScreen(screenInfo.screens[screen]);
64
65 return TRUE1;
66}
67
68_X_HIDDEN__attribute__((visibility("hidden"))) int
69validGlxFBConfig(ClientPtr client, __GLXscreen * pGlxScreen, XID id,
70 __GLXconfig ** config, int *err)
71{
72 __GLXconfig *m;
73
74 for (m = pGlxScreen->fbconfigs; m != NULL((void*)0); m = m->next)
75 if (m->fbconfigID == id) {
76 *config = m;
77 return TRUE1;
78 }
79
80 client->errorValue = id;
81 *err = __glXError(GLXBadFBConfig9);
82
83 return FALSE0;
84}
85
86static int
87validGlxVisual(ClientPtr client, __GLXscreen * pGlxScreen, XID id,
88 __GLXconfig ** config, int *err)
89{
90 int i;
91
92 for (i = 0; i < pGlxScreen->numVisuals; i++)
93 if (pGlxScreen->visuals[i]->visualID == id) {
94 *config = pGlxScreen->visuals[i];
95 return TRUE1;
96 }
97
98 client->errorValue = id;
99 *err = BadValue2;
100
101 return FALSE0;
102}
103
104static int
105validGlxFBConfigForWindow(ClientPtr client, __GLXconfig * config,
106 DrawablePtr pDraw, int *err)
107{
108 ScreenPtr pScreen = pDraw->pScreen;
109 VisualPtr pVisual = NULL((void*)0);
110 XID vid;
111 int i;
112
113 vid = wVisual((WindowPtr) pDraw)(((WindowPtr) pDraw)->optional ? ((WindowPtr) pDraw)->optional
->visual : FindWindowWithOptional((WindowPtr) pDraw)->optional
->visual)
;
114 for (i = 0; i < pScreen->numVisuals; i++) {
115 if (pScreen->visuals[i].vid == vid) {
116 pVisual = &pScreen->visuals[i];
117 break;
118 }
119 }
120
121 /* FIXME: What exactly should we check here... */
122 if (pVisual->class != glxConvertToXVisualType(config->visualType) ||
123 !(config->drawableType & GLX_WINDOW_BIT0x00000001)) {
124 client->errorValue = pDraw->id;
125 *err = BadMatch8;
126 return FALSE0;
127 }
128
129 return TRUE1;
130}
131
132_X_HIDDEN__attribute__((visibility("hidden"))) int
133validGlxContext(ClientPtr client, XID id, int access_mode,
134 __GLXcontext ** context, int *err)
135{
136 *err = dixLookupResourceByType((void **) context, id,
137 __glXContextRes, client, access_mode);
138 if (*err != Success0 || (*context)->idExists == GL_FALSE0x0) {
139 client->errorValue = id;
140 if (*err == BadValue2 || *err == Success0)
141 *err = __glXError(GLXBadContext0);
142 return FALSE0;
143 }
144
145 return TRUE1;
146}
147
148static int
149validGlxDrawable(ClientPtr client, XID id, int type, int access_mode,
150 __GLXdrawable ** drawable, int *err)
151{
152 int rc;
153
154 rc = dixLookupResourceByType((void **) drawable, id,
155 __glXDrawableRes, client, access_mode);
156 if (rc != Success0 && rc != BadValue2) {
157 *err = rc;
158 client->errorValue = id;
159 return FALSE0;
160 }
161
162 /* If the ID of the glx drawable we looked up doesn't match the id
163 * we looked for, it's because we looked it up under the X
164 * drawable ID (see DoCreateGLXDrawable). */
165 if (rc == BadValue2 ||
166 (*drawable)->drawId != id ||
167 (type != GLX_DRAWABLE_ANY && type != (*drawable)->type)) {
168 client->errorValue = id;
169 switch (type) {
170 case GLX_DRAWABLE_WINDOW:
171 *err = __glXError(GLXBadWindow12);
172 return FALSE0;
173 case GLX_DRAWABLE_PIXMAP:
174 *err = __glXError(GLXBadPixmap3);
175 return FALSE0;
176 case GLX_DRAWABLE_PBUFFER:
177 *err = __glXError(GLXBadPbuffer10);
178 return FALSE0;
179 case GLX_DRAWABLE_ANY:
180 *err = __glXError(GLXBadDrawable2);
181 return FALSE0;
182 }
183 }
184
185 return TRUE1;
186}
187
188void
189__glXContextDestroy(__GLXcontext * context)
190{
191 lastGLContext = NULL((void*)0);
192}
193
194static void
195__glXdirectContextDestroy(__GLXcontext * context)
196{
197 __glXContextDestroy(context);
198 free(context);
199}
200
201static int
202__glXdirectContextLoseCurrent(__GLXcontext * context)
203{
204 return GL_TRUE0x1;
205}
206
207_X_HIDDEN__attribute__((visibility("hidden"))) __GLXcontext *
208__glXdirectContextCreate(__GLXscreen * screen,
209 __GLXconfig * modes, __GLXcontext * shareContext)
210{
211 __GLXcontext *context;
212
213 context = calloc(1, sizeof(__GLXcontext));
214 if (context == NULL((void*)0))
215 return NULL((void*)0);
216
217 context->destroy = __glXdirectContextDestroy;
218 context->loseCurrent = __glXdirectContextLoseCurrent;
219
220 return context;
221}
222
223/**
224 * Create a GL context with the given properties. This routine is used
225 * to implement \c glXCreateContext, \c glXCreateNewContext, and
226 * \c glXCreateContextWithConfigSGIX. This works becuase of the hack way
227 * that GLXFBConfigs are implemented. Basically, the FBConfigID is the
228 * same as the VisualID.
229 */
230
231static int
232DoCreateContext(__GLXclientState * cl, GLXContextID gcId,
233 GLXContextID shareList, __GLXconfig * config,
234 __GLXscreen * pGlxScreen, GLboolean isDirect)
235{
236 ClientPtr client = cl->client;
237 __GLXcontext *glxc, *shareglxc;
238 int err;
239
240 LEGAL_NEW_RESOURCE(gcId, client)if (!LegalNewID(gcId,client)) { client->errorValue = gcId;
return 14; }
;
241
242 /*
243 ** Find the display list space that we want to share.
244 **
245 ** NOTE: In a multithreaded X server, we would need to keep a reference
246 ** count for each display list so that if one client detroyed a list that
247 ** another client was using, the list would not really be freed until it
248 ** was no longer in use. Since this sample implementation has no support
249 ** for multithreaded servers, we don't do this.
250 */
251 if (shareList == None0L) {
252 shareglxc = 0;
253 }
254 else {
255 if (!validGlxContext(client, shareList, DixReadAccess(1<<0),
256 &shareglxc, &err))
257 return err;
258
259 /* Page 26 (page 32 of the PDF) of the GLX 1.4 spec says:
260 *
261 * "The server context state for all sharing contexts must exist
262 * in a single address space or a BadMatch error is generated."
263 *
264 * If the share context is indirect, force the new context to also be
265 * indirect. If the shard context is direct but the new context
266 * cannot be direct, generate BadMatch.
267 */
268 if (shareglxc->isDirect && !isDirect) {
269 client->errorValue = shareList;
270 return BadMatch8;
271 }
272 else if (!shareglxc->isDirect) {
273 /*
274 ** Create an indirect context regardless of what the client asked
275 ** for; this way we can share display list space with shareList.
276 */
277 isDirect = GL_FALSE0x0;
278 }
279 }
280
281 /*
282 ** Allocate memory for the new context
283 */
284 if (!isDirect) {
285 /* Only allow creating indirect GLX contexts if allowed by
286 * server command line. Indirect GLX is of limited use (since
287 * it's only GL 1.4), it's slower than direct contexts, and
288 * it's a massive attack surface for buffer overflow type
289 * errors.
290 */
291 if (!enableIndirectGLX) {
292 client->errorValue = isDirect;
293 return BadValue2;
294 }
295
296 /* Without any attributes, the only error that the driver should be
297 * able to generate is BadAlloc. As result, just drop the error
298 * returned from the driver on the floor.
299 */
300 glxc = pGlxScreen->createContext(pGlxScreen, config, shareglxc,
301 0, NULL((void*)0), &err);
302 }
303 else
304 glxc = __glXdirectContextCreate(pGlxScreen, config, shareglxc);
305 if (!glxc) {
306 return BadAlloc11;
307 }
308
309 /* Initialize the GLXcontext structure.
310 */
311 glxc->pGlxScreen = pGlxScreen;
312 glxc->config = config;
313 glxc->id = gcId;
314 glxc->share_id = shareList;
315 glxc->idExists = GL_TRUE0x1;
316 glxc->currentClient = NULL((void*)0);
317 glxc->isDirect = isDirect;
318 glxc->hasUnflushedCommands = GL_FALSE0x0;
319 glxc->renderMode = GL_RENDER0x1C00;
320 glxc->feedbackBuf = NULL((void*)0);
321 glxc->feedbackBufSize = 0;
322 glxc->selectBuf = NULL((void*)0);
323 glxc->selectBufSize = 0;
324 glxc->drawPriv = NULL((void*)0);
325 glxc->readPriv = NULL((void*)0);
326
327 /* The GLX_ARB_create_context_robustness spec says:
328 *
329 * "The default value for GLX_CONTEXT_RESET_NOTIFICATION_STRATEGY_ARB
330 * is GLX_NO_RESET_NOTIFICATION_ARB."
331 *
332 * Without using glXCreateContextAttribsARB, there is no way to specify a
333 * non-default reset notification strategy.
334 */
335 glxc->resetNotificationStrategy = GLX_NO_RESET_NOTIFICATION_ARB0x8261;
336
337#ifdef GLX_CONTEXT_RELEASE_BEHAVIOR_ARB
338 /* The GLX_ARB_context_flush_control spec says:
339 *
340 * "The default value [for GLX_CONTEXT_RELEASE_BEHAVIOR] is
341 * CONTEXT_RELEASE_BEHAVIOR_FLUSH, and may in some cases be changed
342 * using platform-specific context creation extensions."
343 *
344 * Without using glXCreateContextAttribsARB, there is no way to specify a
345 * non-default release behavior.
346 */
347 glxc->releaseBehavior = GLX_CONTEXT_RELEASE_BEHAVIOR_FLUSH_ARB;
348#endif
349
350 /* Add the new context to the various global tables of GLX contexts.
351 */
352 if (!__glXAddContext(glxc)) {
353 (*glxc->destroy) (glxc);
354 client->errorValue = gcId;
355 return BadAlloc11;
356 }
357
358 return Success0;
359}
360
361int
362__glXDisp_CreateContext(__GLXclientState * cl, GLbyte * pc)
363{
364 ClientPtr client = cl->client;
365 xGLXCreateContextReq *req = (xGLXCreateContextReq *) pc;
366 __GLXconfig *config;
367 __GLXscreen *pGlxScreen;
368 int err;
369
370 REQUEST_SIZE_MATCH(xGLXCreateContextReq)if ((sizeof(xGLXCreateContextReq) >> 2) != client->req_len
) return(16)
;
371
372 if (!validGlxScreen(cl->client, req->screen, &pGlxScreen, &err))
373 return err;
374 if (!validGlxVisual(cl->client, pGlxScreen, req->visual, &config, &err))
375 return err;
376
377 return DoCreateContext(cl, req->context, req->shareList,
378 config, pGlxScreen, req->isDirect);
379}
380
381int
382__glXDisp_CreateNewContext(__GLXclientState * cl, GLbyte * pc)
383{
384 ClientPtr client = cl->client;
385 xGLXCreateNewContextReq *req = (xGLXCreateNewContextReq *) pc;
386 __GLXconfig *config;
387 __GLXscreen *pGlxScreen;
388 int err;
389
390 REQUEST_SIZE_MATCH(xGLXCreateNewContextReq)if ((sizeof(xGLXCreateNewContextReq) >> 2) != client->
req_len) return(16)
;
391
392 if (!validGlxScreen(cl->client, req->screen, &pGlxScreen, &err))
393 return err;
394 if (!validGlxFBConfig(cl->client, pGlxScreen, req->fbconfig, &config, &err))
395 return err;
396
397 return DoCreateContext(cl, req->context, req->shareList,
398 config, pGlxScreen, req->isDirect);
399}
400
401int
402__glXDisp_CreateContextWithConfigSGIX(__GLXclientState * cl, GLbyte * pc)
403{
404 ClientPtr client = cl->client;
405 xGLXCreateContextWithConfigSGIXReq *req =
406 (xGLXCreateContextWithConfigSGIXReq *) pc;
407 __GLXconfig *config;
408 __GLXscreen *pGlxScreen;
409 int err;
410
411 REQUEST_SIZE_MATCH(xGLXCreateContextWithConfigSGIXReq)if ((sizeof(xGLXCreateContextWithConfigSGIXReq) >> 2) !=
client->req_len) return(16)
;
412
413 if (!validGlxScreen(cl->client, req->screen, &pGlxScreen, &err))
414 return err;
415 if (!validGlxFBConfig(cl->client, pGlxScreen, req->fbconfig, &config, &err))
416 return err;
417
418 return DoCreateContext(cl, req->context, req->shareList,
419 config, pGlxScreen, req->isDirect);
420}
421
422int
423__glXDisp_DestroyContext(__GLXclientState * cl, GLbyte * pc)
424{
425 ClientPtr client = cl->client;
426 xGLXDestroyContextReq *req = (xGLXDestroyContextReq *) pc;
427 __GLXcontext *glxc;
428 int err;
429
430 REQUEST_SIZE_MATCH(xGLXDestroyContextReq)if ((sizeof(xGLXDestroyContextReq) >> 2) != client->
req_len) return(16)
;
431
432 if (!validGlxContext(cl->client, req->context, DixDestroyAccess(1<<2),
433 &glxc, &err))
434 return err;
435
436 glxc->idExists = GL_FALSE0x0;
437 if (!glxc->currentClient)
438 FreeResourceByType(req->context, __glXContextRes, FALSE0);
439
440 return Success0;
441}
442
443/*
444 * This will return "deleted" contexts, ie, where idExists is GL_FALSE.
445 * Contrast validGlxContext, which will not. We're cheating here and
446 * using the XID as the context tag, which is fine as long as we defer
447 * actually destroying the context until it's no longer referenced, and
448 * block clients from trying to MakeCurrent on contexts that are on the
449 * way to destruction. Notice that DoMakeCurrent calls validGlxContext
450 * for new contexts but __glXLookupContextByTag for previous contexts.
451 */
452__GLXcontext *
453__glXLookupContextByTag(__GLXclientState * cl, GLXContextTag tag)
454{
455 __GLXcontext *ret;
456
457 if (dixLookupResourceByType((void **) &ret, tag, __glXContextRes,
458 cl->client, DixUseAccess(1<<24)) == Success0)
459 return ret;
460
461 return NULL((void*)0);
462}
463
464/*****************************************************************************/
465
466static void
467StopUsingContext(__GLXcontext * glxc)
468{
469 if (glxc) {
470 glxc->currentClient = NULL((void*)0);
471 if (!glxc->idExists) {
472 FreeResourceByType(glxc->id, __glXContextRes, FALSE0);
473 }
474 }
475}
476
477static void
478StartUsingContext(__GLXclientState * cl, __GLXcontext * glxc)
479{
480 glxc->currentClient = cl->client;
481}
482
483/**
484 * This is a helper function to handle the legacy (pre GLX 1.3) cases
485 * where passing an X window to glXMakeCurrent is valid. Given a
486 * resource ID, look up the GLX drawable if available, otherwise, make
487 * sure it's an X window and create a GLX drawable one the fly.
488 */
489static __GLXdrawable *
490__glXGetDrawable(__GLXcontext * glxc, GLXDrawable drawId, ClientPtr client,
491 int *error)
492{
493 DrawablePtr pDraw;
494 __GLXdrawable *pGlxDraw;
495 int rc;
496
497 if (validGlxDrawable(client, drawId, GLX_DRAWABLE_ANY,
498 DixWriteAccess(1<<1), &pGlxDraw, &rc)) {
499 if (glxc != NULL((void*)0) && pGlxDraw->config != glxc->config) {
500 client->errorValue = drawId;
501 *error = BadMatch8;
502 return NULL((void*)0);
503 }
504
505 return pGlxDraw;
506 }
507
508 /* No active context and an unknown drawable, bail. */
509 if (glxc == NULL((void*)0)) {
510 client->errorValue = drawId;
511 *error = BadMatch8;
512 return NULL((void*)0);
513 }
514
515 /* The drawId wasn't a GLX drawable. Make sure it's a window and
516 * create a GLXWindow for it. Check that the drawable screen
517 * matches the context screen and that the context fbconfig is
518 * compatible with the window visual. */
519
520 rc = dixLookupDrawable(&pDraw, drawId, client, 0, DixGetAttrAccess(1<<4));
521 if (rc != Success0 || pDraw->type != DRAWABLE_WINDOW0) {
522 client->errorValue = drawId;
523 *error = __glXError(GLXBadDrawable2);
524 return NULL((void*)0);
525 }
526
527 if (pDraw->pScreen != glxc->pGlxScreen->pScreen) {
528 client->errorValue = pDraw->pScreen->myNum;
529 *error = BadMatch8;
530 return NULL((void*)0);
531 }
532
533 if (!validGlxFBConfigForWindow(client, glxc->config, pDraw, error))
534 return NULL((void*)0);
535
536 pGlxDraw = glxc->pGlxScreen->createDrawable(client, glxc->pGlxScreen,
537 pDraw, drawId,
538 GLX_DRAWABLE_WINDOW,
539 drawId, glxc->config);
540 if (!pGlxDraw) {
541 *error = BadAlloc11;
542 return NULL((void*)0);
543 }
544
545 /* since we are creating the drawablePrivate, drawId should be new */
546 if (!AddResourceDarwin_X_AddResource(drawId, __glXDrawableRes, pGlxDraw)) {
547 pGlxDraw->destroy(pGlxDraw);
548 *error = BadAlloc11;
549 return NULL((void*)0);
550 }
551
552 return pGlxDraw;
553}
554
555/*****************************************************************************/
556/*
557** Make an OpenGL context and drawable current.
558*/
559
560static int
561DoMakeCurrent(__GLXclientState * cl,
562 GLXDrawable drawId, GLXDrawable readId,
563 GLXContextID contextId, GLXContextTag tag)
564{
565 ClientPtr client = cl->client;
566 xGLXMakeCurrentReply reply;
567 __GLXcontext *glxc, *prevglxc;
568 __GLXdrawable *drawPriv = NULL((void*)0);
569 __GLXdrawable *readPriv = NULL((void*)0);
570 int error;
571 GLuint mask;
572
573 /*
574 ** If one is None and the other isn't, it's a bad match.
575 */
576
577 mask = (drawId == None0L) ? (1 << 0) : 0;
578 mask |= (readId == None0L) ? (1 << 1) : 0;
579 mask |= (contextId == None0L) ? (1 << 2) : 0;
580
581 if ((mask != 0x00) && (mask != 0x07)) {
582 return BadMatch8;
583 }
584
585 /*
586 ** Lookup old context. If we have one, it must be in a usable state.
587 */
588 if (tag != 0) {
589 prevglxc = __glXLookupContextByTag(cl, tag);
590 if (!prevglxc) {
591 /*
592 ** Tag for previous context is invalid.
593 */
594 return __glXError(GLXBadContextTag4);
595 }
596 if (prevglxc->renderMode != GL_RENDER0x1C00) {
597 /* Oops. Not in render mode render. */
598 client->errorValue = prevglxc->id;
599 return __glXError(GLXBadContextState1);
600 }
601 }
602 else {
603 prevglxc = 0;
604 }
605
606 /*
607 ** Lookup new context. It must not be current for someone else.
608 */
609 if (contextId != None0L) {
610 int status;
611
612 if (!validGlxContext(client, contextId, DixUseAccess(1<<24), &glxc, &error))
613 return error;
614 if ((glxc != prevglxc) && glxc->currentClient) {
615 /* Context is current to somebody else */
616 return BadAccess10;
617 }
618
619 assert(drawId != None)(__builtin_expect(!(drawId != 0L), 0) ? __assert_rtn(__func__
, "glxcmds.c", 619, "drawId != None") : (void)0)
;
620 assert(readId != None)(__builtin_expect(!(readId != 0L), 0) ? __assert_rtn(__func__
, "glxcmds.c", 620, "readId != None") : (void)0)
;
621
622 drawPriv = __glXGetDrawable(glxc, drawId, client, &status);
623 if (drawPriv == NULL((void*)0))
624 return status;
625
626 readPriv = __glXGetDrawable(glxc, readId, client, &status);
627 if (readPriv == NULL((void*)0))
628 return status;
629
630 }
631 else {
632 /* Switching to no context. Ignore new drawable. */
633 glxc = 0;
634 drawPriv = 0;
635 readPriv = 0;
636 }
637
638 if (prevglxc) {
639 /*
640 ** Flush the previous context if needed.
641 */
642 Bool need_flush = GL_TRUE0x1;
643#ifdef GLX_CONTEXT_RELEASE_BEHAVIOR_ARB
644 if (prevglxc->releaseBehavior == GLX_CONTEXT_RELEASE_BEHAVIOR_NONE_ARB)
645 need_flush = GL_FALSE0x0;
646#endif
647 if (prevglxc->hasUnflushedCommands && need_flush) {
648 if (__glXForceCurrent(cl, tag, (int *) &error)) {
649 glFlush();
650 prevglxc->hasUnflushedCommands = GL_FALSE0x0;
651 }
652 else {
653 return error;
654 }
655 }
656
657 /*
658 ** Make the previous context not current.
659 */
660 if (!(*prevglxc->loseCurrent) (prevglxc)) {
661 return __glXError(GLXBadContext0);
662 }
663 lastGLContext = NULL((void*)0);
664 if (!prevglxc->isDirect) {
665 prevglxc->drawPriv = NULL((void*)0);
666 prevglxc->readPriv = NULL((void*)0);
667 }
668 }
669
670 if ((glxc != 0) && !glxc->isDirect) {
671
672 glxc->drawPriv = drawPriv;
673 glxc->readPriv = readPriv;
674
675 /* make the context current */
676 lastGLContext = glxc;
677 if (!(*glxc->makeCurrent) (glxc)) {
678 lastGLContext = NULL((void*)0);
679 glxc->drawPriv = NULL((void*)0);
680 glxc->readPriv = NULL((void*)0);
681 return __glXError(GLXBadContext0);
682 }
683
684 glxc->currentClient = client;
685 }
686
687 StopUsingContext(prevglxc);
688
689 reply = (xGLXMakeCurrentReply) {
690 .type = X_Reply1,
691 .sequenceNumber = client->sequence,
692 .length = 0,
693 .contextTag = 0
694 };
695
696 if (glxc) {
697 StartUsingContext(cl, glxc);
698 reply.contextTag = glxc->id;
699 }
700
701 if (client->swapped) {
702 __glXSwapMakeCurrentReply(client, &reply);
703 }
704 else {
705 WriteToClient(client, sz_xGLXMakeCurrentReply32, &reply);
706 }
707 return Success0;
708}
709
710int
711__glXDisp_MakeCurrent(__GLXclientState * cl, GLbyte * pc)
712{
713 ClientPtr client = cl->client;
714 xGLXMakeCurrentReq *req = (xGLXMakeCurrentReq *) pc;
715
716 REQUEST_SIZE_MATCH(xGLXMakeCurrentReq)if ((sizeof(xGLXMakeCurrentReq) >> 2) != client->req_len
) return(16)
;
717
718 return DoMakeCurrent(cl, req->drawable, req->drawable,
719 req->context, req->oldContextTag);
720}
721
722int
723__glXDisp_MakeContextCurrent(__GLXclientState * cl, GLbyte * pc)
724{
725 ClientPtr client = cl->client;
726 xGLXMakeContextCurrentReq *req = (xGLXMakeContextCurrentReq *) pc;
727
728 REQUEST_SIZE_MATCH(xGLXMakeContextCurrentReq)if ((sizeof(xGLXMakeContextCurrentReq) >> 2) != client->
req_len) return(16)
;
729
730 return DoMakeCurrent(cl, req->drawable, req->readdrawable,
731 req->context, req->oldContextTag);
732}
733
734int
735__glXDisp_MakeCurrentReadSGI(__GLXclientState * cl, GLbyte * pc)
736{
737 ClientPtr client = cl->client;
738 xGLXMakeCurrentReadSGIReq *req = (xGLXMakeCurrentReadSGIReq *) pc;
739
740 REQUEST_SIZE_MATCH(xGLXMakeCurrentReadSGIReq)if ((sizeof(xGLXMakeCurrentReadSGIReq) >> 2) != client->
req_len) return(16)
;
741
742 return DoMakeCurrent(cl, req->drawable, req->readable,
743 req->context, req->oldContextTag);
744}
745
746int
747__glXDisp_IsDirect(__GLXclientState * cl, GLbyte * pc)
748{
749 ClientPtr client = cl->client;
750 xGLXIsDirectReq *req = (xGLXIsDirectReq *) pc;
751 xGLXIsDirectReply reply;
752 __GLXcontext *glxc;
753 int err;
754
755 REQUEST_SIZE_MATCH(xGLXIsDirectReq)if ((sizeof(xGLXIsDirectReq) >> 2) != client->req_len
) return(16)
;
756
757 if (!validGlxContext(cl->client, req->context, DixReadAccess(1<<0), &glxc, &err))
758 return err;
759
760 reply = (xGLXIsDirectReply) {
761 .type = X_Reply1,
762 .sequenceNumber = client->sequence,
763 .length = 0,
764 .isDirect = glxc->isDirect
765 };
766
767 if (client->swapped) {
768 __glXSwapIsDirectReply(client, &reply);
769 }
770 else {
771 WriteToClient(client, sz_xGLXIsDirectReply32, &reply);
772 }
773
774 return Success0;
775}
776
777int
778__glXDisp_QueryVersion(__GLXclientState * cl, GLbyte * pc)
779{
780 ClientPtr client = cl->client;
781 xGLXQueryVersionReq *req = (xGLXQueryVersionReq *) pc;
782 xGLXQueryVersionReply reply;
783 GLuint major, minor;
784
785 REQUEST_SIZE_MATCH(xGLXQueryVersionReq)if ((sizeof(xGLXQueryVersionReq) >> 2) != client->req_len
) return(16)
;
786
787 major = req->majorVersion;
788 minor = req->minorVersion;
789 (void) major;
790 (void) minor;
791
792 /*
793 ** Server should take into consideration the version numbers sent by the
794 ** client if it wants to work with older clients; however, in this
795 ** implementation the server just returns its version number.
796 */
797 reply = (xGLXQueryVersionReply) {
798 .type = X_Reply1,
799 .sequenceNumber = client->sequence,
800 .length = 0,
801 .majorVersion = glxMajorVersion,
802 .minorVersion = glxMinorVersion
803 };
804
805 if (client->swapped) {
806 __glXSwapQueryVersionReply(client, &reply);
807 }
808 else {
809 WriteToClient(client, sz_xGLXQueryVersionReply32, &reply);
810 }
811 return Success0;
812}
813
814int
815__glXDisp_WaitGL(__GLXclientState * cl, GLbyte * pc)
816{
817 ClientPtr client = cl->client;
818 xGLXWaitGLReq *req = (xGLXWaitGLReq *) pc;
819 GLXContextTag tag;
820 __GLXcontext *glxc = NULL((void*)0);
821 int error;
822
823 REQUEST_SIZE_MATCH(xGLXWaitGLReq)if ((sizeof(xGLXWaitGLReq) >> 2) != client->req_len)
return(16)
;
824
825 tag = req->contextTag;
826 if (tag) {
827 glxc = __glXLookupContextByTag(cl, tag);
828 if (!glxc)
829 return __glXError(GLXBadContextTag4);
830
831 if (!__glXForceCurrent(cl, req->contextTag, &error))
832 return error;
833
834 glFinish();
835 }
836
837 if (glxc && glxc->drawPriv->waitGL)
838 (*glxc->drawPriv->waitGL) (glxc->drawPriv);
839
840 return Success0;
841}
842
843int
844__glXDisp_WaitX(__GLXclientState * cl, GLbyte * pc)
845{
846 ClientPtr client = cl->client;
847 xGLXWaitXReq *req = (xGLXWaitXReq *) pc;
848 GLXContextTag tag;
849 __GLXcontext *glxc = NULL((void*)0);
850 int error;
851
852 REQUEST_SIZE_MATCH(xGLXWaitXReq)if ((sizeof(xGLXWaitXReq) >> 2) != client->req_len) return
(16)
;
853
854 tag = req->contextTag;
855 if (tag) {
856 glxc = __glXLookupContextByTag(cl, tag);
857 if (!glxc)
858 return __glXError(GLXBadContextTag4);
859
860 if (!__glXForceCurrent(cl, req->contextTag, &error))
861 return error;
862 }
863
864 if (glxc && glxc->drawPriv->waitX)
865 (*glxc->drawPriv->waitX) (glxc->drawPriv);
866
867 return Success0;
868}
869
870int
871__glXDisp_CopyContext(__GLXclientState * cl, GLbyte * pc)
872{
873 ClientPtr client = cl->client;
874 xGLXCopyContextReq *req = (xGLXCopyContextReq *) pc;
875 GLXContextID source;
876 GLXContextID dest;
877 GLXContextTag tag;
878 unsigned long mask;
879 __GLXcontext *src, *dst;
880 int error;
881
882 REQUEST_SIZE_MATCH(xGLXCopyContextReq)if ((sizeof(xGLXCopyContextReq) >> 2) != client->req_len
) return(16)
;
883
884 source = req->source;
885 dest = req->dest;
886 tag = req->contextTag;
887 mask = req->mask;
888 if (!validGlxContext(cl->client, source, DixReadAccess(1<<0), &src, &error))
889 return error;
890 if (!validGlxContext(cl->client, dest, DixWriteAccess(1<<1), &dst, &error))
891 return error;
892
893 /*
894 ** They must be in the same address space, and same screen.
895 ** NOTE: no support for direct rendering contexts here.
896 */
897 if (src->isDirect || dst->isDirect || (src->pGlxScreen != dst->pGlxScreen)) {
898 client->errorValue = source;
899 return BadMatch8;
900 }
901
902 /*
903 ** The destination context must not be current for any client.
904 */
905 if (dst->currentClient) {
906 client->errorValue = dest;
907 return BadAccess10;
908 }
909
910 if (tag) {
911 __GLXcontext *tagcx = __glXLookupContextByTag(cl, tag);
912
913 if (!tagcx) {
914 return __glXError(GLXBadContextTag4);
915 }
916 if (tagcx != src) {
917 /*
918 ** This would be caused by a faulty implementation of the client
919 ** library.
920 */
921 return BadMatch8;
922 }
923 /*
924 ** In this case, glXCopyContext is in both GL and X streams, in terms
925 ** of sequentiality.
926 */
927 if (__glXForceCurrent(cl, tag, &error)) {
928 /*
929 ** Do whatever is needed to make sure that all preceding requests
930 ** in both streams are completed before the copy is executed.
931 */
932 glFinish();
933 tagcx->hasUnflushedCommands = GL_FALSE0x0;
934 }
935 else {
936 return error;
937 }
938 }
939 /*
940 ** Issue copy. The only reason for failure is a bad mask.
941 */
942 if (!(*dst->copy) (dst, src, mask)) {
943 client->errorValue = mask;
944 return BadValue2;
945 }
946 return Success0;
947}
948
949enum {
950 GLX_VIS_CONFIG_UNPAIRED = 18,
951 GLX_VIS_CONFIG_PAIRED = 22
952};
953
954enum {
955 GLX_VIS_CONFIG_TOTAL = GLX_VIS_CONFIG_UNPAIRED + GLX_VIS_CONFIG_PAIRED
956};
957
958int
959__glXDisp_GetVisualConfigs(__GLXclientState * cl, GLbyte * pc)
960{
961 xGLXGetVisualConfigsReq *req = (xGLXGetVisualConfigsReq *) pc;
962 ClientPtr client = cl->client;
963 xGLXGetVisualConfigsReply reply;
964 __GLXscreen *pGlxScreen;
965 __GLXconfig *modes;
966 CARD32 buf[GLX_VIS_CONFIG_TOTAL];
967 int p, i, err;
968
969 __GLX_DECLARE_SWAP_VARIABLESGLbyte sw;
970 __GLX_DECLARE_SWAP_ARRAY_VARIABLESGLbyte *swapPC; GLbyte *swapEnd;
971
972 REQUEST_SIZE_MATCH(xGLXGetVisualConfigsReq)if ((sizeof(xGLXGetVisualConfigsReq) >> 2) != client->
req_len) return(16)
;
973
974 if (!validGlxScreen(cl->client, req->screen, &pGlxScreen, &err))
975 return err;
976
977 reply = (xGLXGetVisualConfigsReply) {
978 .type = X_Reply1,
979 .sequenceNumber = client->sequence,
980 .length = (pGlxScreen->numVisuals *
981 __GLX_SIZE_CARD324 * GLX_VIS_CONFIG_TOTAL) >> 2,
982 .numVisuals = pGlxScreen->numVisuals,
983 .numProps = GLX_VIS_CONFIG_TOTAL
984 };
985
986 if (client->swapped) {
987 __GLX_SWAP_SHORT(&reply.sequenceNumber)sw = ((GLbyte *)(&reply.sequenceNumber))[0]; ((GLbyte *)(
&reply.sequenceNumber))[0] = ((GLbyte *)(&reply.sequenceNumber
))[1]; ((GLbyte *)(&reply.sequenceNumber))[1] = sw;
;
988 __GLX_SWAP_INT(&reply.length)sw = ((GLbyte *)(&reply.length))[0]; ((GLbyte *)(&reply
.length))[0] = ((GLbyte *)(&reply.length))[3]; ((GLbyte *
)(&reply.length))[3] = sw; sw = ((GLbyte *)(&reply.length
))[1]; ((GLbyte *)(&reply.length))[1] = ((GLbyte *)(&
reply.length))[2]; ((GLbyte *)(&reply.length))[2] = sw;
;
989 __GLX_SWAP_INT(&reply.numVisuals)sw = ((GLbyte *)(&reply.numVisuals))[0]; ((GLbyte *)(&
reply.numVisuals))[0] = ((GLbyte *)(&reply.numVisuals))[3
]; ((GLbyte *)(&reply.numVisuals))[3] = sw; sw = ((GLbyte
*)(&reply.numVisuals))[1]; ((GLbyte *)(&reply.numVisuals
))[1] = ((GLbyte *)(&reply.numVisuals))[2]; ((GLbyte *)(&
reply.numVisuals))[2] = sw;
;
990 __GLX_SWAP_INT(&reply.numProps)sw = ((GLbyte *)(&reply.numProps))[0]; ((GLbyte *)(&reply
.numProps))[0] = ((GLbyte *)(&reply.numProps))[3]; ((GLbyte
*)(&reply.numProps))[3] = sw; sw = ((GLbyte *)(&reply
.numProps))[1]; ((GLbyte *)(&reply.numProps))[1] = ((GLbyte
*)(&reply.numProps))[2]; ((GLbyte *)(&reply.numProps
))[2] = sw;
;
991 }
992
993 WriteToClient(client, sz_xGLXGetVisualConfigsReply32, &reply);
994
995 for (i = 0; i < pGlxScreen->numVisuals; i++) {
996 modes = pGlxScreen->visuals[i];
997
998 p = 0;
999 buf[p++] = modes->visualID;
1000 buf[p++] = glxConvertToXVisualType(modes->visualType);
1001 buf[p++] = (modes->renderType & GLX_RGBA_BIT0x00000001) ? GL_TRUE0x1 : GL_FALSE0x0;
1002
1003 buf[p++] = modes->redBits;
1004 buf[p++] = modes->greenBits;
1005 buf[p++] = modes->blueBits;
1006 buf[p++] = modes->alphaBits;
1007 buf[p++] = modes->accumRedBits;
1008 buf[p++] = modes->accumGreenBits;
1009 buf[p++] = modes->accumBlueBits;
1010 buf[p++] = modes->accumAlphaBits;
1011
1012 buf[p++] = modes->doubleBufferMode;
1013 buf[p++] = modes->stereoMode;
1014
1015 buf[p++] = modes->rgbBits;
1016 buf[p++] = modes->depthBits;
1017 buf[p++] = modes->stencilBits;
1018 buf[p++] = modes->numAuxBuffers;
1019 buf[p++] = modes->level;
1020
1021 assert(p == GLX_VIS_CONFIG_UNPAIRED)(__builtin_expect(!(p == GLX_VIS_CONFIG_UNPAIRED), 0) ? __assert_rtn
(__func__, "glxcmds.c", 1021, "p == GLX_VIS_CONFIG_UNPAIRED")
: (void)0)
;
1022 /*
1023 ** Add token/value pairs for extensions.
1024 */
1025 buf[p++] = GLX_VISUAL_CAVEAT_EXT0x20;
1026 buf[p++] = modes->visualRating;
1027 buf[p++] = GLX_TRANSPARENT_TYPE0x23;
1028 buf[p++] = modes->transparentPixel;
1029 buf[p++] = GLX_TRANSPARENT_RED_VALUE0x25;
1030 buf[p++] = modes->transparentRed;
1031 buf[p++] = GLX_TRANSPARENT_GREEN_VALUE0x26;
1032 buf[p++] = modes->transparentGreen;
1033 buf[p++] = GLX_TRANSPARENT_BLUE_VALUE0x27;
1034 buf[p++] = modes->transparentBlue;
1035 buf[p++] = GLX_TRANSPARENT_ALPHA_VALUE0x28;
1036 buf[p++] = modes->transparentAlpha;
1037 buf[p++] = GLX_TRANSPARENT_INDEX_VALUE0x24;
1038 buf[p++] = modes->transparentIndex;
1039 buf[p++] = GLX_SAMPLES_SGIS100001;
1040 buf[p++] = modes->samples;
1041 buf[p++] = GLX_SAMPLE_BUFFERS_SGIS100000;
1042 buf[p++] = modes->sampleBuffers;
1043 /* Add attribute only if its value is not default. */
1044 if (modes->sRGBCapable != GL_FALSE0x0) {
1045 buf[p++] = GLX_FRAMEBUFFER_SRGB_CAPABLE_EXT0x20B2;
1046 buf[p++] = modes->sRGBCapable;
1047 }
1048 /* Don't add visualSelectGroup (GLX_VISUAL_SELECT_GROUP_SGIX)?
1049 * Pad the remaining place with zeroes, so that attributes count is constant. */
1050 while (p < GLX_VIS_CONFIG_TOTAL) {
1051 buf[p++] = 0;
1052 buf[p++] = 0;
1053 }
1054
1055 assert(p == GLX_VIS_CONFIG_TOTAL)(__builtin_expect(!(p == GLX_VIS_CONFIG_TOTAL), 0) ? __assert_rtn
(__func__, "glxcmds.c", 1055, "p == GLX_VIS_CONFIG_TOTAL") : (
void)0)
;
1056 if (client->swapped) {
1057 __GLX_SWAP_INT_ARRAY(buf, p)swapPC = ((GLbyte *)(buf)); swapEnd = ((GLbyte *)(buf)) + (p)
*4; while (swapPC < swapEnd) { sw = ((GLbyte *)(swapPC))[0
]; ((GLbyte *)(swapPC))[0] = ((GLbyte *)(swapPC))[3]; ((GLbyte
*)(swapPC))[3] = sw; sw = ((GLbyte *)(swapPC))[1]; ((GLbyte *
)(swapPC))[1] = ((GLbyte *)(swapPC))[2]; ((GLbyte *)(swapPC))
[2] = sw;; swapPC += 4; }
;
1058 }
1059 WriteToClient(client, __GLX_SIZE_CARD324 * p, buf);
1060 }
1061 return Success0;
1062}
1063
1064#define __GLX_TOTAL_FBCONFIG_ATTRIBS(44) (44)
1065#define __GLX_FBCONFIG_ATTRIBS_LENGTH((44) * 2) (__GLX_TOTAL_FBCONFIG_ATTRIBS(44) * 2)
1066/**
1067 * Send the set of GLXFBConfigs to the client. There is not currently
1068 * and interface into the driver on the server-side to get GLXFBConfigs,
1069 * so we "invent" some based on the \c __GLXvisualConfig structures that
1070 * the driver does supply.
1071 *
1072 * The reply format for both \c glXGetFBConfigs and \c glXGetFBConfigsSGIX
1073 * is the same, so this routine pulls double duty.
1074 */
1075
1076static int
1077DoGetFBConfigs(__GLXclientState * cl, unsigned screen)
1078{
1079 ClientPtr client = cl->client;
1080 xGLXGetFBConfigsReply reply;
1081 __GLXscreen *pGlxScreen;
1082 CARD32 buf[__GLX_FBCONFIG_ATTRIBS_LENGTH((44) * 2)];
1083 int p, err;
1084 __GLXconfig *modes;
1085
1086 __GLX_DECLARE_SWAP_VARIABLESGLbyte sw;
1087 __GLX_DECLARE_SWAP_ARRAY_VARIABLESGLbyte *swapPC; GLbyte *swapEnd;
1088
1089 if (!validGlxScreen(cl->client, screen, &pGlxScreen, &err))
1
Taking false branch
1090 return err;
1091
1092 reply = (xGLXGetFBConfigsReply) {
1093 .type = X_Reply1,
1094 .sequenceNumber = client->sequence,
1095 .length = __GLX_FBCONFIG_ATTRIBS_LENGTH((44) * 2) * pGlxScreen->numFBConfigs,
1096 .numFBConfigs = pGlxScreen->numFBConfigs,
1097 .numAttribs = __GLX_TOTAL_FBCONFIG_ATTRIBS(44)
1098 };
1099
1100 if (client->swapped) {
2
Taking false branch
1101 __GLX_SWAP_SHORT(&reply.sequenceNumber)sw = ((GLbyte *)(&reply.sequenceNumber))[0]; ((GLbyte *)(
&reply.sequenceNumber))[0] = ((GLbyte *)(&reply.sequenceNumber
))[1]; ((GLbyte *)(&reply.sequenceNumber))[1] = sw;
;
1102 __GLX_SWAP_INT(&reply.length)sw = ((GLbyte *)(&reply.length))[0]; ((GLbyte *)(&reply
.length))[0] = ((GLbyte *)(&reply.length))[3]; ((GLbyte *
)(&reply.length))[3] = sw; sw = ((GLbyte *)(&reply.length
))[1]; ((GLbyte *)(&reply.length))[1] = ((GLbyte *)(&
reply.length))[2]; ((GLbyte *)(&reply.length))[2] = sw;
;
1103 __GLX_SWAP_INT(&reply.numFBConfigs)sw = ((GLbyte *)(&reply.numFBConfigs))[0]; ((GLbyte *)(&
reply.numFBConfigs))[0] = ((GLbyte *)(&reply.numFBConfigs
))[3]; ((GLbyte *)(&reply.numFBConfigs))[3] = sw; sw = ((
GLbyte *)(&reply.numFBConfigs))[1]; ((GLbyte *)(&reply
.numFBConfigs))[1] = ((GLbyte *)(&reply.numFBConfigs))[2]
; ((GLbyte *)(&reply.numFBConfigs))[2] = sw;
;
1104 __GLX_SWAP_INT(&reply.numAttribs)sw = ((GLbyte *)(&reply.numAttribs))[0]; ((GLbyte *)(&
reply.numAttribs))[0] = ((GLbyte *)(&reply.numAttribs))[3
]; ((GLbyte *)(&reply.numAttribs))[3] = sw; sw = ((GLbyte
*)(&reply.numAttribs))[1]; ((GLbyte *)(&reply.numAttribs
))[1] = ((GLbyte *)(&reply.numAttribs))[2]; ((GLbyte *)(&
reply.numAttribs))[2] = sw;
;
1105 }
1106
1107 WriteToClient(client, sz_xGLXGetFBConfigsReply32, &reply);
1108
1109 for (modes = pGlxScreen->fbconfigs; modes != NULL((void*)0); modes = modes->next) {
3
Assuming 'modes' is not equal to null
4
Loop condition is true. Entering loop body
1110 p = 0;
1111
1112#define WRITE_PAIR(tag,value)do { buf[p++] = tag ; buf[p++] = value ; } while( 0 ) \
1113 do { buf[p++] = tag ; buf[p++] = value ; } while( 0 )
1114
1115 WRITE_PAIR(GLX_VISUAL_ID, modes->visualID)do { buf[p++] = 0x800B ; buf[p++] = modes->visualID ; } while
( 0 )
;
1116 WRITE_PAIR(GLX_FBCONFIG_ID, modes->fbconfigID)do { buf[p++] = 0x8013 ; buf[p++] = modes->fbconfigID ; } while
( 0 )
;
1117 WRITE_PAIR(GLX_X_RENDERABLE, GL_TRUE)do { buf[p++] = 0x8012 ; buf[p++] = 0x1 ; } while( 0 );
1118
1119 WRITE_PAIR(GLX_RGBA,do { buf[p++] = 4 ; buf[p++] = (modes->renderType & 0x00000001
) ? 0x1 : 0x0 ; } while( 0 )
1120 (modes->renderType & GLX_RGBA_BIT) ? GL_TRUE : GL_FALSE)do { buf[p++] = 4 ; buf[p++] = (modes->renderType & 0x00000001
) ? 0x1 : 0x0 ; } while( 0 )
;
1121 WRITE_PAIR(GLX_RENDER_TYPE, modes->renderType)do { buf[p++] = 0x8011 ; buf[p++] = modes->renderType ; } while
( 0 )
;
1122 WRITE_PAIR(GLX_DOUBLEBUFFER, modes->doubleBufferMode)do { buf[p++] = 5 ; buf[p++] = modes->doubleBufferMode ; }
while( 0 )
;
1123 WRITE_PAIR(GLX_STEREO, modes->stereoMode)do { buf[p++] = 6 ; buf[p++] = modes->stereoMode ; } while
( 0 )
;
1124
1125 WRITE_PAIR(GLX_BUFFER_SIZE, modes->rgbBits)do { buf[p++] = 2 ; buf[p++] = modes->rgbBits ; } while( 0
)
;
1126 WRITE_PAIR(GLX_LEVEL, modes->level)do { buf[p++] = 3 ; buf[p++] = modes->level ; } while( 0 );
1127 WRITE_PAIR(GLX_AUX_BUFFERS, modes->numAuxBuffers)do { buf[p++] = 7 ; buf[p++] = modes->numAuxBuffers ; } while
( 0 )
;
1128 WRITE_PAIR(GLX_RED_SIZE, modes->redBits)do { buf[p++] = 8 ; buf[p++] = modes->redBits ; } while( 0
)
;
1129 WRITE_PAIR(GLX_GREEN_SIZE, modes->greenBits)do { buf[p++] = 9 ; buf[p++] = modes->greenBits ; } while(
0 )
;
1130 WRITE_PAIR(GLX_BLUE_SIZE, modes->blueBits)do { buf[p++] = 10 ; buf[p++] = modes->blueBits ; } while(
0 )
;
1131 WRITE_PAIR(GLX_ALPHA_SIZE, modes->alphaBits)do { buf[p++] = 11 ; buf[p++] = modes->alphaBits ; } while
( 0 )
;
1132 WRITE_PAIR(GLX_ACCUM_RED_SIZE, modes->accumRedBits)do { buf[p++] = 14 ; buf[p++] = modes->accumRedBits ; } while
( 0 )
;
1133 WRITE_PAIR(GLX_ACCUM_GREEN_SIZE, modes->accumGreenBits)do { buf[p++] = 15 ; buf[p++] = modes->accumGreenBits ; } while
( 0 )
;
1134 WRITE_PAIR(GLX_ACCUM_BLUE_SIZE, modes->accumBlueBits)do { buf[p++] = 16 ; buf[p++] = modes->accumBlueBits ; } while
( 0 )
;
1135 WRITE_PAIR(GLX_ACCUM_ALPHA_SIZE, modes->accumAlphaBits)do { buf[p++] = 17 ; buf[p++] = modes->accumAlphaBits ; } while
( 0 )
;
1136 WRITE_PAIR(GLX_DEPTH_SIZE, modes->depthBits)do { buf[p++] = 12 ; buf[p++] = modes->depthBits ; } while
( 0 )
;
1137 WRITE_PAIR(GLX_STENCIL_SIZE, modes->stencilBits)do { buf[p++] = 13 ; buf[p++] = modes->stencilBits ; } while
( 0 )
;
1138 WRITE_PAIR(GLX_X_VISUAL_TYPE, modes->visualType)do { buf[p++] = 0x22 ; buf[p++] = modes->visualType ; } while
( 0 )
;
1139 WRITE_PAIR(GLX_CONFIG_CAVEAT, modes->visualRating)do { buf[p++] = 0x20 ; buf[p++] = modes->visualRating ; } while
( 0 )
;
1140 WRITE_PAIR(GLX_TRANSPARENT_TYPE, modes->transparentPixel)do { buf[p++] = 0x23 ; buf[p++] = modes->transparentPixel ;
} while( 0 )
;
1141 WRITE_PAIR(GLX_TRANSPARENT_RED_VALUE, modes->transparentRed)do { buf[p++] = 0x25 ; buf[p++] = modes->transparentRed ; }
while( 0 )
;
1142 WRITE_PAIR(GLX_TRANSPARENT_GREEN_VALUE, modes->transparentGreen)do { buf[p++] = 0x26 ; buf[p++] = modes->transparentGreen ;
} while( 0 )
;
1143 WRITE_PAIR(GLX_TRANSPARENT_BLUE_VALUE, modes->transparentBlue)do { buf[p++] = 0x27 ; buf[p++] = modes->transparentBlue ;
} while( 0 )
;
1144 WRITE_PAIR(GLX_TRANSPARENT_ALPHA_VALUE, modes->transparentAlpha)do { buf[p++] = 0x28 ; buf[p++] = modes->transparentAlpha ;
} while( 0 )
;
1145 WRITE_PAIR(GLX_TRANSPARENT_INDEX_VALUE, modes->transparentIndex)do { buf[p++] = 0x24 ; buf[p++] = modes->transparentIndex ;
} while( 0 )
;
1146 WRITE_PAIR(GLX_SWAP_METHOD_OML, modes->swapMethod)do { buf[p++] = 0x8060 ; buf[p++] = modes->swapMethod ; } while
( 0 )
;
1147 WRITE_PAIR(GLX_SAMPLES_SGIS, modes->samples)do { buf[p++] = 100001 ; buf[p++] = modes->samples ; } while
( 0 )
;
1148 WRITE_PAIR(GLX_SAMPLE_BUFFERS_SGIS, modes->sampleBuffers)do { buf[p++] = 100000 ; buf[p++] = modes->sampleBuffers ;
} while( 0 )
;
1149 WRITE_PAIR(GLX_VISUAL_SELECT_GROUP_SGIX, modes->visualSelectGroup)do { buf[p++] = 0x8028 ; buf[p++] = modes->visualSelectGroup
; } while( 0 )
;
1150 WRITE_PAIR(GLX_DRAWABLE_TYPE, modes->drawableType)do { buf[p++] = 0x8010 ; buf[p++] = modes->drawableType ; }
while( 0 )
;
1151 WRITE_PAIR(GLX_BIND_TO_TEXTURE_RGB_EXT, modes->bindToTextureRgb)do { buf[p++] = 0x20D0 ; buf[p++] = modes->bindToTextureRgb
; } while( 0 )
;
1152 WRITE_PAIR(GLX_BIND_TO_TEXTURE_RGBA_EXT, modes->bindToTextureRgba)do { buf[p++] = 0x20D1 ; buf[p++] = modes->bindToTextureRgba
; } while( 0 )
;
1153 WRITE_PAIR(GLX_BIND_TO_MIPMAP_TEXTURE_EXT, modes->bindToMipmapTexture)do { buf[p++] = 0x20D2 ; buf[p++] = modes->bindToMipmapTexture
; } while( 0 )
;
1154 WRITE_PAIR(GLX_BIND_TO_TEXTURE_TARGETS_EXT,do { buf[p++] = 0x20D3 ; buf[p++] = modes->bindToTextureTargets
; } while( 0 )
1155 modes->bindToTextureTargets)do { buf[p++] = 0x20D3 ; buf[p++] = modes->bindToTextureTargets
; } while( 0 )
;
1156 /* can't report honestly until mesa is fixed */
1157 WRITE_PAIR(GLX_Y_INVERTED_EXT, GLX_DONT_CARE)do { buf[p++] = 0x20D4 ; buf[p++] = 0xFFFFFFFF ; } while( 0 );
1158 if (modes->drawableType & GLX_PBUFFER_BIT0x00000004) {
5
Taking true branch
1159 WRITE_PAIR(GLX_MAX_PBUFFER_WIDTH, modes->maxPbufferWidth)do { buf[p++] = 0x8016 ; buf[p++] = modes->maxPbufferWidth
; } while( 0 )
;
1160 WRITE_PAIR(GLX_MAX_PBUFFER_HEIGHT, modes->maxPbufferHeight)do { buf[p++] = 0x8017 ; buf[p++] = modes->maxPbufferHeight
; } while( 0 )
;
1161 WRITE_PAIR(GLX_MAX_PBUFFER_PIXELS, modes->maxPbufferPixels)do { buf[p++] = 0x8018 ; buf[p++] = modes->maxPbufferPixels
; } while( 0 )
;
1162 WRITE_PAIR(GLX_OPTIMAL_PBUFFER_WIDTH_SGIX,do { buf[p++] = 0x8019 ; buf[p++] = modes->optimalPbufferWidth
; } while( 0 )
1163 modes->optimalPbufferWidth)do { buf[p++] = 0x8019 ; buf[p++] = modes->optimalPbufferWidth
; } while( 0 )
;
1164 WRITE_PAIR(GLX_OPTIMAL_PBUFFER_HEIGHT_SGIX,do { buf[p++] = 0x801A ; buf[p++] = modes->optimalPbufferHeight
; } while( 0 )
1165 modes->optimalPbufferHeight)do { buf[p++] = 0x801A ; buf[p++] = modes->optimalPbufferHeight
; } while( 0 )
;
1166 }
1167 /* Add attribute only if its value is not default. */
1168 if (modes->sRGBCapable != GL_FALSE0x0) {
6
Taking true branch
1169 WRITE_PAIR(GLX_FRAMEBUFFER_SRGB_CAPABLE_EXT, modes->sRGBCapable)do { buf[p++] = 0x20B2 ; buf[p++] = modes->sRGBCapable ; }
while( 0 )
;
1170 }
1171 /* Pad the remaining place with zeroes, so that attributes count is constant. */
1172 while (p < __GLX_FBCONFIG_ATTRIBS_LENGTH((44) * 2)) {
7
Loop condition is false. Execution continues on line 1175
1173 WRITE_PAIR(0, 0)do { buf[p++] = 0 ; buf[p++] = 0 ; } while( 0 );
1174 }
1175 assert(p == __GLX_FBCONFIG_ATTRIBS_LENGTH)(__builtin_expect(!(p == ((44) * 2)), 0) ? __assert_rtn(__func__
, "glxcmds.c", 1175, "p == __GLX_FBCONFIG_ATTRIBS_LENGTH") : (
void)0)
;
1176
1177 if (client->swapped) {
8
Taking true branch
1178 __GLX_SWAP_INT_ARRAY(buf, __GLX_FBCONFIG_ATTRIBS_LENGTH)swapPC = ((GLbyte *)(buf)); swapEnd = ((GLbyte *)(buf)) + (((
44) * 2))*4; while (swapPC < swapEnd) { sw = ((GLbyte *)(swapPC
))[0]; ((GLbyte *)(swapPC))[0] = ((GLbyte *)(swapPC))[3]; ((GLbyte
*)(swapPC))[3] = sw; sw = ((GLbyte *)(swapPC))[1]; ((GLbyte *
)(swapPC))[1] = ((GLbyte *)(swapPC))[2]; ((GLbyte *)(swapPC))
[2] = sw;; swapPC += 4; }
;
9
Within the expansion of the macro '__GLX_SWAP_INT_ARRAY':
a
Assigned value is garbage or undefined
1179 }
1180 WriteToClient(client, __GLX_SIZE_CARD324 * __GLX_FBCONFIG_ATTRIBS_LENGTH((44) * 2),
1181 (char *) buf);
1182 }
1183 return Success0;
1184}
1185
1186int
1187__glXDisp_GetFBConfigs(__GLXclientState * cl, GLbyte * pc)
1188{
1189 ClientPtr client = cl->client;
1190 xGLXGetFBConfigsReq *req = (xGLXGetFBConfigsReq *) pc;
1191
1192 REQUEST_SIZE_MATCH(xGLXGetFBConfigsReq)if ((sizeof(xGLXGetFBConfigsReq) >> 2) != client->req_len
) return(16)
;
1193 return DoGetFBConfigs(cl, req->screen);
1194}
1195
1196int
1197__glXDisp_GetFBConfigsSGIX(__GLXclientState * cl, GLbyte * pc)
1198{
1199 ClientPtr client = cl->client;
1200 xGLXGetFBConfigsSGIXReq *req = (xGLXGetFBConfigsSGIXReq *) pc;
1201
1202 /* work around mesa bug, don't use REQUEST_SIZE_MATCH */
1203 REQUEST_AT_LEAST_SIZE(xGLXGetFBConfigsSGIXReq)if ((sizeof(xGLXGetFBConfigsSGIXReq) >> 2) > client->
req_len ) return(16)
;
1204 return DoGetFBConfigs(cl, req->screen);
1205}
1206
1207GLboolean
1208__glXDrawableInit(__GLXdrawable * drawable,
1209 __GLXscreen * screen, DrawablePtr pDraw, int type,
1210 XID drawId, __GLXconfig * config)
1211{
1212 drawable->pDraw = pDraw;
1213 drawable->type = type;
1214 drawable->drawId = drawId;
1215 drawable->config = config;
1216 drawable->eventMask = 0;
1217
1218 return GL_TRUE0x1;
1219}
1220
1221void
1222__glXDrawableRelease(__GLXdrawable * drawable)
1223{
1224}
1225
1226static int
1227DoCreateGLXDrawable(ClientPtr client, __GLXscreen * pGlxScreen,
1228 __GLXconfig * config, DrawablePtr pDraw, XID drawableId,
1229 XID glxDrawableId, int type)
1230{
1231 __GLXdrawable *pGlxDraw;
1232
1233 if (pGlxScreen->pScreen != pDraw->pScreen)
1234 return BadMatch8;
1235
1236 pGlxDraw = pGlxScreen->createDrawable(client, pGlxScreen, pDraw,
1237 drawableId, type,
1238 glxDrawableId, config);
1239 if (pGlxDraw == NULL((void*)0))
1240 return BadAlloc11;
1241
1242 if (!AddResourceDarwin_X_AddResource(glxDrawableId, __glXDrawableRes, pGlxDraw)) {
1243 pGlxDraw->destroy(pGlxDraw);
1244 return BadAlloc11;
1245 }
1246
1247 /*
1248 * Windows aren't refcounted, so track both the X and the GLX window
1249 * so we get called regardless of destruction order.
1250 */
1251 if (drawableId != glxDrawableId && type == GLX_DRAWABLE_WINDOW &&
1252 !AddResourceDarwin_X_AddResource(pDraw->id, __glXDrawableRes, pGlxDraw)) {
1253 pGlxDraw->destroy(pGlxDraw);
1254 return BadAlloc11;
1255 }
1256
1257 return Success0;
1258}
1259
1260static int
1261DoCreateGLXPixmap(ClientPtr client, __GLXscreen * pGlxScreen,
1262 __GLXconfig * config, XID drawableId, XID glxDrawableId)
1263{
1264 DrawablePtr pDraw;
1265 int err;
1266
1267 LEGAL_NEW_RESOURCE(glxDrawableId, client)if (!LegalNewID(glxDrawableId,client)) { client->errorValue
= glxDrawableId; return 14; }
;
1268
1269 err = dixLookupDrawable(&pDraw, drawableId, client, 0, DixAddAccess(1<<12));
1270 if (err != Success0) {
1271 client->errorValue = drawableId;
1272 return err;
1273 }
1274 if (pDraw->type != DRAWABLE_PIXMAP1) {
1275 client->errorValue = drawableId;
1276 return BadPixmap4;
1277 }
1278
1279 err = DoCreateGLXDrawable(client, pGlxScreen, config, pDraw, drawableId,
1280 glxDrawableId, GLX_DRAWABLE_PIXMAP);
1281
1282 if (err == Success0)
1283 ((PixmapPtr) pDraw)->refcnt++;
1284
1285 return err;
1286}
1287
1288static void
1289determineTextureTarget(ClientPtr client, XID glxDrawableID,
1290 CARD32 *attribs, CARD32 numAttribs)
1291{
1292 GLenum target = 0;
1293 GLenum format = 0;
1294 int i, err;
1295 __GLXdrawable *pGlxDraw;
1296
1297 if (!validGlxDrawable(client, glxDrawableID, GLX_DRAWABLE_PIXMAP,
1298 DixWriteAccess(1<<1), &pGlxDraw, &err))
1299 /* We just added it in CreatePixmap, so we should never get here. */
1300 return;
1301
1302 for (i = 0; i < numAttribs; i++) {
1303 if (attribs[2 * i] == GLX_TEXTURE_TARGET_EXT0x20D6) {
1304 switch (attribs[2 * i + 1]) {
1305 case GLX_TEXTURE_2D_EXT0x20DC:
1306 target = GL_TEXTURE_2D0x0DE1;
1307 break;
1308 case GLX_TEXTURE_RECTANGLE_EXT0x20DD:
1309 target = GL_TEXTURE_RECTANGLE_ARB0x84F5;
1310 break;
1311 }
1312 }
1313
1314 if (attribs[2 * i] == GLX_TEXTURE_FORMAT_EXT0x20D5)
1315 format = attribs[2 * i + 1];
1316 }
1317
1318 if (!target) {
1319 int w = pGlxDraw->pDraw->width, h = pGlxDraw->pDraw->height;
1320
1321 if (h & (h - 1) || w & (w - 1))
1322 target = GL_TEXTURE_RECTANGLE_ARB0x84F5;
1323 else
1324 target = GL_TEXTURE_2D0x0DE1;
1325 }
1326
1327 pGlxDraw->target = target;
1328 pGlxDraw->format = format;
1329}
1330
1331int
1332__glXDisp_CreateGLXPixmap(__GLXclientState * cl, GLbyte * pc)
1333{
1334 ClientPtr client = cl->client;
1335 xGLXCreateGLXPixmapReq *req = (xGLXCreateGLXPixmapReq *) pc;
1336 __GLXconfig *config;
1337 __GLXscreen *pGlxScreen;
1338 int err;
1339
1340 REQUEST_SIZE_MATCH(xGLXCreateGLXPixmapReq)if ((sizeof(xGLXCreateGLXPixmapReq) >> 2) != client->
req_len) return(16)
;
1341
1342 if (!validGlxScreen(cl->client, req->screen, &pGlxScreen, &err))
1343 return err;
1344 if (!validGlxVisual(cl->client, pGlxScreen, req->visual, &config, &err))
1345 return err;
1346
1347 return DoCreateGLXPixmap(cl->client, pGlxScreen, config,
1348 req->pixmap, req->glxpixmap);
1349}
1350
1351int
1352__glXDisp_CreatePixmap(__GLXclientState * cl, GLbyte * pc)
1353{
1354 ClientPtr client = cl->client;
1355 xGLXCreatePixmapReq *req = (xGLXCreatePixmapReq *) pc;
1356 __GLXconfig *config;
1357 __GLXscreen *pGlxScreen;
1358 int err;
1359
1360 REQUEST_AT_LEAST_SIZE(xGLXCreatePixmapReq)if ((sizeof(xGLXCreatePixmapReq) >> 2) > client->
req_len ) return(16)
;
1361 if (req->numAttribs > (UINT32_MAX4294967295U >> 3)) {
1362 client->errorValue = req->numAttribs;
1363 return BadValue2;
1364 }
1365 REQUEST_FIXED_SIZE(xGLXCreatePixmapReq, req->numAttribs << 3)if (((sizeof(xGLXCreatePixmapReq) >> 2) > client->
req_len) || (((req->numAttribs << 3) >> 2) >=
client->req_len) || ((((uint64_t) sizeof(xGLXCreatePixmapReq
) + (req->numAttribs << 3) + 3) >> 2) != (uint64_t
) client->req_len)) return(16)
;
1366
1367 if (!validGlxScreen(cl->client, req->screen, &pGlxScreen, &err))
1368 return err;
1369 if (!validGlxFBConfig(cl->client, pGlxScreen, req->fbconfig, &config, &err))
1370 return err;
1371
1372 err = DoCreateGLXPixmap(cl->client, pGlxScreen, config,
1373 req->pixmap, req->glxpixmap);
1374 if (err != Success0)
1375 return err;
1376
1377 determineTextureTarget(cl->client, req->glxpixmap,
1378 (CARD32 *) (req + 1), req->numAttribs);
1379
1380 return Success0;
1381}
1382
1383int
1384__glXDisp_CreateGLXPixmapWithConfigSGIX(__GLXclientState * cl, GLbyte * pc)
1385{
1386 ClientPtr client = cl->client;
1387 xGLXCreateGLXPixmapWithConfigSGIXReq *req =
1388 (xGLXCreateGLXPixmapWithConfigSGIXReq *) pc;
1389 __GLXconfig *config;
1390 __GLXscreen *pGlxScreen;
1391 int err;
1392
1393 REQUEST_SIZE_MATCH(xGLXCreateGLXPixmapWithConfigSGIXReq)if ((sizeof(xGLXCreateGLXPixmapWithConfigSGIXReq) >> 2)
!= client->req_len) return(16)
;
1394
1395 if (!validGlxScreen(cl->client, req->screen, &pGlxScreen, &err))
1396 return err;
1397 if (!validGlxFBConfig(cl->client, pGlxScreen, req->fbconfig, &config, &err))
1398 return err;
1399
1400 return DoCreateGLXPixmap(cl->client, pGlxScreen,
1401 config, req->pixmap, req->glxpixmap);
1402}
1403
1404static int
1405DoDestroyDrawable(__GLXclientState * cl, XID glxdrawable, int type)
1406{
1407 __GLXdrawable *pGlxDraw;
1408 int err;
1409
1410 if (!validGlxDrawable(cl->client, glxdrawable, type,
1411 DixDestroyAccess(1<<2), &pGlxDraw, &err))
1412 return err;
1413
1414 FreeResource(glxdrawable, FALSE0);
1415
1416 return Success0;
1417}
1418
1419int
1420__glXDisp_DestroyGLXPixmap(__GLXclientState * cl, GLbyte * pc)
1421{
1422 ClientPtr client = cl->client;
1423 xGLXDestroyGLXPixmapReq *req = (xGLXDestroyGLXPixmapReq *) pc;
1424
1425 REQUEST_SIZE_MATCH(xGLXDestroyGLXPixmapReq)if ((sizeof(xGLXDestroyGLXPixmapReq) >> 2) != client->
req_len) return(16)
;
1426
1427 return DoDestroyDrawable(cl, req->glxpixmap, GLX_DRAWABLE_PIXMAP);
1428}
1429
1430int
1431__glXDisp_DestroyPixmap(__GLXclientState * cl, GLbyte * pc)
1432{
1433 ClientPtr client = cl->client;
1434 xGLXDestroyPixmapReq *req = (xGLXDestroyPixmapReq *) pc;
1435
1436 /* should be REQUEST_SIZE_MATCH, but mesa's glXDestroyPixmap used to set
1437 * length to 3 instead of 2 */
1438 REQUEST_AT_LEAST_SIZE(xGLXDestroyPixmapReq)if ((sizeof(xGLXDestroyPixmapReq) >> 2) > client->
req_len ) return(16)
;
1439
1440 return DoDestroyDrawable(cl, req->glxpixmap, GLX_DRAWABLE_PIXMAP);
1441}
1442
1443static int
1444DoCreatePbuffer(ClientPtr client, int screenNum, XID fbconfigId,
1445 int width, int height, XID glxDrawableId)
1446{
1447 __GLXconfig *config;
1448 __GLXscreen *pGlxScreen;
1449 PixmapPtr pPixmap;
1450 int err;
1451
1452 LEGAL_NEW_RESOURCE(glxDrawableId, client)if (!LegalNewID(glxDrawableId,client)) { client->errorValue
= glxDrawableId; return 14; }
;
1453
1454 if (!validGlxScreen(client, screenNum, &pGlxScreen, &err))
1455 return err;
1456 if (!validGlxFBConfig(client, pGlxScreen, fbconfigId, &config, &err))
1457 return err;
1458
1459 __glXenterServer(GL_FALSE0x0);
1460 pPixmap = (*pGlxScreen->pScreen->CreatePixmap) (pGlxScreen->pScreen,
1461 width, height,
1462 config->rgbBits, 0);
1463 __glXleaveServer(GL_FALSE0x0);
1464 if (!pPixmap)
1465 return BadAlloc11;
1466
1467 /* Assign the pixmap the same id as the pbuffer and add it as a
1468 * resource so it and the DRI2 drawable will be reclaimed when the
1469 * pbuffer is destroyed. */
1470 pPixmap->drawable.id = glxDrawableId;
1471 if (!AddResourceDarwin_X_AddResource(pPixmap->drawable.id, RT_PIXMAP((RESTYPE)2|((RESTYPE)1<<30)), pPixmap))
1472 return BadAlloc11;
1473
1474 return DoCreateGLXDrawable(client, pGlxScreen, config, &pPixmap->drawable,
1475 glxDrawableId, glxDrawableId,
1476 GLX_DRAWABLE_PBUFFER);
1477}
1478
1479int
1480__glXDisp_CreatePbuffer(__GLXclientState * cl, GLbyte * pc)
1481{
1482 ClientPtr client = cl->client;
1483 xGLXCreatePbufferReq *req = (xGLXCreatePbufferReq *) pc;
1484 CARD32 *attrs;
1485 int width, height, i;
1486
1487 REQUEST_AT_LEAST_SIZE(xGLXCreatePbufferReq)if ((sizeof(xGLXCreatePbufferReq) >> 2) > client->
req_len ) return(16)
;
1488 if (req->numAttribs > (UINT32_MAX4294967295U >> 3)) {
1489 client->errorValue = req->numAttribs;
1490 return BadValue2;
1491 }
1492 REQUEST_FIXED_SIZE(xGLXCreatePbufferReq, req->numAttribs << 3)if (((sizeof(xGLXCreatePbufferReq) >> 2) > client->
req_len) || (((req->numAttribs << 3) >> 2) >=
client->req_len) || ((((uint64_t) sizeof(xGLXCreatePbufferReq
) + (req->numAttribs << 3) + 3) >> 2) != (uint64_t
) client->req_len)) return(16)
;
1493
1494 attrs = (CARD32 *) (req + 1);
1495 width = 0;
1496 height = 0;
1497
1498 for (i = 0; i < req->numAttribs; i++) {
1499 switch (attrs[i * 2]) {
1500 case GLX_PBUFFER_WIDTH0x8041:
1501 width = attrs[i * 2 + 1];
1502 break;
1503 case GLX_PBUFFER_HEIGHT0x8040:
1504 height = attrs[i * 2 + 1];
1505 break;
1506 case GLX_LARGEST_PBUFFER0x801C:
1507 /* FIXME: huh... */
1508 break;
1509 }
1510 }
1511
1512 return DoCreatePbuffer(cl->client, req->screen, req->fbconfig,
1513 width, height, req->pbuffer);
1514}
1515
1516int
1517__glXDisp_CreateGLXPbufferSGIX(__GLXclientState * cl, GLbyte * pc)
1518{
1519 ClientPtr client = cl->client;
1520 xGLXCreateGLXPbufferSGIXReq *req = (xGLXCreateGLXPbufferSGIXReq *) pc;
1521
1522 REQUEST_AT_LEAST_SIZE(xGLXCreateGLXPbufferSGIXReq)if ((sizeof(xGLXCreateGLXPbufferSGIXReq) >> 2) > client
->req_len ) return(16)
;
1523
1524 /*
1525 * We should really handle attributes correctly, but this extension
1526 * is so rare I have difficulty caring.
1527 */
1528 return DoCreatePbuffer(cl->client, req->screen, req->fbconfig,
1529 req->width, req->height, req->pbuffer);
1530}
1531
1532int
1533__glXDisp_DestroyPbuffer(__GLXclientState * cl, GLbyte * pc)
1534{
1535 ClientPtr client = cl->client;
1536 xGLXDestroyPbufferReq *req = (xGLXDestroyPbufferReq *) pc;
1537
1538 REQUEST_SIZE_MATCH(xGLXDestroyPbufferReq)if ((sizeof(xGLXDestroyPbufferReq) >> 2) != client->
req_len) return(16)
;
1539
1540 return DoDestroyDrawable(cl, req->pbuffer, GLX_DRAWABLE_PBUFFER);
1541}
1542
1543int
1544__glXDisp_DestroyGLXPbufferSGIX(__GLXclientState * cl, GLbyte * pc)
1545{
1546 ClientPtr client = cl->client;
1547 xGLXDestroyGLXPbufferSGIXReq *req = (xGLXDestroyGLXPbufferSGIXReq *) pc;
1548
1549 REQUEST_SIZE_MATCH(xGLXDestroyGLXPbufferSGIXReq)if ((sizeof(xGLXDestroyGLXPbufferSGIXReq) >> 2) != client
->req_len) return(16)
;
1550
1551 return DoDestroyDrawable(cl, req->pbuffer, GLX_DRAWABLE_PBUFFER);
1552}
1553
1554static int
1555DoChangeDrawableAttributes(ClientPtr client, XID glxdrawable,
1556 int numAttribs, CARD32 *attribs)
1557{
1558 __GLXdrawable *pGlxDraw;
1559 int i, err;
1560
1561 if (!validGlxDrawable(client, glxdrawable, GLX_DRAWABLE_ANY,
1562 DixSetAttrAccess(1<<5), &pGlxDraw, &err))
1563 return err;
1564
1565 for (i = 0; i < numAttribs; i++) {
1566 switch (attribs[i * 2]) {
1567 case GLX_EVENT_MASK0x801F:
1568 /* All we do is to record the event mask so we can send it
1569 * back when queried. We never actually clobber the
1570 * pbuffers, so we never need to send out the event. */
1571 pGlxDraw->eventMask = attribs[i * 2 + 1];
1572 break;
1573 }
1574 }
1575
1576 return Success0;
1577}
1578
1579int
1580__glXDisp_ChangeDrawableAttributes(__GLXclientState * cl, GLbyte * pc)
1581{
1582 ClientPtr client = cl->client;
1583 xGLXChangeDrawableAttributesReq *req =
1584 (xGLXChangeDrawableAttributesReq *) pc;
1585
1586 REQUEST_AT_LEAST_SIZE(xGLXChangeDrawableAttributesReq)if ((sizeof(xGLXChangeDrawableAttributesReq) >> 2) >
client->req_len ) return(16)
;
1587 if (req->numAttribs > (UINT32_MAX4294967295U >> 3)) {
1588 client->errorValue = req->numAttribs;
1589 return BadValue2;
1590 }
1591#if 0
1592 /* mesa sends an additional 8 bytes */
1593 REQUEST_FIXED_SIZE(xGLXChangeDrawableAttributesReq, req->numAttribs << 3)if (((sizeof(xGLXChangeDrawableAttributesReq) >> 2) >
client->req_len) || (((req->numAttribs << 3) >>
2) >= client->req_len) || ((((uint64_t) sizeof(xGLXChangeDrawableAttributesReq
) + (req->numAttribs << 3) + 3) >> 2) != (uint64_t
) client->req_len)) return(16)
;
1594#else
1595 if (((sizeof(xGLXChangeDrawableAttributesReq) +
1596 (req->numAttribs << 3)) >> 2) < client->req_len)
1597 return BadLength16;
1598#endif
1599
1600 return DoChangeDrawableAttributes(cl->client, req->drawable,
1601 req->numAttribs, (CARD32 *) (req + 1));
1602}
1603
1604int
1605__glXDisp_ChangeDrawableAttributesSGIX(__GLXclientState * cl, GLbyte * pc)
1606{
1607 ClientPtr client = cl->client;
1608 xGLXChangeDrawableAttributesSGIXReq *req =
1609 (xGLXChangeDrawableAttributesSGIXReq *) pc;
1610
1611 REQUEST_AT_LEAST_SIZE(xGLXChangeDrawableAttributesSGIXReq)if ((sizeof(xGLXChangeDrawableAttributesSGIXReq) >> 2) >
client->req_len ) return(16)
;
1612 if (req->numAttribs > (UINT32_MAX4294967295U >> 3)) {
1613 client->errorValue = req->numAttribs;
1614 return BadValue2;
1615 }
1616 REQUEST_FIXED_SIZE(xGLXChangeDrawableAttributesSGIXReq,if (((sizeof(xGLXChangeDrawableAttributesSGIXReq) >> 2)
> client->req_len) || (((req->numAttribs << 3
) >> 2) >= client->req_len) || ((((uint64_t) sizeof
(xGLXChangeDrawableAttributesSGIXReq) + (req->numAttribs <<
3) + 3) >> 2) != (uint64_t) client->req_len)) return
(16)
1617 req->numAttribs << 3)if (((sizeof(xGLXChangeDrawableAttributesSGIXReq) >> 2)
> client->req_len) || (((req->numAttribs << 3
) >> 2) >= client->req_len) || ((((uint64_t) sizeof
(xGLXChangeDrawableAttributesSGIXReq) + (req->numAttribs <<
3) + 3) >> 2) != (uint64_t) client->req_len)) return
(16)
;
1618
1619 return DoChangeDrawableAttributes(cl->client, req->drawable,
1620 req->numAttribs, (CARD32 *) (req + 1));
1621}
1622
1623int
1624__glXDisp_CreateWindow(__GLXclientState * cl, GLbyte * pc)
1625{
1626 xGLXCreateWindowReq *req = (xGLXCreateWindowReq *) pc;
1627 __GLXconfig *config;
1628 __GLXscreen *pGlxScreen;
1629 ClientPtr client = cl->client;
1630 DrawablePtr pDraw;
1631 int err;
1632
1633 REQUEST_AT_LEAST_SIZE(xGLXCreateWindowReq)if ((sizeof(xGLXCreateWindowReq) >> 2) > client->
req_len ) return(16)
;
1634 if (req->numAttribs > (UINT32_MAX4294967295U >> 3)) {
1635 client->errorValue = req->numAttribs;
1636 return BadValue2;
1637 }
1638 REQUEST_FIXED_SIZE(xGLXCreateWindowReq, req->numAttribs << 3)if (((sizeof(xGLXCreateWindowReq) >> 2) > client->
req_len) || (((req->numAttribs << 3) >> 2) >=
client->req_len) || ((((uint64_t) sizeof(xGLXCreateWindowReq
) + (req->numAttribs << 3) + 3) >> 2) != (uint64_t
) client->req_len)) return(16)
;
1639
1640 LEGAL_NEW_RESOURCE(req->glxwindow, client)if (!LegalNewID(req->glxwindow,client)) { client->errorValue
= req->glxwindow; return 14; }
;
1641
1642 if (!validGlxScreen(client, req->screen, &pGlxScreen, &err))
1643 return err;
1644 if (!validGlxFBConfig(client, pGlxScreen, req->fbconfig, &config, &err))
1645 return err;
1646
1647 err = dixLookupDrawable(&pDraw, req->window, client, 0, DixAddAccess(1<<12));
1648 if (err != Success0 || pDraw->type != DRAWABLE_WINDOW0) {
1649 client->errorValue = req->window;
1650 return BadWindow3;
1651 }
1652
1653 if (!validGlxFBConfigForWindow(client, config, pDraw, &err))
1654 return err;
1655
1656 return DoCreateGLXDrawable(client, pGlxScreen, config,
1657 pDraw, req->window,
1658 req->glxwindow, GLX_DRAWABLE_WINDOW);
1659}
1660
1661int
1662__glXDisp_DestroyWindow(__GLXclientState * cl, GLbyte * pc)
1663{
1664 ClientPtr client = cl->client;
1665 xGLXDestroyWindowReq *req = (xGLXDestroyWindowReq *) pc;
1666
1667 /* mesa's glXDestroyWindow used to set length to 3 instead of 2 */
1668 REQUEST_AT_LEAST_SIZE(xGLXDestroyWindowReq)if ((sizeof(xGLXDestroyWindowReq) >> 2) > client->
req_len ) return(16)
;
1669
1670 return DoDestroyDrawable(cl, req->glxwindow, GLX_DRAWABLE_WINDOW);
1671}
1672
1673/*****************************************************************************/
1674
1675/*
1676** NOTE: There is no portable implementation for swap buffers as of
1677** this time that is of value. Consequently, this code must be
1678** implemented by somebody other than SGI.
1679*/
1680int
1681__glXDisp_SwapBuffers(__GLXclientState * cl, GLbyte * pc)
1682{
1683 ClientPtr client = cl->client;
1684 xGLXSwapBuffersReq *req = (xGLXSwapBuffersReq *) pc;
1685 GLXContextTag tag;
1686 XID drawId;
1687 __GLXcontext *glxc = NULL((void*)0);
1688 __GLXdrawable *pGlxDraw;
1689 int error;
1690
1691 REQUEST_SIZE_MATCH(xGLXSwapBuffersReq)if ((sizeof(xGLXSwapBuffersReq) >> 2) != client->req_len
) return(16)
;
1692
1693 tag = req->contextTag;
1694 drawId = req->drawable;
1695 if (tag) {
1696 glxc = __glXLookupContextByTag(cl, tag);
1697 if (!glxc) {
1698 return __glXError(GLXBadContextTag4);
1699 }
1700 /*
1701 ** The calling thread is swapping its current drawable. In this case,
1702 ** glxSwapBuffers is in both GL and X streams, in terms of
1703 ** sequentiality.
1704 */
1705 if (__glXForceCurrent(cl, tag, &error)) {
1706 /*
1707 ** Do whatever is needed to make sure that all preceding requests
1708 ** in both streams are completed before the swap is executed.
1709 */
1710 glFinish();
1711 glxc->hasUnflushedCommands = GL_FALSE0x0;
1712 }
1713 else {
1714 return error;
1715 }
1716 }
1717
1718 pGlxDraw = __glXGetDrawable(glxc, drawId, client, &error);
1719 if (pGlxDraw == NULL((void*)0))
1720 return error;
1721
1722 if (pGlxDraw->type == DRAWABLE_WINDOW0 &&
1723 (*pGlxDraw->swapBuffers) (cl->client, pGlxDraw) == GL_FALSE0x0)
1724 return __glXError(GLXBadDrawable2);
1725
1726 return Success0;
1727}
1728
1729static int
1730DoQueryContext(__GLXclientState * cl, GLXContextID gcId)
1731{
1732 ClientPtr client = cl->client;
1733 __GLXcontext *ctx;
1734 xGLXQueryContextInfoEXTReply reply;
1735 int nProps = 3;
1736 int sendBuf[nProps * 2];
1737 int nReplyBytes;
1738 int err;
1739
1740 if (!validGlxContext(cl->client, gcId, DixReadAccess(1<<0), &ctx, &err))
1741 return err;
1742
1743 reply = (xGLXQueryContextInfoEXTReply) {
1744 .type = X_Reply1,
1745 .sequenceNumber = client->sequence,
1746 .length = nProps << 1,
1747 .n = nProps
1748 };
1749
1750 nReplyBytes = reply.length << 2;
1751 sendBuf[0] = GLX_SHARE_CONTEXT_EXT0x800A;
1752 sendBuf[1] = (int) (ctx->share_id);
1753 sendBuf[2] = GLX_VISUAL_ID_EXT0x800B;
1754 sendBuf[3] = (int) (ctx->config->visualID);
1755 sendBuf[4] = GLX_SCREEN_EXT0x800C;
1756 sendBuf[5] = (int) (ctx->pGlxScreen->pScreen->myNum);
1757
1758 if (client->swapped) {
1759 __glXSwapQueryContextInfoEXTReply(client, &reply, sendBuf);
1760 }
1761 else {
1762 WriteToClient(client, sz_xGLXQueryContextInfoEXTReply32, &reply);
1763 WriteToClient(client, nReplyBytes, sendBuf);
1764 }
1765
1766 return Success0;
1767}
1768
1769int
1770__glXDisp_QueryContextInfoEXT(__GLXclientState * cl, GLbyte * pc)
1771{
1772 ClientPtr client = cl->client;
1773 xGLXQueryContextInfoEXTReq *req = (xGLXQueryContextInfoEXTReq *) pc;
1774
1775 REQUEST_SIZE_MATCH(xGLXQueryContextInfoEXTReq)if ((sizeof(xGLXQueryContextInfoEXTReq) >> 2) != client
->req_len) return(16)
;
1776
1777 return DoQueryContext(cl, req->context);
1778}
1779
1780int
1781__glXDisp_QueryContext(__GLXclientState * cl, GLbyte * pc)
1782{
1783 ClientPtr client = cl->client;
1784 xGLXQueryContextReq *req = (xGLXQueryContextReq *) pc;
1785
1786 REQUEST_SIZE_MATCH(xGLXQueryContextReq)if ((sizeof(xGLXQueryContextReq) >> 2) != client->req_len
) return(16)
;
1787
1788 return DoQueryContext(cl, req->context);
1789}
1790
1791int
1792__glXDisp_BindTexImageEXT(__GLXclientState * cl, GLbyte * pc)
1793{
1794 xGLXVendorPrivateReq *req = (xGLXVendorPrivateReq *) pc;
1795 ClientPtr client = cl->client;
1796 __GLXcontext *context;
1797 __GLXdrawable *pGlxDraw;
1798 GLXDrawable drawId;
1799 int buffer;
1800 int error;
1801 CARD32 num_attribs;
1802
1803 if ((sizeof(xGLXVendorPrivateReq) + 12) >> 2 > client->req_len)
1804 return BadLength16;
1805
1806 pc += __GLX_VENDPRIV_HDR_SIZE12;
1807
1808 drawId = *((CARD32 *) (pc));
1809 buffer = *((INT32 *) (pc + 4));
1810 num_attribs = *((CARD32 *) (pc + 8));
1811 if (num_attribs > (UINT32_MAX4294967295U >> 3)) {
1812 client->errorValue = num_attribs;
1813 return BadValue2;
1814 }
1815 REQUEST_FIXED_SIZE(xGLXVendorPrivateReq, 12 + (num_attribs << 3))if (((sizeof(xGLXVendorPrivateReq) >> 2) > client->
req_len) || (((12 + (num_attribs << 3)) >> 2) >=
client->req_len) || ((((uint64_t) sizeof(xGLXVendorPrivateReq
) + (12 + (num_attribs << 3)) + 3) >> 2) != (uint64_t
) client->req_len)) return(16)
;
1816
1817 if (buffer != GLX_FRONT_LEFT_EXT0x20DE)
1818 return __glXError(GLXBadPixmap3);
1819
1820 context = __glXForceCurrent(cl, req->contextTag, &error);
1821 if (!context)
1822 return error;
1823
1824 if (!validGlxDrawable(client, drawId, GLX_DRAWABLE_PIXMAP,
1825 DixReadAccess(1<<0), &pGlxDraw, &error))
1826 return error;
1827
1828 if (!context->textureFromPixmap)
1829 return __glXError(GLXUnsupportedPrivateRequest8);
1830
1831 return context->textureFromPixmap->bindTexImage(context, buffer, pGlxDraw);
1832}
1833
1834int
1835__glXDisp_ReleaseTexImageEXT(__GLXclientState * cl, GLbyte * pc)
1836{
1837 xGLXVendorPrivateReq *req = (xGLXVendorPrivateReq *) pc;
1838 ClientPtr client = cl->client;
1839 __GLXdrawable *pGlxDraw;
1840 __GLXcontext *context;
1841 GLXDrawable drawId;
1842 int buffer;
1843 int error;
1844
1845 REQUEST_FIXED_SIZE(xGLXVendorPrivateReq, 8)if (((sizeof(xGLXVendorPrivateReq) >> 2) > client->
req_len) || (((8) >> 2) >= client->req_len) || ((
((uint64_t) sizeof(xGLXVendorPrivateReq) + (8) + 3) >> 2
) != (uint64_t) client->req_len)) return(16)
;
1846
1847 pc += __GLX_VENDPRIV_HDR_SIZE12;
1848
1849 drawId = *((CARD32 *) (pc));
1850 buffer = *((INT32 *) (pc + 4));
1851
1852 context = __glXForceCurrent(cl, req->contextTag, &error);
1853 if (!context)
1854 return error;
1855
1856 if (!validGlxDrawable(client, drawId, GLX_DRAWABLE_PIXMAP,
1857 DixReadAccess(1<<0), &pGlxDraw, &error))
1858 return error;
1859
1860 if (!context->textureFromPixmap)
1861 return __glXError(GLXUnsupportedPrivateRequest8);
1862
1863 return context->textureFromPixmap->releaseTexImage(context,
1864 buffer, pGlxDraw);
1865}
1866
1867int
1868__glXDisp_CopySubBufferMESA(__GLXclientState * cl, GLbyte * pc)
1869{
1870 xGLXVendorPrivateReq *req = (xGLXVendorPrivateReq *) pc;
1871 GLXContextTag tag = req->contextTag;
1872 __GLXcontext *glxc = NULL((void*)0);
1873 __GLXdrawable *pGlxDraw;
1874 ClientPtr client = cl->client;
1875 GLXDrawable drawId;
1876 int error;
1877 int x, y, width, height;
1878
1879 (void) client;
1880 (void) req;
1881
1882 REQUEST_FIXED_SIZE(xGLXVendorPrivateReq, 20)if (((sizeof(xGLXVendorPrivateReq) >> 2) > client->
req_len) || (((20) >> 2) >= client->req_len) || (
(((uint64_t) sizeof(xGLXVendorPrivateReq) + (20) + 3) >>
2) != (uint64_t) client->req_len)) return(16)
;
1883
1884 pc += __GLX_VENDPRIV_HDR_SIZE12;
1885
1886 drawId = *((CARD32 *) (pc));
1887 x = *((INT32 *) (pc + 4));
1888 y = *((INT32 *) (pc + 8));
1889 width = *((INT32 *) (pc + 12));
1890 height = *((INT32 *) (pc + 16));
1891
1892 if (tag) {
1893 glxc = __glXLookupContextByTag(cl, tag);
1894 if (!glxc) {
1895 return __glXError(GLXBadContextTag4);
1896 }
1897 /*
1898 ** The calling thread is swapping its current drawable. In this case,
1899 ** glxSwapBuffers is in both GL and X streams, in terms of
1900 ** sequentiality.
1901 */
1902 if (__glXForceCurrent(cl, tag, &error)) {
1903 /*
1904 ** Do whatever is needed to make sure that all preceding requests
1905 ** in both streams are completed before the swap is executed.
1906 */
1907 glFinish();
1908 glxc->hasUnflushedCommands = GL_FALSE0x0;
1909 }
1910 else {
1911 return error;
1912 }
1913 }
1914
1915 pGlxDraw = __glXGetDrawable(glxc, drawId, client, &error);
1916 if (!pGlxDraw)
1917 return error;
1918
1919 if (pGlxDraw == NULL((void*)0) ||
1920 pGlxDraw->type != GLX_DRAWABLE_WINDOW ||
1921 pGlxDraw->copySubBuffer == NULL((void*)0))
1922 return __glXError(GLXBadDrawable2);
1923
1924 (*pGlxDraw->copySubBuffer) (pGlxDraw, x, y, width, height);
1925
1926 return Success0;
1927}
1928
1929/*
1930** Get drawable attributes
1931*/
1932static int
1933DoGetDrawableAttributes(__GLXclientState * cl, XID drawId)
1934{
1935 ClientPtr client = cl->client;
1936 xGLXGetDrawableAttributesReply reply;
1937 __GLXdrawable *pGlxDraw = NULL((void*)0);
1938 DrawablePtr pDraw;
1939 CARD32 attributes[14];
1940 int num = 0, error;
1941
1942 if (!validGlxDrawable(client, drawId, GLX_DRAWABLE_ANY,
1943 DixGetAttrAccess(1<<4), &pGlxDraw, &error)) {
1944 /* hack for GLX 1.2 naked windows */
1945 int err = dixLookupWindow((WindowPtr *)&pDraw, drawId, client,
1946 DixGetAttrAccess(1<<4));
1947 if (err != Success0)
1948 return error;
1949 }
1950 if (pGlxDraw)
1951 pDraw = pGlxDraw->pDraw;
1952
1953 attributes[2*num] = GLX_Y_INVERTED_EXT0x20D4;
1954 attributes[2*num+1] = GL_FALSE0x0;
1955 num++;
1956 attributes[2*num] = GLX_WIDTH0x801D;
1957 attributes[2*num+1] = pDraw->width;
1958 num++;
1959 attributes[2*num] = GLX_HEIGHT0x801E;
1960 attributes[2*num+1] = pDraw->height;
1961 num++;
1962 if (pGlxDraw) {
1963 attributes[2*num] = GLX_TEXTURE_TARGET_EXT0x20D6;
1964 attributes[2*num+1] = pGlxDraw->target == GL_TEXTURE_2D0x0DE1 ?
1965 GLX_TEXTURE_2D_EXT0x20DC :
1966 GLX_TEXTURE_RECTANGLE_EXT0x20DD;
1967 num++;
1968 attributes[2*num] = GLX_EVENT_MASK0x801F;
1969 attributes[2*num+1] = pGlxDraw->eventMask;
1970 num++;
1971 attributes[2*num] = GLX_FBCONFIG_ID0x8013;
1972 attributes[2*num+1] = pGlxDraw->config->fbconfigID;
1973 num++;
1974 if (pGlxDraw->type == GLX_DRAWABLE_PBUFFER) {
1975 attributes[2*num] = GLX_PRESERVED_CONTENTS0x801B;
1976 attributes[2*num+1] = GL_TRUE0x1;
1977 num++;
1978 }
1979 }
1980
1981 reply = (xGLXGetDrawableAttributesReply) {
1982 .type = X_Reply1,
1983 .sequenceNumber = client->sequence,
1984 .length = num << 1,
1985 .numAttribs = num
1986 };
1987
1988 if (client->swapped) {
1989 __glXSwapGetDrawableAttributesReply(client, &reply, attributes);
1990 }
1991 else {
1992 WriteToClient(client, sz_xGLXGetDrawableAttributesReply32, &reply);
1993 WriteToClient(client, reply.length * sizeof(CARD32), attributes);
1994 }
1995
1996 return Success0;
1997}
1998
1999int
2000__glXDisp_GetDrawableAttributes(__GLXclientState * cl, GLbyte * pc)
2001{
2002 ClientPtr client = cl->client;
2003 xGLXGetDrawableAttributesReq *req = (xGLXGetDrawableAttributesReq *) pc;
2004
2005 /* this should be REQUEST_SIZE_MATCH, but mesa sends an additional 4 bytes */
2006 REQUEST_AT_LEAST_SIZE(xGLXGetDrawableAttributesReq)if ((sizeof(xGLXGetDrawableAttributesReq) >> 2) > client
->req_len ) return(16)
;
2007
2008 return DoGetDrawableAttributes(cl, req->drawable);
2009}
2010
2011int
2012__glXDisp_GetDrawableAttributesSGIX(__GLXclientState * cl, GLbyte * pc)
2013{
2014 ClientPtr client = cl->client;
2015 xGLXGetDrawableAttributesSGIXReq *req =
2016 (xGLXGetDrawableAttributesSGIXReq *) pc;
2017
2018 REQUEST_SIZE_MATCH(xGLXGetDrawableAttributesSGIXReq)if ((sizeof(xGLXGetDrawableAttributesSGIXReq) >> 2) != client
->req_len) return(16)
;
2019
2020 return DoGetDrawableAttributes(cl, req->drawable);
2021}
2022
2023/************************************************************************/
2024
2025/*
2026** Render and Renderlarge are not in the GLX API. They are used by the GLX
2027** client library to send batches of GL rendering commands.
2028*/
2029
2030/*
2031** Execute all the drawing commands in a request.
2032*/
2033int
2034__glXDisp_Render(__GLXclientState * cl, GLbyte * pc)
2035{
2036 xGLXRenderReq *req;
2037 ClientPtr client = cl->client;
2038 int left, cmdlen, error;
2039 int commandsDone;
2040 CARD16 opcode;
2041 __GLXrenderHeader *hdr;
2042 __GLXcontext *glxc;
2043
2044 __GLX_DECLARE_SWAP_VARIABLESGLbyte sw;
2045
2046 REQUEST_AT_LEAST_SIZE(xGLXRenderReq)if ((sizeof(xGLXRenderReq) >> 2) > client->req_len
) return(16)
;
2047
2048 req = (xGLXRenderReq *) pc;
2049 if (client->swapped) {
2050 __GLX_SWAP_SHORT(&req->length)sw = ((GLbyte *)(&req->length))[0]; ((GLbyte *)(&req
->length))[0] = ((GLbyte *)(&req->length))[1]; ((GLbyte
*)(&req->length))[1] = sw;
;
2051 __GLX_SWAP_INT(&req->contextTag)sw = ((GLbyte *)(&req->contextTag))[0]; ((GLbyte *)(&
req->contextTag))[0] = ((GLbyte *)(&req->contextTag
))[3]; ((GLbyte *)(&req->contextTag))[3] = sw; sw = ((
GLbyte *)(&req->contextTag))[1]; ((GLbyte *)(&req->
contextTag))[1] = ((GLbyte *)(&req->contextTag))[2]; (
(GLbyte *)(&req->contextTag))[2] = sw;
;
2052 }
2053
2054 glxc = __glXForceCurrent(cl, req->contextTag, &error);
2055 if (!glxc) {
2056 return error;
2057 }
2058
2059 commandsDone = 0;
2060 pc += sz_xGLXRenderReq8;
2061 left = (req->length << 2) - sz_xGLXRenderReq8;
2062 while (left > 0) {
2063 __GLXrenderSizeData entry;
2064 int extra = 0;
2065 __GLXdispatchRenderProcPtr proc;
2066 int err;
2067
2068 if (left < sizeof(__GLXrenderHeader))
2069 return BadLength16;
2070
2071 /*
2072 ** Verify that the header length and the overall length agree.
2073 ** Also, each command must be word aligned.
2074 */
2075 hdr = (__GLXrenderHeader *) pc;
2076 if (client->swapped) {
2077 __GLX_SWAP_SHORT(&hdr->length)sw = ((GLbyte *)(&hdr->length))[0]; ((GLbyte *)(&hdr
->length))[0] = ((GLbyte *)(&hdr->length))[1]; ((GLbyte
*)(&hdr->length))[1] = sw;
;
2078 __GLX_SWAP_SHORT(&hdr->opcode)sw = ((GLbyte *)(&hdr->opcode))[0]; ((GLbyte *)(&hdr
->opcode))[0] = ((GLbyte *)(&hdr->opcode))[1]; ((GLbyte
*)(&hdr->opcode))[1] = sw;
;
2079 }
2080 cmdlen = hdr->length;
2081 opcode = hdr->opcode;
2082
2083 if (left < cmdlen)
2084 return BadLength16;
2085
2086 /*
2087 ** Check for core opcodes and grab entry data.
2088 */
2089 err = __glXGetProtocolSizeData(&Render_dispatch_info, opcode, &entry);
2090 proc = (__GLXdispatchRenderProcPtr)
2091 __glXGetProtocolDecodeFunction(&Render_dispatch_info,
2092 opcode, client->swapped);
2093
2094 if ((err < 0) || (proc == NULL((void*)0))) {
2095 client->errorValue = commandsDone;
2096 return __glXError(GLXBadRenderRequest6);
2097 }
2098
2099 if (cmdlen < entry.bytes) {
2100 return BadLength16;
2101 }
2102
2103 if (entry.varsize) {
2104 /* variable size command */
2105 extra = (*entry.varsize) (pc + __GLX_RENDER_HDR_SIZE4,
2106 client->swapped,
2107 left - __GLX_RENDER_HDR_SIZE4);
2108 if (extra < 0) {
2109 return BadLength16;
2110 }
2111 }
2112
2113 if (cmdlen != safe_pad(safe_add(entry.bytes, extra))) {
2114 return BadLength16;
2115 }
2116
2117 /*
2118 ** Skip over the header and execute the command. We allow the
2119 ** caller to trash the command memory. This is useful especially
2120 ** for things that require double alignment - they can just shift
2121 ** the data towards lower memory (trashing the header) by 4 bytes
2122 ** and achieve the required alignment.
2123 */
2124 (*proc) (pc + __GLX_RENDER_HDR_SIZE4);
2125 pc += cmdlen;
2126 left -= cmdlen;
2127 commandsDone++;
2128 }
2129 glxc->hasUnflushedCommands = GL_TRUE0x1;
2130 return Success0;
2131}
2132
2133/*
2134** Execute a large rendering request (one that spans multiple X requests).
2135*/
2136int
2137__glXDisp_RenderLarge(__GLXclientState * cl, GLbyte * pc)
2138{
2139 xGLXRenderLargeReq *req;
2140 ClientPtr client = cl->client;
2141 size_t dataBytes;
2142 __GLXrenderLargeHeader *hdr;
2143 __GLXcontext *glxc;
2144 int error;
2145 CARD16 opcode;
2146
2147 __GLX_DECLARE_SWAP_VARIABLESGLbyte sw;
2148
2149 REQUEST_AT_LEAST_SIZE(xGLXRenderLargeReq)if ((sizeof(xGLXRenderLargeReq) >> 2) > client->req_len
) return(16)
;
2150
2151 req = (xGLXRenderLargeReq *) pc;
2152 if (client->swapped) {
2153 __GLX_SWAP_SHORT(&req->length)sw = ((GLbyte *)(&req->length))[0]; ((GLbyte *)(&req
->length))[0] = ((GLbyte *)(&req->length))[1]; ((GLbyte
*)(&req->length))[1] = sw;
;
2154 __GLX_SWAP_INT(&req->contextTag)sw = ((GLbyte *)(&req->contextTag))[0]; ((GLbyte *)(&
req->contextTag))[0] = ((GLbyte *)(&req->contextTag
))[3]; ((GLbyte *)(&req->contextTag))[3] = sw; sw = ((
GLbyte *)(&req->contextTag))[1]; ((GLbyte *)(&req->
contextTag))[1] = ((GLbyte *)(&req->contextTag))[2]; (
(GLbyte *)(&req->contextTag))[2] = sw;
;
2155 __GLX_SWAP_INT(&req->dataBytes)sw = ((GLbyte *)(&req->dataBytes))[0]; ((GLbyte *)(&
req->dataBytes))[0] = ((GLbyte *)(&req->dataBytes))
[3]; ((GLbyte *)(&req->dataBytes))[3] = sw; sw = ((GLbyte
*)(&req->dataBytes))[1]; ((GLbyte *)(&req->dataBytes
))[1] = ((GLbyte *)(&req->dataBytes))[2]; ((GLbyte *)(
&req->dataBytes))[2] = sw;
;
2156 __GLX_SWAP_SHORT(&req->requestNumber)sw = ((GLbyte *)(&req->requestNumber))[0]; ((GLbyte *)
(&req->requestNumber))[0] = ((GLbyte *)(&req->requestNumber
))[1]; ((GLbyte *)(&req->requestNumber))[1] = sw;
;
2157 __GLX_SWAP_SHORT(&req->requestTotal)sw = ((GLbyte *)(&req->requestTotal))[0]; ((GLbyte *)(
&req->requestTotal))[0] = ((GLbyte *)(&req->requestTotal
))[1]; ((GLbyte *)(&req->requestTotal))[1] = sw;
;
2158 }
2159
2160 glxc = __glXForceCurrent(cl, req->contextTag, &error);
2161 if (!glxc) {
2162 /* Reset in case this isn't 1st request. */
2163 __glXResetLargeCommandStatus(cl);
2164 return error;
2165 }
2166 if (safe_pad(req->dataBytes) < 0)
2167 return BadLength16;
2168 dataBytes = req->dataBytes;
2169
2170 /*
2171 ** Check the request length.
2172 */
2173 if ((req->length << 2) != safe_pad(dataBytes) + sz_xGLXRenderLargeReq16) {
2174 client->errorValue = req->length;
2175 /* Reset in case this isn't 1st request. */
2176 __glXResetLargeCommandStatus(cl);
2177 return BadLength16;
2178 }
2179 pc += sz_xGLXRenderLargeReq16;
2180
2181 if (cl->largeCmdRequestsSoFar == 0) {
2182 __GLXrenderSizeData entry;
2183 int extra = 0;
2184 int left = (req->length << 2) - sz_xGLXRenderLargeReq16;
2185 int cmdlen;
2186 int err;
2187
2188 /*
2189 ** This is the first request of a multi request command.
2190 ** Make enough space in the buffer, then copy the entire request.
2191 */
2192 if (req->requestNumber != 1) {
2193 client->errorValue = req->requestNumber;
2194 return __glXError(GLXBadLargeRequest7);
2195 }
2196
2197 if (dataBytes < __GLX_RENDER_LARGE_HDR_SIZE8)
2198 return BadLength16;
2199
2200 hdr = (__GLXrenderLargeHeader *) pc;
2201 if (client->swapped) {
2202 __GLX_SWAP_INT(&hdr->length)sw = ((GLbyte *)(&hdr->length))[0]; ((GLbyte *)(&hdr
->length))[0] = ((GLbyte *)(&hdr->length))[3]; ((GLbyte
*)(&hdr->length))[3] = sw; sw = ((GLbyte *)(&hdr->
length))[1]; ((GLbyte *)(&hdr->length))[1] = ((GLbyte *
)(&hdr->length))[2]; ((GLbyte *)(&hdr->length))
[2] = sw;
;
2203 __GLX_SWAP_INT(&hdr->opcode)sw = ((GLbyte *)(&hdr->opcode))[0]; ((GLbyte *)(&hdr
->opcode))[0] = ((GLbyte *)(&hdr->opcode))[3]; ((GLbyte
*)(&hdr->opcode))[3] = sw; sw = ((GLbyte *)(&hdr->
opcode))[1]; ((GLbyte *)(&hdr->opcode))[1] = ((GLbyte *
)(&hdr->opcode))[2]; ((GLbyte *)(&hdr->opcode))
[2] = sw;
;
2204 }
2205 opcode = hdr->opcode;
2206 if ((cmdlen = safe_pad(hdr->length)) < 0)
2207 return BadLength16;
2208
2209 /*
2210 ** Check for core opcodes and grab entry data.
2211 */
2212 err = __glXGetProtocolSizeData(&Render_dispatch_info, opcode, &entry);
2213 if (err < 0) {
2214 client->errorValue = opcode;
2215 return __glXError(GLXBadLargeRequest7);
2216 }
2217
2218 if (entry.varsize) {
2219 /*
2220 ** If it's a variable-size command (a command whose length must
2221 ** be computed from its parameters), all the parameters needed
2222 ** will be in the 1st request, so it's okay to do this.
2223 */
2224 extra = (*entry.varsize) (pc + __GLX_RENDER_LARGE_HDR_SIZE8,
2225 client->swapped,
2226 left - __GLX_RENDER_LARGE_HDR_SIZE8);
2227 if (extra < 0) {
2228 return BadLength16;
2229 }
2230 }
2231
2232 /* the +4 is safe because we know entry.bytes is small */
2233 if (cmdlen != safe_pad(safe_add(entry.bytes + 4, extra))) {
2234 return BadLength16;
2235 }
2236
2237 /*
2238 ** Make enough space in the buffer, then copy the entire request.
2239 */
2240 if (cl->largeCmdBufSize < cmdlen) {
2241 GLbyte *newbuf = cl->largeCmdBuf;
2242
2243 if (!(newbuf = realloc(newbuf, cmdlen)))
2244 return BadAlloc11;
2245
2246 cl->largeCmdBuf = newbuf;
2247 cl->largeCmdBufSize = cmdlen;
2248 }
2249 memcpy(cl->largeCmdBuf, pc, dataBytes)__builtin___memcpy_chk (cl->largeCmdBuf, pc, dataBytes, __builtin_object_size
(cl->largeCmdBuf, 0))
;
2250
2251 cl->largeCmdBytesSoFar = dataBytes;
2252 cl->largeCmdBytesTotal = cmdlen;
2253 cl->largeCmdRequestsSoFar = 1;
2254 cl->largeCmdRequestsTotal = req->requestTotal;
2255 return Success0;
2256
2257 }
2258 else {
2259 /*
2260 ** We are receiving subsequent (i.e. not the first) requests of a
2261 ** multi request command.
2262 */
2263 int bytesSoFar; /* including this packet */
2264
2265 /*
2266 ** Check the request number and the total request count.
2267 */
2268 if (req->requestNumber != cl->largeCmdRequestsSoFar + 1) {
2269 client->errorValue = req->requestNumber;
2270 __glXResetLargeCommandStatus(cl);
2271 return __glXError(GLXBadLargeRequest7);
2272 }
2273 if (req->requestTotal != cl->largeCmdRequestsTotal) {
2274 client->errorValue = req->requestTotal;
2275 __glXResetLargeCommandStatus(cl);
2276 return __glXError(GLXBadLargeRequest7);
2277 }
2278
2279 /*
2280 ** Check that we didn't get too much data.
2281 */
2282 if ((bytesSoFar = safe_add(cl->largeCmdBytesSoFar, dataBytes)) < 0) {
2283 client->errorValue = dataBytes;
2284 __glXResetLargeCommandStatus(cl);
2285 return __glXError(GLXBadLargeRequest7);
2286 }
2287
2288 if (bytesSoFar > cl->largeCmdBytesTotal) {
2289 client->errorValue = dataBytes;
2290 __glXResetLargeCommandStatus(cl);
2291 return __glXError(GLXBadLargeRequest7);
2292 }
2293
2294 memcpy(cl->largeCmdBuf + cl->largeCmdBytesSoFar, pc, dataBytes)__builtin___memcpy_chk (cl->largeCmdBuf + cl->largeCmdBytesSoFar
, pc, dataBytes, __builtin_object_size (cl->largeCmdBuf + cl
->largeCmdBytesSoFar, 0))
;
2295 cl->largeCmdBytesSoFar += dataBytes;
2296 cl->largeCmdRequestsSoFar++;
2297
2298 if (req->requestNumber == cl->largeCmdRequestsTotal) {
2299 __GLXdispatchRenderProcPtr proc;
2300
2301 /*
2302 ** This is the last request; it must have enough bytes to complete
2303 ** the command.
2304 */
2305 /* NOTE: the pad macro below is needed because the client library
2306 ** pads the total byte count, but not the per-request byte counts.
2307 ** The Protocol Encoding says the total byte count should not be
2308 ** padded, so a proposal will be made to the ARB to relax the
2309 ** padding constraint on the total byte count, thus preserving
2310 ** backward compatibility. Meanwhile, the padding done below
2311 ** fixes a bug that did not allow large commands of odd sizes to
2312 ** be accepted by the server.
2313 */
2314 if (safe_pad(cl->largeCmdBytesSoFar) != cl->largeCmdBytesTotal) {
2315 client->errorValue = dataBytes;
2316 __glXResetLargeCommandStatus(cl);
2317 return __glXError(GLXBadLargeRequest7);
2318 }
2319 hdr = (__GLXrenderLargeHeader *) cl->largeCmdBuf;
2320 /*
2321 ** The opcode and length field in the header had already been
2322 ** swapped when the first request was received.
2323 **
2324 ** Use the opcode to index into the procedure table.
2325 */
2326 opcode = hdr->opcode;
2327
2328 proc = (__GLXdispatchRenderProcPtr)
2329 __glXGetProtocolDecodeFunction(&Render_dispatch_info, opcode,
2330 client->swapped);
2331 if (proc == NULL((void*)0)) {
2332 client->errorValue = opcode;
2333 return __glXError(GLXBadLargeRequest7);
2334 }
2335
2336 /*
2337 ** Skip over the header and execute the command.
2338 */
2339 (*proc) (cl->largeCmdBuf + __GLX_RENDER_LARGE_HDR_SIZE8);
2340 glxc->hasUnflushedCommands = GL_TRUE0x1;
2341
2342 /*
2343 ** Reset for the next RenderLarge series.
2344 */
2345 __glXResetLargeCommandStatus(cl);
2346 }
2347 else {
2348 /*
2349 ** This is neither the first nor the last request.
2350 */
2351 }
2352 return Success0;
2353 }
2354}
2355
2356/************************************************************************/
2357
2358/*
2359** No support is provided for the vendor-private requests other than
2360** allocating the entry points in the dispatch table.
2361*/
2362
2363int
2364__glXDisp_VendorPrivate(__GLXclientState * cl, GLbyte * pc)
2365{
2366 ClientPtr client = cl->client;
2367 xGLXVendorPrivateReq *req = (xGLXVendorPrivateReq *) pc;
2368 GLint vendorcode = req->vendorCode;
2369 __GLXdispatchVendorPrivProcPtr proc;
2370
2371 REQUEST_AT_LEAST_SIZE(xGLXVendorPrivateReq)if ((sizeof(xGLXVendorPrivateReq) >> 2) > client->
req_len ) return(16)
;
2372
2373 proc = (__GLXdispatchVendorPrivProcPtr)
2374 __glXGetProtocolDecodeFunction(&VendorPriv_dispatch_info,
2375 vendorcode, 0);
2376 if (proc != NULL((void*)0)) {
2377 (*proc) (cl, (GLbyte *) req);
2378 return Success0;
2379 }
2380
2381 cl->client->errorValue = req->vendorCode;
2382 return __glXError(GLXUnsupportedPrivateRequest8);
2383}
2384
2385int
2386__glXDisp_VendorPrivateWithReply(__GLXclientState * cl, GLbyte * pc)
2387{
2388 ClientPtr client = cl->client;
2389 xGLXVendorPrivateReq *req = (xGLXVendorPrivateReq *) pc;
2390 GLint vendorcode = req->vendorCode;
2391 __GLXdispatchVendorPrivProcPtr proc;
2392
2393 REQUEST_AT_LEAST_SIZE(xGLXVendorPrivateReq)if ((sizeof(xGLXVendorPrivateReq) >> 2) > client->
req_len ) return(16)
;
2394
2395 proc = (__GLXdispatchVendorPrivProcPtr)
2396 __glXGetProtocolDecodeFunction(&VendorPriv_dispatch_info,
2397 vendorcode, 0);
2398 if (proc != NULL((void*)0)) {
2399 return (*proc) (cl, (GLbyte *) req);
2400 }
2401
2402 cl->client->errorValue = vendorcode;
2403 return __glXError(GLXUnsupportedPrivateRequest8);
2404}
2405
2406int
2407__glXDisp_QueryExtensionsString(__GLXclientState * cl, GLbyte * pc)
2408{
2409 ClientPtr client = cl->client;
2410 xGLXQueryExtensionsStringReq *req = (xGLXQueryExtensionsStringReq *) pc;
2411 xGLXQueryExtensionsStringReply reply;
2412 __GLXscreen *pGlxScreen;
2413 size_t n, length;
2414 char *buf;
2415 int err;
2416
2417 REQUEST_SIZE_MATCH(xGLXQueryExtensionsStringReq)if ((sizeof(xGLXQueryExtensionsStringReq) >> 2) != client
->req_len) return(16)
;
2418
2419 if (!validGlxScreen(client, req->screen, &pGlxScreen, &err))
2420 return err;
2421
2422 n = strlen(pGlxScreen->GLXextensions) + 1;
2423 length = __GLX_PAD(n)(((n)+3) & (GLuint)~3) >> 2;
2424 reply = (xGLXQueryExtensionsStringReply) {
2425 .type = X_Reply1,
2426 .sequenceNumber = client->sequence,
2427 .length = length,
2428 .n = n
2429 };
2430
2431 /* Allocate buffer to make sure it's a multiple of 4 bytes big. */
2432 buf = calloc(length, 4);
2433 if (buf == NULL((void*)0))
2434 return BadAlloc11;
2435 memcpy(buf, pGlxScreen->GLXextensions, n)__builtin___memcpy_chk (buf, pGlxScreen->GLXextensions, n,
__builtin_object_size (buf, 0))
;
2436
2437 if (client->swapped) {
2438 glxSwapQueryExtensionsStringReply(client, &reply, buf);
2439 }
2440 else {
2441 WriteToClient(client, sz_xGLXQueryExtensionsStringReply32, &reply);
2442 WriteToClient(client, (int) (length << 2), buf);
2443 }
2444
2445 free(buf);
2446 return Success0;
2447}
2448
2449int
2450__glXDisp_QueryServerString(__GLXclientState * cl, GLbyte * pc)
2451{
2452 ClientPtr client = cl->client;
2453 xGLXQueryServerStringReq *req = (xGLXQueryServerStringReq *) pc;
2454 xGLXQueryServerStringReply reply;
2455 size_t n, length;
2456 const char *ptr;
2457 char *buf;
2458 __GLXscreen *pGlxScreen;
2459 int err;
2460 char ver_str[16];
2461
2462 REQUEST_SIZE_MATCH(xGLXQueryServerStringReq)if ((sizeof(xGLXQueryServerStringReq) >> 2) != client->
req_len) return(16)
;
2463
2464 if (!validGlxScreen(client, req->screen, &pGlxScreen, &err))
2465 return err;
2466
2467 switch (req->name) {
2468 case GLX_VENDOR0x1:
2469 ptr = GLXServerVendorName;
2470 break;
2471 case GLX_VERSION0x2:
2472 /* Return to the server version rather than the screen version
2473 * to prevent confusion when they do not match.
2474 */
2475 snprintf(ver_str, 16, "%d.%d", glxMajorVersion, glxMinorVersion)__builtin___snprintf_chk (ver_str, 16, 0, __builtin_object_size
(ver_str, 2 > 1 ? 1 : 0), "%d.%d", glxMajorVersion, glxMinorVersion
)
;
2476 ptr = ver_str;
2477 break;
2478 case GLX_EXTENSIONS0x3:
2479 ptr = pGlxScreen->GLXextensions;
2480 break;
2481 default:
2482 return BadValue2;
2483 }
2484
2485 n = strlen(ptr) + 1;
2486 length = __GLX_PAD(n)(((n)+3) & (GLuint)~3) >> 2;
2487 reply = (xGLXQueryServerStringReply) {
2488 .type = X_Reply1,
2489 .sequenceNumber = client->sequence,
2490 .length = length,
2491 .n = n
2492 };
2493
2494 buf = calloc(length, 4);
2495 if (buf == NULL((void*)0)) {
2496 return BadAlloc11;
2497 }
2498 memcpy(buf, ptr, n)__builtin___memcpy_chk (buf, ptr, n, __builtin_object_size (buf
, 0))
;
2499
2500 if (client->swapped) {
2501 glxSwapQueryServerStringReply(client, &reply, buf);
2502 }
2503 else {
2504 WriteToClient(client, sz_xGLXQueryServerStringReply32, &reply);
2505 WriteToClient(client, (int) (length << 2), buf);
2506 }
2507
2508 free(buf);
2509 return Success0;
2510}
2511
2512int
2513__glXDisp_ClientInfo(__GLXclientState * cl, GLbyte * pc)
2514{
2515 ClientPtr client = cl->client;
2516 xGLXClientInfoReq *req = (xGLXClientInfoReq *) pc;
2517 const char *buf;
2518
2519 REQUEST_AT_LEAST_SIZE(xGLXClientInfoReq)if ((sizeof(xGLXClientInfoReq) >> 2) > client->req_len
) return(16)
;
2520
2521 buf = (const char *) (req + 1);
2522 if (!memchr(buf, 0, (client->req_len << 2) - sizeof(xGLXClientInfoReq)))
2523 return BadLength16;
2524
2525 free(cl->GLClientextensions);
2526 cl->GLClientextensions = strdup(buf);
2527
2528 return Success0;
2529}
2530
2531#include <GL/glxtokens.h>
2532
2533void
2534__glXsendSwapEvent(__GLXdrawable *drawable, int type, CARD64 ust,
2535 CARD64 msc, CARD32 sbc)
2536{
2537 ClientPtr client = clients[CLIENT_ID(drawable->drawId)((int)(((drawable->drawId) & (((1 << 8) - 1) <<
(29 - 8))) >> (29 - 8)))
];
2538
2539 xGLXBufferSwapComplete2 wire = {
2540 .type = __glXEventBase + GLX_BufferSwapComplete1
2541 };
2542
2543 if (!client)
2544 return;
2545
2546 if (!(drawable->eventMask & GLX_BUFFER_SWAP_COMPLETE_INTEL_MASK0x04000000))
2547 return;
2548
2549 wire.event_type = type;
2550 wire.drawable = drawable->drawId;
2551 wire.ust_hi = ust >> 32;
2552 wire.ust_lo = ust & 0xffffffff;
2553 wire.msc_hi = msc >> 32;
2554 wire.msc_lo = msc & 0xffffffff;
2555 wire.sbc = sbc;
2556
2557 WriteEventsToClient(client, 1, (xEvent *) &wire);
2558}
2559
2560#if PRESENT1
2561static void
2562__glXpresentCompleteNotify(WindowPtr window, CARD8 present_kind, CARD8 present_mode,
2563 CARD32 serial, uint64_t ust, uint64_t msc)
2564{
2565 __GLXdrawable *drawable;
2566 int glx_type;
2567 int rc;
2568
2569 if (present_kind != PresentCompleteKindPixmap0)
2570 return;
2571
2572 rc = dixLookupResourceByType((void **) &drawable, window->drawable.id,
2573 __glXDrawableRes, serverClient, DixGetAttrAccess(1<<4));
2574
2575 if (rc != Success0)
2576 return;
2577
2578 if (present_mode == PresentCompleteModeFlip1)
2579 glx_type = GLX_FLIP_COMPLETE_INTEL0x8182;
2580 else
2581 glx_type = GLX_BLIT_COMPLETE_INTEL0x8181;
2582
2583 __glXsendSwapEvent(drawable, glx_type, ust, msc, serial);
2584}
2585
2586#include <present.h>
2587
2588void
2589__glXregisterPresentCompleteNotify(void)
2590{
2591 present_register_complete_notify(__glXpresentCompleteNotify);
2592}
2593#endif