From db4b49a5cabd2b70e2680a8384453568e6e09d38 Mon Sep 17 00:00:00 2001 From: Ned <7358345+nedpals@users.noreply.github.com> Date: Tue, 17 May 2022 19:56:34 +0800 Subject: [PATCH] builtin: print libbacktrace output to stderr, on panics/segfault crash (#14434) --- vlib/builtin/builtin.c.v | 4 +-- vlib/builtin/builtin.v | 6 +++- vlib/builtin/builtin_d_use_libbacktrace.c.v | 28 ++++++++++++++----- .../builtin/builtin_notd_use_libbacktrace.c.v | 4 +++ 4 files changed, 32 insertions(+), 10 deletions(-) diff --git a/vlib/builtin/builtin.c.v b/vlib/builtin/builtin.c.v index 5a4faca7a4..5b585fa9e5 100644 --- a/vlib/builtin/builtin.c.v +++ b/vlib/builtin/builtin.c.v @@ -55,7 +55,7 @@ fn panic_debug(line_no int, file string, mod string, fn_name string, s string) { C.exit(1) } $if use_libbacktrace ? { - print_libbacktrace(1) + eprint_libbacktrace(1) } $else { print_backtrace_skipping_top_frames(1) } @@ -106,7 +106,7 @@ pub fn panic(s string) { C.exit(1) } $if use_libbacktrace ? { - print_libbacktrace(1) + eprint_libbacktrace(1) } $else { print_backtrace_skipping_top_frames(1) } diff --git a/vlib/builtin/builtin.v b/vlib/builtin/builtin.v index 990ebdbc8c..f64e7b3c0f 100644 --- a/vlib/builtin/builtin.v +++ b/vlib/builtin/builtin.v @@ -130,6 +130,10 @@ pub: [markused] fn v_segmentation_fault_handler(signal int) { eprintln('signal 11: segmentation fault') - print_backtrace() + $if use_libbacktrace ? { + eprint_libbacktrace(1) + } $else { + print_backtrace() + } exit(128 + 11) } diff --git a/vlib/builtin/builtin_d_use_libbacktrace.c.v b/vlib/builtin/builtin_d_use_libbacktrace.c.v index 577dcb1abc..9fd93b8c66 100644 --- a/vlib/builtin/builtin_d_use_libbacktrace.c.v +++ b/vlib/builtin/builtin_d_use_libbacktrace.c.v @@ -33,11 +33,11 @@ fn init_bt_state() &C.backtrace_state { } // for bt_error_callback -// struct BacktraceData { -// state &C.backtrace_state -// } +struct BacktraceOptions { + stdin bool = true +} -fn bt_print_callback(data voidptr, pc voidptr, filename_ptr &char, line int, fn_name_ptr &char) int { +fn bt_print_callback(data &BacktraceOptions, pc voidptr, filename_ptr &char, line int, fn_name_ptr &char) int { filename := if isnil(filename_ptr) { '???' } else { unsafe { filename_ptr.vstring() } } fn_name := if isnil(fn_name_ptr) { '???' @@ -46,7 +46,12 @@ fn bt_print_callback(data voidptr, pc voidptr, filename_ptr &char, line int, fn_ } // keep it for later // pc_64 := u64(pc) - println('$filename:$line: by $fn_name') + bt_str := '$filename:$line: by $fn_name' + if data.stdin { + println(bt_str) + } else { + eprintln(bt_str) + } return 0 } @@ -81,6 +86,15 @@ fn print_libbacktrace(frames_to_skip int) { $if no_backtrace ? { return } - // data := &BacktraceData{bt_state} - C.backtrace_full(bt_state, frames_to_skip, bt_print_callback, bt_error_callback, 0) + data := &BacktraceOptions{} + C.backtrace_full(bt_state, frames_to_skip, bt_print_callback, bt_error_callback, data) +} + +[noinline] +fn eprint_libbacktrace(frames_to_skip int) { + $if no_backtrace ? { + return + } + data := &BacktraceOptions{stdin: false} + C.backtrace_full(bt_state, frames_to_skip, bt_print_callback, bt_error_callback, data) } diff --git a/vlib/builtin/builtin_notd_use_libbacktrace.c.v b/vlib/builtin/builtin_notd_use_libbacktrace.c.v index 4a675e2753..708ec6e5ce 100644 --- a/vlib/builtin/builtin_notd_use_libbacktrace.c.v +++ b/vlib/builtin/builtin_notd_use_libbacktrace.c.v @@ -2,3 +2,7 @@ module builtin fn print_libbacktrace(frames_to_skip int) { } + +[noinline] +fn eprint_libbacktrace(frames_to_skip int) { +}