Use glproc.hpp also for both tracing and retracing.
authorJosé Fonseca <jose.r.fonseca@gmail.com>
Sun, 20 Feb 2011 11:25:25 +0000 (11:25 +0000)
committerJosé Fonseca <jose.r.fonseca@gmail.com>
Tue, 22 Feb 2011 07:15:58 +0000 (07:15 +0000)
CMakeLists.txt
glproc.py
glretrace.py
glxapi.py
glxtrace.py
stdapi.py
trace.py
trace_write.hpp
wglapi.py
wgltrace.py

index 0761a78..9da61a1 100644 (file)
@@ -116,6 +116,12 @@ endif (PNG_FOUND)
 
 include_directories (${CMAKE_CURRENT_SOURCE_DIR})
 
+add_custom_command (
+    OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/glproc.hpp
+    COMMAND ${PYTHON_EXECUTABLE} ${CMAKE_CURRENT_SOURCE_DIR}/glproc.py > ${CMAKE_CURRENT_BINARY_DIR}/glproc.hpp
+    DEPENDS glproc.py wglapi.py glxapi.py glapi.py glenum.py stdapi.py
+)
+
 if (WIN32)
     # Put wrappers in a separate directory
     set (LIBRARY_OUTPUT_PATH ${PROJECT_BINARY_DIR}/wrappers)
@@ -162,12 +168,12 @@ if (WIN32)
         COMMAND ${PYTHON_EXECUTABLE} ${CMAKE_CURRENT_SOURCE_DIR}/wgltrace.py > ${CMAKE_CURRENT_BINARY_DIR}/wgltrace.cpp
         DEPENDS wgltrace.py trace.py wglapi.py glapi.py glenum.py winapi.py stdapi.py
     )
-    add_library (opengl SHARED opengl32.def wgltrace.cpp trace_write.cpp os_win32.cpp)
+    add_library (opengl SHARED opengl32.def wgltrace.cpp trace_write.cpp os_win32.cpp ${CMAKE_CURRENT_BINARY_DIR}/glproc.hpp)
     set_target_properties (opengl PROPERTIES
         PREFIX ""
         OUTPUT_NAME opengl32)
     if (MINGW)
-        SET_TARGET_PROPERTIES(opengl PROPERTIES LINK_FLAGS "-Wl,--enable-stdcall-fixup ${CMAKE_CURRENT_SOURCE_DIR}/opengl32.def")
+        set_target_properties(opengl PROPERTIES LINK_FLAGS "-Wl,--enable-stdcall-fixup ${CMAKE_CURRENT_SOURCE_DIR}/opengl32.def")
     endif (MINGW)
 
 else ()
@@ -179,8 +185,11 @@ else ()
         DEPENDS glxtrace.py trace.py glxapi.py glapi.py glenum.py stdapi.py
     )
 
-    add_library (glxtrace SHARED glxtrace.cpp trace_write.cpp os_posix.cpp)
-    set_target_properties (glxtrace PROPERTIES PREFIX "")
+    add_library (glxtrace SHARED glxtrace.cpp trace_write.cpp os_posix.cpp ${CMAKE_CURRENT_BINARY_DIR}/glproc.hpp)
+    set_target_properties (glxtrace PROPERTIES 
+        COMPILER_DEFINITIONS "-DRETRACE"
+        PREFIX ""
+    )
     target_link_libraries (glxtrace dl)
 endif ()
 
