Add start of a malloc trace evaluation executable.
authorMilian Wolff <mail@milianw.de>
Mon, 19 May 2014 14:24:10 +0000 (16:24 +0200)
committerMilian Wolff <mail@milianw.de>
Mon, 19 May 2014 14:24:10 +0000 (16:24 +0200)
This shows that we can do post-mortem address resolution.
Not yet really functional but enough for a quick test.

CMakeLists.txt
malloctrace_main.cpp [new file with mode: 0644]

index ac4133e..2e7534b 100644 (file)
@@ -15,4 +15,7 @@ target_link_libraries(mallocinfo dumpmallocinfo)
 add_library(malloctrace SHARED malloctrace.cpp)
 target_link_libraries(malloctrace -ldl backtrace)
 
+add_executable(malloctrace_eval malloctrace_main.cpp)
+target_link_libraries(malloctrace_eval backtrace)
+
 install(TARGETS mallocinfo RUNTIME DESTINATION bin)
diff --git a/malloctrace_main.cpp b/malloctrace_main.cpp
new file mode 100644 (file)
index 0000000..9565613
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2014 Milian Wolff <mail@milianw.de>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Library General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+#include <iostream>
+#include <fstream>
+#include <unordered_map>
+
+#include "libbacktrace/backtrace.h"
+
+using namespace std;
+
+namespace {
+
+void printUsage(ostream& out)
+{
+    out << "malloctrace_main MALLOCTRACE_LOG_FILE..." << endl;
+}
+
+struct Module
+{
+    Module(string _fileName, uintptr_t baseAddress, bool isExe)
+        : backtraceState(nullptr)
+        , fileName(move(_fileName))
+        , baseAddress(baseAddress)
+        , isExe(isExe)
+    {
+        backtraceState = backtrace_create_state(fileName.c_str(), /* we are single threaded, so: not thread safe */ false,
+                                                [] (void *data, const char *msg, int errnum) {
+                                                    const Module* module = reinterpret_cast<Module*>(data);
+                                                    cerr << "Failed to create backtrace state for file " << module->fileName
+                                                         << ": " << msg << " (error code " << errnum << ")" << endl;
+                                                }, this);
+
+        if (backtraceState) {
+            backtrace_fileline_initialize(backtraceState, baseAddress, isExe,
+                                          [] (void *data, const char *msg, int errnum) {
+                                            const Module* module = reinterpret_cast<Module*>(data);
+                                            cerr << "Failed to initialize backtrace fileline for file " << module->fileName
+                                                 << ", base address: " << hex << module->baseAddress << dec << ", exe: " << module->isExe
+                                                 << ": " << msg << " (error code " << errnum << ")" << endl;
+                                        }, this);
+        }
+    }
+
+    string resolveAddress(uintptr_t address)
+    {
+        string ret;
+        backtrace_syminfo(backtraceState, address,
+                          [] (void *data, uintptr_t /*pc*/, const char *symname, uintptr_t /*symval*/, uintptr_t /*symsize*/) {
+                            *reinterpret_cast<string*>(data) = symname;
+                          }, &errorCallback, &ret);
+        return ret;
+    }
+
+    static void errorCallback(void */*data*/, const char *msg, int errnum)
+    {
+        cerr << "Module backtrace error (code " << errnum << "): " << msg << endl;
+    }
+
+    backtrace_state* backtraceState;
+    string fileName;
+    uintptr_t baseAddress;
+    bool isExe;
+};
+
+struct AccumulatedTraceData
+{
+    unordered_map<unsigned int, Module> modules;
+};
+
+}
+
+int main(int argc, char** argv)
+{
+    if (argc < 2) {
+        printUsage(cerr);
+        return 1;
+    }
+
+
+    for (int i = 1; i < argc; ++i) {
+        fstream in(argv[i], std::fstream::in);
+        if (!in.is_open()) {
+            cerr << "Failed to open malloctrace log file: " << argv[1] << endl;
+            cerr << endl;
+            printUsage(cerr);
+            return 1;
+        }
+        // TODO: parse file
+    }
+
+    return 0;
+}