Ian Romanick wrote:

Here's an updated version of that patch. There are some significant differences.

I hate it when I do that....

Index: src/mesa/glapi/gl_procs.py
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/glapi/gl_procs.py,v
retrieving revision 1.1
diff -u -d -r1.1 gl_procs.py
--- a/src/mesa/glapi/gl_procs.py        18 May 2004 18:33:40 -0000      1.1
+++ b/src/mesa/glapi/gl_procs.py        24 May 2004 23:04:12 -0000
@@ -36,48 +36,137 @@
 class PrintGlProcs(gl_XML.FilterGLAPISpecBase):
        name = "gl_procs.py (from Mesa)"
 
-       def __init__(self):
+       def __init__(self, long_strings):
+               self.long_strings = long_strings
                gl_XML.FilterGLAPISpecBase.__init__(self)
                self.license = license.bsd_license_template % ( \
 """Copyright (C) 1999-2001  Brian Paul   All Rights Reserved.
 (C) Copyright IBM Corporation 2004""", "BRIAN PAUL, IBM")
 
+
        def printRealHeader(self):
-               print ''
                print '/* This file is only included by glapi.c and is used for'
                print ' * the GetProcAddress() function'
                print ' */'
                print ''
-               print 'static const struct name_address_offset static_functions[] = {'
+               print 'typedef struct {'
+               print '    int Name_offset;'
+               print '#ifdef NEED_FUNCTION_POINTER'
+               print '    void * Address;'
+               print '#endif'
+               print '    unsigned int Offset;'
+               print '} glprocs_table_t;'
+               print ''
+               print '#ifdef NEED_FUNCTION_POINTER'
+               print '#  define NAME_FUNC_OFFSET(n,f,o) { n , gl ## f , o }'
+               print '#else'
+               print '#  define NAME_FUNC_OFFSET(n,f,o) { n , o }'
+               print '#endif'
+               print ''
                return
 
        def printRealFooter(self):
-               print '   { NULL, NULL, 0 }  /* end of list marker */'
-               print '};'
+               print ''
+               print '#undef NAME_FUNC_OFFSET'
                return
 
-       def printFunction(self, f):
-               print '   { "gl%s", (GLvoid *) gl%s, _gloffset_%s },' \
-                       % (f.name, f.name, f.real_name)
+       def printFunctionString(self, f):
+               if self.long_strings:
+                       print '    "gl%s\\0"' % (f.name)
+               else:
+                       print "    'g','l',",
+                       for c in f.name:
+                               print "'%s'," % (c),
+                       
+                       print "'\\0',"
+
+       def printFunctionOffset(self, f, offset_of_name):
+               print '    NAME_FUNC_OFFSET( % 5u, %s, _gloffset_%s ),' % 
(offset_of_name, f.name, f.real_name)
+
+
+       def printFunctions(self):
+               print ''
+               if self.long_strings:
+                       print 'static const char gl_string_table[] ='
+               else:
+                       print 'static const char gl_string_table[] = {'
+
+               keys = self.functions.keys()
+               keys.sort()
+               for k in keys:
+                       if k < 0: continue
+                       self.printFunctionString(self.functions[k])
+
+               keys.reverse()
+               for k in keys:
+                       if k >= -1: continue
+                       self.printFunctionString(self.functions[k])
+
+               if self.long_strings:
+                       print '    ;'
+               else:
+                       print '};'
+
+               print ''
+               print 'static const glprocs_table_t static_functions[] = {'
+
+               keys = self.functions.keys()
+               keys.sort()
+               base_offset = 0
+               for k in keys:
+                       if k < 0: continue
+                       self.printFunctionOffset(self.functions[k], base_offset)
+
+                       # The length of the function's name, plus 2 for "gl",
+                       # plus 1 for the NUL.
+
+                       base_offset += len(self.functions[k].name) + 3
+
+               keys.reverse()
+               for k in keys:
+                       if k >= -1: continue
+                       self.printFunctionOffset(self.functions[k], base_offset)
+
+                       # The length of the function's name, plus 2 for "gl",
+                       # plus 1 for the NUL.
+
+                       base_offset += len(self.functions[k].name) + 3
+
+               print '    NAME_FUNC_OFFSET( -1, NULL, -1 )'
+               print '};'
+               return
 
 
 def show_usage():
