Skip to content
Snippets Groups Projects
Commit ba526ce5 authored by Sebastian Hahta's avatar Sebastian Hahta
Browse files

Do not decode trace when it is not used.

parent 1a3995aa
Branches
Tags
1 merge request!309Decode trace symbols only when trace requested (GCC)
Pipeline #27103 passed
......@@ -44,17 +44,25 @@ class exception : public std::exception
return msg_.c_str();
}
const char * trace () const throw () {
return trace_.c_str();
std::string trace() const throw () {
return decode_backtrace();
}
void ignore() const { processed_ = true; }
private:
std::string decode_backtrace() const;
std::string msg_;
std::string trace_;
mutable bool processed_;
#ifdef __GNUC__
static const int TRACE_SIZE_MAX_ = 16;
void* trace_[TRACE_SIZE_MAX_];
int trace_size_;
#endif
};
}
#define FTL_Error(A) (ftl::exception(ftl::Formatter() << __FILE__ << ":" << __LINE__ << ": " << A))
......
......@@ -7,53 +7,52 @@
#include <execinfo.h>
#include <dlfcn.h>
#include <cxxabi.h>
#endif
using ftl::exception;
using std::string;
static std::string demangle(const char* name) {
std::string demangle(const char* name) {
if (!name) {
return "[unknown symbol]";
}
#ifdef __GNUC__
int status;
char* demangled = abi::__cxa_demangle(name, NULL, 0, &status);
if (!demangled) {
return std::string(name);
}
else {
auto result = string(demangled);
auto result = std::string(demangled);
free(demangled);
return result;
}
#else
return std::string(name);
#endif
}
static std::string addr_to_string(const void* addr) {
#endif
using ftl::exception;
using std::string;
string addr_to_string(const void* addr) {
std::stringstream ss;
ss << addr;
return ss.str();
}
static std::string getBackTrace() {
#ifdef __GNUC__
string exception::decode_backtrace() const {
string result;
void *trace[16];
int trace_size = 0;
trace_size = backtrace(trace, 16);
char **messages = backtrace_symbols(trace, trace_size);
// backtrace_symbols() as fallback (no data from dladdr())
char **messages = backtrace_symbols(trace_, trace_size_);
result = "[bt] Trace:\n";
if (!messages) {
return string("[bt] no trace");
}
/* skip first stack frame (points here) */
for (int i=2; i < trace_size; ++i) {
result += string("[bt] #") + std::to_string(i-1) + string(" ");
for (int i=1; i < trace_size_; ++i) {
result += string("[bt] #") + std::to_string(i-1)
+ string(TRACE_SIZE_MAX_/10 - (i-1)/10, ' ')
+ string(" ");
Dl_info info;
if (dladdr(trace[i], &info) && info.dli_saddr) {
if (dladdr(trace_[i], &info) && info.dli_saddr) {
auto name = demangle(info.dli_sname);
string fname = info.dli_fname ? info.dli_fname: "[unknown file]";
......@@ -71,25 +70,31 @@ static std::string getBackTrace() {
free(messages);
return result;
}
#elif _MSC_VER
return "";
#else
return "";
#endif
string exception::decode_backtrace() const {
return string();
}
#endif
exception::exception(const char *msg) : msg_(msg), processed_(false) {
trace_ = std::move(getBackTrace());
#ifdef __GNUC__
trace_size_ = backtrace(trace_, TRACE_SIZE_MAX_);
#endif
}
exception::exception(const ftl::Formatter &msg) : msg_(msg.str()), processed_(false) {
trace_ = std::move(getBackTrace());
#ifdef __GNUC__
trace_size_ = backtrace(trace_, TRACE_SIZE_MAX_);
#endif
}
exception::~exception() {
if (!processed_) {
LOG(ERROR) << "Unhandled exception: " << what();
LOG(ERROR) << trace_;
#ifdef __GNUC__
LOG(ERROR) << "Trace:\n" << decode_backtrace();
#endif
}
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment