mfabik / rpms / satyr

Forked from rpms/satyr 3 years ago
Clone

Blame SOURCES/satyr-0.13-debug-unwinding-from-core-hook-using-satyr-binary.patch

0e0bbf
From 455c47f1f18858c439ff0a0b833ce93c9f79045f Mon Sep 17 00:00:00 2001
0e0bbf
From: Martin Milata <mmilata@redhat.com>
0e0bbf
Date: Mon, 24 Nov 2014 14:38:06 +0100
0e0bbf
Subject: [PATCH 4/5] debug unwinding from core hook using satyr binary
0e0bbf
0e0bbf
Write "|/usr/bin/satyr debug unwind-from-hook %e %i %s" to
0e0bbf
/proc/sys/kernel/core_pattern in order to use this. Before kernel 3.18
0e0bbf
the %i flag is not available - you can use %p for single-thread
0e0bbf
processes.
0e0bbf
0e0bbf
Related to abrt/abrt#829.
0e0bbf
0e0bbf
Signed-off-by: Martin Milata <mmilata@redhat.com>
0e0bbf
---
0e0bbf
 satyr.c | 81 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
0e0bbf
 1 file changed, 81 insertions(+)
0e0bbf
0e0bbf
diff --git a/satyr.c b/satyr.c
0e0bbf
index 7bdaa45..6e1ed28 100644
0e0bbf
--- a/satyr.c
0e0bbf
+++ b/satyr.c
0e0bbf
@@ -20,6 +20,8 @@
0e0bbf
 #include "gdb/stacktrace.h"
0e0bbf
 #include "gdb/thread.h"
0e0bbf
 #include "gdb/frame.h"
0e0bbf
+#include "core/unwind.h"
0e0bbf
+#include "core/stacktrace.h"
0e0bbf
 #include "utils.h"
0e0bbf
 #include "location.h"
0e0bbf
 #include "strbuf.h"
0e0bbf
@@ -37,6 +39,7 @@
0e0bbf
 #include <sysexits.h>
0e0bbf
 #include <assert.h>
0e0bbf
 #include <libgen.h>
0e0bbf
+#include <time.h>
0e0bbf
 
0e0bbf
 static char *g_program_name;
0e0bbf
 
0e0bbf
@@ -275,6 +278,82 @@ debug_duphash(int argc, char **argv)
0e0bbf
 }
0e0bbf
 
0e0bbf
 static void
0e0bbf
+debug_unwind_from_hook(int argc, char **argv)
0e0bbf
+{
0e0bbf
+    if (argc != 3)
0e0bbf
+    {
0e0bbf
+        fprintf(stderr, "Wrong number of arguments.\n");
0e0bbf
+        fprintf(stderr, "Usage: satyr debug unwind-from-hook "
0e0bbf
+                        "<executable> <tid> <signal>\n");
0e0bbf
+        exit(1);
0e0bbf
+    }
0e0bbf
+
0e0bbf
+    char *executable = argv[0];
0e0bbf
+    char *end;
0e0bbf
+    unsigned long tid = strtoul(argv[1], &end, 10);
0e0bbf
+    if (*end != '\0')
0e0bbf
+    {
0e0bbf
+        fprintf(stderr, "Wrong tid\n");
0e0bbf
+        exit(1);
0e0bbf
+    }
0e0bbf
+
0e0bbf
+    unsigned long signum = strtoul(argv[2], &end, 10);
0e0bbf
+    if (*end != '\0')
0e0bbf
+    {
0e0bbf
+        fprintf(stderr, "Wrong signal number\n");
0e0bbf
+        exit(1);
0e0bbf
+    }
0e0bbf
+
0e0bbf
+    char *error_message = NULL;
0e0bbf
+    struct sr_core_stacktrace *core_stacktrace;
0e0bbf
+
0e0bbf
+    core_stacktrace = sr_core_stacktrace_from_core_hook(tid, executable, signum,
0e0bbf
+                                                        &error_message);
0e0bbf
+    if (!core_stacktrace)
0e0bbf
+    {
0e0bbf
+        fprintf(stderr, "Unwind failed: %s\n", error_message);
0e0bbf
+        exit(1);
0e0bbf
+    }
0e0bbf
+
0e0bbf
+    char *json = sr_core_stacktrace_to_json(core_stacktrace);
0e0bbf
+    // Add newline to the end of core stacktrace file to make text
0e0bbf
+    // editors happy.
0e0bbf
+    json = sr_realloc(json, strlen(json) + 2);
0e0bbf
+    strcat(json, "\n");
0e0bbf
+
0e0bbf
+    time_t t = time(NULL);
0e0bbf
+    struct tm *tm = localtime(&t);
0e0bbf
+    char core_backtrace_filename[256];
0e0bbf
+
0e0bbf
+    if (tm == NULL)
0e0bbf
+    {
0e0bbf
+        perror("localtime");
0e0bbf
+        exit(1);
0e0bbf
+    }
0e0bbf
+
0e0bbf
+    if (strftime(core_backtrace_filename, sizeof(core_backtrace_filename),
0e0bbf
+                 "/tmp/satyr-core-stacktrace-%F-%T.json", tm) == 0)
0e0bbf
+    {
0e0bbf
+        fprintf(stderr, "stftime failed\n");
0e0bbf
+        exit(1);
0e0bbf
+    }
0e0bbf
+
0e0bbf
+
0e0bbf
+    bool success = sr_string_to_file(core_backtrace_filename,
0e0bbf
+                                    json,
0e0bbf
+                                    &error_message);
0e0bbf
+
0e0bbf
+    if (!success)
0e0bbf
+    {
0e0bbf
+        fprintf(stderr, "Failed to write stacktrace: %s\n", error_message);
0e0bbf
+        exit(1);
0e0bbf
+    }
0e0bbf
+
0e0bbf
+    free(json);
0e0bbf
+    sr_core_stacktrace_free(core_stacktrace);
0e0bbf
+}
0e0bbf
+
0e0bbf
+static void
0e0bbf
 debug(int argc, char **argv)
0e0bbf
 {
0e0bbf
     /* Debug command requires a subcommand. */
0e0bbf
@@ -288,6 +367,8 @@ debug(int argc, char **argv)
0e0bbf
         debug_normalize(argc - 1, argv + 1);
0e0bbf
     else if (0 == strcmp(argv[0], "duphash"))
0e0bbf
         debug_duphash(argc - 1, argv + 1);
0e0bbf
+    else if (0 == strcmp(argv[0], "unwind-from-hook"))
0e0bbf
+        debug_unwind_from_hook(argc - 1, argv + 1);
0e0bbf
     else
0e0bbf
     {
0e0bbf
         fprintf(stderr, "Unknown debug subcommand.\n");
0e0bbf
-- 
0e0bbf
2.4.3
0e0bbf