Exemple #1
0
static __GLXDRIdrawable *
FetchDRIDrawable(Display * dpy, GLXDrawable glxDrawable, GLXContext gc)
{
   __GLXdisplayPrivate *const priv = __glXInitialize(dpy);
   __GLXDRIdrawable *pdraw;
   __GLXscreenConfigs *psc;

   if (priv == NULL)
      return NULL;

   psc = &priv->screenConfigs[gc->screen];
   if (psc->drawHash == NULL)
      return NULL;

   if (__glxHashLookup(psc->drawHash, glxDrawable, (void *) &pdraw) == 0)
      return pdraw;

   pdraw = psc->driScreen->createDrawable(psc, glxDrawable,
                                          glxDrawable, gc->mode);
   if (__glxHashInsert(psc->drawHash, glxDrawable, pdraw)) {
      (*pdraw->destroyDrawable) (pdraw);
      return NULL;
   }

   return pdraw;
}
Exemple #2
0
static GLboolean
CreateDRIDrawable(Display *dpy, struct glx_config *config,
		  XID drawable, XID glxdrawable,
		  const int *attrib_list, size_t num_attribs)
{
   struct glx_display *const priv = __glXInitialize(dpy);
   __GLXDRIdrawable *pdraw;
   struct glx_screen *psc;

   psc = priv->screens[config->screen];
   if (psc->driScreen == NULL)
      return GL_TRUE;

   pdraw = psc->driScreen->createDrawable(psc, drawable,
					  glxdrawable, config);
   if (pdraw == NULL) {
      fprintf(stderr, "failed to create drawable\n");
      return GL_FALSE;
   }

   if (__glxHashInsert(priv->drawHash, glxdrawable, pdraw)) {
      (*pdraw->destroyDrawable) (pdraw);
      return GL_FALSE;
   }

   pdraw->textureTarget = determineTextureTarget(attrib_list, num_attribs);
   pdraw->textureFormat = determineTextureFormat(attrib_list, num_attribs);

   return GL_TRUE;
}
Exemple #3
0
_X_HIDDEN __GLXDRIdrawable *
driFetchDrawable(struct glx_context *gc, GLXDrawable glxDrawable)
{
   struct glx_display *const priv = __glXInitialize(gc->psc->dpy);
   __GLXDRIdrawable *pdraw;
   struct glx_screen *psc;

   if (priv == NULL)
      return NULL;

   psc = priv->screens[gc->screen];
   if (priv->drawHash == NULL)
      return NULL;

   if (__glxHashLookup(priv->drawHash, glxDrawable, (void *) &pdraw) == 0) {
      pdraw->refcount ++;
      return pdraw;
   }

   pdraw = psc->driScreen->createDrawable(psc, glxDrawable,
                                          glxDrawable, gc->config);

   if (pdraw == NULL) {
      ErrorMessageF("failed to create drawable\n");
      return NULL;
   }

   if (__glxHashInsert(priv->drawHash, glxDrawable, pdraw)) {
      (*pdraw->destroyDrawable) (pdraw);
      return NULL;
   }
   pdraw->refcount = 1;

   return pdraw;
}
Exemple #4
0
/*
** Setup for sending a GLX command on dpy.  Make sure the extension is
** initialized.  Try to avoid calling __glXInitialize as its kinda slow.
*/
_X_HIDDEN CARD8
__glXSetupForCommand(Display * dpy)
{
    struct glx_context *gc;
    struct glx_display *priv;

   /* If this thread has a current context, flush its rendering commands */
   gc = __glXGetCurrentContext();
   if (gc->currentDpy) {
      /* Flush rendering buffer of the current context, if any */
      (void) __glXFlushRenderBuffer(gc, gc->pc);

      if (gc->currentDpy == dpy) {
         /* Use opcode from gc because its right */
         return gc->majorOpcode;
      }
      else {
         /*
          ** Have to get info about argument dpy because it might be to
          ** a different server
          */
      }
   }

   /* Forced to lookup extension via the slow initialize route */
   priv = __glXInitialize(dpy);
   if (!priv) {
      return 0;
   }
   return priv->majorOpcode;
}
Exemple #5
0
static int64_t
dri2SwapBuffers(__GLXDRIdrawable *pdraw, int64_t target_msc, int64_t divisor,
                int64_t remainder)
{
    __GLXDRIdrawablePrivate *priv = (__GLXDRIdrawablePrivate *) pdraw;
    __GLXdisplayPrivate *dpyPriv = __glXInitialize(priv->base.psc->dpy);
    __GLXDRIdisplayPrivate *pdp =
        (__GLXDRIdisplayPrivate *)dpyPriv->dri2Display;
    int64_t ret;

#ifdef __DRI2_FLUSH
    if (pdraw->psc->f)
        (*pdraw->psc->f->flush)(pdraw->driDrawable);
#endif

    /* Old servers don't send invalidate events */
    if (!pdp->invalidateAvailable)
        dri2InvalidateBuffers(dpyPriv->dpy, pdraw->drawable);

    /* Old servers can't handle swapbuffers */
    if (!pdp->swapAvailable) {
        dri2CopySubBuffer(pdraw, 0, 0, priv->width, priv->height);
        return 0;
    }

#ifdef X_DRI2SwapBuffers
    DRI2SwapBuffers(pdraw->psc->dpy, pdraw->xDrawable, target_msc, divisor,
                    remainder, &ret);
#endif

    return ret;
}
Exemple #6
0
void
__glXSendError(Display * dpy, int_fast8_t errorCode, uint_fast32_t resourceID,
               uint_fast16_t minorCode, bool coreX11error)
{
   struct glx_display *glx_dpy = __glXInitialize(dpy);
   struct glx_context *gc = __glXGetCurrentContext();
   xError error;

   assert(glx_dpy);
   assert(gc);

   LockDisplay(dpy);

   error.type = X_Error;

   if (coreX11error) {
      error.errorCode = errorCode;
   }
   else {
      error.errorCode = glx_dpy->codes->first_error + errorCode;
   }

   error.sequenceNumber = dpy->request;
   error.resourceID = resourceID;
   error.minorCode = minorCode;
   error.majorCode = gc ? gc->majorOpcode : 0;

   _XError(dpy, &error);

   UnlockDisplay(dpy);
}
Exemple #7
0
/* We don't actually support this.  It doesn't make sense for clients to
 * send each other GLX events.
 */
