[Libreoffice-commits] core.git: sal/osl
Stephan Bergmann
sbergman at redhat.com
Thu Feb 9 09:44:42 UTC 2017
sal/osl/unx/backtrace.c | 20 ++++++++++++++++++++
sal/osl/unx/backtrace.h | 2 ++
sal/osl/unx/backtraceapi.cxx | 43 ++++++++++++++++++++++++++++++++++++++++---
3 files changed, 62 insertions(+), 3 deletions(-)
New commits:
commit c71f4dc97b8927cc5690454006b8aa6136dbcce2
Author: Stephan Bergmann <sbergman at redhat.com>
Date: Thu Feb 9 10:37:25 2017 +0100
Implement SAL_DEBUG_BACKTRACE for Linux
...by using glibc's backtrace_symbols(3). If this is ever implemented for other
platforms, backtrace_symbols' interface may turn out to be awkward; but just use
it directly for now. Also, the output from backtrace_symbols isn't too useful
in itself, as for non-exported symbols it only prints soname+offset, but some
addr2line postprocessing can turn that into something half-way decent.
Change-Id: I58cc7912aa7d8031729fc116a82a409c1c16977a
diff --git a/sal/osl/unx/backtrace.c b/sal/osl/unx/backtrace.c
index 1945f03..b32fbef 100644
--- a/sal/osl/unx/backtrace.c
+++ b/sal/osl/unx/backtrace.c
@@ -94,6 +94,11 @@ int backtrace( void **buffer, int max_frames )
return i;
}
+char ** backtrace_symbols(void * const * buffer, int size)
+{
+ return NULL; /*TODO*/
+}
+
void backtrace_symbols_fd( void **buffer, int size, int fd )
{
FILE *fp = fdopen( fd, "w" );
@@ -171,6 +176,11 @@ int backtrace( void **buffer, int max_frames )
return i;
}
+char ** backtrace_symbols(void * const * buffer, int size)
+{
+ return NULL; /*TODO*/
+}
+
void backtrace_symbols_fd( void **buffer, int size, int fd )
{
FILE *fp = fdopen( fd, "w" );
@@ -239,6 +249,11 @@ int backtrace( void **buffer, int max_frames )
return i;
}
+char ** backtrace_symbols(void * const * buffer, int size)
+{
+ return NULL; /*TODO*/
+}
+
void backtrace_symbols_fd( void **buffer, int size, int fd )
{
FILE *fp = fdopen( fd, "w" );
@@ -282,6 +297,11 @@ int backtrace( void **buffer, int max_frames )
return 0;
}
+char ** backtrace_symbols(void * const * buffer, int size)
+{
+ return NULL; /*TODO*/
+}
+
void backtrace_symbols_fd( void **buffer, int size, int fd )
{
}
diff --git a/sal/osl/unx/backtrace.h b/sal/osl/unx/backtrace.h
index 7cc574b..4695fd2 100644
--- a/sal/osl/unx/backtrace.h
+++ b/sal/osl/unx/backtrace.h
@@ -28,6 +28,8 @@ extern "C" {
int backtrace( void **buffer, int max_frames );
+char ** backtrace_symbols(void * const * buffer, int size);
+
void backtrace_symbols_fd( void **buffer, int size, int fd );
/* no frame.h on FreeBSD */
diff --git a/sal/osl/unx/backtraceapi.cxx b/sal/osl/unx/backtraceapi.cxx
index c212184..267a331 100644
--- a/sal/osl/unx/backtraceapi.cxx
+++ b/sal/osl/unx/backtraceapi.cxx
@@ -9,13 +9,50 @@
#include <sal/config.h>
+#include <cassert>
+#include <cstdlib>
+#include <memory>
+
+#include <o3tl/runtimetooustring.hxx>
+#include <rtl/ustrbuf.hxx>
#include <rtl/ustring.hxx>
+
+#include "backtrace.h"
#include "backtraceasstring.hxx"
-// FIXME: no-op for now; it needs implementing, cf. above.
-OUString osl::detail::backtraceAsString(int /*maxNoStackFramesToDisplay*/)
+namespace {
+
+struct FreeGuard {
+ FreeGuard(char ** theBuffer): buffer(theBuffer) {}
+
+ ~FreeGuard() { std::free(buffer); }
+
+ char ** buffer;
+};
+
+}
+
+OUString osl::detail::backtraceAsString(int maxNoStackFramesToDisplay)
{
- return OUString();
+ assert(maxNoStackFramesToDisplay >= 0);
+ if (maxNoStackFramesToDisplay == 0) {
+ return OUString();
+ }
+ auto b1 = std::unique_ptr<void *[]>(new void *[maxNoStackFramesToDisplay]);
+ int n = backtrace(b1.get(), maxNoStackFramesToDisplay);
+ FreeGuard b2(backtrace_symbols(b1.get(), n));
+ b1.reset();
+ if (b2.buffer == nullptr) {
+ return OUString();
+ }
+ OUStringBuffer b3;
+ for (int i = 0; i != n; ++i) {
+ if (i != 0) {
+ b3.append("\n");
+ }
+ b3.append(o3tl::runtimeToOUString(b2.buffer[i]));
+ }
+ return b3.makeStringAndClear();
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
More information about the Libreoffice-commits
mailing list