From b16a4a88f021ec70cae2fc6278c2bd25224681a8 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Jos=C3=A9=20Fonseca?= Date: Fri, 16 Mar 2012 08:21:29 +0000 Subject: [PATCH] Diff with symbolic names. --- cli/cli_pickle.cpp | 74 +++++++++++++++++++++++++++++++++--------- common/pickle.hpp | 8 +++-- common/trace_dump.cpp | 15 +++++---- common/trace_model.hpp | 11 +++++++ scripts/tracediff2.py | 7 +++- 5 files changed, 89 insertions(+), 26 deletions(-) diff --git a/cli/cli_pickle.cpp b/cli/cli_pickle.cpp index 8fdcd44..e3222db 100644 --- a/cli/cli_pickle.cpp +++ b/cli/cli_pickle.cpp @@ -47,10 +47,12 @@ class PickleVisitor : public trace::Visitor { protected: PickleWriter &writer; + bool symbolic; public: - PickleVisitor(PickleWriter &_writer) : - writer(_writer) { + PickleVisitor(PickleWriter &_writer, bool _symbolic) : + writer(_writer), + symbolic(_symbolic) { } void visit(Null *node) { @@ -82,23 +84,56 @@ public: } void visit(Enum *node) { - // TODO: keep symbolic name + if (symbolic) { + const EnumValue *it = node->lookup(); + if (it) { + writer.writeString(it->name); + return; + } + } writer.writeInt(node->value); } void visit(Bitmask *node) { - // TODO: keep symbolic name - writer.writeInt(node->value); + if (symbolic) { + unsigned long long value = node->value; + const BitmaskSig *sig = node->sig; + writer.beginList(); + for (const BitmaskFlag *it = sig->flags; it != sig->flags + sig->num_flags; ++it) { + if ((it->value && (value & it->value) == it->value) || + (!it->value && value == 0)) { + writer.writeString(it->name); + value &= ~it->value; + } + if (value == 0) { + break; + } + } + if (value) { + writer.writeInt(value); + } + writer.endList(); + } else { + writer.writeInt(node->value); + } } void visit(Struct *node) { - writer.beginDict(); - for (unsigned i = 0; i < node->sig->num_members; ++i) { - writer.beginItem(node->sig->member_names[i]); - _visit(node->members[i]); - writer.endItem(); + if (false) { + writer.beginDict(); + for (unsigned i = 0; i < node->sig->num_members; ++i) { + writer.beginItem(node->sig->member_names[i]); + _visit(node->members[i]); + writer.endItem(); + } + writer.endDict(); + } else { + writer.beginTuple(); + for (unsigned i = 0; i < node->sig->num_members; ++i) { + _visit(node->members[i]); + } + writer.endTuple(); } - writer.endDict(); } void visit(Array *node) { @@ -157,6 +192,7 @@ usage(void) << synopsis << "\n" "\n" " -h, --help show this help message and exit\n" + " -s, --symbolic dump symbolic names\n" " --calls=CALLSET only dump specified calls\n" ; } @@ -166,11 +202,12 @@ enum { }; const static char * -shortOptions = "h"; +shortOptions = "hs"; const static struct option longOptions[] = { {"help", no_argument, 0, 'h'}, + {"symbolic", no_argument, 0, 's'}, {"calls", required_argument, 0, CALLS_OPT}, {0, 0, 0, 0} }; @@ -178,12 +215,17 @@ longOptions[] = { static int command(int argc, char *argv[]) { + bool symbolic; + int opt; while ((opt = getopt_long(argc, argv, shortOptions, longOptions, NULL)) != -1) { switch (opt) { case 'h': usage(); return 0; + case 's': + symbolic = true; + break; case CALLS_OPT: calls = trace::CallSet(optarg); break; @@ -195,6 +237,9 @@ command(int argc, char *argv[]) } os::setBinaryMode(stdout); + + PickleWriter writer(std::cout); + PickleVisitor visitor(writer, symbolic); for (int i = optind; i < argc; ++i) { trace::Parser parser; @@ -207,10 +252,9 @@ command(int argc, char *argv[]) trace::Call *call; while ((call = parser.parse_call())) { if (calls.contains(*call)) { - PickleWriter writer(std::cout); - PickleVisitor visitor(writer); - + writer.begin(); visitor.visit(call); + writer.end(); } delete call; } diff --git a/common/pickle.hpp b/common/pickle.hpp index f333960..736025b 100644 --- a/common/pickle.hpp +++ b/common/pickle.hpp @@ -106,13 +106,15 @@ private: public: PickleWriter(std::ostream &_os) : - os(_os) - { + os(_os) { + } + + inline void begin() { os.put(PROTO); os.put(2); } - ~PickleWriter() { + inline void end() { os.put(STOP); } diff --git a/common/trace_dump.cpp b/common/trace_dump.cpp index c55bbb1..0f7ee36 100644 --- a/common/trace_dump.cpp +++ b/common/trace_dump.cpp @@ -129,12 +129,10 @@ public: } void visit(Enum *node) { - const EnumSig *sig = node->sig; - for (const EnumValue *it = sig->values; it != sig->values + sig->num_values; ++it) { - if (it->value == node->value) { - os << literal << it->name << normal; - return; - } + const EnumValue *it = node->lookup(); + if (it) { + os << literal << it->name << normal; + return; } os << literal << node->value << normal; } @@ -143,7 +141,7 @@ public: unsigned long long value = bitmask->value; const BitmaskSig *sig = bitmask->sig; bool first = true; - for (const BitmaskFlag *it = sig->flags; value != 0 && it != sig->flags + sig->num_flags; ++it) { + for (const BitmaskFlag *it = sig->flags; it != sig->flags + sig->num_flags; ++it) { if ((it->value && (value & it->value) == it->value) || (!it->value && value == 0)) { if (!first) { @@ -153,6 +151,9 @@ public: value &= ~it->value; first = false; } + if (value == 0) { + break; + } } if (value || first) { if (!first) { diff --git a/common/trace_model.hpp b/common/trace_model.hpp index 7973026..a2fd97f 100644 --- a/common/trace_model.hpp +++ b/common/trace_model.hpp @@ -228,6 +228,17 @@ public: void visit(Visitor &visitor); const EnumSig *sig; + + const EnumValue * + lookup() { + // TODO: use a std::map + for (const EnumValue *it = sig->values; it != sig->values + sig->num_values; ++it) { + if (it->value == value) { + return it; + } + } + return NULL; + } }; diff --git a/scripts/tracediff2.py b/scripts/tracediff2.py index 001f322..168c7ce 100755 --- a/scripts/tracediff2.py +++ b/scripts/tracediff2.py @@ -63,6 +63,7 @@ def readtrace(trace): args = [ options.apitrace, 'pickle', + '--symbolic', '--calls=' + options.calls, trace ], @@ -129,10 +130,11 @@ class SDiffer: b_call = self.b[blo + i] assert a_call.functionName == b_call.functionName assert len(a_call.args) == len(b_call.args) - self.equal_prefix() + self.replace_prefix() self.highlighter.bold(True) self.highlighter.write(b_call.functionName) self.highlighter.bold(False) + self.highlighter.write('(') sep = '' for j in xrange(len(b_call.args)): self.highlighter.write(sep) @@ -206,6 +208,9 @@ class SDiffer: def normal_suffix(self): self.highlighter.normal() + + def replace_prefix(self): + self.highlighter.write('| ') def main(): -- 2.43.0