COMPILE_FLAGS "${CMAKE_SHARED_LIBRARY_CXX_FLAGS}"
)
+target_link_libraries(common cairo)
if (ANDROID)
target_link_libraries (common
log
inline Library
openLibrary(const char *filename) {
+ std::cout << "In apitrace::openLibrary\n";
#if defined(_WIN32)
return LoadLibraryA(filename);
#else
inline void *
getLibrarySymbol(Library library, const char *symbol) {
+ std::cout << "In apitrace::getLibrarySymbol\n";
#if defined(_WIN32)
return (void *)GetProcAddress(library, symbol);
#else
${CMAKE_SOURCE_DIR}/specs/glapi.py
${CMAKE_SOURCE_DIR}/specs/gltypes.py
${CMAKE_SOURCE_DIR}/specs/stdapi.py
+ ${CMAKE_SOURCE_DIR}/specs/xapi.py
)
from specs.cglapi import cglapi
from specs.eglapi import eglapi
from specs.glesapi import glesapi
+from specs.xapi import xapi
# See http://www.opengl.org/registry/ABI/
"wglUseFontOutlinesA",
"wglUseFontOutlinesW",
+ # X
+ "XCreatePixmap",
+
])
# EGL 1.4
print
dispatcher.dispatchModule(glxapi)
print
+ dispatcher.dispatchModule(xapi)
+ print
print '#endif'
print
dispatcher.dispatchModule(glapi)
{
void *result;
+ printf ("In apitrace::_libgl_sym\n");
+
if (!_libGlHandle) {
/*
* Unfortunately we can't just dlopen the true dynamic library because
if (mktemp(temp_filename) != NULL) {
if (symlink(libgl_filename, temp_filename) == 0) {
- _libGlHandle = dlopen(temp_filename, RTLD_LOCAL | RTLD_NOW | RTLD_FIRST);
+ _libGlHandle = dlopen(temp_filename, RTLD_LOCAL | RTLD_NOW);
remove(temp_filename);
}
}
--- /dev/null
+#ifndef _XPROC_HPP_
+#define _XPROC_HPP_
+
+#include <X/X11.h>
+
+#include "os.hpp"
+
+#if defined(HAVE_X11)
+
+typedef Pixmap (* PFN_XCREATEPIXMAP)(Display * dpy, Drawable d, unsigned int width, unsigned int height, unsigned int depth);
+static PFN_XCREATEPIXMAP _XCreatePixmap_ptr = NULL;
+
+static inline Pixmap _XCreatePixmap(Display * dpy, Drawable d, unsigned int width, unsigned int height, unsigned int depth) {
+ const char *_name = "XCreatePixmap";
+ if (!_XCreatePixmap_ptr) {
+ _XCreatePixmap_ptr = (PFN_XCREATEPIXMAP)_getPublicProcAddress(_name);
+ if (!_XCreatePixmap_ptr) {
+ os::log("error: unavailable function %s\n", _name);
+ os::abort();
+ }
+ }
+ return _XCreatePixmap_ptr(dpy, d, width, height, depth);
+}
+
+typedef int (* PFN_XFREEPIXMAP)(Display * dpy, Drawable pixmap);
+static PFN_XFREEPIXMAP _XFreePixmap_ptr = NULL;
+
+static inline int _XFreePixmap(Display * dpy, Drawable pixmap) {
+ const char *_name = "XFreePixmap";
+ if (!_XFreePixmap_ptr) {
+ _XFreePixmap_ptr = (PFN_XFREEPIXMAP)_getPrivateProcAddress(_name);
+ if (!_XFreePixmap_ptr) {
+ os::log("error: unavailable function %s\n", _name);
+ os::abort();
+ }
+ }
+ return _XFreePixmap_ptr(dpy, pixmap);
+}
+
+#ifdef RETRACE
+#define XCreatePixmap _XCreatePixmap
+#define XFreePixmap _XFreePixmap
+#endif /* RETRACE */
+
+
+#endif
bool
makeCurrent(trace::Call &call, glws::Drawable *drawable, Context *context);
+void
+createWindow(glws::Drawable *drawable);
+
+void
+destroyWindow(glws::Drawable *drawable);
+
+glws::Drawable *
+createPixmap(unsigned width, unsigned height, unsigned depth);
+
+glws::Drawable *
+createGLPixmap(GLXFBConfig fbconfig, glws::Drawable *pixmap,
+ unsigned width, unsigned height, int *attrib_list);
+
+void
+bindTexImage(glws::Drawable *drawable, int buffer);
+
+void
+releaseTexImage(glws::Drawable *drawable, int buffer);
+
+void
+copySubBuffer(glws::Drawable *drawable, int x, int y, int width, int height);
+
+void
+putImageData(glws::Drawable *drawable, char *data,
+ int width, int height, int depth,
+ int bits_per_pixel, int bytes_per_line, int byte_order);
+
+GLXFBConfig
+chooseConfig(int *attrib_list);
void
checkGlError(trace::Call &call);
using namespace glretrace;
+typedef struct {
+ int width;
+ int height;
+ int depth;
+} PixmapDesc;
typedef std::map<unsigned long, glws::Drawable *> DrawableMap;
typedef std::map<unsigned long long, Context *> ContextMap;
+typedef std::map<unsigned long, PixmapDesc *> PixmapDescMap;
+typedef std::map<GLXFBConfig, GLXFBConfig> ConfigMap;
static DrawableMap drawable_map;
static ContextMap context_map;
-
+static PixmapDescMap pixmap_desc_map;
+static ConfigMap config_map;
static glws::Drawable *
getDrawable(unsigned long drawable_id) {
glretrace::makeCurrent(call, new_drawable, new_context);
}
+static void retrace_glXCreateWindow(trace::Call &call) {
+ glws::Drawable *window = getDrawable(call.arg(2).toUInt());
+
+ glretrace::createWindow(window);
+}
+
+static void retrace_glXDestroyWindow(trace::Call &call) {
+ glws::Drawable *window = getDrawable(call.arg(1).toUInt());
+
+ glretrace::destroyWindow(window);
+}
+
+static void retrace_XCreatePixmap(trace::Call &call) {
+ unsigned pixmap_id = call.ret->toUInt();
+
+ PixmapDesc *desc = new(PixmapDesc);
+
+ desc->width = call.arg(2).toUInt();
+ desc->height = call.arg(3).toUInt();
+ desc->depth = call.arg(4).toUInt();
+
+ pixmap_desc_map[pixmap_id] = desc;
+}
+
+static void retrace_XFreePixmap(trace::Call &call) {
+ unsigned pixmap_id = call.arg(1).toUInt();
+ PixmapDescMap::iterator it;
+
+ it = pixmap_desc_map.find(pixmap_id);
+ delete it->second;
+ pixmap_desc_map.erase(it);
+}
+
+static void retrace_glXCreatePixmap(trace::Call &call) {
+ retrace::ScopedAllocator _allocator;
+ GLXFBConfig fbconfig, orig_fbconfig = (GLXFBConfig) call.arg(1).toPointer();
+ unsigned orig_pixmap = call.arg(2).toUInt();
+ unsigned orig_gl_pixmap = call.ret->toUInt();
+ PixmapDesc *desc = pixmap_desc_map[orig_pixmap];
+ glws::Drawable *pixmap, *gl_pixmap;
+
+ int *attrib_list;
+ attrib_list = static_cast<int *>(_allocator.alloc(&call.arg(3), sizeof *attrib_list));
+ if (attrib_list) {
+ const trace::Array *arg_list = dynamic_cast<const trace::Array *>(&call.arg(3));
+ for (size_t i = 0; i < arg_list->values.size(); i++) {
+ attrib_list[i] = (*arg_list->values[i]).toSInt();
+ }
+ }
+
+ printf("Looking for %p in FB-config map\n", orig_fbconfig);
+ fbconfig = config_map[orig_fbconfig];
+
+ pixmap = glretrace::createPixmap(desc->width, desc->height, desc->depth);
+
+ gl_pixmap = glretrace::createGLPixmap(fbconfig, pixmap, desc->width, desc->height, attrib_list);
+
+ drawable_map[orig_pixmap] = pixmap;
+ drawable_map[orig_gl_pixmap] = gl_pixmap;
+}
+
+static void retrace_glXBindTexImageEXT(trace::Call &call) {
+ glws::Drawable *pixmap = getDrawable(call.arg(1).toUInt());
+
+ glretrace::bindTexImage(pixmap, call.arg(2).toSInt());
+}
+
+static void retrace_glXReleaseTexImageEXT(trace::Call &call) {
+ glws::Drawable *pixmap = getDrawable(call.arg(1).toUInt());
+
+ glretrace::releaseTexImage(pixmap, call.arg(2).toSInt());
+}
+
+static void retrace_glXCopySubBufferMESA(trace::Call &call) {
+ glws::Drawable *drawable = getDrawable(call.arg(1).toUInt());
+ int x, y, width, height;
+
+ x = call.arg(2).toSInt();
+ y = call.arg(3).toSInt();
+ width = call.arg(4).toSInt();
+ height = call.arg(5).toSInt();
+
+ glretrace::copySubBuffer(drawable, x, y, width, height);
+}
+
+static void retrace_PutImageData(trace::Call &call) {
+ glws::Drawable *drawable = getDrawable(call.arg(0).toUInt());
+ int width, height, depth, bits_per_pixel, bytes_per_line, byte_order;
+ char *data;
+
+ data = static_cast<char *>((call.arg(1)).toPointer());
+ width = call.arg(2).toSInt();
+ height = call.arg(3).toSInt();
+ depth = call.arg(4).toSInt();
+ bits_per_pixel = call.arg(5).toSInt();
+ bytes_per_line = call.arg(6).toSInt();
+ byte_order = call.arg(7).toSInt();
+
+ glretrace::putImageData(drawable, data, width, height, depth,
+ bits_per_pixel, bytes_per_line, byte_order);
+}
+
+static void retrace_glXChooseFBConfig(trace::Call &call) {
+ retrace::ScopedAllocator _allocator;
+ int orig_nelements;
+ const trace::Array *orig_configs;
+ GLXFBConfig config;
+
+ int *attrib_list;
+ attrib_list = static_cast<int *>(_allocator.alloc(&call.arg(2), sizeof *attrib_list));
+ if (attrib_list) {
+ const trace::Array *arg_list = dynamic_cast<const trace::Array *>(&call.arg(2));
+ for (size_t i = 0; i < arg_list->values.size(); i++) {
+ attrib_list[i] = arg_list->values[i]->toSInt();
+ }
+ }
+
+ orig_nelements = dynamic_cast<const trace::Array *>(&call.arg(3))->values[0]->toSInt();
+ orig_configs = dynamic_cast<const trace::Array *>(call.ret);
+
+ config = glretrace::chooseConfig(attrib_list);
+ for (size_t i = 0; i < orig_nelements; i++) {
+ printf("Mapping FB config %p to %p\n", orig_configs->values[i]->toPointer(), config);
+ config_map[static_cast<GLXFBConfig>(orig_configs->values[i]->toPointer())] = config;
+ }
+}
+
const retrace::Entry glretrace::glx_callbacks[] = {
//{"glXBindChannelToWindowSGIX", &retrace_glXBindChannelToWindowSGIX},
//{"glXBindSwapBarrierNV", &retrace_glXBindSwapBarrierNV},
//{"glXBindSwapBarrierSGIX", &retrace_glXBindSwapBarrierSGIX},
- //{"glXBindTexImageEXT", &retrace_glXBindTexImageEXT},
+ {"glXBindTexImageEXT", &retrace_glXBindTexImageEXT},
//{"glXChannelRectSGIX", &retrace_glXChannelRectSGIX},
//{"glXChannelRectSyncSGIX", &retrace_glXChannelRectSyncSGIX},
- {"glXChooseFBConfig", &retrace::ignore},
+ {"glXChooseFBConfig", &retrace_glXChooseFBConfig},
{"glXChooseFBConfigSGIX", &retrace::ignore},
{"glXChooseVisual", &retrace::ignore},
//{"glXCopyContext", &retrace_glXCopyContext},
//{"glXCopyImageSubDataNV", &retrace_glXCopyImageSubDataNV},
- //{"glXCopySubBufferMESA", &retrace_glXCopySubBufferMESA},
+ {"glXCopySubBufferMESA", &retrace_glXCopySubBufferMESA},
{"glXCreateContextAttribsARB", &retrace_glXCreateContextAttribsARB},
{"glXCreateContext", &retrace_glXCreateContext},
//{"glXCreateContextWithConfigSGIX", &retrace_glXCreateContextWithConfigSGIX},
//{"glXCreateGLXPixmapWithConfigSGIX", &retrace_glXCreateGLXPixmapWithConfigSGIX},
{"glXCreateNewContext", &retrace_glXCreateNewContext},
{"glXCreatePbuffer", &retrace_glXCreatePbuffer},
- //{"glXCreatePixmap", &retrace_glXCreatePixmap},
- //{"glXCreateWindow", &retrace_glXCreateWindow},
+ {"glXCreatePixmap", &retrace_glXCreatePixmap},
+ {"XCreatePixmap", &retrace_XCreatePixmap},
+ {"XFreePixmap", &retrace_XFreePixmap},
+ {"PutImageData", &retrace_PutImageData},
+ {"glXCreateWindow", &retrace_glXCreateWindow},
//{"glXCushionSGI", &retrace_glXCushionSGI},
{"glXDestroyContext", &retrace_glXDestroyContext},
//{"glXDestroyGLXPbufferSGIX", &retrace_glXDestroyGLXPbufferSGIX},
//{"glXDestroyGLXPixmap", &retrace_glXDestroyGLXPixmap},
{"glXDestroyPbuffer", &retrace_glXDestroyPbuffer},
//{"glXDestroyPixmap", &retrace_glXDestroyPixmap},
- //{"glXDestroyWindow", &retrace_glXDestroyWindow},
+ {"glXDestroyWindow", &retrace_glXDestroyWindow},
//{"glXFreeContextEXT", &retrace_glXFreeContextEXT},
{"glXGetAGPOffsetMESA", &retrace::ignore},
{"glXGetClientString", &retrace::ignore},
{"glXQuerySwapGroupNV", &retrace::ignore},
{"glXQueryVersion", &retrace::ignore},
//{"glXReleaseBuffersMESA", &retrace_glXReleaseBuffersMESA},
- //{"glXReleaseTexImageEXT", &retrace_glXReleaseTexImageEXT},
+ {"glXReleaseTexImageEXT", &retrace_glXReleaseTexImageEXT},
//{"glXResetFrameCountNV", &retrace_glXResetFrameCountNV},
//{"glXSelectEvent", &retrace_glXSelectEvent},
//{"glXSelectEventSGIX", &retrace_glXSelectEventSGIX},
return default_;
}
+void
+createWindow(glws::Drawable *window)
+{
+ glws::Visual *visual = getVisual(getDefaultProfile());
+
+ glws::createWindow(window, visual);
+}
+
+void
+destroyWindow(glws::Drawable *window)
+{
+ glws::destroyWindow(window);
+}
+
+glws::Drawable *
+createPixmap(unsigned width, unsigned height, unsigned depth)
+{
+ return glws::createPixmap(width, height, depth);
+}
+
+glws::Drawable *
+createGLPixmap(GLXFBConfig fbconfig, glws::Drawable *pixmap,
+ unsigned width, unsigned height, int *attrib_list)
+{
+ return glws::createGLPixmap(fbconfig, pixmap, width, height, attrib_list);
+}
+
+void
+bindTexImage(glws::Drawable *pixmap, int buffer)
+{
+ glws::bindTexImage(pixmap, buffer);
+}
+
+void
+releaseTexImage(glws::Drawable *pixmap, int buffer)
+{
+ glws::releaseTexImage(pixmap, buffer);
+}
+
+void
+copySubBuffer(glws::Drawable *drawable, int x, int y, int width, int height)
+{
+ glws::copySubBuffer(drawable, x, y, width, height);
+}
+
+void
+putImageData(glws::Drawable *drawable, char *data,
+ int width, int height, int depth,
+ int bits_per_pixel, int bytes_per_line, int byte_order)
+{
+ glws::putImageData(drawable, data, width, height, depth,
+ bits_per_pixel, bytes_per_line, byte_order);
+}
+
+GLXFBConfig
+chooseConfig(int *attrib_list)
+{
+ return glws::chooseConfig(attrib_list);
+}
+
} /* namespace glretrace */
virtual ~Visual() {}
};
-
class Drawable
{
public:
virtual void swapBuffers(void) = 0;
};
-
class Context
{
public:
bool
makeCurrent(Drawable *drawable, Context *context);
+void
+createWindow(Drawable *drawable, const Visual *visual);
+
+void
+destroyWindow(Drawable *drawable);
+
+Drawable *
+createPixmap(unsigned width, unsigned height, unsigned depth);
+
+Drawable *
+createGLPixmap(GLXFBConfig fbconfig, Drawable *pixmap,
+ unsigned width, unsigned height, int *attrib_list);
+
+void
+bindTexImage(glws::Drawable *pixmap, int buffer);
+
+void
+releaseTexImage(glws::Drawable *pixmap, int buffer);
+
+void
+copySubBuffer(glws::Drawable *drawable, int x, int y, int width, int height);
+
+void
+putImageData(glws::Drawable *drawable, char *data,
+ int width, int height, int depth,
+ int bits_per_pixel, int bytes_per_line, int byte_order);
+
+GLXFBConfig
+chooseConfig(int *attrib_list);
+
bool
processEvents(void);
return true;
}
+void
+createWindow(Drawable *drawable, const Visual *_visual)
+{
+ EglDrawable *eglDrawable = static_cast<EglDrawable *>(drawable);
+ const EglVisual *visual = static_cast<const EglVisual *>(_visual);
+
+ eglDrawable->surface = eglCreateWindowSurface(display, visual->config,
+ eglDrawable->window, NULL);
+}
+
+void
+destroyWindow(Drawable *drawable)
+{
+ EglDrawable *eglDrawable = static_cast<EglDrawable *>(drawable);
+
+ eglDestroySurface(display, eglDrawable->surface);
+}
+
+Pixmap
+createPixmap(unsigned width, unsigned height, unsigned depth)
+{
+ return XCreatePixmap(display, DefaultRootWindow(display),
+ width, height, depth);
+}
+
} /* namespace glws */
#include "glproc.hpp"
#include "glws.hpp"
+#include <cairo/cairo-xlib.h>
+
namespace glws {
glXWaitX();
}
+ GlxDrawable(const unsigned pixmap_id, int width, int height) :
+ Drawable(NULL, width, height, false)
+ {
+ window = pixmap_id;
+ }
+
void processKeys(void) {
XEvent event;
while (XCheckWindowEvent(display, window, StructureNotifyMask | KeyPressMask, &event)) {
}
};
-
class GlxContext : public Context
{
public:
return true;
}
+void
+createWindow(Drawable *drawable, const Visual *_visual)
+{
+ GlxDrawable *glxDrawable = static_cast<GlxDrawable *>(drawable);
+ const GlxVisual *visual = static_cast<const GlxVisual *>(_visual);
+
+ glXCreateWindow(display, visual->fbconfig, glxDrawable->window, NULL);
+}
+
+Drawable *
+createPixmap(unsigned width, unsigned height, unsigned depth)
+{
+ Pixmap pixmap;
+
+ pixmap = XCreatePixmap(display, DefaultRootWindow(display),
+ width, height, depth);
+
+ printf ("Replayed XCreatePixmap to create pixmap %ld\n", pixmap);
+
+ return new GlxDrawable(pixmap, width, height);
+}
+
+Drawable *
+createGLPixmap(GLXFBConfig fbconfig, Drawable *_pixmap,
+ unsigned width, unsigned height, int *attrib_list)
+{
+ GlxDrawable *pixmap = static_cast<GlxDrawable *>(_pixmap);
+ Pixmap gl_pixmap;
+
+ gl_pixmap = glXCreatePixmap(display, fbconfig, pixmap->window, attrib_list);
+
+ printf ("And replayed glXCreatePixmap to create pixmap %ld\n", gl_pixmap);
+
+ return new GlxDrawable(gl_pixmap, width, height);
+}
+
+void
+destroyWindow(Drawable *drawable)
+{
+/*
+ GlxDrawable *glxDrawable = static_cast<GlxDrawable *>(drawable);
+
+ glXDestroyWindow(display, glxDrawable->window);
+*/
+}
+
+void
+bindTexImage(Drawable *drawable, int buffer)
+{
+ GlxDrawable *glxDrawable = static_cast<GlxDrawable *>(drawable);
+
+ glXBindTexImageEXT(display, glxDrawable->window, buffer, NULL);
+}
+
+void
+releaseTexImage(Drawable *drawable, int buffer)
+{
+ GlxDrawable *glxDrawable = static_cast<GlxDrawable *>(drawable);
+
+ glXReleaseTexImageEXT(display, glxDrawable->window, buffer);
+}
+
+void
+copySubBuffer(Drawable *drawable, int x, int y, int width, int height)
+{
+ GlxDrawable *glxDrawable = static_cast<GlxDrawable *>(drawable);
+
+ glXCopySubBufferMESA(display, glxDrawable->window, x, y, width, height);
+}
+
+void
+putImageData(glws::Drawable *drawable, char *data,
+ int width, int height, int depth,
+ int bits_per_pixel, int bytes_per_line, int byte_order)
+{
+ GlxDrawable *glxDrawable = static_cast<GlxDrawable *>(drawable);
+ GC gc;
+ XImage image;
+
+ printf ("Calling XPutImage to pixmap %ld\n", glxDrawable->window);
+
+ image.width = width;
+ image.height = height;
+ image.format = ZPixmap;
+ image.data = data;
+ image.byte_order = byte_order;
+ image.bitmap_unit = 32;
+ image.bitmap_bit_order = byte_order;
+ image.bitmap_pad = 32;
+ image.depth = depth,
+ image.bytes_per_line = bytes_per_line;
+ image.bits_per_pixel = bits_per_pixel;
+ image.red_mask = 0;
+ image.green_mask = 0;
+ image.blue_mask = 0;
+ image.obdata = 0;
+
+ XInitImage(&image);
+
+ {
+ Window root;
+ int x_ignore, y_ignore;
+ unsigned width, height, depth, border_width_ignore;
+ XGetGeometry(display, glxDrawable->window, &root, &x_ignore, &y_ignore,
+ &width, &height, &border_width_ignore, &depth);
+ }
+
+ gc = XCreateGC(display, glxDrawable->window, 0, NULL);
+ XPutImage(display, glxDrawable->window, gc, &image, 0, 0, 0, 0, width, height);
+
+ {
+ static int count = 0;
+ char filename[] = "put-image-data-X.png";
+ cairo_surface_t *surface;
+
+ surface = cairo_xlib_surface_create(display, glxDrawable->window, DefaultVisual(display, DefaultScreen(display)), width, height);
+
+ filename[15] = '0' + count;
+ cairo_surface_write_to_png(surface, filename);
+
+ cairo_surface_destroy(surface);
+ count++;
+ }
+
+}
+
+GLXFBConfig
+chooseConfig(int *attrib_list)
+{
+ GLXFBConfig *configs;
+ int nelements;
+ configs = glXChooseFBConfig(display, DefaultScreen(display), attrib_list, &nelements);
+ if (nelements)
+ return configs[nelements - 1];
+ else
+ return NULL;
+}
-} /* namespace glws */
+} /* drawable glws */
--- /dev/null
+##########################################################################
+#
+# Copyright 2013 Intel Corporation
+# Copyright 2008-2009 VMware, Inc.
+# All Rights Reserved.
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+# THE SOFTWARE.
+#
+##########################################################################/
+
+"""X API description (minimal functions needed to enable GLX tracing)."""
+
+
+from stdapi import *
+from glapi import *
+
+Display = Opaque("Display *")
+Pixmap = Alias("Pixmap", UInt32)
+Drawable = Alias("Drawable", UInt32)
+
+xapi = Module("X")
+
+xapi.addFunctions([
+ Function(Pixmap, "XCreatePixmap", [(Display, "dpy"), (Drawable, "d"),
+ (UInt, "width"), (UInt, "height"), (UInt, "depth")]),
+ Function(Int, "XFreePixmap", [(Display, "dpy"), (Drawable, "pixmap")]),
+])
${CMAKE_SOURCE_DIR}/specs/stdapi.py
)
+ add_custom_command (
+ OUTPUT xtrace.cpp
+ COMMAND ${PYTHON_EXECUTABLE} ${CMAKE_CURRENT_SOURCE_DIR}/xtrace.py > ${CMAKE_CURRENT_BINARY_DIR}/xtrace.cpp
+ DEPENDS
+ xtrace.py
+ gltrace.py
+ trace.py
+ ${CMAKE_SOURCE_DIR}/specs/xapi.py
+ ${CMAKE_SOURCE_DIR}/specs/glapi.py
+ ${CMAKE_SOURCE_DIR}/specs/glparams.py
+ ${CMAKE_SOURCE_DIR}/specs/gltypes.py
+ ${CMAKE_SOURCE_DIR}/specs/stdapi.py
+ )
+
add_library (glxtrace SHARED
glxtrace.cpp
glcaps.cpp
gltrace_state.cpp
+ xtrace.cpp
)
add_dependencies (glxtrace glproc)
--- /dev/null
+/* Check that our prototypes match */
+#include <X11/X.h>
+
+#include "trace_writer_local.hpp"
+
+#include <cairo/cairo-xlib.h>
+
+#include "glproc.hpp"
+
+#ifdef _WIN32
+# include <malloc.h> // alloca
+# ifndef alloca
+# define alloca _alloca
+# endif
+#else
+# include <alloca.h> // alloca
+#endif
+
+#include "trace.hpp"
+
+static std::map<void *, void *> g_WrappedObjects;
+
+
+static const char * _XCreatePixmap_args[5] = {"dpy", "d", "width", "height", "depth"};
+static const trace::FunctionSig _XCreatePixmap_sig = {2466, "XCreatePixmap", 5, _XCreatePixmap_args};
+
+static const char * _XFreePixmap_args[2] = {"dpy", "pixmap"};
+static const trace::FunctionSig _XFreePixmap_sig = {2467, "XFreePixmap", 2, _XFreePixmap_args};
+
+static const char * _PutImageData_args[8] = {"drawable", "data", "width", "height", "depth", "bits_per_pixel", "bytes_per_line", "byte_order"};
+static const trace::FunctionSig _PutImageData_sig = {2468, "PutImageData", 8, _PutImageData_args};
+
+void
+emit_fake_put_image_data(Display *dpy, Drawable pixmap)
+{
+ Window root;
+ int x_ignore, y_ignore;
+ unsigned width, height, depth, border_width_ignore;
+
+ XGetGeometry(dpy, pixmap, &root, &x_ignore, &y_ignore,
+ &width, &height, &border_width_ignore, &depth);
+
+ {
+ static int count = 0;
+ char filename[] = "image-data-X.png";
+ cairo_surface_t *surface;
+
+ surface = cairo_xlib_surface_create(dpy, pixmap, DefaultVisual(dpy, DefaultScreen(dpy)), width, height);
+
+ filename[11] = '0' + count;
+ cairo_surface_write_to_png(surface, filename);
+
+ cairo_surface_destroy(surface);
+ count++;
+ }
+
+
+ XImage *image = XGetImage(dpy, pixmap, 0, 0, width, height, AllPlanes, ZPixmap);
+ unsigned _call = trace::localWriter.beginEnter(&_PutImageData_sig);
+ trace::localWriter.beginArg(0);
+ trace::localWriter.writeUInt(pixmap);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(1);
+ trace::localWriter.writeBlob(image->data, image->bytes_per_line * image->height);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(2);
+ trace::localWriter.writeSInt(width);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(3);
+ trace::localWriter.writeSInt(height);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(4);
+ trace::localWriter.writeSInt(image->depth);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(5);
+ trace::localWriter.writeSInt(image->bits_per_pixel);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(6);
+ trace::localWriter.writeSInt(image->bytes_per_line);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(7);
+ trace::localWriter.writeSInt(image->byte_order);
+ trace::localWriter.endArg();
+ trace::localWriter.endEnter();
+ trace::localWriter.beginLeave(_call);
+ trace::localWriter.endLeave();
+}
+
+void
+emit_fake_x_create_pixmap(Display *dpy, Drawable pixmap)
+{
+ Window root;
+ int x_ignore, y_ignore;
+ unsigned width, height, depth, border_width_ignore;
+ XGetGeometry(dpy, pixmap, &root, &x_ignore, &y_ignore,
+ &width, &height, &border_width_ignore, &depth);
+ unsigned _call = trace::localWriter.beginEnter(&_XCreatePixmap_sig);
+ printf("Yes, really emitting fake XCreatePixmap (call no. %d)\n", _call);
+ trace::localWriter.beginArg(0);
+ trace::localWriter.writePointer((uintptr_t)dpy);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(1);
+ trace::localWriter.writeUInt(root);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(2);
+ trace::localWriter.writeUInt(width);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(3);
+ trace::localWriter.writeUInt(height);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(4);
+ trace::localWriter.writeUInt(depth);
+ trace::localWriter.endArg();
+ trace::localWriter.endEnter();
+ trace::localWriter.beginLeave(_call);
+ trace::localWriter.beginReturn();
+ trace::localWriter.writeUInt(pixmap);
+ trace::localWriter.endReturn();
+ trace::localWriter.endLeave();
+}
+
+#if 0
+extern "C" PUBLIC
+Pixmap XCreatePixmap(Display * dpy, Drawable d, unsigned int width, unsigned int height, unsigned int depth) {
+ Pixmap _result;
+ if (!trace::isTracingEnabled()) {
+ _result = _XCreatePixmap(dpy, d, width, height, depth);
+ return _result;
+ }
+ unsigned _call = trace::localWriter.beginEnter(&_XCreatePixmap_sig);
+ trace::localWriter.beginArg(0);
+ trace::localWriter.writePointer((uintptr_t)dpy);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(1);
+ trace::localWriter.writeUInt(d);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(2);
+ trace::localWriter.writeUInt(width);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(3);
+ trace::localWriter.writeUInt(height);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(4);
+ trace::localWriter.writeUInt(depth);
+ trace::localWriter.endArg();
+ trace::localWriter.endEnter();
+ _result = _XCreatePixmap(dpy, d, width, height, depth);
+ trace::localWriter.beginLeave(_call);
+ if (true) {
+ }
+ trace::localWriter.beginReturn();
+ trace::localWriter.writeUInt(_result);
+ trace::localWriter.endReturn();
+ trace::localWriter.endLeave();
+ return _result;
+}
+
+extern "C" PUBLIC
+int XFreePixmap(Display * dpy, Drawable pixmap) {
+ int _result;
+ if (!trace::isTracingEnabled()) {
+ _result = _XFreePixmap(dpy, pixmap);
+ return _result;
+ }
+ unsigned _call = trace::localWriter.beginEnter(&_XFreePixmap_sig);
+ trace::localWriter.beginArg(0);
+ trace::localWriter.writePointer((uintptr_t)dpy);
+ trace::localWriter.endArg();
+ trace::localWriter.beginArg(1);
+ trace::localWriter.writeUInt(pixmap);
+ trace::localWriter.endArg();
+ trace::localWriter.endEnter();
+ _result = _XFreePixmap(dpy, pixmap);
+ trace::localWriter.beginLeave(_call);
+ if (true) {
+ }
+ trace::localWriter.beginReturn();
+ trace::localWriter.writeSInt(_result);
+ trace::localWriter.endReturn();
+ trace::localWriter.endLeave();
+ return _result;
+}
+#endif
--- /dev/null
+##########################################################################
+#
+# Copyright 2013 Intel Corporation
+# Copyright 2011 Jose Fonseca
+# Copyright 2008-2010 VMware, Inc.
+# All Rights Reserved.
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+# THE SOFTWARE.
+#
+##########################################################################/
+
+
+"""X tracing generator (minimal calls needed to enable GLX tracing)."""
+
+from trace import Tracer
+from specs.stdapi import Module, API
+from specs.xapi import xapi
+
+class XTracer(Tracer):
+ pass
+
+if __name__ == '__main__':
+ print '/* Check that our prototypes match */'
+ print '#include <X11/X.h>'
+ print
+ print '#include "trace_writer_local.hpp"'
+ print
+ print '#include "glproc.hpp"'
+ print
+
+ module = Module()
+ module.mergeModule(xapi)
+ api = API()
+ api.addModule(module)
+ tracer = XTracer()
+ tracer.traceApi(api)