static Status
__glXEventToWire(Display *dpy, XEvent *event, xEvent *wire)
{
     struct glx_display *glx_dpy = __glXInitialize(dpy);

   if (glx_dpy == NULL)
      return False;

   switch (event->type) {
   case GLX_DAMAGED:
      break;
   case GLX_SAVED:
      break;
   case GLX_EXCHANGE_COMPLETE_INTEL:
      break;
   case GLX_COPY_COMPLETE_INTEL:
      break;
   case GLX_FLIP_COMPLETE_INTEL:
      break;
   default:
      /* client doesn't support server event */
      break;
   }

   return Success;
}
Exemple #8
0
static boolean
x11_screen_init_glx(struct x11_screen *xscr)
{
   if (!xscr->glx_dpy)
      xscr->glx_dpy = __glXInitialize(xscr->dpy);
   return (xscr->glx_dpy != NULL);
}
Exemple #9
0
static Bool
__glXWireToEvent(Display *dpy, XEvent *event, xEvent *wire)
{
     struct glx_display *glx_dpy = __glXInitialize(dpy);

   if (glx_dpy == NULL)
      return False;

   switch ((wire->u.u.type & 0x7f) - glx_dpy->codes->first_event) {
   case GLX_PbufferClobber:
   {
      GLXPbufferClobberEvent *aevent = (GLXPbufferClobberEvent *)event;
      xGLXPbufferClobberEvent *awire = (xGLXPbufferClobberEvent *)wire;
      aevent->event_type = awire->type;
      aevent->serial = awire->sequenceNumber;
      aevent->event_type = awire->event_type;
      aevent->draw_type = awire->draw_type;
      aevent->drawable = awire->drawable;
      aevent->buffer_mask = awire->buffer_mask;
      aevent->aux_buffer = awire->aux_buffer;
      aevent->x = awire->x;
      aevent->y = awire->y;
      aevent->width = awire->width;
      aevent->height = awire->height;
      aevent->count = awire->count;
      return True;
   }
   case GLX_BufferSwapComplete:
   {
      GLXBufferSwapComplete *aevent = (GLXBufferSwapComplete *)event;
      xGLXBufferSwapComplete2 *awire = (xGLXBufferSwapComplete2 *)wire;
      struct glx_drawable *glxDraw = GetGLXDrawable(dpy, awire->drawable);
      aevent->event_type = awire->event_type;
      aevent->drawable = awire->drawable;
      aevent->ust = ((CARD64)awire->ust_hi << 32) | awire->ust_lo;
      aevent->msc = ((CARD64)awire->msc_hi << 32) | awire->msc_lo;

      if (!glxDraw)
	 return False;

      if (awire->sbc < glxDraw->lastEventSbc)
	 glxDraw->eventSbcWrap += 0x100000000;
      glxDraw->lastEventSbc = awire->sbc;
      aevent->sbc = awire->sbc + glxDraw->eventSbcWrap;
      return True;
   }
   default:
      /* client doesn't support server event */
      break;
   }

   return False;
}
Exemple #10
0
/**
 * Emit a warning when clients use GLX 1.3 functions on pre-1.3 systems.
 */
static void
warn_GLX_1_3(Display * dpy, const char *function_name)
{
   __GLXdisplayPrivate *priv = __glXInitialize(dpy);

   if (priv->minorVersion < 3) {
      fprintf(stderr,
              "WARNING: Application calling GLX 1.3 function \"%s\" "
              "when GLX 1.3 is not supported!  This is an application bug!\n",
              function_name);
   }
}
Exemple #11
0
/**
 * This is called from src/glx/dri2.c.
 */
void
dri2InvalidateBuffers(Display *dpy, XID drawable)
{
   __GLXdisplayPrivate *priv = __glXInitialize(dpy);
   struct x11_screen *xscr = NULL;

   if (priv && priv->xscr)
      xscr = priv->xscr;
   if (!xscr || !xscr->dri_invalidate_buffers)
      return;

   xscr->dri_invalidate_buffers(xscr, drawable, xscr->dri_user_data);
}
Exemple #12
0
static void
dri2FlushFrontBuffer(__DRIdrawable *driDrawable, void *loaderPrivate)
{
    __GLXDRIdrawablePrivate *pdraw = loaderPrivate;
    __GLXdisplayPrivate *priv = __glXInitialize(pdraw->base.psc->dpy);
    __GLXDRIdisplayPrivate *pdp = (__GLXDRIdisplayPrivate *)priv->dri2Display;

    /* Old servers don't send invalidate events */
    if (!pdp->invalidateAvailable)
        dri2InvalidateBuffers(priv->dpy, pdraw->base.drawable);

    dri2WaitGL(loaderPrivate);
}
Exemple #13
0
/**
 * Change a drawable's attribute.
 *
 * This function is used to implement \c glXSelectEvent and
 * \c glXSelectEventSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 *
 * \todo
 * This function needs to be modified to work with direct-rendering drivers.
 */
