diff options
Diffstat (limited to 'kernel')
-rw-r--r-- | kernel/ptrace.c | 22 |
1 files changed, 9 insertions, 13 deletions
diff --git a/kernel/ptrace.c b/kernel/ptrace.c index c9cf48b21f05..f62a568e84ec 100644 --- a/kernel/ptrace.c +++ b/kernel/ptrace.c | |||
@@ -235,16 +235,6 @@ out: | |||
235 | return retval; | 235 | return retval; |
236 | } | 236 | } |
237 | 237 | ||
238 | static inline void __ptrace_detach(struct task_struct *child, unsigned int data) | ||
239 | { | ||
240 | child->exit_code = data; | ||
241 | /* .. re-parent .. */ | ||
242 | __ptrace_unlink(child); | ||
243 | /* .. and wake it up. */ | ||
244 | if (child->exit_state != EXIT_ZOMBIE) | ||
245 | wake_up_process(child); | ||
246 | } | ||
247 | |||
248 | int ptrace_detach(struct task_struct *child, unsigned int data) | 238 | int ptrace_detach(struct task_struct *child, unsigned int data) |
249 | { | 239 | { |
250 | if (!valid_signal(data)) | 240 | if (!valid_signal(data)) |
@@ -254,10 +244,16 @@ int ptrace_detach(struct task_struct *child, unsigned int data) | |||
254 | ptrace_disable(child); | 244 | ptrace_disable(child); |
255 | clear_tsk_thread_flag(child, TIF_SYSCALL_TRACE); | 245 | clear_tsk_thread_flag(child, TIF_SYSCALL_TRACE); |
256 | 246 | ||
257 | write_lock_irq(&tasklist_lock); | ||
258 | /* protect against de_thread()->release_task() */ | 247 | /* protect against de_thread()->release_task() */ |
259 | if (child->ptrace) | 248 | write_lock_irq(&tasklist_lock); |
260 | __ptrace_detach(child, data); | 249 | if (child->ptrace) { |
250 | child->exit_code = data; | ||
251 | |||
252 | __ptrace_unlink(child); | ||
253 | |||
254 | if (!child->exit_state) | ||
255 | wake_up_process(child); | ||
256 | } | ||
261 | write_unlock_irq(&tasklist_lock); | 257 | write_unlock_irq(&tasklist_lock); |
262 | 258 | ||
263 | return 0; | 259 | return 0; |