From e70a5f8b7febfa19a689d4978943602d625eaba3 Mon Sep 17 00:00:00 2001 From: Nicolas Viennot Date: Wed, 12 Jun 2013 17:57:53 -0400 Subject: [PATCH] Add strack trace debug function --- Makefile.am | 1 + tmate-debug.c | 75 +++++++++++++++++++++++++++++++++++++++++++++++++++ tmate.h | 3 +++ 3 files changed, 79 insertions(+) create mode 100644 tmate-debug.c diff --git a/Makefile.am b/Makefile.am index 9cf3fe46..beff8484 100644 --- a/Makefile.am +++ b/Makefile.am @@ -177,6 +177,7 @@ dist_tmate_SOURCES = \ session.c \ signal.c \ status.c \ + tmate-debug.c \ tmate-ssh-client.c \ tmate-encoder.c \ tmate-decoder.c \ diff --git a/tmate-debug.c b/tmate-debug.c new file mode 100644 index 00000000..c480e658 --- /dev/null +++ b/tmate-debug.c @@ -0,0 +1,75 @@ +#include +#include +#include +#include +#include "tmate.h" + +#if DEBUG + +static int print_resolved_stack_frame(const char *frame) +{ + char file[100]; + char cmd[200]; + char output[300]; + char address[20]; + char *line; + FILE *ps; + + static regex_t _regex; + static regex_t *regex; + regmatch_t matches[3]; + + if (!regex) { + if (regcomp(&_regex, "(.+)\\(\\) \\[([^]]+)\\]", REG_EXTENDED)) + return -1; + regex = &_regex; + } + + if (regexec(regex, frame, 3, matches, 0)) + return -1; + + memcpy(file, &frame[matches[1].rm_so], matches[1].rm_eo - matches[1].rm_so); + file[matches[1].rm_eo - matches[1].rm_so] = 0; + + memcpy(address, &frame[matches[2].rm_so], matches[2].rm_eo - matches[2].rm_so); + address[matches[2].rm_eo - matches[2].rm_so] = 0; + + sprintf(cmd, "addr2line -e %s %s -f -p -s", file, address); + + ps = popen(cmd, "r"); + if (!ps) + return -1; + + line = fgets(output, sizeof(output), ps); + pclose(ps); + + if (!line) + return -1; + + line[strlen(line)-1] = 0; /* remove \n */ + tmate_debug("%s(%s) [%s]", file, line, address); + return 0; +} +#endif + +void tmate_print_trace(void) +{ + void *array[20]; + size_t size; + char **strings; + size_t i; + + size = backtrace (array, 20); + strings = backtrace_symbols (array, size); + + tmate_debug ("============ %zd stack frames ============", size); + + for (i = 1; i < size; i++) { +#if DEBUG + if (print_resolved_stack_frame(strings[i]) < 0) +#endif + tmate_debug("%s", strings[i]); + } + + free (strings); +} diff --git a/tmate.h b/tmate.h index 7a07facd..c9848045 100644 --- a/tmate.h +++ b/tmate.h @@ -109,4 +109,7 @@ extern void tmate_ssh_client_init(struct tmate_ssh_client *client, extern struct tmate_encoder *tmate_encoder; extern void tmate_client_start(void); +/* tmate-debug.c */ +extern void tmate_print_trace (void); + #endif