static void
ChangeDrawableAttribute(Display * dpy, GLXDrawable drawable,
                        const CARD32 * attribs, size_t num_attribs)
{
   __GLXdisplayPrivate *priv = __glXInitialize(dpy);
   CARD32 *output;
   CARD8 opcode;

   if ((dpy == NULL) || (drawable == 0)) {
      return;
   }

   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return;

   LockDisplay(dpy);

   if ((priv->majorVersion > 1) || (priv->minorVersion >= 3)) {
      xGLXChangeDrawableAttributesReq *req;

      GetReqExtra(GLXChangeDrawableAttributes, 8 + (8 * num_attribs), req);
      output = (CARD32 *) (req + 1);

      req->reqType = opcode;
      req->glxCode = X_GLXChangeDrawableAttributes;
      req->drawable = drawable;
      req->numAttribs = (CARD32) num_attribs;
   }
   else {
      xGLXVendorPrivateWithReplyReq *vpreq;

      GetReqExtra(GLXVendorPrivateWithReply, 4 + (8 * num_attribs), vpreq);
      output = (CARD32 *) (vpreq + 1);

      vpreq->reqType = opcode;
      vpreq->glxCode = X_GLXVendorPrivateWithReply;
      vpreq->vendorCode = X_GLXvop_ChangeDrawableAttributesSGIX;

      output[0] = (CARD32) drawable;
      output++;
   }

   (void) memcpy(output, attribs, sizeof(CARD32) * 2 * num_attribs);

   UnlockDisplay(dpy);
   SyncHandle();

   return;
}
Exemple #14
0
static void
DestroyDRIDrawable(Display *dpy, GLXDrawable drawable, int destroy_xdrawable)
{
   struct glx_display *const priv = __glXInitialize(dpy);
   __GLXDRIdrawable *pdraw = GetGLXDRIDrawable(dpy, drawable);
   XID xid;

   if (pdraw != NULL) {
      xid = pdraw->xDrawable;
      (*pdraw->destroyDrawable) (pdraw);
      __glxHashDelete(priv->drawHash, drawable);
      if (destroy_xdrawable)
         XFreePixmap(priv->dpy, xid);
   }
}
Exemple #15
0
static __GLXDRIdrawable *
dri2CreateDrawable(__GLXscreenConfigs * psc,
                   XID xDrawable,
                   GLXDrawable drawable, const __GLcontextModes * modes)
{
    __GLXDRIdrawablePrivate *pdraw;
    __GLXDRIconfigPrivate *config = (__GLXDRIconfigPrivate *) modes;
    __GLXdisplayPrivate *dpyPriv;
    __GLXDRIdisplayPrivate *pdp;

    pdraw = Xmalloc(sizeof(*pdraw));
    if (!pdraw)
        return NULL;

    pdraw->base.destroyDrawable = dri2DestroyDrawable;
    pdraw->base.xDrawable = xDrawable;
    pdraw->base.drawable = drawable;
    pdraw->base.psc = psc;
    pdraw->bufferCount = 0;
    pdraw->swap_interval = 1;
    pdraw->have_back = 0;

    DRI2CreateDrawable(psc->dpy, xDrawable);

    dpyPriv = __glXInitialize(psc->dpy);
    pdp = (__GLXDRIdisplayPrivate *)dpyPriv->dri2Display;;
    /* Create a new drawable */
    pdraw->base.driDrawable =
        (*psc->dri2->createNewDrawable) (psc->__driScreen,
                                         config->driConfig, pdraw);

    if (!pdraw->base.driDrawable) {
        DRI2DestroyDrawable(psc->dpy, xDrawable);
        Xfree(pdraw);
        return NULL;
    }

#ifdef X_DRI2SwapInterval
    /*
     * Make sure server has the same swap interval we do for the new
     * drawable.
     */
    if (pdp->swapAvailable)
        DRI2SwapInterval(psc->dpy, xDrawable, pdraw->swap_interval);
#endif

    return &pdraw->base;
}
Exemple #16
0
/**
 * Destroy a pbuffer.
 *
 * This function is used to implement \c glXDestroyPbuffer and
 * \c glXDestroyGLXPbufferSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 */
static void
DestroyPbuffer(Display * dpy, GLXDrawable drawable)
{
   struct glx_display *priv = __glXInitialize(dpy);
   CARD8 opcode;

   if ((dpy == NULL) || (drawable == 0)) {
      return;
   }

   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return;

   LockDisplay(dpy);

   if ((priv->majorVersion > 1) || (priv->minorVersion >= 3)) {
      xGLXDestroyPbufferReq *req;

      GetReq(GLXDestroyPbuffer, req);
      req->reqType = opcode;
      req->glxCode = X_GLXDestroyPbuffer;
      req->pbuffer = (GLXPbuffer) drawable;
   }
   else {
      xGLXVendorPrivateWithReplyReq *vpreq;
      CARD32 *data;

      GetReqExtra(GLXVendorPrivateWithReply, 4, vpreq);
      data = (CARD32 *) (vpreq + 1);

      data[0] = (CARD32) drawable;

      vpreq->reqType = opcode;
      vpreq->glxCode = X_GLXVendorPrivateWithReply;
      vpreq->vendorCode = X_GLXvop_DestroyGLXPbufferSGIX;
   }

   UnlockDisplay(dpy);
   SyncHandle();

   DestroyDRIDrawable(dpy, drawable, GL_TRUE);

   return;
}
Exemple #17
0
/**
 * Destroy a non-pbuffer GLX drawable.
 *
 * \todo
 * This function needs to be modified to work with direct-rendering drivers.
 */