@@ -194,12 +203,6 @@ endif (WIN32)
 
 if (GLUT_INCLUDE_DIR)
     add_custom_command (
-        OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/glproc.hpp
-        COMMAND ${PYTHON_EXECUTABLE} ${CMAKE_CURRENT_SOURCE_DIR}/glproc.py > ${CMAKE_CURRENT_BINARY_DIR}/glproc.hpp
-        DEPENDS glproc.py wglapi.py glxapi.py glapi.py glenum.py stdapi.py
-    )
-
-    add_custom_command (
         OUTPUT glretrace.cpp
         COMMAND ${PYTHON_EXECUTABLE} ${CMAKE_CURRENT_SOURCE_DIR}/glretrace.py > ${CMAKE_CURRENT_BINARY_DIR}/glretrace.cpp
         DEPENDS glretrace.py retrace.py codegen.py glapi.py glenum.py stdapi.py
index 3945ab6..f3dc3d2 100644 (file)
--- a/glproc.py
+++ b/glproc.py
@@ -35,6 +35,7 @@ from glxapi import glxapi
 from wglapi import wglapi
 
 
+# See http://www.opengl.org/registry/ABI/
 public_symbols = set([
        "glAccum",
        "glAlphaFunc",
@@ -398,11 +399,33 @@ public_symbols = set([
        "wglUseFontBitmapsW",
        "wglUseFontOutlinesA",
        "wglUseFontOutlinesW",
+
+    "glXGetProcAddressARB",
+    "glXGetProcAddress",
 ])
 
 
 class Dispatcher:
 
+    def header(self):
+        pass
+        #print 'typedef void (*__PROC)(void);'
+        #print
+        #print 'static __PROC __getPublicProcAddress(const char *name);'
+        #print 'static __PROC __getPrivateProcAddress(const char *name);'
+        #print
+
+    def dispatch_api(self, api):
+        for function in api.functions:
+            dispatcher.dispatch_function(function)
+        
+        print '#ifdef RETRACE'
+        for function in api.functions:
+            if not self.is_public_function(function):
+                print '#define %s __%s' % (function.name, function.name)
+        print '#endif /* RETRACE */'
+        print
+
     def function_pointer_type(self, function):
         return '__PFN' + function.name.upper()
 
@@ -410,9 +433,9 @@ class Dispatcher:
         return '__' + function.name + '_ptr'
 
     def dispatch_function(self, function):
-        if function.name in public_symbols:
-            return
-
+        if self.is_public_function(function):
+            print '#ifndef RETRACE'
+            print
         ptype = self.function_pointer_type(function)
         pvalue = self.function_pointer_value(function)
         print 'typedef ' + function.prototype('* %s' % ptype) + ';'
@@ -428,15 +451,20 @@ class Dispatcher:
         print '    %s%s(%s);' % (ret, pvalue, ', '.join([str(arg.name) for arg in function.args]))
         print '}'
         print
-        print '#define %s __%s' % (function.name, function.name)
+        if self.is_public_function(function):
+            print '#endif /* !RETRACE */'
+            print
+
+    def is_public_function(self, function):
+        return True
 
     def get_true_pointer(self, function):
         ptype = self.function_pointer_type(function)
         pvalue = self.function_pointer_value(function)
-        if function.name in public_symbols:
-            get_proc_address = '__getProcAddress'
+        if self.is_public_function(function):
+            get_proc_address = '__getPublicProcAddress'
         else:
-            get_proc_address = '__glGetProcAddress'
+            get_proc_address = '__getPrivateProcAddress'
         print '    if (!%s) {' % (pvalue,)
         print '        %s = (%s)%s("%s");' % (pvalue, ptype, get_proc_address, function.name)
         print '        if (!%s) {' % (pvalue,)
@@ -445,7 +473,7 @@ class Dispatcher:
         print '    }'
 
     def fail_function(self, function):
-        print '    std::cerr << "error: unavailable function \\"%s\\"\\n";' % function.name
+        print '            OS::DebugMessage("error: unavailable function \\"%s\\"\\n");' % function.name
         if function.fail is not None:
             if function.type is stdapi.Void:
                 assert function.fail == ''
@@ -454,7 +482,35 @@ class Dispatcher:
                 assert function.fail != ''
                 print '            return %s;' % function.fail
         else:
-            print '            abort();'
+            print '            __abort();'
+
+
+class GlDispatcher(Dispatcher):
+
+    def header(self):
+        Dispatcher.header(self)
+        print '#ifdef RETRACE'
+        print '#  ifdef WIN32'
+        print '#    define __getPrivateProcAddress(name) wglGetProcAddress(name)'
+        print '#  else'
+        print '#    define __getPrivateProcAddress(name) glXGetProcAddressARB((const GLubyte *)(name))'
+        print '#  endif'
+        print '#  define __abort() OS::Abort()'
+        print '#else /* !RETRACE */'
+        print '#  ifdef WIN32'
+        print '#    define __getPrivateProcAddress(name) __wglGetProcAddress(name)'
+        print '     static inline PROC __stdcall __wglGetProcAddress(const char * lpszProc);'
+        print '#  else'
+        print '#    define __getPublicProcAddress(name) dlsym(RTLD_NEXT, name)'
+        print '#    define __getPrivateProcAddress(name) __glXGetProcAddressARB((const GLubyte *)(name))'
+        print '     static inline __GLXextFuncPtr __glXGetProcAddressARB(const GLubyte * procName);'
+        print '#  endif'
+        print '#  define __abort() Trace::Abort()'
+        print '#endif /* !RETRACE */'
+        print
+        
+    def is_public_function(self, function):
+        return function.name in public_symbols
 
 
 if __name__ == '__main__':
@@ -462,22 +518,18 @@ if __name__ == '__main__':
     print '#include "glimports.hpp"'
     print '#include "os.hpp"'
     print
-    if 0:
-        print 'typedef void (*__PROC)(void);'
-        print
-        print 'static __PROC __getProcAddress(const char *name);'
-        print
-        print 'static __PROC __glGetProcAddress(const char *name);'
-    else:
-        print '#ifdef WIN32'
-        print '#define __glGetProcAddress wglGetProcAddress'
-        print '#else'
-        print '#define __glGetProcAddress(name) glXGetProcAddress((const GLubyte *)(name))'
-        print '#endif'
     print
-    dispatcher = Dispatcher()
-    for function in glapi.functions:
-        dispatcher.dispatch_function(function)
+    dispatcher = GlDispatcher()
+    dispatcher.header()
+    print '#ifdef WIN32'
+    print
+    dispatcher.dispatch_api(wglapi)
+    print '#else /* !WIN32 */'
+    print
+    dispatcher.dispatch_api(glxapi)
+    print '#endif /* !WIN32 */'
+    print
+    dispatcher.dispatch_api(glapi)
     print
     if 0:
         print '''
@@ -507,11 +559,6 @@ __getProcAddress(const char *name)
     return GetProcAddress(g_hDll, name);
 }
 
-static inline __PROC
-__glGetProcAddress(const char *name) {
-    return __wglGetProcAddress(name);
-}
-
 #else
 
 static void g_module = NULL;
@@ -531,7 +578,7 @@ __getProcAddress(const char *name)
 
 static inline __PROC
 __glGetProcAddress(const char *name) {
-    return __glXGetProcAddress(name);
+    return __glXGetProcAddressARB(name);
 }
 
 #endif
index 761be80..451c938 100644 (file)
@@ -151,6 +151,8 @@ if __name__ == '__main__':
 #include <stdio.h>
 #include <iostream>
 
+#define RETRACE
+
 #include "glproc.hpp"
 #include <GL/glut.h>
 
index a99fbd0..3d345b9 100644 (file)
--- a/glxapi.py
+++ b/glxapi.py
@@ -54,7 +54,6 @@ glxapi = API("GLX")
 
 PROC = Opaque("__GLXextFuncPtr")
 
-glxapi.add_functions(glapi.functions)
 glxapi.add_functions([
     Function(GLXContext, "glXCreateContext", [(Display, "dpy"), (Pointer(XVisualInfo), "vis"), (GLXContext, "shareList"), (Bool_, "direct")]),
     # TODO: the rest
index 2759319..bd86e5b 100644 (file)
@@ -27,6 +27,8 @@
 """GLX tracing generator."""
 
 
+from stdapi import API
+from glapi import glapi
 from glxapi import glxapi
 from trace import Tracer
 
@@ -34,15 +36,7 @@ from trace import Tracer
 class GlxTracer(Tracer):
 
     def get_function_address(self, function):
-        if function.name.startswith("glXGetProcAddress"):
-            return 'dlsym(RTLD_NEXT, "%s")' % (function.name,)
-        else:
-            print '    if (!pglXGetProcAddress) {'
-            print '        pglXGetProcAddress = (PglXGetProcAddress)dlsym(RTLD_NEXT, "glXGetProcAddress");'
-            print '        if (!pglXGetProcAddress)'
-            print '            Trace::Abort();'
-            print '    }'
-            return 'pglXGetProcAddress((const GLubyte *)"%s")' % (function.name,)
+        return '__%s' % (function.name,)
 
     def wrap_ret(self, function, instance):
         if function.name.startswith("glXGetProcAddress"):
@@ -63,14 +57,17 @@ if __name__ == '__main__':
     print '#include <string.h>'
     print '#include <dlfcn.h>'
     print
-    print '#include "glimports.hpp"'
-    print
     print '#include "trace_write.hpp"'
+    print
+    print '#include "glproc.hpp"'
     print '#include "glsize.hpp"'
     print
     print 'extern "C" {'
     print
+    api = API()
+    api.add_api(glxapi)
+    api.add_api(glapi)
     tracer = GlxTracer()
-    tracer.trace_api(glxapi)
+    tracer.trace_api(api)
     print
     print '} /* extern "C" */'
index 7d0c982..1f8b81e 100644 (file)
--- a/stdapi.py
+++ b/stdapi.py
@@ -510,7 +510,7 @@ class Collector(Visitor):
 
 class API:
 
-    def __init__(self, name):
+    def __init__(self, name = None):
         self.name = name
         self.headers = []
         self.functions = []
@@ -543,6 +543,11 @@ class API:
     def add_interfaces(self, interfaces):
         self.interfaces.extend(interfaces)
 
+    def add_api(self, api):
+        self.headers.extend(api.headers)
+        self.add_functions(api.functions)
+        self.add_interfaces(api.interfaces)
+
     def get_function_by_name(self, name):
         for function in self.functions:
             if function.name == name:
index 7c39467..01fdeb5 100644 (file)
--- a/trace.py
+++ b/trace.py
@@ -453,8 +453,7 @@ class DllTracer(Tracer):
         self.dllname = dllname
     
     def get_function_address(self, function):
-        return '__GetProcAddress("%s")' % (function.name,)
-
+        return '__%s' % (function.name,)
 
     def header(self, api):
         Tracer.header(self, api)
index 1dfa463..7ba1154 100644 (file)
@@ -30,6 +30,8 @@
 #ifndef _TRACE_WRITE_HPP_
 #define _TRACE_WRITE_HPP_
 
+#include <stddef.h>
+
 namespace Trace {
 
     typedef unsigned Id;
index b802362..3f5caf1 100644 (file)
--- a/wglapi.py
+++ b/wglapi.py
@@ -32,7 +32,6 @@ from winapi import *
 
 
 wglapi = API("WGL")
-wglapi.add_functions(glapi.functions)
 
 
 HGLRC = Alias("HGLRC", HANDLE)
index 7dcb850..5c860d7 100644 (file)
@@ -27,6 +27,8 @@
 """WGL tracing code generator."""
 
 
+from stdapi import API
+from glapi import glapi
 from wglapi import wglapi
 from trace import Tracer
 from codegen import *
@@ -400,16 +402,7 @@ public_symbols = set([
 class WglTracer(Tracer):
 
     def get_function_address(self, function):
-        #print 'DebugBreak();'
-        if function.name in public_symbols:
-            return '__GetProcAddress("%s")' % (function.name,)
-        else:
-            print '        if (!pwglGetProcAddress) {'
-            print '            pwglGetProcAddress = (PwglGetProcAddress)__GetProcAddress("wglGetProcAddress");'
-            print '            if (!pwglGetProcAddress)'
-            print '                Trace::Abort();'
-            print '        }'
-            return 'pwglGetProcAddress("%s")' % (function.name,)
+        return '__%s' % (function.name,)
 
     def wrap_ret(self, function, instance):
         if function.name == "wglGetProcAddress":
@@ -435,18 +428,17 @@ if __name__ == '__main__':
     print
     print '#define _GDI32_'
     print
-    print '#include "glimports.hpp"'
+    print '#include <string.h>'
+    print '#include <windows.h>'
     print
     print '#include "trace_write.hpp"'
     print '#include "os.hpp"'
-    print '#include "glsize.hpp"'
     print
-    print 'extern "C" {'
     print '''
 static HINSTANCE g_hDll = NULL;
 
 static PROC
-__GetProcAddress(LPCSTR lpProcName)
+__getPublicProcAddress(LPCSTR lpProcName)
 {
     if (!g_hDll) {
         char szDll[MAX_PATH] = {0};
@@ -467,7 +459,15 @@ __GetProcAddress(LPCSTR lpProcName)
 }
 
     '''
+    print '#include "glproc.hpp"'
+    print '#include "glsize.hpp"'
+    print
+    print 'extern "C" {'
+    print
+    api = API()
+    api.add_api(wglapi)
+    api.add_api(glapi)
     tracer = WglTracer()
-    tracer.trace_api(wglapi)
+    tracer.trace_api(api)
     print
     print '} /* extern "C" */'