summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sys/kern/kern_fork.c18
1 files changed, 13 insertions, 5 deletions
diff --git a/sys/kern/kern_fork.c b/sys/kern/kern_fork.c
index adc491b5fc2..7682b5d3abc 100644
--- a/sys/kern/kern_fork.c
+++ b/sys/kern/kern_fork.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: kern_fork.c,v 1.55 2002/05/16 16:16:51 provos Exp $ */
+/* $OpenBSD: kern_fork.c,v 1.56 2002/10/21 21:15:17 art Exp $ */
/* $NetBSD: kern_fork.c,v 1.29 1996/02/09 18:59:34 christos Exp $ */
/*
@@ -168,6 +168,7 @@ fork1(p1, exitsig, flags, stack, stacksize, func, arg, retval)
tablefull("proc");
return (EAGAIN);
}
+ nprocs++;
/*
* Increment the count of procs running with this uid. Don't allow
@@ -176,15 +177,23 @@ fork1(p1, exitsig, flags, stack, stacksize, func, arg, retval)
count = chgproccnt(uid, 1);
if (uid != 0 && count > p1->p_rlimit[RLIMIT_NPROC].rlim_cur) {
(void)chgproccnt(uid, -1);
+ nprocs--;
return (EAGAIN);
}
/*
* Allocate a pcb and kernel stack for the process
*/
- uaddr = uvm_km_valloc(kernel_map, USPACE);
- if (uaddr == 0)
- return ENOMEM;
+ uaddr = uvm_km_valloc_noexec(kernel_map, USPACE);
+ if (uaddr == 0) {
+ chgproccnt(uid, -1);
+ nprocs--;
+ return (ENOMEM);
+ }
+
+ /*
+ * From now on, we're comitted to the fork and cannot fail.
+ */
/* Allocate new proc. */
newproc = pool_get(&proc_pool, PR_WAITOK);
@@ -194,7 +203,6 @@ fork1(p1, exitsig, flags, stack, stacksize, func, arg, retval)
lastpid = 1 + (randompid ? arc4random() : lastpid) % PID_MAX;
} while (pidtaken(lastpid));
- nprocs++;
p2 = newproc;
p2->p_stat = SIDL; /* protect against others */
p2->p_pid = lastpid;