static void
DestroyDrawable(Display * dpy, GLXDrawable drawable, CARD32 glxCode)
{
   xGLXDestroyPbufferReq *req;
   CARD8 opcode;

   if ((dpy == NULL) || (drawable == 0)) {
      return;
   }


   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return;

   LockDisplay(dpy);

   GetReqExtra(GLXDestroyPbuffer, 4, req);
   req->reqType = opcode;
   req->glxCode = glxCode;
   req->pbuffer = (GLXPbuffer) drawable;

   UnlockDisplay(dpy);
   SyncHandle();

#if defined(GLX_DIRECT_RENDERING) && !defined(GLX_USE_APPLEGL)
   {
      int screen;
      __GLXdisplayPrivate *const priv = __glXInitialize(dpy);
      __GLXDRIdrawable *pdraw = GetGLXDRIDrawable(dpy, drawable, &screen);
      __GLXscreenConfigs *psc = &priv->screenConfigs[screen];

      if (pdraw != NULL) {
         (*pdraw->destroyDrawable) (pdraw);
         __glxHashDelete(psc->drawHash, drawable);
      }
   }
#endif

   return;
}
Exemple #18
0
/*
 * Return pointer to the __GLXvisualConfig specified by dpy, scrn and vid.
 * Return NULL if not found.
 */
static __GLXvisualConfig *
__driFindGlxConfig(Display *dpy, int scrn, VisualID vid)
{
    __GLXdisplayPrivate *priv;
    __GLXscreenConfigs *glxScrnConfigs;
    __GLXvisualConfig *glxConfigs;
    int numConfigs, i;

    priv = __glXInitialize(dpy);
    assert(priv);

    glxScrnConfigs = priv->screenConfigs;
    assert(glxScrnConfigs);

    numConfigs = glxScrnConfigs[scrn].numConfigs;
    glxConfigs = glxScrnConfigs[scrn].configs;

    for (i = 0; i < numConfigs; i++) {
        if (glxConfigs[i].vid == vid) {
            return glxConfigs +i;
        }
    }
    return NULL;
}
/**
 * Get a drawable's attribute.
 *
 * This function is used to implement \c glXGetSelectedEvent and
 * \c glXGetSelectedEventSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 *
 * \todo
 * The number of attributes returned is likely to be small, probably less than
 * 10.  Given that, this routine should try to use an array on the stack to
 * capture the reply rather than always calling Xmalloc.
 */
static int
GetDrawableAttribute(Display * dpy, GLXDrawable drawable,
                     int attribute, unsigned int *value)
{
   struct glx_display *priv;
   xGLXGetDrawableAttributesReply reply;
   CARD32 *data;
   CARD8 opcode;
   unsigned int length;
   unsigned int i;
   unsigned int num_attributes;
   GLboolean use_glx_1_3;

#if defined(GLX_DIRECT_RENDERING) && !defined(GLX_USE_APPLEGL)
   __GLXDRIdrawable *pdraw;
#endif

   if (dpy == NULL)
      return 0;

   /* Page 38 (page 52 of the PDF) of glxencode1.3.pdf says:
    *
    *     "If drawable is not a valid GLX drawable, a GLXBadDrawable error is
    *     generated."
    */
   if (drawable == 0) {
      __glXSendError(dpy, GLXBadDrawable, 0, X_GLXGetDrawableAttributes, false);
      return 0;
   }

   priv = __glXInitialize(dpy);
   if (priv == NULL)
      return 0;

   use_glx_1_3 = ((priv->majorVersion > 1) || (priv->minorVersion >= 3));

   *value = 0;


   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return 0;

#if defined(GLX_DIRECT_RENDERING) && !defined(GLX_USE_APPLEGL)
   pdraw = GetGLXDRIDrawable(dpy, drawable);

   if (attribute == GLX_BACK_BUFFER_AGE_EXT) {
      struct glx_context *gc = __glXGetCurrentContext();
      struct glx_screen *psc;

      /* The GLX_EXT_buffer_age spec says:
       *
       *   "If querying GLX_BACK_BUFFER_AGE_EXT and <draw> is not bound to
       *   the calling thread's current context a GLXBadDrawable error is
       *   generated."
       */
      if (pdraw == NULL || gc == &dummyContext || gc->currentDpy != dpy ||
         (gc->currentDrawable != drawable &&
         gc->currentReadable != drawable)) {
         __glXSendError(dpy, GLXBadDrawable, drawable,
                        X_GLXGetDrawableAttributes, false);
         return 0;
      }

      psc = pdraw->psc;

      if (psc->driScreen->getBufferAge != NULL)
         *value = psc->driScreen->getBufferAge(pdraw);

      return 0;
   }
#endif

   LockDisplay(dpy);

   if (use_glx_1_3) {
      xGLXGetDrawableAttributesReq *req;

      GetReq(GLXGetDrawableAttributes, req);
      req->reqType = opcode;
      req->glxCode = X_GLXGetDrawableAttributes;
      req->drawable = drawable;
   }
   else {
      xGLXVendorPrivateWithReplyReq *vpreq;

      GetReqExtra(GLXVendorPrivateWithReply, 4, vpreq);
      data = (CARD32 *) (vpreq + 1);
      data[0] = (CARD32) drawable;

      vpreq->reqType = opcode;
      vpreq->glxCode = X_GLXVendorPrivateWithReply;
      vpreq->vendorCode = X_GLXvop_GetDrawableAttributesSGIX;
   }

   _XReply(dpy, (xReply *) & reply, 0, False);

   if (reply.type == X_Error) {
      UnlockDisplay(dpy);
      SyncHandle();
      return 0;
   }

   length = reply.length;
   if (length) {
      num_attributes = (use_glx_1_3) ? reply.numAttribs : length / 2;
      data = malloc(length * sizeof(CARD32));
      if (data == NULL) {
         /* Throw data on the floor */
         _XEatData(dpy, length);
      }
      else {
         _XRead(dpy, (char *) data, length * sizeof(CARD32));

         /* Search the set of returned attributes for the attribute requested by
          * the caller.
          */
         for (i = 0; i < num_attributes; i++) {
            if (data[i * 2] == attribute) {
               *value = data[(i * 2) + 1];
               break;
            }
         }

#if defined(GLX_DIRECT_RENDERING) && !defined(GLX_USE_APPLEGL)
         if (pdraw != NULL) {
            if (!pdraw->textureTarget)
               pdraw->textureTarget =
                  determineTextureTarget((const int *) data, num_attributes);
            if (!pdraw->textureFormat)
               pdraw->textureFormat =
                  determineTextureFormat((const int *) data, num_attributes);
         }
#endif

         free(data);
      }
   }

   UnlockDisplay(dpy);
   SyncHandle();

   return 0;
}
Exemple #20
0
/**
 * Called via eglInitialize(), xdri_dpy->API.Initialize().
 */
