Re: [PATCH v2 5/8] x86/debug: Simplify #DB signal code

From: Andy Lutomirski
Date: Mon Aug 24 2020 - 19:07:17 EST


On Mon, Aug 24, 2020 at 4:26 AM Andrew Cooper <andrew.cooper3@xxxxxxxxxx> wrote:
>
> On 24/08/2020 12:05, peterz@xxxxxxxxxxxxx wrote:
> > On Sun, Aug 23, 2020 at 04:09:42PM -0700, Andy Lutomirski wrote:
> >> On Fri, Aug 21, 2020 at 3:21 AM Peter Zijlstra <peterz@xxxxxxxxxxxxx> wrote:
> >>> Get rid of the two variables, avoid computing si_code when not needed
> >>> and be consistent about which dr6 value is used.
> >>>
> >>> - if (tsk->thread.debugreg6 & (DR_STEP | DR_TRAP_BITS) || user_icebp)
> >>> - send_sigtrap(regs, 0, si_code);
> >>> + /*
> >>> + * If dr6 has no reason to give us about the origin of this trap,
> >>> + * then it's very likely the result of an icebp/int01 trap.
> >>> + * User wants a sigtrap for that.
> >>> + */
> >>> + if (dr6 & (DR_STEP | DR_TRAP_BITS) || !dr6)
> >>> + send_sigtrap(regs, 0, get_si_code(dr6));
> >> The old condition was ... || (actual DR6 value) and the new condition
> >> was ... || (stupid notifier-modified DR6 value). I think the old code
> >> was more correct.
> > Hurmph.. /me goes re-read the SDM.
> >
> > INT1 is a trap,
> > instruction breakpoint is a fault
> >
> > So if you have:
> >
> > INT1
> > 1: some-instr
> >
> > and set an X breakpoint on 1, we'll loose the INT1, right?
>
> You should get two. First with a dr6 of 0 (ICEBP, RIP pointing at 1:),
> and a second with dr6 indicating the X breakpoint (again, RIP pointing
> at 1:).
>
> SDM Vol3 6.9 PRIORITY AMONG SIMULTANEOUS EXCEPTIONS AND INTERRUPTS
>
> Traps on previous instructions are at priority 4, because they still
> "part" of the previous instruction. X breakpoints are priority 7.
>
> The two #DB's shouldn't merge because nothing inhibits delivery[1] of
> the trap at priority 4, and on return from the handler, RF isn't set so
> the instruction breakpoint will trigger.
>

I think that the whole "priority among simultaneous exceptions and
interrupts" section is largely BS. An instruction that traps will
deliver the exception when it finishes executing unless some other
event prevents the instruction from retiring or unless some other trap
preempts it. This will happen before the following instruction is
decoded, let alone before any possible faults from its execution will
occur.


Correct me if I'm wrong, but I don't think I am.