1 // Copyright 2006-2008 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "src/base/logging.h"
6 
7 #if V8_LIBC_GLIBC || V8_OS_BSD
8 # include <cxxabi.h>
9 # include <execinfo.h>
10 #elif V8_OS_QNX
11 # include <backtrace.h>
12 #endif  // V8_LIBC_GLIBC || V8_OS_BSD
13 #include <stdio.h>
14 #include <stdlib.h>
15 
16 #include "src/base/platform/platform.h"
17 
18 namespace v8 {
19 namespace base {
20 
21 // Attempts to dump a backtrace (if supported).
DumpBacktrace()22 void DumpBacktrace() {
23 #if V8_LIBC_GLIBC || V8_OS_BSD
24   void* trace[100];
25   int size = backtrace(trace, arraysize(trace));
26   char** symbols = backtrace_symbols(trace, size);
27   OS::PrintError("\n==== C stack trace ===============================\n\n");
28   if (size == 0) {
29     OS::PrintError("(empty)\n");
30   } else if (symbols == NULL) {
31     OS::PrintError("(no symbols)\n");
32   } else {
33     for (int i = 1; i < size; ++i) {
34       OS::PrintError("%2d: ", i);
35       char mangled[201];
36       if (sscanf(symbols[i], "%*[^(]%*[(]%200[^)+]", mangled) == 1) {  // NOLINT
37         int status;
38         size_t length;
39         char* demangled = abi::__cxa_demangle(mangled, NULL, &length, &status);
40         OS::PrintError("%s\n", demangled != NULL ? demangled : mangled);
41         free(demangled);
42       } else {
43         OS::PrintError("??\n");
44       }
45     }
46   }
47   free(symbols);
48 #elif V8_OS_QNX
49   char out[1024];
50   bt_accessor_t acc;
51   bt_memmap_t memmap;
52   bt_init_accessor(&acc, BT_SELF);
53   bt_load_memmap(&acc, &memmap);
54   bt_sprn_memmap(&memmap, out, sizeof(out));
55   OS::PrintError(out);
56   bt_addr_t trace[100];
57   int size = bt_get_backtrace(&acc, trace, arraysize(trace));
58   OS::PrintError("\n==== C stack trace ===============================\n\n");
59   if (size == 0) {
60     OS::PrintError("(empty)\n");
61   } else {
62     bt_sprnf_addrs(&memmap, trace, size, const_cast<char*>("%a\n"),
63                    out, sizeof(out), NULL);
64     OS::PrintError(out);
65   }
66   bt_unload_memmap(&memmap);
67   bt_release_accessor(&acc);
68 #endif  // V8_LIBC_GLIBC || V8_OS_BSD
69 }
70 
71 } }  // namespace v8::base
72 
73 
74 // Contains protection against recursive calls (faults while handling faults).
V8_Fatal(const char * file,int line,const char * format,...)75 extern "C" void V8_Fatal(const char* file, int line, const char* format, ...) {
76   fflush(stdout);
77   fflush(stderr);
78   v8::base::OS::PrintError("\n\n#\n# Fatal error in %s, line %d\n# ", file,
79                            line);
80   va_list arguments;
81   va_start(arguments, format);
82   v8::base::OS::VPrintError(format, arguments);
83   va_end(arguments);
84   v8::base::OS::PrintError("\n#\n");
85   v8::base::DumpBacktrace();
86   fflush(stderr);
87   v8::base::OS::Abort();
88 }
89