static EGLBoolean
xdri_eglInitialize(_EGLDriver *drv, _EGLDisplay *dpy,
                   EGLint *minor, EGLint *major)
{
   struct xdri_egl_display *xdri_dpy;
   __GLXdisplayPrivate *dpyPriv;
   __GLXDRIdisplay *driDisplay;
   __GLXscreenConfigs *psc;
   EGLint first_id = 1;
   int scr;

   xdri_dpy = CALLOC_STRUCT(xdri_egl_display);
   if (!xdri_dpy)
      return _eglError(EGL_BAD_ALLOC, "eglInitialize");

   xdri_dpy->dpy = (Display *) dpy->NativeDisplay;
   if (!xdri_dpy->dpy) {
      xdri_dpy->dpy = XOpenDisplay(NULL);
      if (!xdri_dpy->dpy) {
         free(xdri_dpy);
         return _eglError(EGL_NOT_INITIALIZED, "eglInitialize");
      }
   }

   dpyPriv = __glXInitialize(xdri_dpy->dpy);
   if (!dpyPriv) {
      _eglLog(_EGL_WARNING, "failed to create GLX display");
      free(xdri_dpy);
      return _eglError(EGL_NOT_INITIALIZED, "eglInitialize");
   }

   driDisplay = __driCreateDisplay(dpyPriv, NULL);
   if (!driDisplay) {
      _eglLog(_EGL_WARNING, "failed to create DRI display");
      free(xdri_dpy);
      return _eglError(EGL_NOT_INITIALIZED, "eglInitialize");
   }

   scr = DefaultScreen(xdri_dpy->dpy);
   psc = &dpyPriv->screenConfigs[scr];

   xdri_dpy->dpyPriv = dpyPriv;
   xdri_dpy->driDisplay = driDisplay;
   xdri_dpy->psc = psc;
   xdri_dpy->scr = scr;

   psc->driScreen = driDisplay->createScreen(psc, scr, dpyPriv);
   if (!psc->driScreen) {
      _eglLog(_EGL_WARNING, "failed to create DRI screen #%d", scr);
      free(xdri_dpy);
      return _eglError(EGL_NOT_INITIALIZED, "eglInitialize");
   }

   /* add visuals and fbconfigs */
   first_id = create_configs(dpy, psc->visuals, first_id);
   create_configs(dpy, psc->configs, first_id);

   dpy->DriverData = xdri_dpy;
   dpy->ClientAPIsMask = (EGL_OPENGL_BIT |
                          EGL_OPENGL_ES_BIT |
                          EGL_OPENGL_ES2_BIT |
                          EGL_OPENVG_BIT);

   /* we're supporting EGL 1.4 */
   *minor = 1;
   *major = 4;

   return EGL_TRUE;
}
Exemple #21
0
/**
 * Create a pbuffer.
 *
 * This function is used to implement \c glXCreatePbuffer and
 * \c glXCreateGLXPbufferSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 *
 * \todo
 * This function needs to be modified to work with direct-rendering drivers.
 */
static GLXDrawable
CreatePbuffer(Display * dpy, const __GLcontextModes * fbconfig,
              unsigned int width, unsigned int height,
              const int *attrib_list, GLboolean size_in_attribs)
{
   __GLXdisplayPrivate *priv = __glXInitialize(dpy);
   GLXDrawable id = 0;
   CARD32 *data;
   CARD8 opcode;
   unsigned int i;

   i = 0;
   if (attrib_list) {
      while (attrib_list[i * 2])
         i++;
   }

   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return None;

   LockDisplay(dpy);
   id = XAllocID(dpy);

   if ((priv->majorVersion > 1) || (priv->minorVersion >= 3)) {
      xGLXCreatePbufferReq *req;
      unsigned int extra = (size_in_attribs) ? 0 : 2;

      GetReqExtra(GLXCreatePbuffer, (8 * (i + extra)), req);
      data = (CARD32 *) (req + 1);

      req->reqType = opcode;
      req->glxCode = X_GLXCreatePbuffer;
      req->screen = (CARD32) fbconfig->screen;
      req->fbconfig = fbconfig->fbconfigID;
      req->pbuffer = (GLXPbuffer) id;
      req->numAttribs = (CARD32) (i + extra);

      if (!size_in_attribs) {
         data[(2 * i) + 0] = GLX_PBUFFER_WIDTH;
         data[(2 * i) + 1] = width;
         data[(2 * i) + 2] = GLX_PBUFFER_HEIGHT;
         data[(2 * i) + 3] = height;
         data += 4;
      }
   }
   else {
      xGLXVendorPrivateReq *vpreq;

      GetReqExtra(GLXVendorPrivate, 20 + (8 * i), vpreq);
      data = (CARD32 *) (vpreq + 1);

      vpreq->reqType = opcode;
      vpreq->glxCode = X_GLXVendorPrivate;
      vpreq->vendorCode = X_GLXvop_CreateGLXPbufferSGIX;

      data[0] = (CARD32) fbconfig->screen;
      data[1] = (CARD32) fbconfig->fbconfigID;
      data[2] = (CARD32) id;
      data[3] = (CARD32) width;
      data[4] = (CARD32) height;
      data += 5;
   }

   (void) memcpy(data, attrib_list, sizeof(CARD32) * 2 * i);

   UnlockDisplay(dpy);
   SyncHandle();

   return id;
}
Exemple #22
0
/**
 * Create a non-pbuffer GLX drawable.
 *
 * \todo
 * This function needs to be modified to work with direct-rendering drivers.
 */
