Don't enter DDB for fatal traps before panic by default.

Add a new 'debugger_on_trap' knob separate from 'debugger_on_panic'
and make the calls to kdb_trap() in MD fatal trap handlers prior to
calling panic() conditional on this new knob instead of
'debugger_on_panic'.  Disable the new knob by default.  Developers who
wish to recover from a fatal fault by adjusting saved register state
and retrying the faulting instruction can still do so by enabling the
new knob.  However, for the more common case this makes the user
experience for panics due to a fatal fault match the user experience
for other panics, e.g. 'c' in DDB will generate a crash dump and
reboot the system rather than being stuck in an infinite loop of fatal
fault messages and DDB prompts.

Reviewed by:	kib, avg
MFC after:	2 months
Sponsored by:	Chelsio Communications
Differential Revision:	https://reviews.freebsd.org/D17768
This commit is contained in:
jhb 2018-11-01 21:34:17 +00:00
parent c9ddd1f763
commit d180d56f38
9 changed files with 15 additions and 10 deletions

View File

@ -916,7 +916,7 @@ trap_fatal(frame, eva)
curproc->p_pid, curthread->td_name);
#ifdef KDB
if (debugger_on_panic) {
if (debugger_on_trap) {
kdb_why = KDB_WHY_TRAP;
handled = kdb_trap(type, 0, frame);
kdb_why = KDB_WHY_UNSET;

View File

@ -456,7 +456,7 @@ dab_fatal(struct trapframe *tf, u_int fsr, u_int far, struct thread *td,
printf(", pc =%08x\n\n", tf->tf_pc);
#ifdef KDB
if (debugger_on_panic) {
if (debugger_on_trap) {
kdb_why = KDB_WHY_TRAP;
handled = kdb_trap(fsr, 0, tf);
kdb_why = KDB_WHY_UNSET;

View File

@ -599,7 +599,7 @@ abort_fatal(struct trapframe *tf, u_int idx, u_int fsr, u_int far,
printf(", pc =%08x\n\n", tf->tf_pc);
#ifdef KDB
if (debugger_on_panic) {
if (debugger_on_trap) {
kdb_why = KDB_WHY_TRAP;
kdb_trap(fsr, 0, tf);
kdb_why = KDB_WHY_UNSET;

View File

@ -256,7 +256,7 @@ data_abort(struct thread *td, struct trapframe *frame, uint64_t esr,
printf(" esr: %.8lx\n", esr);
#ifdef KDB
if (debugger_on_panic) {
if (debugger_on_trap) {
kdb_why = KDB_WHY_TRAP;
handled = kdb_trap(ESR_ELx_EXCEPTION(esr), 0,
frame);

View File

@ -977,7 +977,7 @@ trap_fatal(frame, eva)
curproc->p_pid, curthread->td_name);
#ifdef KDB
if (debugger_on_panic) {
if (debugger_on_trap) {
kdb_why = KDB_WHY_TRAP;
frame->tf_err = eva; /* smuggle fault address to ddb */
handled = kdb_trap(type, 0, frame);

View File

@ -115,14 +115,19 @@ SYSCTL_INT(_kern, OID_AUTO, panic_reboot_wait_time, CTLFLAG_RWTUN,
#ifdef KDB
#ifdef KDB_UNATTENDED
int debugger_on_panic = 0;
static int debugger_on_panic = 0;
#else
int debugger_on_panic = 1;
static int debugger_on_panic = 1;
#endif
SYSCTL_INT(_debug, OID_AUTO, debugger_on_panic,
CTLFLAG_RWTUN | CTLFLAG_SECURE,
&debugger_on_panic, 0, "Run debugger on kernel panic");
int debugger_on_trap = 0;
SYSCTL_INT(_debug, OID_AUTO, debugger_on_trap,
CTLFLAG_RWTUN | CTLFLAG_SECURE,
&debugger_on_trap, 0, "Run debugger on kernel trap before panic");
#ifdef KDB_TRACE
static int trace_on_panic = 1;
static bool trace_all_panics = true;

View File

@ -1100,7 +1100,7 @@ trap(struct trapframe *trapframe)
#endif
#ifdef KDB
if (debugger_on_panic) {
if (debugger_on_trap) {
kdb_why = KDB_WHY_TRAP;
kdb_trap(type, 0, trapframe);
kdb_why = KDB_WHY_UNSET;

View File

@ -455,7 +455,7 @@ trap_fatal(struct trapframe *frame)
printtrap(frame->exc, frame, 1, (frame->srr1 & PSL_PR));
#ifdef KDB
if (debugger_on_panic) {
if (debugger_on_trap) {
kdb_why = KDB_WHY_TRAP;
handled = kdb_trap(frame->exc, 0, frame);
kdb_why = KDB_WHY_UNSET;

View File

@ -62,7 +62,7 @@ struct kdb_dbbe {
DATA_SET(kdb_dbbe_set, name##_dbbe)
extern u_char kdb_active; /* Non-zero while in debugger. */
extern int debugger_on_panic; /* enter the debugger on panic. */
extern int debugger_on_trap; /* enter the debugger on trap. */
extern struct kdb_dbbe *kdb_dbbe; /* Default debugger backend or NULL. */
extern struct trapframe *kdb_frame; /* Frame to kdb_trap(). */
extern struct pcb *kdb_thrctx; /* Current context. */