Commit b2450cc1b7ce07d73545ece32db50197d649e230

Authored by Carlos O'Donell
Committed by Kyle McMartin
1 parent 8b631342dd

[PARISC] Implement 5 argument clone.

* arch/parisc/kernel/process.c (sys_clone): Use 5 args, and process
  CLONE_PARENT_SETTID, CLONE_CHILD_SETTID, CLONE_CHILD_CLEARTID.
  (copy_thread): First cut at CLONE_SETTLS.

Signed-off-by: Carlos O'Donell <carlos@parisc-linux.org>

Signed-off-by: Kyle McMartin <kyle@parisc-linux.org>

Showing 1 changed file with 29 additions and 5 deletions Side-by-side Diff

arch/parisc/kernel/process.c
... ... @@ -9,7 +9,7 @@
9 9 * Copyright (C) 2000-2003 Paul Bame <bame at parisc-linux.org>
10 10 * Copyright (C) 2000 Philipp Rumpf <prumpf with tux.org>
11 11 * Copyright (C) 2000 David Kennedy <dkennedy with linuxcare.com>
12   - * Copyright (C) 2000 Richard Hirst <rhirst with parisc-lixux.org>
  12 + * Copyright (C) 2000 Richard Hirst <rhirst with parisc-linux.org>
13 13 * Copyright (C) 2000 Grant Grundler <grundler with parisc-linux.org>
14 14 * Copyright (C) 2001 Alan Modra <amodra at parisc-linux.org>
15 15 * Copyright (C) 2001-2002 Ryan Bradetich <rbrad at parisc-linux.org>
... ... @@ -245,7 +245,17 @@
245 245 sys_clone(unsigned long clone_flags, unsigned long usp,
246 246 struct pt_regs *regs)
247 247 {
248   - int __user *user_tid = (int __user *)regs->gr[26];
  248 + /* Arugments from userspace are:
  249 + r26 = Clone flags.
  250 + r25 = Child stack.
  251 + r24 = parent_tidptr.
  252 + r23 = Is the TLS storage descriptor
  253 + r22 = child_tidptr
  254 +
  255 + However, these last 3 args are only examined
  256 + if the proper flags are set. */
  257 + int __user *child_tidptr;
  258 + int __user *parent_tidptr;
249 259  
250 260 /* usp must be word aligned. This also prevents users from
251 261 * passing in the value 1 (which is the signal for a special
252 262  
... ... @@ -253,10 +263,20 @@
253 263 usp = ALIGN(usp, 4);
254 264  
255 265 /* A zero value for usp means use the current stack */
256   - if(usp == 0)
257   - usp = regs->gr[30];
  266 + if (usp == 0)
  267 + usp = regs->gr[30];
258 268  
259   - return do_fork(clone_flags, usp, regs, 0, user_tid, NULL);
  269 + if (clone_flags & CLONE_PARENT_SETTID)
  270 + parent_tidptr = (int __user *)regs->gr[24];
  271 + else
  272 + parent_tidptr = NULL;
  273 +
  274 + if (clone_flags & (CLONE_CHILD_SETTID | CLONE_CHILD_CLEARTID))
  275 + child_tidptr = (int __user *)regs->gr[22];
  276 + else
  277 + child_tidptr = NULL;
  278 +
  279 + return do_fork(clone_flags, usp, regs, 0, parent_tidptr, child_tidptr);
260 280 }
261 281  
262 282 int
... ... @@ -332,6 +352,10 @@
332 352 } else {
333 353 cregs->kpc = (unsigned long) &child_return;
334 354 }
  355 + /* Setup thread TLS area from the 4th parameter in clone */
  356 + if (clone_flags & CLONE_SETTLS)
  357 + cregs->cr27 = pregs->gr[23];
  358 +
335 359 }
336 360  
337 361 return 0;