diff options
| author | Takashi Iwai <tiwai@suse.de> | 2012-01-31 15:13:14 +0100 | 
|---|---|---|
| committer | Takashi Iwai <tiwai@suse.de> | 2012-01-31 15:13:14 +0100 | 
| commit | ea51e5040e24eefe44d70bc654a237ca1f0225b0 (patch) | |
| tree | df2e5922dcdfafae62a10d8cd97f98121064fc23 /kernel/exit.c | |
| parent | 3422a47041b8cb8f14ac1e3926bcf711121df6dc (diff) | |
| parent | 8dbd52daee38adaae4d5a674bcca837e694a4f4c (diff) | |
Merge branch 'fix/asoc' into for-linus
Diffstat (limited to 'kernel/exit.c')
| -rw-r--r-- | kernel/exit.c | 46 | 
1 files changed, 22 insertions, 24 deletions
| diff --git a/kernel/exit.c b/kernel/exit.c index d0b7d988f873..294b1709170d 100644 --- a/kernel/exit.c +++ b/kernel/exit.c @@ -51,6 +51,7 @@  #include <trace/events/sched.h>  #include <linux/hw_breakpoint.h>  #include <linux/oom.h> +#include <linux/writeback.h>  #include <asm/uaccess.h>  #include <asm/unistd.h> @@ -121,9 +122,9 @@ static void __exit_signal(struct task_struct *tsk)  		 * We won't ever get here for the group leader, since it  		 * will have been the last reference on the signal_struct.  		 */ -		sig->utime = cputime_add(sig->utime, tsk->utime); -		sig->stime = cputime_add(sig->stime, tsk->stime); -		sig->gtime = cputime_add(sig->gtime, tsk->gtime); +		sig->utime += tsk->utime; +		sig->stime += tsk->stime; +		sig->gtime += tsk->gtime;  		sig->min_flt += tsk->min_flt;  		sig->maj_flt += tsk->maj_flt;  		sig->nvcsw += tsk->nvcsw; @@ -679,8 +680,6 @@ static void exit_mm(struct task_struct * tsk)  	tsk->mm = NULL;  	up_read(&mm->mmap_sem);  	enter_lazy_tlb(mm, current); -	/* We don't want this task to be frozen prematurely */ -	clear_freeze_flag(tsk);  	task_unlock(tsk);  	mm_update_next_owner(mm);  	mmput(mm); @@ -888,7 +887,7 @@ static void check_stack_usage(void)  static inline void check_stack_usage(void) {}  #endif -NORET_TYPE void do_exit(long code) +void do_exit(long code)  {  	struct task_struct *tsk = current;  	int group_dead; @@ -965,8 +964,7 @@ NORET_TYPE void do_exit(long code)  	acct_collect(code, group_dead);  	if (group_dead)  		tty_audit_exit(); -	if (unlikely(tsk->audit_context)) -		audit_free(tsk); +	audit_free(tsk);  	tsk->exit_code = code;  	taskstats_exit(tsk, group_dead); @@ -1037,9 +1035,12 @@ NORET_TYPE void do_exit(long code)  	validate_creds_for_do_exit(tsk);  	preempt_disable(); +	if (tsk->nr_dirtied) +		__this_cpu_add(dirty_throttle_leaks, tsk->nr_dirtied);  	exit_rcu();  	/* causes final put_task_struct in finish_task_switch(). */  	tsk->state = TASK_DEAD; +	tsk->flags |= PF_NOFREEZE;	/* tell freezer to ignore us */  	schedule();  	BUG();  	/* Avoid "noreturn function does return".  */ @@ -1049,7 +1050,7 @@ NORET_TYPE void do_exit(long code)  EXPORT_SYMBOL_GPL(do_exit); -NORET_TYPE void complete_and_exit(struct completion *comp, long code) +void complete_and_exit(struct completion *comp, long code)  {  	if (comp)  		complete(comp); @@ -1068,7 +1069,7 @@ SYSCALL_DEFINE1(exit, int, error_code)   * Take down every thread in the group.  This is called by fatal signals   * as well as by sys_exit_group (below).   */ -NORET_TYPE void +void  do_group_exit(int exit_code)  {  	struct signal_struct *sig = current->signal; @@ -1255,19 +1256,9 @@ static int wait_task_zombie(struct wait_opts *wo, struct task_struct *p)  		spin_lock_irq(&p->real_parent->sighand->siglock);  		psig = p->real_parent->signal;  		sig = p->signal; -		psig->cutime = -			cputime_add(psig->cutime, -			cputime_add(tgutime, -				    sig->cutime)); -		psig->cstime = -			cputime_add(psig->cstime, -			cputime_add(tgstime, -				    sig->cstime)); -		psig->cgtime = -			cputime_add(psig->cgtime, -			cputime_add(p->gtime, -			cputime_add(sig->gtime, -				    sig->cgtime))); +		psig->cutime += tgutime + sig->cutime; +		psig->cstime += tgstime + sig->cstime; +		psig->cgtime += p->gtime + sig->gtime + sig->cgtime;  		psig->cmin_flt +=  			p->min_flt + sig->min_flt + sig->cmin_flt;  		psig->cmaj_flt += @@ -1540,8 +1531,15 @@ static int wait_consider_task(struct wait_opts *wo, int ptrace,  	}  	/* dead body doesn't have much to contribute */ -	if (p->exit_state == EXIT_DEAD) +	if (unlikely(p->exit_state == EXIT_DEAD)) { +		/* +		 * But do not ignore this task until the tracer does +		 * wait_task_zombie()->do_notify_parent(). +		 */ +		if (likely(!ptrace) && unlikely(ptrace_reparented(p))) +			wo->notask_error = 0;  		return 0; +	}  	/* slay zombie? */  	if (p->exit_state == EXIT_ZOMBIE) { | 
