From: José Fonseca Date: Sat, 20 Nov 2010 09:03:10 +0000 (+0000) Subject: Make better use of C++ implicit casts. Support arrays. X-Git-Url: https://git.cworth.org/git?a=commitdiff_plain;h=c9edb83044ae17a35c42c10504ffffd0f12f3598;p=apitrace Make better use of C++ implicit casts. Support arrays. --- diff --git a/base.py b/base.py index ab2382f..2f2b1d0 100644 --- a/base.py +++ b/base.py @@ -70,6 +70,44 @@ class Visitor: raise NotImplementedError +class Rebuilder(Visitor): + + def visit_void(self, void): + return void + + def visit_literal(self, literal): + return literal + + def visit_const(self, const): + return Const(const.type) + + def visit_struct(self, struct): + members = [self.visit(member) for member in struct.members] + return Struct(struct.name, members) + + def visit_array(self, array): + type = self.visit(array.type) + return Array(type, array.length) + + def visit_enum(self, enum): + return enum + + def visit_bitmask(self, bitmask): + type = self.visit(bitmask.type) + return Bitmask(type, bitmask.values) + + def visit_pointer(self, pointer): + type = self.visit(pointer.type) + return Pointer(type) + + def visit_alias(self, alias): + type = self.visit(alias.type) + return Alias(alias.expr, type) + + def visit_opaque(self, opaque): + return opaque + + class Type: __seq = 0 @@ -321,8 +359,8 @@ class Struct(Concrete): class Alias(Type): - def __init__(self, name, type): - Type.__init__(self, name) + def __init__(self, expr, type): + Type.__init__(self, expr) self.type = type def visit(self, visitor, *args, **kwargs): diff --git a/gl.py b/gl.py index 4db1041..7f74380 100644 --- a/gl.py +++ b/gl.py @@ -25,7 +25,7 @@ from base import * -GLboolean = Enum("GLboolean", ["GL_FALSE", "GL_TRUE"]) +GLboolean = Alias("GLboolean", Bool) GLvoid = Alias("GLvoid", Void) GLbyte = Alias("GLbyte", SChar) GLshort = Alias("GLshort", Short) diff --git a/glretrace.py b/glretrace.py index 5644e36..a689cc1 100644 --- a/glretrace.py +++ b/glretrace.py @@ -28,22 +28,34 @@ import base from glx import libgl + +class ConstRemover(base.Rebuilder): + + def visit_const(self, const): + return const.type + + class ValueExtractor(base.Visitor): def visit_literal(self, type, lvalue, rvalue): - #print ' %s = static_cast<%s>(Trace::as%s(%s));' % (lvalue, type, type.format, rvalue) - print ' %s = Trace::as%s(%s);' % (lvalue, type.format, rvalue) + print ' %s = %s;' % (lvalue, rvalue) def visit_alias(self, type, lvalue, rvalue): self.visit(type.type, lvalue, rvalue) def visit_enum(self, type, lvalue, rvalue): - #print ' %s = static_cast<%s>(Trace::as%s(%s));' % (lvalue, type, 'SInt', rvalue) - print ' %s = Trace::as%s(%s);' % (lvalue, 'SInt', rvalue) + print ' %s = %s;' % (lvalue, rvalue) def visit_bitmask(self, type, lvalue, rvalue): self.visit(type.type, lvalue, rvalue) + def visit_array(self, array, lvalue, rvalue): + print ' %s = new %s[%s];' % (lvalue, array.type, array.length) + index = '__i' + array.id + print ' for(size_t {i} = 0; {i} < {length}; ++{i}) {{'.format(i = index, length = array.length) + self.visit(array.type, '%s[%s]' % (lvalue, index), '%s[%s]' % (rvalue, index)) + print ' }' + def retrace_function(function): @@ -51,8 +63,8 @@ def retrace_function(function): if not function.name.startswith('glX'): success = True for arg_type, arg_name in function.args: + arg_type = ConstRemover().visit(arg_type) print ' %s %s;' % (arg_type, arg_name) - for arg_type, arg_name in function.args: rvalue = 'call.arg("%s")' % (arg_name,) lvalue = arg_name try: diff --git a/trace_model.cpp b/trace_model.cpp index 8f10224..b832587 100644 --- a/trace_model.cpp +++ b/trace_model.cpp @@ -121,26 +121,27 @@ std::ostream & operator <<(std::ostream &os, Value *value) { } -static const Value *unwrap(const Value &node) { - const Const *c = dynamic_cast(&node); +static inline const Value *unwrap(const Value *node) { + const Const *c = dynamic_cast(node); if (c) return c->value; - return &node; + return node; } -signed long long asSInt(const Value &node) { - const SInt *sint = dynamic_cast(unwrap(node)); + +Value::operator signed long long(void) const { + const SInt *sint = dynamic_cast(unwrap(this)); if (sint) return sint->value; - const UInt *uint = dynamic_cast(unwrap(node)); + const UInt *uint = dynamic_cast(unwrap(this)); if (uint) return uint->value; assert(0); return 0; } -unsigned long long asUInt(const Value &node) { - const UInt *uint = dynamic_cast(unwrap(node)); +Value::operator unsigned long long(void) const { + const UInt *uint = dynamic_cast(unwrap(this)); if (uint) return uint->value; assert(0); @@ -148,14 +149,24 @@ unsigned long long asUInt(const Value &node) { } -double asFloat(const Value &node) { - const Float *fl = dynamic_cast(unwrap(node)); +Value::operator double(void) const { + const Float *fl = dynamic_cast(unwrap(this)); assert(fl); return fl->value; } static Void void_; +const Value & Value::operator[](size_t index) const { + const Array *array = dynamic_cast(unwrap(this)); + if (array) { + if (index < array->values.size()) { + return *array->values[index]; + } + } + return void_; +} + Value & Call::arg(const char *name) { for (std::list::iterator it = args.begin(); it != args.end(); ++it) { if (it->first == name) { diff --git a/trace_model.hpp b/trace_model.hpp index 8702374..26a378d 100644 --- a/trace_model.hpp +++ b/trace_model.hpp @@ -48,6 +48,48 @@ class Value { public: virtual void visit(Visitor &visitor) = 0; + + operator signed long long (void) const; + operator unsigned long long (void) const; + operator double (void) const; + + inline operator signed char (void) const { + return static_cast(*this); + } + + inline operator unsigned char (void) const { + return static_cast(*this); + } + + inline operator signed short (void) const { + return static_cast(*this); + } + + inline operator unsigned short (void) const { + return static_cast(*this); + } + + inline operator signed (void) const { + return static_cast(*this); + } + + inline operator unsigned (void) const { + return static_cast(*this); + } + + inline operator signed long (void) const { + return static_cast(*this); + } + + inline operator unsigned long (void) const { + return static_cast(*this); + } + + inline operator float (void) const { + return static_cast(*this); + } + + const Value & operator[](size_t index) const; };