-       print "Usage: %s [-f input_file_name]" % sys.argv[0]
+       print "Usage: %s [-f input_file_name] [-m mode]" % sys.argv[0]
+       print "mode can be one of:"
+       print "    long  - Create code for compilers that can handle very "
+       print "            long string constants. (default)"
+       print "    short - Create code for compilers that can only handle "
+       print "            ANSI C89 string constants."
        sys.exit(1)
 
 if __name__ == '__main__':
        file_name = "gl_API.xml"
     
        try:
-               (args, trail) = getopt.getopt(sys.argv[1:], "f:")
+               (args, trail) = getopt.getopt(sys.argv[1:], "f:m:")
        except Exception,e:
                show_usage()
 
+       long_string = 1
        for (arg,val) in args:
                if arg == "-f":
                        file_name = val
+               elif arg == "-m":
+                       if val == "short":
+                               long_string = 0
+                       elif val == "long":
+                               long_string = 1
+                       else:
+                               show_usage()
 
-       dh = PrintGlProcs()
+       dh = PrintGlProcs( long_string )
 
        parser = make_parser()
        parser.setFeature(feature_namespaces, 0)
Index: src/mesa/glapi/gl_x86_asm.py
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/glapi/gl_x86_asm.py,v
retrieving revision 1.1
diff -u -d -r1.1 gl_x86_asm.py
--- a/src/mesa/glapi/gl_x86_asm.py      18 May 2004 18:33:40 -0000      1.1
+++ b/src/mesa/glapi/gl_x86_asm.py      24 May 2004 23:04:12 -0000
@@ -77,15 +77,57 @@
                print '#define GLOBL_FN(x) GLOBL x'
                print '#endif'
                print ''
-               print '#define GL_STUB(fn,off,stack)\t\t\t\t\\'
+               print '#if defined(PTHREADS)'
+               print '#  define GL_STUB(fn,off,fn_alt)\t\t\t\t\\'
                print 'ALIGNTEXT16;\t\t\t\t\t\t\\'
-               print 'GLOBL_FN(GL_PREFIX(fn, fn ## @ ## stack));\t\t\\'
-               print 'GL_PREFIX(fn, fn ## @ ## stack):\t\t\t\\'
+               print 'GLOBL_FN(GL_PREFIX(fn, fn_alt));\t\t\\'
+               print 'GL_PREFIX(fn, fn_alt):\t\t\t\\'
                print '\tMOV_L(CONTENT(GLNAME(_glapi_Dispatch)), EAX) ;\t\\'
+               print '\tTEST_L(EAX, EAX) ;\t\t\t\t\\'
+               print '\tJE(1f) ;\t\t\t\t\t\\'
+               print '\tJMP(GL_OFFSET(off)) ;\t\t\t\t\\'
+               print '1:\tCALL(get_dispatch) ;\t\t\t\t\\'
                print '\tJMP(GL_OFFSET(off))'
+               print '#elif defined(THREADS)'
+               print '#  define GL_STUB(fn,off,fn_alt)\t\t\t\t\\'
+               print 'ALIGNTEXT16;\t\t\t\t\t\t\\'
+               print 'GLOBL_FN(GL_PREFIX(fn, fn_alt));\t\t\\'
+               print 'GL_PREFIX(fn, fn_alt):\t\t\t\\'
+               print '\tMOV_L(CONTENT(GLNAME(_glapi_Dispatch)), EAX) ;\t\\'
+               print '\tTEST_L(EAX, EAX) ;\t\t\t\t\\'
+               print '\tJE(1f) ;\t\t\t\t\t\\'
+               print '\tJMP(GL_OFFSET(off)) ;\t\t\t\t\\'
+               print '1:\tCALL(_glapi_get_dispatch) ;\t\t\t\t\\'
+               print '\tJMP(GL_OFFSET(off))'
+               print '#else /* Non-threaded version. */'
+               print '#  define GL_STUB(fn,off,fn_alt)\t\t\t\t\\'
+               print 'ALIGNTEXT16;\t\t\t\t\t\t\\'
+               print 'GLOBL_FN(GL_PREFIX(fn, fn_alt));\t\t\\'
+               print 'GL_PREFIX(fn, fn_alt):\t\t\t\\'
+               print '\tMOV_L(CONTENT(GLNAME(_glapi_Dispatch)), EAX) ;\t\\'
+               print '\tJMP(GL_OFFSET(off))'
+               print '#endif'
                print ''
                print 'SEG_TEXT'
