]> git.neil.brown.name Git - history.git/commitdiff
this is a fragile piece of the ptrace code, the code relies on a single wakeup coming...
authorIngo Molnar <mingo@elte.hu>
Wed, 13 Feb 2002 14:32:22 +0000 (15:32 +0100)
committerIngo Molnar <mingo@elte.hu>
Wed, 13 Feb 2002 14:32:22 +0000 (15:32 +0100)
This fix is necessery after the preempt_schedule() cleanups, it unbreaks 'strace strace ...'.

arch/i386/kernel/ptrace.c
arch/i386/kernel/signal.c

index 4afb2afc64d3f585c727aef15237a834f53f3c90..b2d3c92ff14b174a70e88fe45c62daece4c272b0 100644 (file)
@@ -455,9 +455,11 @@ void do_syscall_trace(struct pt_regs *regs, int entryexit)
           between a syscall stop and SIGTRAP delivery */
        current->exit_code = SIGTRAP | ((current->ptrace & PT_TRACESYSGOOD)
                                        ? 0x80 : 0);
+       preempt_disable();
        current->state = TASK_STOPPED;
        notify_parent(current, SIGCHLD);
        schedule();
+       preempt_enable();
        /*
         * this isn't the same as continuing with a signal, but it will do
         * for normal use.  strace only continues with a signal if the
index d904a13b66450d0ff22690540d836fa62b9cf11a..82ae8558a72ca2375b95bc208060c58455ce2cad 100644 (file)
@@ -610,9 +610,11 @@ int do_signal(struct pt_regs *regs, sigset_t *oldset)
                if ((current->ptrace & PT_PTRACED) && signr != SIGKILL) {
                        /* Let the debugger run.  */
                        current->exit_code = signr;
+                       preempt_disable();
                        current->state = TASK_STOPPED;
                        notify_parent(current, SIGCHLD);
                        schedule();
+                       preempt_enable();
 
                        /* We're back.  Did the debugger cancel the sig?  */
                        if (!(signr = current->exit_code))
@@ -667,12 +669,14 @@ int do_signal(struct pt_regs *regs, sigset_t *oldset)
 
                        case SIGSTOP: {
                                struct signal_struct *sig;
-                               current->state = TASK_STOPPED;
                                current->exit_code = signr;
                                sig = current->p_pptr->sig;
+                               preempt_disable();
+                               current->state = TASK_STOPPED;
                                if (sig && !(sig->action[SIGCHLD-1].sa.sa_flags & SA_NOCLDSTOP))
                                        notify_parent(current, SIGCHLD);
                                schedule();
+                               preempt_enable();
                                continue;
                        }