1/* Copyright (C) 2003, 2004 Free Software Foudnation, Inc.
2   This file is part of the GNU C Library.
3   Contributed by Alexandre Oliva <aoliva@redhat.com>, 2003.
4
5   The GNU C Library is free software; you can redistribute it and/or
6   modify it under the terms of the GNU Lesser General Public
7   License as published by the Free Software Foundation; either
8   version 2.1 of the License, or (at your option) any later version.
9
10   The GNU C Library is distributed in the hope that it will be useful,
11   but WITHOUT ANY WARRANTY; without even the implied warranty of
12   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13   Lesser General Public License for more details.
14
15   You should have received a copy of the GNU Lesser General Public
16   License along with the GNU C Library; if not, see
17   <http://www.gnu.org/licenses/>.  */
18
19/* clone() is even more special than fork() as it mucks with stacks
20   and invokes a function in the right context after its all over.  */
21
22#include <features.h>
23#include <asm/unistd.h>
24#define _ERRNO_H	1
25#include <bits/errno.h>
26
27	.text
28	.globl	clone
29	.type clone,@function
30/* int clone(int (*fn)(void *arg), void *child_stack, int flags, void *arg) */
31clone:
32	/* Sanity check arguments.  */
33	cmp.p	gr8, gr0, icc0
34	cmp	gr9, gr0, icc1
35	mov.p	gr8, gr4
36	beq	icc0, #0, .Lerror
37	mov.p	gr11, gr5
38	beq	icc1, #0, .Lerror
39
40	mov.p	gr10, gr8
41	setlos	#__NR_clone, gr7
42	tra	gr0,gr0
43
44	cmp.p	gr8, gr0, icc0
45	setlos #-4096, gr6
46	cmp.p	gr8, gr6, icc1
47	beq	icc0, #0, .Lthread_start
48	blslr	icc1, #2
49
50.Lsys_error:
51	sethi.p	#gotofffuncdeschi(__syscall_error), gr14
52	setlo	#gotofffuncdesclo(__syscall_error), gr14
53	ldd	@(gr14, gr15), gr14
54	jmpl	@(gr14, gr0)
55
56.Lerror:
57	setlos.p #-EINVAL, gr8
58	bra	.Lsys_error
59
60###############################################################################
61#
62# come here as the new thread [GR4 is fn, GR5 is arg]
63#
64###############################################################################
65.Lthread_start:
66	/* Save the PIC register.  */
67	mov	gr15, gr17
68
69	/* Call the user's function.  */
70	ldd.p	@(gr4, gr0), gr14
71	mov	gr5, gr8
72	calll	@(gr14, gr0)
73
74	/* Call _exit, rather simply inlining the syscall, such that
75	   breakpoints work.*/
76
77	mov.p	gr17, gr15
78	call	HIDDEN_JUMPTARGET(_exit)
79
80	/* Should never get here.  */
81	jmpl	@(gr0, gr0)
82	.size	clone,.-clone
83