Add glXCreateNewContext support in Xephyr #54798

Similar to how we intercept and pass through CreateContext, also pass
through newer CreateNewContext requests.

Fixes Clutter → Xephyr → VirtualBox.

Signed-off-by: Frederic Plourde <frederic.plourde@collabora.com>
Reviewed-by: Daniel Stone <daniel@fooishbar.org>
This commit is contained in:
Frederic Plourde 2012-09-12 10:48:32 -04:00 committed by Daniel Stone
parent 11afebc92c
commit e3903a9383
3 changed files with 107 additions and 17 deletions

View File

@ -61,6 +61,8 @@ int ephyrGLXGetFBConfigsSGIX(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXGetFBConfigsSGIXSwap(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXCreateContext(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXCreateContextSwap(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXCreateNewContext(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXCreateNewContextSwap(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXDestroyContext(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXDestroyContextSwap(__GLXclientState * a_cl, GLbyte * a_pc);
int ephyrGLXMakeCurrent(__GLXclientState * a_cl, GLbyte * a_pc);
@ -112,6 +114,9 @@ ephyrHijackGLXExtension(void)
dispatch_functions[X_GLXCreateContext][0] = ephyrGLXCreateContext;
dispatch_functions[X_GLXCreateContext][1] = ephyrGLXCreateContextSwap;
dispatch_functions[X_GLXCreateNewContext][0] = ephyrGLXCreateNewContext;
dispatch_functions[X_GLXCreateNewContext][1] = ephyrGLXCreateNewContextSwap;
dispatch_functions[X_GLXDestroyContext][0] = ephyrGLXDestroyContext;
dispatch_functions[X_GLXDestroyContext][1] = ephyrGLXDestroyContextSwap;
@ -459,7 +464,8 @@ ephyrGLXCreateContextReal(xGLXCreateContextReq * a_req, Bool a_do_swap)
if (!ephyrHostGLXCreateContext(a_req->screen,
host_w_attrs.visualid,
a_req->context,
a_req->shareList, a_req->isDirect)) {
a_req->shareList, 0,
a_req->isDirect, X_GLXCreateContext)) {
EPHYR_LOG_ERROR("ephyrHostGLXCreateContext() failed\n");
goto out;
}
@ -469,6 +475,45 @@ ephyrGLXCreateContextReal(xGLXCreateContextReq * a_req, Bool a_do_swap)
return res;
}
static int
ephyrGLXCreateNewContextReal(xGLXCreateNewContextReq * a_req, Bool a_do_swap)
{
int res = BadImplementation;
__GLX_DECLARE_SWAP_VARIABLES;
EPHYR_RETURN_VAL_IF_FAIL(a_req, BadValue);
EPHYR_LOG("enter\n");
if (a_do_swap) {
__GLX_SWAP_SHORT(&a_req->length);
__GLX_SWAP_INT(&a_req->context);
__GLX_SWAP_INT(&a_req->fbconfig);
__GLX_SWAP_INT(&a_req->screen);
__GLX_SWAP_INT(&a_req->renderType);
__GLX_SWAP_INT(&a_req->shareList);
}
EPHYR_LOG("context creation requested. localid:%d, "
"screen:%d, fbconfig:%d, renderType:%d, direct:%d\n",
(int) a_req->context, (int) a_req->screen,
(int) a_req->fbconfig, (int) a_req->renderType,
(int) a_req->isDirect);
if (!ephyrHostGLXCreateContext(a_req->screen,
a_req->fbconfig,
a_req->context,
a_req->shareList, a_req->renderType,
a_req->isDirect, X_GLXCreateNewContext)) {
EPHYR_LOG_ERROR("ephyrHostGLXCreateNewContext() failed\n");
goto out;
}
res = Success;
out:
EPHYR_LOG("leave\n");
return res;
}
int
ephyrGLXCreateContext(__GLXclientState * cl, GLbyte * pc)
{
@ -485,6 +530,22 @@ ephyrGLXCreateContextSwap(__GLXclientState * cl, GLbyte * pc)
return ephyrGLXCreateContextReal(req, TRUE);
}
int
ephyrGLXCreateNewContext(__GLXclientState * cl, GLbyte * pc)
{
xGLXCreateNewContextReq *req = (xGLXCreateNewContextReq *) pc;
return ephyrGLXCreateNewContextReal(req, FALSE);
}
int
ephyrGLXCreateNewContextSwap(__GLXclientState * cl, GLbyte * pc)
{
xGLXCreateNewContextReq *req = (xGLXCreateNewContextReq *) pc;
return ephyrGLXCreateNewContextReal(req, TRUE);
}
static int
ephyrGLXDestroyContextReal(__GLXclientState * a_cl,
GLbyte * a_pc, Bool a_do_swap)

View File

@ -439,17 +439,20 @@ ephyrHostGLXSendClientInfo(int32_t a_major, int32_t a_minor,
Bool
ephyrHostGLXCreateContext(int a_screen,
int a_visual_id,
int a_generic_id,
int a_context_id,
int a_share_list_ctxt_id, Bool a_direct)
int a_share_list_ctxt_id,
int a_render_type,
Bool a_direct,
int code)
{
Bool is_ok = FALSE;
Display *dpy = hostx_get_display();
int major_opcode = 0, remote_context_id = 0;
xGLXCreateContextReq *req;
EPHYR_LOG("enter. screen:%d, visual:%d, contextid:%d, direct:%d\n",
a_screen, a_visual_id, a_context_id, a_direct);
EPHYR_LOG("enter. screen:%d, generic_id:%d, contextid:%d, rendertype:%d, "
"direct:%d\n", a_screen, a_generic_id, a_context_id,
a_render_type, a_direct);
if (!hostx_allocate_resource_id_peer(a_context_id, &remote_context_id)) {
EPHYR_LOG_ERROR("failed to peer the context id %d host X",
@ -464,15 +467,38 @@ ephyrHostGLXCreateContext(int a_screen,
LockDisplay(dpy);
/* Send the glXCreateContext request */
GetReq(GLXCreateContext, req);
req->reqType = major_opcode;
req->glxCode = X_GLXCreateContext;
req->context = remote_context_id;
req->visual = a_visual_id;
req->screen = DefaultScreen(dpy);
req->shareList = a_share_list_ctxt_id;
req->isDirect = a_direct;
switch (code) {
case X_GLXCreateContext: {
/* Send the glXCreateContext request */
xGLXCreateContextReq *req;
GetReq(GLXCreateContext, req);
req->reqType = major_opcode;
req->glxCode = X_GLXCreateContext;
req->context = remote_context_id;
req->visual = a_generic_id;
req->screen = DefaultScreen(dpy);
req->shareList = a_share_list_ctxt_id;
req->isDirect = a_direct;
}
case X_GLXCreateNewContext: {
/* Send the glXCreateNewContext request */
xGLXCreateNewContextReq *req;
GetReq(GLXCreateNewContext, req);
req->reqType = major_opcode;
req->glxCode = X_GLXCreateNewContext;
req->context = remote_context_id;
req->fbconfig = a_generic_id;
req->screen = DefaultScreen(dpy);
req->renderType = a_render_type;
req->shareList = a_share_list_ctxt_id;
req->isDirect = a_direct;
}
default:
/* This should never be reached !*/
EPHYR_LOG("Internal error! Invalid CreateContext code!\n");
}
UnlockDisplay(dpy);
SyncHandle();

View File

@ -55,9 +55,12 @@ Bool ephyrHostGLXGetMajorOpcode(int32_t * a_opcode);
Bool ephyrHostGLXSendClientInfo(int32_t a_major, int32_t a_minor,
const char *a_extension_list);
Bool ephyrHostGLXCreateContext(int a_screen,
int a_visual_id,
int a_generic_id,
int a_context_id,
int a_shared_list_ctx_id, Bool a_direct);
int a_share_list_ctxt_id,
int a_render_type,
Bool a_direct,
int code);
Bool ephyrHostDestroyContext(int a_ctxt_id);