On Sun, 6 Mar 2005, Daniel Jacobowitz wrote:
> 
> The reason this happens is that when the inferior hits a breakpoint, the
> first thing GDB will do is remove the breakpoint, single-step past it, and
> reinsert it.  So GDB does a PTRACE_SINGLESTEP, and the kernel invokes the
> signal handler (without single-step - good so far).

No, not good so far.

Yes, it cleared TF, but it saved eflags with TF set on-stack, even though 
the TF was due to a TIF_SINGLESTEP (and was thus "temporary", not a real 
flag). That's why you see the bogus SIGTRAP after returning from the 
signal handler.

Now, we actually get this _right_ if the signal is due to a single-step, 
because do_debug() will do:

                if (likely(tsk->ptrace & PT_DTRACE)) {
                        tsk->ptrace &= ~PT_DTRACE;
                        regs->eflags &= ~TF_MASK;
                }

but that's the only place we do that. So any _other_ signal won't do this, 
and we'll enter the signal handler without checking the PT_DTRACE flag to 
see if TF was a temporary thing from debugger rather than something the 
program actually did on its own.

I _think_ your test-case would work right if you just moved that code from
the special-case in do_debug(), and moved it to the top of
setup_sigcontext() instead. I've not tested it, though, and haven't really 
given it any "deep thought". Maybe somebody smarter can say "yeah, that's 
obviously the right thing to do" or "no, that won't work because.."

                Linus
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

Reply via email to