+               print ''
+               print '#ifdef PTHREADS'
                print 'EXTERN GLNAME(_glapi_Dispatch)'
+               print 'EXTERN GLNAME(_gl_DispatchTSD)'
+               print 'EXTERN GLNAME(pthread_getspecific)'
+               print ''
+               print 'ALIGNTEXT16'
+               print 'GLNAME(get_dispatch):'
+               print '\tSUB_L(CONST(24), ESP)'
+               print '\tPUSH_L(GLNAME(_gl_DispatchTSD))'
+               print '\tCALL(GLNAME(pthread_getspecific))'
+               print '\tADD_L(CONST(28), ESP)'
+               print '\tRET'
+               print '#elif defined(THREADS)'
+               print 'EXTERN GLNAME(_glapi_get_dispatch)'
+               print '#endif'
+               print ''
+               print '\t\tALIGNTEXT16 ; GLOBL gl_dispatch_functions_start'
+               print 'gl_dispatch_functions_start:'
                print ''
                return
 
@@ -95,11 +137,10 @@
                return
 
        def printFunction(self, f):
-               if f.fn_offset == -1: return
-
                stack = self.get_stack_size(f)
 
-               print '\tGL_STUB(%s, _gloffset_%s, %u)' % (f.name, f.real_name, stack)
+               alt = "[EMAIL PROTECTED]" % (f.name, stack)
+               print '\tGL_STUB(%s, _gloffset_%s, %s)' % (f.name, f.real_name, alt)
                return
 
 def show_usage():
Index: src/mesa/glapi/glapi.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/glapi/glapi.c,v
retrieving revision 1.73
diff -u -d -r1.73 glapi.c
--- a/src/mesa/glapi/glapi.c    23 Apr 2004 20:33:07 -0000      1.73
+++ b/src/mesa/glapi/glapi.c    24 May 2004 23:04:12 -0000
@@ -142,42 +142,11 @@
 #if defined(THREADS)
 
 static GLboolean ThreadSafe = GL_FALSE;  /* In thread-safe mode? */
-static _glthread_TSD DispatchTSD;        /* Per-thread dispatch pointer */
+_glthread_TSD _gl_DispatchTSD;           /* Per-thread dispatch pointer */
 static _glthread_TSD RealDispatchTSD;    /* only when using override */
 static _glthread_TSD ContextTSD;         /* Per-thread context pointer */
 
-
-#define KEYWORD1 static
-#define KEYWORD2 GLAPIENTRY
-#define NAME(func)  _ts_##func
-
-#define DISPATCH(FUNC, ARGS, MESSAGE)                                  \
-   struct _glapi_table *dispatch;                                      \
-   dispatch = (struct _glapi_table *) _glthread_GetTSD(&DispatchTSD);  \
-   if (!dispatch)                                                      \
-      dispatch = (struct _glapi_table *) __glapi_noop_table;           \
-   (dispatch->FUNC) ARGS
-
-#define RETURN_DISPATCH(FUNC, ARGS, MESSAGE)                           \
-   struct _glapi_table *dispatch;                                      \
-   dispatch = (struct _glapi_table *) _glthread_GetTSD(&DispatchTSD);  \
-   if (!dispatch)                                                      \
-      dispatch = (struct _glapi_table *) __glapi_noop_table;           \
-   return (dispatch->FUNC) ARGS
-
-#define DISPATCH_TABLE_NAME __glapi_threadsafe_table
-#define UNUSED_TABLE_NAME __usused_threadsafe_functions
-
-#define TABLE_ENTRY(name) (void *) _ts_##name
-
-static int _ts_Unused(void)
-{
-   return 0;
-}
-
-#include "glapitemp.h"
-
-#endif
+#endif /* defined(THREADS) */
 
 /***** END THREAD-SAFE DISPATCH *****/
 
