summaryrefslogtreecommitdiff
path: root/kernel/fork.c
diff options
context:
space:
mode:
authorRusty Russell <rusty@rustcorp.com.au>2002-05-12 23:52:31 -0700
committerDavid Woodhouse <dwmw2@infradead.org>2002-05-12 23:52:31 -0700
commit27568369be8ce189a1bd32c80497ff229ed3de3a (patch)
tree79680bec95707de6e830cf9b59941bf6a37e2e60 /kernel/fork.c
parent5e8a4a7d95318e8cf84e59dfb5659d178240f879 (diff)
[PATCH] Hotplug CPU prep
This changes do_fork() to return the task struct, rather than the PID. Also changes CLONE_PID ("if my pid is 0, copy it") to CLONE_IDLETASK ("set child's pid to zero"), and disallows access to the flag from user mode.
Diffstat (limited to 'kernel/fork.c')
-rw-r--r--kernel/fork.c33
1 files changed, 13 insertions, 20 deletions
diff --git a/kernel/fork.c b/kernel/fork.c
index 61a6c7799bb3..3a778712a98d 100644
--- a/kernel/fork.c
+++ b/kernel/fork.c
@@ -136,8 +136,8 @@ static int get_pid(unsigned long flags)
struct task_struct *p;
int pid;
- if (flags & CLONE_PID)
- return current->pid;
+ if (flags & CLONE_IDLETASK)
+ return 0;
spin_lock(&lastpid_lock);
if((++last_pid) & 0xffff8000) {
@@ -608,27 +608,18 @@ static inline void copy_flags(unsigned long clone_flags, struct task_struct *p)
* For an example that's using stack_top, see
* arch/ia64/kernel/process.c.
*/
-int do_fork(unsigned long clone_flags, unsigned long stack_start,
- struct pt_regs *regs, unsigned long stack_size)
+struct task_struct *do_fork(unsigned long clone_flags,
+ unsigned long stack_start,
+ struct pt_regs *regs,
+ unsigned long stack_size)
{
int retval;
unsigned long flags;
- struct task_struct *p;
+ struct task_struct *p = NULL;
struct completion vfork;
if ((clone_flags & (CLONE_NEWNS|CLONE_FS)) == (CLONE_NEWNS|CLONE_FS))
- return -EINVAL;
-
- retval = -EPERM;
-
- /*
- * CLONE_PID is only allowed for the initial SMP swapper
- * calls
- */
- if (clone_flags & CLONE_PID) {
- if (current->pid)
- goto fork_out;
- }
+ return ERR_PTR(-EINVAL);
retval = -ENOMEM;
p = dup_task_struct(current);
@@ -768,8 +759,7 @@ int do_fork(unsigned long clone_flags, unsigned long stack_start,
*
* Let it rip!
*/
- retval = p->pid;
- p->tgid = retval;
+ p->tgid = p->pid;
INIT_LIST_HEAD(&p->thread_group);
/* Need tasklist lock for parent etc handling! */
@@ -807,9 +797,12 @@ int do_fork(unsigned long clone_flags, unsigned long stack_start,
* COW overhead when the child exec()s afterwards.
*/
set_need_resched();
+ retval = 0;
fork_out:
- return retval;
+ if (retval)
+ return ERR_PTR(retval);
+ return p;
bad_fork_cleanup_namespace:
exit_namespace(p);