diff options
Diffstat (limited to 'kernel/fork.c')
| -rw-r--r-- | kernel/fork.c | 33 | 
1 files changed, 28 insertions, 5 deletions
| diff --git a/kernel/fork.c b/kernel/fork.c index 26a7a6707fa..37674ec55cd 100644 --- a/kernel/fork.c +++ b/kernel/fork.c @@ -193,6 +193,7 @@ void __put_task_struct(struct task_struct *tsk)  	WARN_ON(atomic_read(&tsk->usage));  	WARN_ON(tsk == current); +	security_task_free(tsk);  	exit_creds(tsk);  	delayacct_tsk_free(tsk);  	put_signal_struct(tsk->signal); @@ -355,7 +356,7 @@ static int dup_mmap(struct mm_struct *mm, struct mm_struct *oldmm)  		charge = 0;  		if (mpnt->vm_flags & VM_ACCOUNT) {  			unsigned int len = (mpnt->vm_end - mpnt->vm_start) >> PAGE_SHIFT; -			if (security_vm_enough_memory(len)) +			if (security_vm_enough_memory_mm(oldmm, len)) /* sic */  				goto fail_nomem;  			charge = len;  		} @@ -511,6 +512,23 @@ static struct mm_struct *mm_init(struct mm_struct *mm, struct task_struct *p)  	return NULL;  } +static void check_mm(struct mm_struct *mm) +{ +	int i; + +	for (i = 0; i < NR_MM_COUNTERS; i++) { +		long x = atomic_long_read(&mm->rss_stat.count[i]); + +		if (unlikely(x)) +			printk(KERN_ALERT "BUG: Bad rss-counter state " +					  "mm:%p idx:%d val:%ld\n", mm, i, x); +	} + +#ifdef CONFIG_TRANSPARENT_HUGEPAGE +	VM_BUG_ON(mm->pmd_huge_pte); +#endif +} +  /*   * Allocate and initialize an mm_struct.   */ @@ -538,9 +556,7 @@ void __mmdrop(struct mm_struct *mm)  	mm_free_pgd(mm);  	destroy_context(mm);  	mmu_notifier_mm_destroy(mm); -#ifdef CONFIG_TRANSPARENT_HUGEPAGE -	VM_BUG_ON(mm->pmd_huge_pte); -#endif +	check_mm(mm);  	free_mm(mm);  }  EXPORT_SYMBOL_GPL(__mmdrop); @@ -1222,6 +1238,7 @@ static struct task_struct *copy_process(unsigned long clone_flags,  #ifdef CONFIG_CPUSETS  	p->cpuset_mem_spread_rotor = NUMA_NO_NODE;  	p->cpuset_slab_spread_rotor = NUMA_NO_NODE; +	seqcount_init(&p->mems_allowed_seq);  #endif  #ifdef CONFIG_TRACE_IRQFLAGS  	p->irq_events = 0; @@ -1340,7 +1357,13 @@ static struct task_struct *copy_process(unsigned long clone_flags,  	clear_all_latency_tracing(p);  	/* ok, now we should be set up.. */ -	p->exit_signal = (clone_flags & CLONE_THREAD) ? -1 : (clone_flags & CSIGNAL); +	if (clone_flags & CLONE_THREAD) +		p->exit_signal = -1; +	else if (clone_flags & CLONE_PARENT) +		p->exit_signal = current->group_leader->exit_signal; +	else +		p->exit_signal = (clone_flags & CSIGNAL); +  	p->pdeath_signal = 0;  	p->exit_state = 0; | 