@@ -303,15 +272,15 @@
    if (DispatchOverride) {
       _glthread_SetTSD(&RealDispatchTSD, (void *) dispatch);
       if (ThreadSafe)
-         _glapi_RealDispatch = (struct _glapi_table*) __glapi_threadsafe_table;
+         _glapi_RealDispatch = (struct _glapi_table*) NULL;
       else
          _glapi_RealDispatch = dispatch;
    }
    else {
       /* normal operation */
-      _glthread_SetTSD(&DispatchTSD, (void *) dispatch);
+      _glthread_SetTSD(&_gl_DispatchTSD, (void *) dispatch);
       if (ThreadSafe)
-         _glapi_Dispatch = (struct _glapi_table *) __glapi_threadsafe_table;
+         _glapi_Dispatch = (struct _glapi_table *) NULL;
       else
          _glapi_Dispatch = dispatch;
    }
@@ -339,7 +308,7 @@
          return (struct _glapi_table *) _glthread_GetTSD(&RealDispatchTSD);
       }
       else {
-         return (struct _glapi_table *) _glthread_GetTSD(&DispatchTSD);
+         return (struct _glapi_table *) _glthread_GetTSD(&_gl_DispatchTSD);
       }
    }
    else {
@@ -391,9 +360,9 @@
    _glapi_set_dispatch(real);
 
 #if defined(THREADS)
-   _glthread_SetTSD(&DispatchTSD, (void *) override);
+   _glthread_SetTSD(&_gl_DispatchTSD, (void *) override);
    if (ThreadSafe)
-      _glapi_Dispatch = (struct _glapi_table *) __glapi_threadsafe_table;
+      _glapi_Dispatch = (struct _glapi_table *) NULL;
    else
       _glapi_Dispatch = override;
 #else
@@ -427,7 +396,7 @@
    else {
       if (DispatchOverride) {
 #if defined(THREADS)
-         return (struct _glapi_table *) _glthread_GetTSD(&DispatchTSD);
+         return (struct _glapi_table *) _glthread_GetTSD(&_gl_DispatchTSD);
 #else
          return _glapi_Dispatch;
 #endif
@@ -446,10 +415,30 @@
 };
 
 
+#if !defined( USE_X86_ASM )
+#define NEED_FUNC_POINTER
+#endif
+
 /* The code in this file is auto-generated with Python */
 #include "glprocs.h"
 
 
+static const glprocs_table_t *
+find_entry( const char * n )
+{
+   unsigned   i;
+
+   for ( i = 0 ; static_functions[i].Name_offset >= 0 ; i++ ) {
+      const char * test_name;
+
+      test_name = gl_string_table + static_functions[i].Name_offset;
+      if (strcmp(test_name, n) == 0) {
+        return & static_functions[i];
+      }
+   }
+   return NULL;
+}
+
 
 /*
  * Return dispatch table offset of the named static (built-in) function.
@@ -458,27 +447,67 @@
 static GLint
 get_static_proc_offset(const char *funcName)
 {
-   GLuint i;
-   for (i = 0; static_functions[i].Name; i++) {
-      if (strcmp(static_functions[i].Name, funcName) == 0) {
-        return static_functions[i].Offset;
-      }
+   const glprocs_table_t * const f = find_entry( funcName );
+
+   if ( f != NULL ) {
+      return f->Offset;
    }
    return -1;
 }
 
 
+#ifdef USE_X86_ASM
+extern const GLubyte gl_dispatch_functions_start[];
+
+# if defined(PTHREADS)
+#  define X86_DISPATCH_FUNCTION_SIZE  32
+# else
+#  define X86_DISPATCH_FUNCTION_SIZE  16
+# endif
+
+
 /*
  * Return dispatch function address the named static (built-in) function.
  * Return NULL if function not found.
  */
-static GLvoid *
+static const GLvoid *
 get_static_proc_address(const char *funcName)
 {
-   GLint i;
-   for (i = 0; static_functions[i].Name; i++) {
-      if (strcmp(static_functions[i].Name, funcName) == 0) {
-         return static_functions[i].Address;
+   const glprocs_table_t * const f = find_entry( funcName );
+
+   if ( f != NULL ) {
+      return gl_dispatch_functions_start 
+          + (X86_DISPATCH_FUNCTION_SIZE * f->Offset);
+   }
+   else {
+      return NULL;
+   }
+}
+
+#else
+
+/*
+ * Return dispatch function address the named static (built-in) function.
+ * Return NULL if function not found.
+ */
+static const GLvoid *
+get_static_proc_address(const char *funcName)
+{
+   const glprocs_table_t * const f = find_entry( funcName );
+   return ( f != NULL ) ? f->Address : NULL;
+}
+
+#endif /* USE_X86_ASM */
+
+
+static const char *
+get_static_proc_name( GLuint offset )
+{
+   unsigned   i;
+
+   for ( i = 0 ; static_functions[i].Name_offset >= 0 ; i++ ) {
+      if (static_functions[i].Offset == offset) {
+        return gl_string_table + static_functions[i].Name_offset;
       }
    }
    return NULL;
@@ -802,13 +831,13 @@
 const char *
 _glapi_get_proc_name(GLuint offset)
 {
-   const GLuint n = sizeof(static_functions) / sizeof(struct name_address_offset);
    GLuint i;
+   const char * n;
 
    /* search built-in functions */
-   for (i = 0; i < n; i++) {
-      if (static_functions[i].Offset == offset)
-         return static_functions[i].Name;
+   n = get_static_proc_name(offset);
+   if ( n != NULL ) {
+      return n;
    }
 
    /* search added extension functions */
Index: src/mesa/main/dispatch.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/main/dispatch.c,v
retrieving revision 1.31
diff -u -d -r1.31 dispatch.c
--- a/src/mesa/main/dispatch.c  21 Oct 2003 22:22:19 -0000      1.31
+++ b/src/mesa/main/dispatch.c  24 May 2004 23:04:12 -0000
@@ -57,25 +57,40 @@
 #define NAME(func)  gl##func
 #endif
 
+#if !defined __GNUC__ || __GNUC__ < 3
+# define __builtin_expect(x, y) x
+#endif
 
 #if 0  /* Use this to log GL calls to stdout (for DEBUG only!) */
 
 #define F stdout
-#define DISPATCH(FUNC, ARGS, MESSAGE)          \
-   fprintf MESSAGE;                            \
-   (_glapi_Dispatch->FUNC) ARGS;
+#define DISPATCH(FUNC, ARGS, MESSAGE)                  \
+   const struct _glapi_table * const d =               \
+       (__builtin_expect(_glapi_Dispatch != NULL, 1))  \
+       ? _glapiDispatch : _glapi_get_dispatch();       \
+   fprintf MESSAGE;                                    \
+   (d->FUNC) ARGS;
 
 #define RETURN_DISPATCH(FUNC, ARGS, MESSAGE)   \
-   fprintf MESSAGE;                            \
-   return (_glapi_Dispatch->FUNC) ARGS
+   const struct _glapi_table * const d =               \
+       (__builtin_expect(_glapi_Dispatch != NULL, 1))  \
+       ? _glapiDispatch : _glapi_get_dispatch();       \
+   fprintf MESSAGE;                                    \
+   return (d->FUNC) ARGS;
 
 #else
 
 #define DISPATCH(FUNC, ARGS, MESSAGE)          \
-   (_glapi_Dispatch->FUNC) ARGS;
+   const struct _glapi_table * const d =               \
+       (__builtin_expect(_glapi_Dispatch != NULL, 1))  \
+       ? _glapiDispatch : _glapi_get_dispatch();       \
+   (d->FUNC) ARGS;
 
 #define RETURN_DISPATCH(FUNC, ARGS, MESSAGE)   \
-   return (_glapi_Dispatch->FUNC) ARGS
+   const struct _glapi_table * const d =               \
+       (__builtin_expect(_glapi_Dispatch != NULL, 1))  \
+       ? _glapiDispatch : _glapi_get_dispatch();       \
+   return (d->FUNC) ARGS;
 
 #endif /* logging */
 

Reply via email to