diff options
Diffstat (limited to 'kernel/fork.c')
-rw-r--r-- | kernel/fork.c | 19 |
1 files changed, 12 insertions, 7 deletions
diff --git a/kernel/fork.c b/kernel/fork.c index 17bbf093356d..b0ec34abc0bb 100644 --- a/kernel/fork.c +++ b/kernel/fork.c | |||
@@ -329,15 +329,17 @@ static int dup_mmap(struct mm_struct *mm, struct mm_struct *oldmm) | |||
329 | if (!tmp) | 329 | if (!tmp) |
330 | goto fail_nomem; | 330 | goto fail_nomem; |
331 | *tmp = *mpnt; | 331 | *tmp = *mpnt; |
332 | INIT_LIST_HEAD(&tmp->anon_vma_chain); | ||
332 | pol = mpol_dup(vma_policy(mpnt)); | 333 | pol = mpol_dup(vma_policy(mpnt)); |
333 | retval = PTR_ERR(pol); | 334 | retval = PTR_ERR(pol); |
334 | if (IS_ERR(pol)) | 335 | if (IS_ERR(pol)) |
335 | goto fail_nomem_policy; | 336 | goto fail_nomem_policy; |
336 | vma_set_policy(tmp, pol); | 337 | vma_set_policy(tmp, pol); |
338 | if (anon_vma_fork(tmp, mpnt)) | ||
339 | goto fail_nomem_anon_vma_fork; | ||
337 | tmp->vm_flags &= ~VM_LOCKED; | 340 | tmp->vm_flags &= ~VM_LOCKED; |
338 | tmp->vm_mm = mm; | 341 | tmp->vm_mm = mm; |
339 | tmp->vm_next = NULL; | 342 | tmp->vm_next = NULL; |
340 | anon_vma_link(tmp); | ||
341 | file = tmp->vm_file; | 343 | file = tmp->vm_file; |
342 | if (file) { | 344 | if (file) { |
343 | struct inode *inode = file->f_path.dentry->d_inode; | 345 | struct inode *inode = file->f_path.dentry->d_inode; |
@@ -392,6 +394,8 @@ out: | |||
392 | flush_tlb_mm(oldmm); | 394 | flush_tlb_mm(oldmm); |
393 | up_write(&oldmm->mmap_sem); | 395 | up_write(&oldmm->mmap_sem); |
394 | return retval; | 396 | return retval; |
397 | fail_nomem_anon_vma_fork: | ||
398 | mpol_put(pol); | ||
395 | fail_nomem_policy: | 399 | fail_nomem_policy: |
396 | kmem_cache_free(vm_area_cachep, tmp); | 400 | kmem_cache_free(vm_area_cachep, tmp); |
397 | fail_nomem: | 401 | fail_nomem: |
@@ -455,8 +459,7 @@ static struct mm_struct * mm_init(struct mm_struct * mm, struct task_struct *p) | |||
455 | (current->mm->flags & MMF_INIT_MASK) : default_dump_filter; | 459 | (current->mm->flags & MMF_INIT_MASK) : default_dump_filter; |
456 | mm->core_state = NULL; | 460 | mm->core_state = NULL; |
457 | mm->nr_ptes = 0; | 461 | mm->nr_ptes = 0; |
458 | set_mm_counter(mm, file_rss, 0); | 462 | memset(&mm->rss_stat, 0, sizeof(mm->rss_stat)); |
459 | set_mm_counter(mm, anon_rss, 0); | ||
460 | spin_lock_init(&mm->page_table_lock); | 463 | spin_lock_init(&mm->page_table_lock); |
461 | mm->free_area_cache = TASK_UNMAPPED_BASE; | 464 | mm->free_area_cache = TASK_UNMAPPED_BASE; |
462 | mm->cached_hole_size = ~0UL; | 465 | mm->cached_hole_size = ~0UL; |
@@ -825,6 +828,8 @@ void __cleanup_sighand(struct sighand_struct *sighand) | |||
825 | */ | 828 | */ |
826 | static void posix_cpu_timers_init_group(struct signal_struct *sig) | 829 | static void posix_cpu_timers_init_group(struct signal_struct *sig) |
827 | { | 830 | { |
831 | unsigned long cpu_limit; | ||
832 | |||
828 | /* Thread group counters. */ | 833 | /* Thread group counters. */ |
829 | thread_group_cputime_init(sig); | 834 | thread_group_cputime_init(sig); |
830 | 835 | ||
@@ -839,9 +844,9 @@ static void posix_cpu_timers_init_group(struct signal_struct *sig) | |||
839 | sig->cputime_expires.virt_exp = cputime_zero; | 844 | sig->cputime_expires.virt_exp = cputime_zero; |
840 | sig->cputime_expires.sched_exp = 0; | 845 | sig->cputime_expires.sched_exp = 0; |
841 | 846 | ||
842 | if (sig->rlim[RLIMIT_CPU].rlim_cur != RLIM_INFINITY) { | 847 | cpu_limit = ACCESS_ONCE(sig->rlim[RLIMIT_CPU].rlim_cur); |
843 | sig->cputime_expires.prof_exp = | 848 | if (cpu_limit != RLIM_INFINITY) { |
844 | secs_to_cputime(sig->rlim[RLIMIT_CPU].rlim_cur); | 849 | sig->cputime_expires.prof_exp = secs_to_cputime(cpu_limit); |
845 | sig->cputimer.running = 1; | 850 | sig->cputimer.running = 1; |
846 | } | 851 | } |
847 | 852 | ||
@@ -1034,7 +1039,7 @@ static struct task_struct *copy_process(unsigned long clone_flags, | |||
1034 | #endif | 1039 | #endif |
1035 | retval = -EAGAIN; | 1040 | retval = -EAGAIN; |
1036 | if (atomic_read(&p->real_cred->user->processes) >= | 1041 | if (atomic_read(&p->real_cred->user->processes) >= |
1037 | p->signal->rlim[RLIMIT_NPROC].rlim_cur) { | 1042 | task_rlimit(p, RLIMIT_NPROC)) { |
1038 | if (!capable(CAP_SYS_ADMIN) && !capable(CAP_SYS_RESOURCE) && | 1043 | if (!capable(CAP_SYS_ADMIN) && !capable(CAP_SYS_RESOURCE) && |
1039 | p->real_cred->user != INIT_USER) | 1044 | p->real_cred->user != INIT_USER) |
1040 | goto bad_fork_free; | 1045 | goto bad_fork_free; |