static GLXDrawable
CreateDrawable(Display * dpy, const __GLcontextModes * fbconfig,
               Drawable drawable, const int *attrib_list, CARD8 glxCode)
{
   xGLXCreateWindowReq *req;
   CARD32 *data;
   unsigned int i;
   CARD8 opcode;

   i = 0;
   if (attrib_list) {
      while (attrib_list[i * 2] != None)
         i++;
   }

   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return None;

   LockDisplay(dpy);
   GetReqExtra(GLXCreateWindow, 8 * i, req);
   data = (CARD32 *) (req + 1);

   req->reqType = opcode;
   req->glxCode = glxCode;
   req->screen = (CARD32) fbconfig->screen;
   req->fbconfig = fbconfig->fbconfigID;
   req->window = (CARD32) drawable;
   req->glxwindow = (GLXWindow) XAllocID(dpy);
   req->numAttribs = (CARD32) i;

   if (attrib_list)
      memcpy(data, attrib_list, 8 * i);

   UnlockDisplay(dpy);
   SyncHandle();

#if defined(GLX_DIRECT_RENDERING) && !defined(GLX_USE_APPLEGL)
   do {
      /* FIXME: Maybe delay __DRIdrawable creation until the drawable
       * is actually bound to a context... */

      __GLXdisplayPrivate *const priv = __glXInitialize(dpy);
      __GLXDRIdrawable *pdraw;
      __GLXscreenConfigs *psc;

      psc = &priv->screenConfigs[fbconfig->screen];
      if (psc->driScreen == NULL)
         break;
      pdraw = psc->driScreen->createDrawable(psc, drawable,
                                             req->glxwindow, fbconfig);
      if (pdraw == NULL) {
         fprintf(stderr, "failed to create drawable\n");
         break;
      }

      if (__glxHashInsert(psc->drawHash, req->glxwindow, pdraw)) {
         (*pdraw->destroyDrawable) (pdraw);
         return None;           /* FIXME: Check what we're supposed to do here... */
      }

      pdraw->textureTarget = determineTextureTarget(attrib_list, i);
      pdraw->textureFormat = determineTextureFormat(attrib_list, i);
   } while (0);
#endif

   return (GLXDrawable) req->glxwindow;
}
Exemple #23
0
/**
 * Get a drawable's attribute.
 *
 * This function is used to implement \c glXGetSelectedEvent and
 * \c glXGetSelectedEventSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 *
 * \todo
 * The number of attributes returned is likely to be small, probably less than
 * 10.  Given that, this routine should try to use an array on the stack to
 * capture the reply rather than always calling Xmalloc.
 *
 * \todo
 * This function needs to be modified to work with direct-rendering drivers.
 */
static int
GetDrawableAttribute(Display * dpy, GLXDrawable drawable,
                     int attribute, unsigned int *value)
{
   __GLXdisplayPrivate *priv;
   xGLXGetDrawableAttributesReply reply;
   CARD32 *data;
   CARD8 opcode;
   unsigned int length;
   unsigned int i;
   unsigned int num_attributes;
   GLboolean use_glx_1_3;

   if ((dpy == NULL) || (drawable == 0)) {
      return 0;
   }

   priv = __glXInitialize(dpy);
   use_glx_1_3 = ((priv->majorVersion > 1) || (priv->minorVersion >= 3));

   *value = 0;


   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return 0;

   LockDisplay(dpy);

   if (use_glx_1_3) {
      xGLXGetDrawableAttributesReq *req;

      GetReqExtra(GLXGetDrawableAttributes, 4, req);
      req->reqType = opcode;
      req->glxCode = X_GLXGetDrawableAttributes;
      req->drawable = drawable;
   }
   else {
      xGLXVendorPrivateWithReplyReq *vpreq;

      GetReqExtra(GLXVendorPrivateWithReply, 4, vpreq);
      data = (CARD32 *) (vpreq + 1);
      data[0] = (CARD32) drawable;

      vpreq->reqType = opcode;
      vpreq->glxCode = X_GLXVendorPrivateWithReply;
      vpreq->vendorCode = X_GLXvop_GetDrawableAttributesSGIX;
   }

   _XReply(dpy, (xReply *) & reply, 0, False);

   if (reply.type == X_Error) {
      UnlockDisplay(dpy);
      SyncHandle();
      return 0;
   }

   length = reply.length;
   if (length) {
      num_attributes = (use_glx_1_3) ? reply.numAttribs : length / 2;
      data = (CARD32 *) Xmalloc(length * sizeof(CARD32));
      if (data == NULL) {
         /* Throw data on the floor */
         _XEatData(dpy, length);
      }
      else {
         _XRead(dpy, (char *) data, length * sizeof(CARD32));

         /* Search the set of returned attributes for the attribute requested by
          * the caller.
          */
         for (i = 0; i < num_attributes; i++) {
            if (data[i * 2] == attribute) {
               *value = data[(i * 2) + 1];
               break;
            }
         }

#if defined(GLX_DIRECT_RENDERING) && !defined(GLX_USE_APPLEGL)
         {
            __GLXDRIdrawable *pdraw = GetGLXDRIDrawable(dpy, drawable, NULL);

            if (pdraw != NULL && !pdraw->textureTarget)
               pdraw->textureTarget =
                  determineTextureTarget((const int *) data, num_attributes);
            if (pdraw != NULL && !pdraw->textureFormat)
               pdraw->textureFormat =
                  determineTextureFormat((const int *) data, num_attributes);
         }
#endif

         Xfree(data);
      }
   }

   UnlockDisplay(dpy);
   SyncHandle();

   return 0;
}
Exemple #24
0
/**
 * Sends a GLX protocol message to the specified display to make the context
 * and the drawables current.
 *
 * \param dpy     Display to send the message to.
 * \param opcode  Major opcode value for the display.
 * \param gc_id   Context tag for the context to be made current.
 * \param draw    Drawable ID for the "draw" drawable.
 * \param read    Drawable ID for the "read" drawable.
 * \param reply   Space to store the X-server's reply.
 *
 * \warning
 * This function assumes that \c dpy is locked with \c LockDisplay on entry.
 */
