Commit af4c1749 authored by idr's avatar idr
Browse files

Enable extensions not specifically listed in the server's extension

string but are implied by the core GL version number.  This code is
not actually enabled, but it's all there.  Comments in glGetString (in
single2.c) explain it all.
parent 5476daf9
......@@ -534,6 +534,18 @@ struct __GLXcontextRec {
* Stored value for \c glXQueryContext attribute \c GLX_RENDER_TYPE.
*/
int renderType;
/**
* \name Raw server GL version
*
* True core GL version supported by the server. This is the raw value
* returned by the server, and it may not reflect what is actually
* supported (or reported) by the client-side library.
*/
/*@{*/
int server_major; /**< Major version number. */
int server_minor; /**< Minor version number. */
/*@}*/
};
#define __glXSetError(gc,code) \
......
......@@ -670,3 +670,16 @@ __glXCalculateUsableGLExtensions( __GLXcontext * gc,
gc->extensions = (unsigned char *)
__glXGetStringFromTable( known_gl_extensions, usable );
}
/**
* Calculates the maximum core GL version that can be supported for indirect
* rendering.
*/
void
__glXGetGLVersion( int * major_version, int * minor_version )
{
__glXExtensionsCtr();
*major_version = gl_major;
*minor_version = gl_minor;
}
......@@ -217,6 +217,7 @@ extern void __glXCalculateUsableExtensions( __GLXscreenConfigs *psc,
extern void __glXScrEnableExtension( __GLXscreenConfigs *psc, const char * name );
extern void __glXCalculateUsableGLExtensions( __GLXcontext * gc,
const char * server_string, int major_version, int minor_version );
extern void __glXGetGLVersion( int * major_version, int * minor_version );
/* Source-level backwards compatibility with old drivers. They won't
* find the respective functions, though.
......
......@@ -38,6 +38,7 @@
#include <stdio.h>
#include "glxclient.h"
#include "packsingle.h"
#include "glxextensions.h"
/* Used for GL_ARB_transpose_matrix */
static void TransposeMatrixf(GLfloat m[16])
......@@ -848,6 +849,25 @@ void glFinish(void)
__GLX_SINGLE_END();
}
/**
* Extract the major and minor version numbers from a version string.
*/
static void
version_from_string( const char * ver,
int * major_version, int * minor_version )
{
const char * end;
long major;
long minor;
major = strtol( ver, (char **) & end, 10 );
minor = strtol( end + 1, NULL, 10 );
*major_version = major;
*minor_version = minor;
}
const GLubyte *glGetString(GLenum name)
{
__GLX_SINGLE_DECLARE_VARIABLES();
......@@ -881,7 +901,25 @@ const GLubyte *glGetString(GLenum name)
** Get requested string from server
*/
__GLX_SINGLE_LOAD_VARIABLES();
__GLX_SINGLE_BEGIN(X_GLsop_GetString,4);
/* This is usually done by the __GLX_SINGLE_BEGIN macro. However, that
* macro actually starts a new block and the __GLX_SINGLE_END macro closes
* it. The problem is that this function would need to use
* __GLX_SINGLE_END macro in two places, and both places are inside other
* blocks. The resulting code would either not compile or not work
* correctly.
*/
(void) __glXFlushRenderBuffer( gc, pc );
LockDisplay(dpy);
GetReqExtra( GLXSingle, 4, req );
req->reqType = gc->majorOpcode;
req->glxCode = X_GLsop_GetString;
req->contextTag = gc->currentContextTag;
pc = ((GLubyte *)(req) + sz_xGLXSingleReq);
__GLX_SINGLE_PUT_LONG(0,name);
__GLX_SINGLE_READ_XREPLY();
__GLX_SINGLE_GET_SIZE(compsize);
......@@ -890,55 +928,107 @@ const GLubyte *glGetString(GLenum name)
/* Throw data on the floor */
_XEatData(dpy, compsize);
__glXSetError(gc, GL_OUT_OF_MEMORY);
UnlockDisplay(dpy);
SyncHandle();
} else {
__GLX_SINGLE_GET_CHAR_ARRAY(s,compsize);
UnlockDisplay(dpy);
SyncHandle();
/*
** Update local cache
*/
switch(name) {
case GL_VENDOR:
case GL_VENDOR:
gc->vendor = s;
break;
case GL_RENDERER:
case GL_RENDERER:
gc->renderer = s;
break;
case GL_VERSION: {
float server_version = strtof(s, NULL);
float client_version = strtof(__glXGLClientVersion, NULL);
if ( server_version <= client_version ) {
case GL_VERSION: {
int client_major;
int client_minor;
version_from_string( (char *) s,
& gc->server_major, & gc->server_minor );
__glXGetGLVersion( & client_major, & client_minor );
if ( (gc->server_major < client_major)
|| ((gc->server_major == client_major)
&& (gc->server_minor <= client_minor)) ) {
gc->version = s;
}
else {
}
else {
gc->version = Xmalloc( strlen(__glXGLClientVersion)
+ strlen((char *)s) + 4 );
if ( gc->version == NULL ) {
/* If we couldn't allocate memory for the new string,
* make a best-effort and just copy the client-side version
* to the string and use that. It probably doesn't
* matter what is done here. If there not memory available
* for a short string, the system is probably going to die
* soon anyway.
*/
strcpy((char *)s, __glXGLClientVersion);
/* If we couldn't allocate memory for the new string,
* make a best-effort and just copy the client-side version
* to the string and use that. It probably doesn't
* matter what is done here. If there not memory available
* for a short string, the system is probably going to die
* soon anyway.
*/
strcpy((char *)s, __glXGLClientVersion);
}
else {
sprintf( (char *)gc->version, "%s (%s)", __glXGLClientVersion, s );
Xfree( s );
s = gc->version;
sprintf( (char *)gc->version, "%s (%s)", __glXGLClientVersion, s );
Xfree( s );
s = gc->version;
}
}
break;
}
case GL_EXTENSIONS:
__glXCalculateUsableGLExtensions( gc, s, 1, 0 );
}
break;
}
case GL_EXTENSIONS: {
int major = 1;
int minor = 0;
/* This code is currently disabled. I was reminded that some
* vendors intentionally exclude some extensions from their
* extension string that are part of the core version they
* advertise. In particular, on Nvidia drivers this means that
* the functionality is supported by the driver, but is not
* hardware accelerated. For example, a TNT will show core
* version 1.5, but most of the post-1.2 functionality is a
* software fallback.
*
* I don't want to break applications that rely on this odd
* behavior. At the same time, the code is written and tested,
* so I didn't want to throw it away. Therefore, the code is here
* but disabled. In the future, we may wish to and an environment
* variable to enable it.
*/
#if 0
/* Call glGetString just to make sure that gc->server_major and
* gc->server_minor are set. This version may be higher than we
* can completely support, but it may imply support for some
* extensions that we can support.
*
* For example, at the time of this writing, the client-side
* library only supports upto core GL version 1.2. However, cubic
* textures, multitexture, multisampling, and some other 1.3
* features are supported. If the server reports back version
* 1.3, but does not report all of those extensions, we will
* enable them.
*/
(void *) glGetString( GL_VERSION );
major = gc->server_major,
minor = gc->server_minor;
#endif
__glXCalculateUsableGLExtensions( gc, (char *) s, major, minor );
XFree( s );
s = gc->extensions;
break;
}
}
}
__GLX_SINGLE_END();
return s;
}
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment