about summary refs log tree commit diff
path: root/nptl
diff options
context:
space:
mode:
Diffstat (limited to 'nptl')
-rw-r--r--nptl/ChangeLog27
-rw-r--r--nptl/sysdeps/ia64/tcb-offsets.sym1
-rw-r--r--nptl/sysdeps/s390/tcb-offsets.sym1
-rw-r--r--nptl/sysdeps/sparc/tcb-offsets.sym1
-rw-r--r--nptl/sysdeps/unix/sysv/linux/ia64/pt-vfork.S13
-rw-r--r--nptl/sysdeps/unix/sysv/linux/ia64/vfork.S68
-rw-r--r--nptl/sysdeps/unix/sysv/linux/s390/s390-32/pt-vfork.S10
-rw-r--r--nptl/sysdeps/unix/sysv/linux/s390/s390-32/vfork.S57
-rw-r--r--nptl/sysdeps/unix/sysv/linux/s390/s390-64/pt-vfork.S15
-rw-r--r--nptl/sysdeps/unix/sysv/linux/s390/s390-64/vfork.S59
-rw-r--r--nptl/sysdeps/unix/sysv/linux/sparc/sparc32/pt-vfork.S (renamed from nptl/sysdeps/unix/sysv/linux/sparc/pt-vfork.S)24
-rw-r--r--nptl/sysdeps/unix/sysv/linux/sparc/sparc32/vfork.S45
-rw-r--r--nptl/sysdeps/unix/sysv/linux/sparc/sparc64/pt-vfork.S42
-rw-r--r--nptl/sysdeps/unix/sysv/linux/sparc/sparc64/vfork.S45
14 files changed, 400 insertions, 8 deletions
diff --git a/nptl/ChangeLog b/nptl/ChangeLog
index 2ca0c7c6d4..94d2273f92 100644
--- a/nptl/ChangeLog
+++ b/nptl/ChangeLog
@@ -1,3 +1,30 @@
+2004-03-10  Jakub Jelinek  <jakub@redhat.com>
+
+	* sysdeps/unix/sysv/linux/s390/s390-32/pt-vfork.S: Include
+	tcb-offsets.h.
+	(__vfork): Negate PID if non-zero and set to INT_MIN if zero
+	before syscall, set to the old value in the parent afterwards.
+	* sysdeps/unix/sysv/linux/s390/s390-32/vfork.S: New file.
+	* sysdeps/unix/sysv/linux/s390/s390-64/pt-vfork.S: Include
+	tcb-offsets.h.
+	(__vfork): Negate PID if non-zero and set to INT_MIN if zero
+	before syscall, set to the old value in the parent afterwards.
+	* sysdeps/unix/sysv/linux/s390/s390-64/vfork.S: New file.
+	* sysdeps/s390/tcb-offsets.sym: Add PID.
+
+	* sysdeps/unix/sysv/linux/sparc/pt-vfork.S: Remove.
+	* sysdeps/unix/sysv/linux/sparc/sparc32/vfork.S: New file.
+	* sysdeps/unix/sysv/linux/sparc/sparc32/pt-vfork.S: New file.
+	* sysdeps/unix/sysv/linux/sparc/sparc64/vfork.S: New file.
+	* sysdeps/unix/sysv/linux/sparc/sparc64/pt-vfork.S: New file.
+	* sysdeps/sparc/tcb-offsets.sym: Add PID.
+
+2004-03-10  Andreas Schwab  <schwab@suse.de>
+
+	* sysdeps/ia64/tcb-offsets.sym: Add PID.
+	* sysdeps/unix/sysv/linux/ia64/vfork.S: New file.
+	* sysdeps/unix/sysv/linux/ia64/pt-vfork.S: Properly handle PID cache.
+
 2004-03-09  Jakub Jelinek  <jakub@redhat.com>
 
 	* tst-cancel20.c (do_one_test): Clear in_sh_body first.
diff --git a/nptl/sysdeps/ia64/tcb-offsets.sym b/nptl/sysdeps/ia64/tcb-offsets.sym
index 24dc3e9683..09ea70ddc7 100644
--- a/nptl/sysdeps/ia64/tcb-offsets.sym
+++ b/nptl/sysdeps/ia64/tcb-offsets.sym
@@ -1,5 +1,6 @@
 #include <sysdep.h>
 #include <tls.h>
 
+PID			offsetof (struct pthread, pid) - sizeof (struct pthread)
 MULTIPLE_THREADS_OFFSET offsetof (struct pthread, header.multiple_threads) - sizeof (struct pthread)
 SYSINFO_OFFSET		offsetof (tcbhead_t, private)
diff --git a/nptl/sysdeps/s390/tcb-offsets.sym b/nptl/sysdeps/s390/tcb-offsets.sym
index aee6be2570..c6e230a315 100644
--- a/nptl/sysdeps/s390/tcb-offsets.sym
+++ b/nptl/sysdeps/s390/tcb-offsets.sym
@@ -2,3 +2,4 @@
 #include <tls.h>
 
 MULTIPLE_THREADS_OFFSET		offsetof (tcbhead_t, multiple_threads)
+PID				offsetof (struct pthread, pid)
diff --git a/nptl/sysdeps/sparc/tcb-offsets.sym b/nptl/sysdeps/sparc/tcb-offsets.sym
index aee6be2570..c6e230a315 100644
--- a/nptl/sysdeps/sparc/tcb-offsets.sym
+++ b/nptl/sysdeps/sparc/tcb-offsets.sym
@@ -2,3 +2,4 @@
 #include <tls.h>
 
 MULTIPLE_THREADS_OFFSET		offsetof (tcbhead_t, multiple_threads)
+PID				offsetof (struct pthread, pid)
diff --git a/nptl/sysdeps/unix/sysv/linux/ia64/pt-vfork.S b/nptl/sysdeps/unix/sysv/linux/ia64/pt-vfork.S
index a8e2e492d3..f59227c695 100644
--- a/nptl/sysdeps/unix/sysv/linux/ia64/pt-vfork.S
+++ b/nptl/sysdeps/unix/sysv/linux/ia64/pt-vfork.S
@@ -1,4 +1,4 @@
-/* Copyright (C) 2000, 2002, 2003 Free Software Foundation, Inc.
+/* Copyright (C) 2000, 2002, 2003, 2004 Free Software Foundation, Inc.
    This file is part of the GNU C Library.
 
    The GNU C Library is free software; you can redistribute it and/or
@@ -32,13 +32,22 @@
 ENTRY(__vfork)
 	.prologue	// work around a GAS bug which triggers if
 	.body		// first .prologue is not at the beginning of proc.
-	alloc r2=ar.pfs,0,0,2,0
+	alloc r2=ar.pfs,0,1,2,0
+	adds r14=PID,r13
+	;; 
+	ld4 loc0=[r14]
+	;;
+	sub r15=0,loc0
 	mov out0=CLONE_VM+CLONE_VFORK+SIGCHLD
 	mov out1=0		/* Standard sp value.			*/
 	;;
+	st4 [r14]=r15
 	DO_CALL (SYS_ify (clone))
+	cmp.eq p0,p7=0,r8
 	cmp.eq p6,p0=-1,r10
+	adds r14=PID,r13
 	;;
+(p7)	st4 [r14]=loc0
 (p6)	br.cond.spnt.few __syscall_error
 	ret
 PSEUDO_END(__vfork)
diff --git a/nptl/sysdeps/unix/sysv/linux/ia64/vfork.S b/nptl/sysdeps/unix/sysv/linux/ia64/vfork.S
new file mode 100644
index 0000000000..bbb34d94f0
--- /dev/null
+++ b/nptl/sysdeps/unix/sysv/linux/ia64/vfork.S
@@ -0,0 +1,68 @@
+/* Copyright (C) 2000, 2002, 2004 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+
+#include <sysdep.h>
+#define _SIGNAL_H
+#include <bits/signum.h>
+#include <tcb-offsets.h>
+
+/* The following are defined in linux/sched.h, which unfortunately	*/
+/* is not safe for inclusion in an assembly file.			*/
+#define CLONE_VM        0x00000100      /* set if VM shared between processes */
+#define CLONE_VFORK     0x00004000      /* set if the parent wants the child to wake it up on mm_release */
+
+/* pid_t vfork(void); */
+/* Implemented as __clone_syscall(CLONE_VFORK | CLONE_VM | SIGCHLD, 0)	*/
+
+ENTRY(__vfork)
+	alloc r2=ar.pfs,0,0,2,0
+	adds r14=PID,r13
+	;;
+	ld4 r16=[r14]
+	;;
+	sub r15=0,r16
+	cmp.eq p6,p0=0,r16
+	;;
+(p6)	movl r15=0x80000000
+	mov out0=CLONE_VM+CLONE_VFORK+SIGCHLD
+	mov out1=0		/* Standard sp value.			*/
+	;;
+	st4 [r14]=r15
+	DO_CALL_VIA_BREAK (SYS_ify (clone))
+	cmp.eq p6,p0=0,r8
+	adds r14=PID,r13
+(p6)	br.cond.dptk 1f
+	;;
+	ld4 r15=[r14]
+	;;
+	extr.u r16=r15,0,31
+	;;
+	cmp.eq p0,p6=0,r16
+	;;
+(p6)	sub r16=0,r15
+	;;
+	st4 [r14]=r16
+1:
+	cmp.eq p6,p0=-1,r10
+(p6)	br.cond.spnt.few __syscall_error
+	ret
+PSEUDO_END(__vfork)
+libc_hidden_def (__vfork)
+
+weak_alias (__vfork, vfork)
diff --git a/nptl/sysdeps/unix/sysv/linux/s390/s390-32/pt-vfork.S b/nptl/sysdeps/unix/sysv/linux/s390/s390-32/pt-vfork.S
index 67a5bc6613..60d6dbdef6 100644
--- a/nptl/sysdeps/unix/sysv/linux/s390/s390-32/pt-vfork.S
+++ b/nptl/sysdeps/unix/sysv/linux/s390/s390-32/pt-vfork.S
@@ -22,6 +22,7 @@
 #include <bits/errno.h>
 #include <kernel-features.h>
 #include <bits/wordsize.h>
+#include <tcb-offsets.h>
 
 /* Clone the calling process, but without copying the whole address space.
    The calling process is suspended until the new process exits or is
@@ -29,9 +30,18 @@
    and the process ID of the new process to the old process.  */
 
 ENTRY (__vfork)
+	ear	%r4,%a0
+	l	%r3,PID(%r4)
+	lcr	%r1,%r3
+	st	%r1,PID(%r4)
+
 	/* Do vfork system call.  */
 	svc	SYS_ify (vfork)
 
+	ltr	%r2,%r2
+	je	1f
+	st	%r3,PID(%r4)
+1:
 	/* Check for error.  */
 	lhi	%r4,-4095
 	clr	%r2,%r4
diff --git a/nptl/sysdeps/unix/sysv/linux/s390/s390-32/vfork.S b/nptl/sysdeps/unix/sysv/linux/s390/s390-32/vfork.S
new file mode 100644
index 0000000000..2dca28fb6f
--- /dev/null
+++ b/nptl/sysdeps/unix/sysv/linux/s390/s390-32/vfork.S
@@ -0,0 +1,57 @@
+/* Copyright (C) 2004 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Jakub Jelinek <jakub@redhat.com>, 2004.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#include <sysdep.h>
+#define _ERRNO_H	1
+#include <bits/errno.h>
+#include <kernel-features.h>
+#include <bits/wordsize.h>
+#include <tcb-offsets.h>
+
+/* Clone the calling process, but without copying the whole address space.
+   The calling process is suspended until the new process exits or is
+   replaced by a call to `execve'.  Return -1 for errors, 0 to the new process,
+   and the process ID of the new process to the old process.  */
+
+ENTRY (__vfork)
+	ear	%r4,%a0
+	lhi	%r1,1
+	icm	%r3,15,PID(%r4)
+	sll	%r1,31
+	je	1f
+	lcr	%r1,%r3
+1:	st	%r1,PID(%r4)
+
+	/* Do vfork system call.  */
+	svc	SYS_ify (vfork)
+
+	ltr	%r2,%r2
+	je	1f
+	st	%r3,PID(%r4)
+1:
+	/* Check for error.  */
+	lhi	%r4,-4095
+	clr	%r2,%r4
+	jnl	SYSCALL_ERROR_LABEL
+
+	/* Normal return.  */
+	br	%r14
+PSEUDO_END(__vfork)
+
+weak_alias (__vfork, vfork)
diff --git a/nptl/sysdeps/unix/sysv/linux/s390/s390-64/pt-vfork.S b/nptl/sysdeps/unix/sysv/linux/s390/s390-64/pt-vfork.S
index e45165e37b..fcc7ee0804 100644
--- a/nptl/sysdeps/unix/sysv/linux/s390/s390-64/pt-vfork.S
+++ b/nptl/sysdeps/unix/sysv/linux/s390/s390-64/pt-vfork.S
@@ -1,4 +1,4 @@
-/* Copyright (C) 2003 Free Software Foundation, Inc.
+/* Copyright (C) 2003, 2004 Free Software Foundation, Inc.
    This file is part of the GNU C Library.
    Contributed by Martin Schwidefsky <schwidefsky@de.ibm.com>, 2003.
 
@@ -22,6 +22,7 @@
 #include <bits/errno.h>
 #include <kernel-features.h>
 #include <bits/wordsize.h>
+#include <tcb-offsets.h>
 
 /* Clone the calling process, but without copying the whole address space.
    The calling process is suspended until the new process exits or is
@@ -29,9 +30,21 @@
    and the process ID of the new process to the old process.  */
 
 ENTRY (__vfork)
+
+	ear	%r4,%a0
+	sllg	%r4,%r4,32
+	ear	%r4,%a1
+	l	%r3,PID(%r4)
+	lcr	%r1,%r3
+	st	%r1,PID(%r4)
+
 	/* Do vfork system call.  */
 	svc	SYS_ify (vfork)
 
+	ltgr	%r2,%r2
+	je	1f
+	st	%r3,PID(%r4)
+1:
 	/* Check for error.  */
 	lghi	%r4,-4095
 	clgr	%r2,%r4
diff --git a/nptl/sysdeps/unix/sysv/linux/s390/s390-64/vfork.S b/nptl/sysdeps/unix/sysv/linux/s390/s390-64/vfork.S
new file mode 100644
index 0000000000..c73d849f25
--- /dev/null
+++ b/nptl/sysdeps/unix/sysv/linux/s390/s390-64/vfork.S
@@ -0,0 +1,59 @@
+/* Copyright (C) 2004 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Jakub Jelinek <jakub@redhat.com>, 2004.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#include <sysdep.h>
+#define _ERRNO_H	1
+#include <bits/errno.h>
+#include <kernel-features.h>
+#include <bits/wordsize.h>
+#include <tcb-offsets.h>
+
+/* Clone the calling process, but without copying the whole address space.
+   The calling process is suspended until the new process exits or is
+   replaced by a call to `execve'.  Return -1 for errors, 0 to the new process,
+   and the process ID of the new process to the old process.  */
+
+ENTRY (__vfork)
+
+	ear	%r4,%a0
+	sllg	%r4,%r4,32
+	ear	%r4,%a1
+	icm	%r3,15,PID(%r4)
+	llilh	%r1,32768
+	je	1f
+	lcr	%r1,%r3
+1:	st	%r1,PID(%r4)
+
+	/* Do vfork system call.  */
+	svc	SYS_ify (vfork)
+
+	ltgr	%r2,%r2
+	je	1f
+	st	%r3,PID(%r4)
+1:
+	/* Check for error.  */
+	lghi	%r4,-4095
+	clgr	%r2,%r4
+	jnl	SYSCALL_ERROR_LABEL
+
+	/* Normal return.  */
+	br	%r14
+PSEUDO_END(__vfork)
+
+weak_alias (__vfork, vfork)
diff --git a/nptl/sysdeps/unix/sysv/linux/sparc/pt-vfork.S b/nptl/sysdeps/unix/sysv/linux/sparc/sparc32/pt-vfork.S
index 006bc96bd6..55229c9e66 100644
--- a/nptl/sysdeps/unix/sysv/linux/sparc/pt-vfork.S
+++ b/nptl/sysdeps/unix/sysv/linux/sparc/sparc32/pt-vfork.S
@@ -1,6 +1,6 @@
-/* Copyright (C) 1999, 2002, 2003 Free Software Foundation, Inc.
+/* Copyright (C) 2004 Free Software Foundation, Inc.
    This file is part of the GNU C Library.
-   Contributed by Jakub Jelinek <jj@ultra.linux.cz>, 1999.
+   Contributed by Jakub Jelinek <jakub@redhat.com>, 2004.
 
    The GNU C Library is free software; you can redistribute it and/or
    modify it under the terms of the GNU Lesser General Public
@@ -18,11 +18,25 @@
    02111-1307 USA.  */
 
 #include <sysdep.h>
+#include <tcb-offsets.h>
 
-PSEUDO (__vfork, vfork, 0)
+	.text
+ENTRY(__vfork)
+	ld	[%g7 + PID], %o5
+	sub	%g0, %o5, %o4
+	st	%o4, [%g7 + PID]
+
+	LOADSYSCALL(vfork)
+	ta	0x10
+	bcs,a	__syscall_error_handler
+	 st	%o5, [%g7 + PID]
+	SYSCALL_ERROR_HANDLER
 	sub	%o1, 1, %o1