static Bool
SendMakeCurrentRequest(Display * dpy, CARD8 opcode,
                       GLXContextID gc_id, GLXContextTag gc_tag,
                       GLXDrawable draw, GLXDrawable read,
                       xGLXMakeCurrentReply * reply)
{
   Bool ret;


   LockDisplay(dpy);

   if (draw == read) {
      xGLXMakeCurrentReq *req;

      GetReq(GLXMakeCurrent, req);
      req->reqType = opcode;
      req->glxCode = X_GLXMakeCurrent;
      req->drawable = draw;
      req->context = gc_id;
      req->oldContextTag = gc_tag;
   }
   else {
      __GLXdisplayPrivate *priv = __glXInitialize(dpy);

      /* If the server can support the GLX 1.3 version, we should
       * perfer that.  Not only that, some servers support GLX 1.3 but
       * not the SGI extension.
       */

      if ((priv->majorVersion > 1) || (priv->minorVersion >= 3)) {
         xGLXMakeContextCurrentReq *req;

         GetReq(GLXMakeContextCurrent, req);
         req->reqType = opcode;
         req->glxCode = X_GLXMakeContextCurrent;
         req->drawable = draw;
         req->readdrawable = read;
         req->context = gc_id;
         req->oldContextTag = gc_tag;
      }
      else {
         xGLXVendorPrivateWithReplyReq *vpreq;
         xGLXMakeCurrentReadSGIReq *req;

         GetReqExtra(GLXVendorPrivateWithReply,
                     sz_xGLXMakeCurrentReadSGIReq -
                     sz_xGLXVendorPrivateWithReplyReq, vpreq);
         req = (xGLXMakeCurrentReadSGIReq *) vpreq;
         req->reqType = opcode;
         req->glxCode = X_GLXVendorPrivateWithReply;
         req->vendorCode = X_GLXvop_MakeCurrentReadSGI;
         req->drawable = draw;
         req->readable = read;
         req->context = gc_id;
         req->oldContextTag = gc_tag;
      }
   }

   ret = _XReply(dpy, (xReply *) reply, 0, False);

   UnlockDisplay(dpy);
   SyncHandle();

   return ret;
}
/**
 * Get a drawable's attribute.
 *
 * This function is used to implement \c glXGetSelectedEvent and
 * \c glXGetSelectedEventSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 *
 * \todo
 * The number of attributes returned is likely to be small, probably less than
 * 10.  Given that, this routine should try to use an array on the stack to
 * capture the reply rather than always calling Xmalloc.
 *
 * \todo
 * This function needs to be modified to work with direct-rendering drivers.
 */
static int
GetDrawableAttribute( Display *dpy, GLXDrawable drawable,
		      int attribute, unsigned int *value )
{
   __GLXdisplayPrivate *priv = __glXInitialize(dpy);
   xGLXGetDrawableAttributesReply reply;
   CARD32 * data;
   unsigned int length;
   unsigned int i;
   unsigned int num_attributes;
   GLboolean use_glx_1_3 = ((priv->majorVersion > 1)
			    || (priv->minorVersion >= 3));


   if ( (dpy == NULL) || (drawable == 0) ) {
      return 0;
   }

   
   LockDisplay(dpy);

   if ( use_glx_1_3 ) {
      xGLXGetDrawableAttributesReq *req;

      GetReqExtra( GLXGetDrawableAttributes, 4, req );
      req->reqType = __glXSetupForCommand(dpy);
      req->glxCode = X_GLXGetDrawableAttributes;
      req->drawable = drawable;
   }
   else {
      xGLXVendorPrivateWithReplyReq *vpreq;

      GetReqExtra( GLXVendorPrivateWithReply, 4, vpreq );
      data = (CARD32 *) (vpreq + 1);
      data[0] = (CARD32) drawable;

      vpreq->reqType = __glXSetupForCommand(dpy);
      vpreq->glxCode = X_GLXVendorPrivateWithReply;
      vpreq->vendorCode = X_GLXvop_GetDrawableAttributesSGIX;
   }

   _XReply(dpy, (xReply*) &reply, 0, False);

   length = reply.length;
   num_attributes = (use_glx_1_3) ? reply.numAttribs : length / 2;
   data = (CARD32 *) Xmalloc( length * sizeof(CARD32) );
   if ( data == NULL ) {
      /* Throw data on the floor */
      _XEatData(dpy, length);
   } else {
      _XRead(dpy, (char *)data, length * sizeof(CARD32) );
   }

   UnlockDisplay(dpy);
   SyncHandle();


   /* Search the set of returned attributes for the attribute requested by
    * the caller.
    */

   for ( i = 0 ; i < num_attributes ; i++ ) {
      if ( data[i*2] == attribute ) {
	 *value = data[ (i*2) + 1 ];
	 break;
      }
   }

   Xfree( data );

   return 0;
}
Exemple #26
0
/**
 * Change a drawable's attribute.
 *
 * This function is used to implement \c glXSelectEvent and
 * \c glXSelectEventSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 */
