Disable interrupts while in kdb_trap() to handle cases where the caller
doesn't do it. This fixes all known causes of "Context switches not allowed in the debugger" in mi_switch(). The main cause was trap_fatal() calling kdb_trap() with interrupts enabled. Switching to ithreads for interrupt handling then made fatal traps more fatal and harder to debug. The problem was limited in -current because most interrupt handlers are blocked by Giant, but it occurred almost deterministically for me because my clock interrupt handlers are non-fast and not blocked by Giant.
This commit is contained in:
parent
5efb531d6c
commit
f261b1f35f
@ -77,6 +77,7 @@ rss(void)
|
||||
int
|
||||
kdb_trap(int type, int code, struct i386_saved_state *regs)
|
||||
{
|
||||
u_int ef;
|
||||
volatile int ddb_mode = !(boothowto & RB_GDB);
|
||||
|
||||
/*
|
||||
@ -96,6 +97,9 @@ kdb_trap(int type, int code, struct i386_saved_state *regs)
|
||||
return (0);
|
||||
}
|
||||
|
||||
ef = read_eflags();
|
||||
disable_intr();
|
||||
|
||||
switch (type) {
|
||||
case T_BPTFLT: /* breakpoint */
|
||||
case T_TRCTRAP: /* debug exception */
|
||||
@ -216,6 +220,9 @@ kdb_trap(int type, int code, struct i386_saved_state *regs)
|
||||
regs->tf_fs = ddb_regs.tf_fs & 0xffff;
|
||||
regs->tf_cs = ddb_regs.tf_cs & 0xffff;
|
||||
regs->tf_ds = ddb_regs.tf_ds & 0xffff;
|
||||
|
||||
write_eflags(ef);
|
||||
|
||||
return (1);
|
||||
}
|
||||
|
||||
|
@ -77,6 +77,7 @@ rss(void)
|
||||
int
|
||||
kdb_trap(int type, int code, struct i386_saved_state *regs)
|
||||
{
|
||||
u_int ef;
|
||||
volatile int ddb_mode = !(boothowto & RB_GDB);
|
||||
|
||||
/*
|
||||
@ -96,6 +97,9 @@ kdb_trap(int type, int code, struct i386_saved_state *regs)
|
||||
return (0);
|
||||
}
|
||||
|
||||
ef = read_eflags();
|
||||
disable_intr();
|
||||
|
||||
switch (type) {
|
||||
case T_BPTFLT: /* breakpoint */
|
||||
case T_TRCTRAP: /* debug exception */
|
||||
@ -216,6 +220,9 @@ kdb_trap(int type, int code, struct i386_saved_state *regs)
|
||||
regs->tf_fs = ddb_regs.tf_fs & 0xffff;
|
||||
regs->tf_cs = ddb_regs.tf_cs & 0xffff;
|
||||
regs->tf_ds = ddb_regs.tf_ds & 0xffff;
|
||||
|
||||
write_eflags(ef);
|
||||
|
||||
return (1);
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user