-	retl
-	 and	%o0, %o1, %o0
+	andcc	%o0, %o1, %o0
+	bne,a	1f
+	 st	%o5, [%g7 + PID]
+1:	retl
+	 nop
 
 PSEUDO_END (__vfork)
 weak_alias (__vfork, vfork)
diff --git a/nptl/sysdeps/unix/sysv/linux/sparc/sparc32/vfork.S b/nptl/sysdeps/unix/sysv/linux/sparc/sparc32/vfork.S
new file mode 100644
index 0000000000..6a65a881af
--- /dev/null
+++ b/nptl/sysdeps/unix/sysv/linux/sparc/sparc32/vfork.S
@@ -0,0 +1,45 @@
+/* Copyright (C) 2004 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Jakub Jelinek <jakub@redhat.com>, 2004.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#include <sysdep.h>
+#include <tcb-offsets.h>
+
+	.text
+ENTRY(__vfork)
+	ld	[%g7 + PID], %o5
+	cmp	%o5, 0
+	bne	1f
+	 sub	%g0, %o5, %o4
+	sethi	%hi(0x80000000), %o4
+1:	st	%o4, [%g7 + PID]
+
+	LOADSYSCALL(vfork)
+	ta	0x10
+	bcs,a	__syscall_error_handler
+	 st	%o5, [%g7 + PID]
+	SYSCALL_ERROR_HANDLER
+	sub	%o1, 1, %o1
+	andcc	%o0, %o1, %o0
+	bne,a	1f
+	 st	%o5, [%g7 + PID]
+1:	retl
+	 nop
+
+PSEUDO_END (__vfork)
+weak_alias (__vfork, vfork)
diff --git a/nptl/sysdeps/unix/sysv/linux/sparc/sparc64/pt-vfork.S b/nptl/sysdeps/unix/sysv/linux/sparc/sparc64/pt-vfork.S
new file mode 100644
index 0000000000..e9018b2e99
--- /dev/null
+++ b/nptl/sysdeps/unix/sysv/linux/sparc/sparc64/pt-vfork.S
@@ -0,0 +1,42 @@
+/* Copyright (C) 2004 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Jakub Jelinek <jakub@redhat.com>, 2004.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#include <sysdep.h>
+#include <tcb-offsets.h>
+
+	.text
+ENTRY(__vfork)
+	ld	[%g7 + PID], %o5
+	sub	%g0, %o5, %o4
+	st	%o4, [%g7 + PID]
+
+	LOADSYSCALL(vfork)
+	ta	0x6d
+	bcs,a,pn %xcc, __syscall_error_handler
+	 st	%o5, [%g7 + PID]
+	SYSCALL_ERROR_HANDLER
+	sub	%o1, 1, %o1
+	andcc	%o0, %o1, %o0
+	bne,a,pt %icc, 1f
+	 st	%o5, [%g7 + PID]
+1:	retl
+	 nop
+
+PSEUDO_END (__vfork)
+weak_alias (__vfork, vfork)
diff --git a/nptl/sysdeps/unix/sysv/linux/sparc/sparc64/vfork.S b/nptl/sysdeps/unix/sysv/linux/sparc/sparc64/vfork.S
new file mode 100644
index 0000000000..c9ccd0f57d
--- /dev/null
+++ b/nptl/sysdeps/unix/sysv/linux/sparc/sparc64/vfork.S
@@ -0,0 +1,45 @@
+/* Copyright (C) 2004 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Jakub Jelinek <jakub@redhat.com>, 2004.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#include <sysdep.h>
+#include <tcb-offsets.h>
+
+	.text
+ENTRY(__vfork)
+	ld	[%g7 + PID], %o5
+	sethi	%hi(0x80000000), %o3
+	cmp	%o5, 0
+	sub	%g0, %o5, %o4
+	move	%icc, %o3, %o4
+	st	%o4, [%g7 + PID]
+
+	LOADSYSCALL(vfork)
+	ta	0x6d
+	bcs,a,pn %xcc, __syscall_error_handler
+	 st	%o5, [%g7 + PID]
+	SYSCALL_ERROR_HANDLER
+	sub	%o1, 1, %o1
+	andcc	%o0, %o1, %o0
+	bne,a,pt %icc, 1f
+	 st	%o5, [%g7 + PID]
+1:	retl
+	 nop
+
+PSEUDO_END (__vfork)
+weak_alias (__vfork, vfork)