static void
ChangeDrawableAttribute(Display * dpy, GLXDrawable drawable,
                        const CARD32 * attribs, size_t num_attribs)
{
   struct glx_display *priv = __glXInitialize(dpy);
#ifdef GLX_DIRECT_RENDERING
   __GLXDRIdrawable *pdraw;
#endif
   CARD32 *output;
   CARD8 opcode;
   int i;

   if ((dpy == NULL) || (drawable == 0)) {
      return;
   }

   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return;

   LockDisplay(dpy);

   if ((priv->majorVersion > 1) || (priv->minorVersion >= 3)) {
      xGLXChangeDrawableAttributesReq *req;

      GetReqExtra(GLXChangeDrawableAttributes, 8 * num_attribs, req);
      output = (CARD32 *) (req + 1);

      req->reqType = opcode;
      req->glxCode = X_GLXChangeDrawableAttributes;
      req->drawable = drawable;
      req->numAttribs = (CARD32) num_attribs;
   }
   else {
      xGLXVendorPrivateWithReplyReq *vpreq;

      GetReqExtra(GLXVendorPrivateWithReply, 8 + (8 * num_attribs), vpreq);
      output = (CARD32 *) (vpreq + 1);

      vpreq->reqType = opcode;
      vpreq->glxCode = X_GLXVendorPrivateWithReply;
      vpreq->vendorCode = X_GLXvop_ChangeDrawableAttributesSGIX;

      output[0] = (CARD32) drawable;
      output[1] = num_attribs;
      output += 2;
   }

   (void) memcpy(output, attribs, sizeof(CARD32) * 2 * num_attribs);

   UnlockDisplay(dpy);
   SyncHandle();

#ifdef GLX_DIRECT_RENDERING
   pdraw = GetGLXDRIDrawable(dpy, drawable);

   if (!pdraw)
      return;

   for (i = 0; i < num_attribs; i++) {
      switch(attribs[i * 2]) {
      case GLX_EVENT_MASK:
	 /* Keep a local copy for masking out DRI2 proto events as needed */
	 pdraw->eventMask = attribs[i * 2 + 1];
	 break;
      }
   }
#endif

   return;
}
Exemple #27
0
/**
 * Create a pbuffer.
 *
 * This function is used to implement \c glXCreatePbuffer and
 * \c glXCreateGLXPbufferSGIX.
 *
 * \note
 * This function dynamically determines whether to use the SGIX_pbuffer
 * version of the protocol or the GLX 1.3 version of the protocol.
 */
static GLXDrawable
CreatePbuffer(Display * dpy, struct glx_config *config,
              unsigned int width, unsigned int height,
              const int *attrib_list, GLboolean size_in_attribs)
{
   struct glx_display *priv = __glXInitialize(dpy);
   GLXDrawable id = 0;
   CARD32 *data;
   CARD8 opcode;
   unsigned int i;
   Pixmap pixmap;
   GLboolean glx_1_3 = GL_FALSE;

   i = 0;
   if (attrib_list) {
      while (attrib_list[i * 2])
         i++;
   }

   opcode = __glXSetupForCommand(dpy);
   if (!opcode)
      return None;

   LockDisplay(dpy);
   id = XAllocID(dpy);

   if ((priv->majorVersion > 1) || (priv->minorVersion >= 3)) {
      xGLXCreatePbufferReq *req;
      unsigned int extra = (size_in_attribs) ? 0 : 2;

      glx_1_3 = GL_TRUE;

      GetReqExtra(GLXCreatePbuffer, (8 * (i + extra)), req);
      data = (CARD32 *) (req + 1);

      req->reqType = opcode;
      req->glxCode = X_GLXCreatePbuffer;
      req->screen = config->screen;
      req->fbconfig = config->fbconfigID;
      req->pbuffer = id;
      req->numAttribs = i + extra;

      if (!size_in_attribs) {
         data[(2 * i) + 0] = GLX_PBUFFER_WIDTH;
         data[(2 * i) + 1] = width;
         data[(2 * i) + 2] = GLX_PBUFFER_HEIGHT;
         data[(2 * i) + 3] = height;
         data += 4;
      }
   }
   else {
      xGLXVendorPrivateReq *vpreq;

      GetReqExtra(GLXVendorPrivate, 20 + (8 * i), vpreq);
      data = (CARD32 *) (vpreq + 1);

      vpreq->reqType = opcode;
      vpreq->glxCode = X_GLXVendorPrivate;
      vpreq->vendorCode = X_GLXvop_CreateGLXPbufferSGIX;

      data[0] = config->screen;
      data[1] = config->fbconfigID;
      data[2] = id;
      data[3] = width;
      data[4] = height;
      data += 5;
   }

   (void) memcpy(data, attrib_list, sizeof(CARD32) * 2 * i);

   UnlockDisplay(dpy);
   SyncHandle();

   pixmap = XCreatePixmap(dpy, RootWindow(dpy, config->screen),
			  width, height, config->rgbBits);

   if (!CreateDRIDrawable(dpy, config, pixmap, id, attrib_list, i)) {
      CARD32 o = glx_1_3 ? X_GLXDestroyPbuffer : X_GLXvop_DestroyGLXPbufferSGIX;
      XFreePixmap(dpy, pixmap);
      protocolDestroyDrawable(dpy, id, o);
      id = None;
   }

   return id;
}