From f980a783a335d83330e832ed92c0aa8f1abb93b8 Mon Sep 17 00:00:00 2001 From: Eric Andersen Date: Thu, 2 Jan 2003 16:48:42 +0000 Subject: Rework sparc architecture support so it will compile and run. Seems to be working... -Erik --- libc/sysdeps/linux/sparc/Makefile | 10 +- libc/sysdeps/linux/sparc/__longjmp.S | 2 +- libc/sysdeps/linux/sparc/bits/syscalls.h | 193 ++++++++++++++++++++++++++++++- libc/sysdeps/linux/sparc/fork.S | 51 ++++---- libc/sysdeps/linux/sparc/rem.S | 4 +- libc/sysdeps/linux/sparc/sdiv.S | 4 +- libc/sysdeps/linux/sparc/setjmp.S | 37 ++++-- libc/sysdeps/linux/sparc/sysdep.h | 146 ----------------------- libc/sysdeps/linux/sparc/udiv.S | 4 +- libc/sysdeps/linux/sparc/umul.S | 2 +- libc/sysdeps/linux/sparc/urem.S | 4 +- libc/sysdeps/linux/sparc/vfork.S | 48 +++++--- 12 files changed, 293 insertions(+), 212 deletions(-) delete mode 100644 libc/sysdeps/linux/sparc/sysdep.h (limited to 'libc/sysdeps/linux/sparc') diff --git a/libc/sysdeps/linux/sparc/Makefile b/libc/sysdeps/linux/sparc/Makefile index bce1752dc..aecb3bd16 100644 --- a/libc/sysdeps/linux/sparc/Makefile +++ b/libc/sysdeps/linux/sparc/Makefile @@ -25,8 +25,8 @@ TOPDIR=../../../../ include $(TOPDIR)Rules.mak ASFLAGS=$(CFLAGS) -CRT0=crt0.c -CRT0_OBJ=$(patsubst %.c,%.o, $(CRT0)) +CRT0_SRC = crt0.c +CRT0_OBJ = crt0.o crt1.o SSRC=__longjmp.S fork.S vfork.S clone.S setjmp.S bsd-setjmp.S bsd-_setjmp.S \ urem.S udiv.S umul.S sdiv.S rem.S @@ -45,10 +45,10 @@ $(LIBC): ar-target ar-target: $(OBJS) $(CRT0_OBJ) $(AR) $(ARFLAGS) $(LIBC) $(OBJS) - cp $(CRT0_OBJ) $(TOPDIR)lib/$(CRT0_OBJ) + cp $(CRT0_OBJ) $(TOPDIR)lib/ -$(CRT0_OBJ): %.o : %.c - $(CC) $(CFLAGS) -c $< -o $@ +$(CRT0_OBJ): $(CRT0_SRC) + $(CC) $(CFLAGS) -DL_$* $< -c -o $*.o $(STRIPTOOL) -x -R .note -R .comment $*.o $(SOBJS): %.o : %.S diff --git a/libc/sysdeps/linux/sparc/__longjmp.S b/libc/sysdeps/linux/sparc/__longjmp.S index 2d568d381..d6e04bd1e 100644 --- a/libc/sysdeps/linux/sparc/__longjmp.S +++ b/libc/sysdeps/linux/sparc/__longjmp.S @@ -16,7 +16,7 @@ Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. */ -#include +#include #define _ASM 1 #define _SETJMP_H diff --git a/libc/sysdeps/linux/sparc/bits/syscalls.h b/libc/sysdeps/linux/sparc/bits/syscalls.h index 62541b873..ddd8e5f6b 100644 --- a/libc/sysdeps/linux/sparc/bits/syscalls.h +++ b/libc/sysdeps/linux/sparc/bits/syscalls.h @@ -4,16 +4,197 @@ # error "Never use directly; include instead." #endif -#include - -/* Do something very evil for now. Until we create our own syscall - * macros, short circuit bits/sysnum.h and use asm/unistd.h instead */ -#include - /* This includes the `__NR_' syscall numbers taken from the Linux kernel * header files. It also defines the traditional `SYS_' macros for older * programs. */ #include +#ifndef __set_errno +# define __set_errno(val) (*__errno_location ()) = (val) +#endif + +/* + macros taken from glibc-2.3/sysdeps/unix/sysv/linux/sparc/sysdep.h + Copyright (C) 2000, 2002 Free Software Foundation, Inc. + Contributed by Jakub Jelinek , 2000. +*/ + +#ifndef __ASSEMBLER__ + +#undef _syscall0 +#define _syscall0(type,name) \ +type name(void) \ +{ \ +return (type) (INLINE_SYSCALL(name, 0)); \ +} + +#undef _syscall1 +#define _syscall1(type,name,type1,arg1) \ +type name(type1 arg1) \ +{ \ +return (type) (INLINE_SYSCALL(name, 1, arg1)); \ +} + +#undef _syscall2 +#define _syscall2(type,name,type1,arg1,type2,arg2) \ +type name(type1 arg1,type2 arg2) \ +{ \ +return (type) (INLINE_SYSCALL(name, 2, arg1, arg2)); \ +} + +#undef _syscall3 +#define _syscall3(type,name,type1,arg1,type2,arg2,type3,arg3) \ +type name(type1 arg1,type2 arg2,type3 arg3) \ +{ \ +return (type) (INLINE_SYSCALL(name, 3, arg1, arg2, arg3)); \ +} + +#undef _syscall4 +#define _syscall4(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4) \ +type name (type1 arg1, type2 arg2, type3 arg3, type4 arg4) \ +{ \ +return (type) (INLINE_SYSCALL(name, 4, arg1, arg2, arg3, arg4)); \ +} + +#undef _syscall5 +#define _syscall5(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4, \ + type5,arg5) \ +type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5) \ +{ \ +return (type) (INLINE_SYSCALL(name, 5, arg1, arg2, arg3, arg4, arg5)); \ +} + +#undef _syscall6 +#define _syscall6(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4, \ + type5,arg5,type6,arg6) \ +type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5, type6 arg6) \ +{ \ +return (type) (INLINE_SYSCALL(name, 6, arg1, arg2, arg3, arg4, arg5, arg6)); \ +} + +#undef _syscall7 +#define _syscall7(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4, \ + type5,arg5,type6,arg6,type7,arg7) \ +type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5, type6 arg6,type7 arg7) \ +{ \ +return (type) (INLINE_SYSCALL(name, 7, arg1, arg2, arg3, arg4, arg5, arg6, arg7)); \ +} + +#define __SYSCALL_STRING \ + "ta 0x10;" \ + "bcs 2f;" \ + " nop;" \ + "1:" \ + ".subsection 2;" \ + "2:" \ + "save %%sp, -192, %%sp;" \ + "call __errno_location;" \ + " nop;" \ + "st %%i0,[%%o0];" \ + "ba 1b;" \ + " restore %%g0, -1, %%o0;" \ + ".previous;" + +#define __SYSCALL_CLOBBERS "g2", "g3", "g4", "g5", "g7", \ + "f0", "f1", "f2", "f3", "f4", "f5", "f6", "f7", \ + "f8", "f9", "f10", "f11", "f12", "f13", "f14", "f15", \ + "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23", \ + "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31", \ + "cc", "memory" + +#undef INLINE_SYSCALL +#define INLINE_SYSCALL(name, nr, args...) _INLINE_SYSCALL##nr(name, args) + +#define _INLINE_SYSCALL0(name,dummy...) \ +({ \ + register long __o0 __asm__ ("o0"); \ + register long __g1 __asm__ ("g1") = __NR_##name; \ + __asm __volatile (__SYSCALL_STRING : "=r" (__g1), "=r" (__o0) : \ + "0" (__g1) : \ + __SYSCALL_CLOBBERS); \ + __o0; \ +}) + +#define _INLINE_SYSCALL1(name,arg1) \ +({ \ + register long __o0 __asm__ ("o0") = (long)(arg1); \ + register long __g1 __asm__ ("g1") = __NR_##name; \ + __asm __volatile (__SYSCALL_STRING : "=r" (__g1), "=r" (__o0) : \ + "0" (__g1), "1" (__o0) : \ + __SYSCALL_CLOBBERS); \ + __o0; \ +}) + +#define _INLINE_SYSCALL2(name,arg1,arg2) \ +({ \ + register long __o0 __asm__ ("o0") = (long)(arg1); \ + register long __o1 __asm__ ("o1") = (long)(arg2); \ + register long __g1 __asm__ ("g1") = __NR_##name; \ + __asm __volatile (__SYSCALL_STRING : "=r" (__g1), "=r" (__o0) : \ + "0" (__g1), "1" (__o0), "r" (__o1) : \ + __SYSCALL_CLOBBERS); \ + __o0; \ +}) + +#define _INLINE_SYSCALL3(name,arg1,arg2,arg3) \ +({ \ + register long __o0 __asm__ ("o0") = (long)(arg1); \ + register long __o1 __asm__ ("o1") = (long)(arg2); \ + register long __o2 __asm__ ("o2") = (long)(arg3); \ + register long __g1 __asm__ ("g1") = __NR_##name; \ + __asm __volatile (__SYSCALL_STRING : "=r" (__g1), "=r" (__o0) : \ + "0" (__g1), "1" (__o0), "r" (__o1), \ + "r" (__o2) : \ + __SYSCALL_CLOBBERS); \ + __o0; \ +}) + +#define _INLINE_SYSCALL4(name,arg1,arg2,arg3,arg4) \ +({ \ + register long __o0 __asm__ ("o0") = (long)(arg1); \ + register long __o1 __asm__ ("o1") = (long)(arg2); \ + register long __o2 __asm__ ("o2") = (long)(arg3); \ + register long __o3 __asm__ ("o3") = (long)(arg4); \ + register long __g1 __asm__ ("g1") = __NR_##name; \ + __asm __volatile (__SYSCALL_STRING : "=r" (__g1), "=r" (__o0) : \ + "0" (__g1), "1" (__o0), "r" (__o1), \ + "r" (__o2), "r" (__o3) : \ + __SYSCALL_CLOBBERS); \ + __o0; \ +}) + +#define _INLINE_SYSCALL5(name,arg1,arg2,arg3,arg4,arg5) \ +({ \ + register long __o0 __asm__ ("o0") = (long)(arg1); \ + register long __o1 __asm__ ("o1") = (long)(arg2); \ + register long __o2 __asm__ ("o2") = (long)(arg3); \ + register long __o3 __asm__ ("o3") = (long)(arg4); \ + register long __o4 __asm__ ("o4") = (long)(arg5); \ + register long __g1 __asm__ ("g1") = __NR_##name; \ + __asm __volatile (__SYSCALL_STRING : "=r" (__g1), "=r" (__o0) : \ + "0" (__g1), "1" (__o0), "r" (__o1), \ + "r" (__o2), "r" (__o3), "r" (__o4) : \ + __SYSCALL_CLOBBERS); \ + __o0; \ +}) + +#define _INLINE_SYSCALL6(name,arg1,arg2,arg3,arg4,arg5,arg6) \ +({ \ + register long __o0 __asm__ ("o0") = (long)(arg1); \ + register long __o1 __asm__ ("o1") = (long)(arg2); \ + register long __o2 __asm__ ("o2") = (long)(arg3); \ + register long __o3 __asm__ ("o3") = (long)(arg4); \ + register long __o4 __asm__ ("o4") = (long)(arg5); \ + register long __o5 __asm__ ("o5") = (long)(arg6); \ + register long __g1 __asm__ ("g1") = __NR_##name; \ + __asm __volatile (__SYSCALL_STRING : "=r" (__g1), "=r" (__o0) : \ + "0" (__g1), "1" (__o0), "r" (__o1), \ + "r" (__o2), "r" (__o3), "r" (__o4), \ + "r" (__o5) : \ + __SYSCALL_CLOBBERS); \ + __o0; \ +}) + +#endif /* __ASSEMBLER__ */ #endif /* _BITS_SYSCALLS_H */ diff --git a/libc/sysdeps/linux/sparc/fork.S b/libc/sysdeps/linux/sparc/fork.S index 6bab58c81..c66856bef 100644 --- a/libc/sysdeps/linux/sparc/fork.S +++ b/libc/sysdeps/linux/sparc/fork.S @@ -1,5 +1,6 @@ -/* Copyright (C) 1991, 92, 94, 95, 97, 99 Free Software Foundation, Inc. +/* Copyright (C) 1997, 1999 Free Software Foundation, Inc. This file is part of the GNU C Library. + Contributed by Miguel de Icaza , 1997. The GNU C Library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public @@ -16,31 +17,31 @@ Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. */ -#include +/* Code taken from glibc2.2.2/sysdeps/unix/sysv/linux/sparc/vfork.S */ + +#include .text; -.global fork; -.align 4; -fork: ; -.type fork ,@function; ; - - mov 2, %g1 ; - ta 0x10; - bcc,a 9000f; - nop; - save %sp,-96,%sp; - call __errno_location; - nop; - st %i0,[%o0]; - jmpl %i7+8,%g0; - restore %g0,-1,%o0; ; - 9000:; - - /* %o1 is now 0 for the parent and 1 for the child. Decrement it to - make it -1 (all bits set) for the parent, and 0 (no bits set) - for the child. Then AND it with %o0, so the parent gets - %o0&-1==pid, and the child gets %o0&0==0. */ - sub %o1, 1, %o1 +.global fork; +.align 4; +.type fork,@function; + +fork: + mov __NR_fork, %g1 + ta 0x10 + bcc,a 9000f + nop + save %sp,-96,%sp + call __errno_location + nop + st %i0,[%o0] + jmpl %i7+8,%g0 + restore %g0,-1,%o0 + +9000: + sub %o1, 1, %o1 retl - and %o0, %o1, %o0 + and %o0, %o1, %o0 + +.size fork,.-fork; diff --git a/libc/sysdeps/linux/sparc/rem.S b/libc/sysdeps/linux/sparc/rem.S index 52bf167a4..3da857e99 100644 --- a/libc/sysdeps/linux/sparc/rem.S +++ b/libc/sysdeps/linux/sparc/rem.S @@ -37,7 +37,7 @@ -#include +#include .global .rem; @@ -364,4 +364,4 @@ retl mov %o3, %o0 -END(.rem) +.size .rem,.-.rem; diff --git a/libc/sysdeps/linux/sparc/sdiv.S b/libc/sysdeps/linux/sparc/sdiv.S index 678a19413..8fdb7daf8 100644 --- a/libc/sysdeps/linux/sparc/sdiv.S +++ b/libc/sysdeps/linux/sparc/sdiv.S @@ -37,7 +37,7 @@ -#include +#include .global .div; .align 4; @@ -363,4 +363,4 @@ retl mov %o2, %o0 -END(.div) +.size .div,.-.div; diff --git a/libc/sysdeps/linux/sparc/setjmp.S b/libc/sysdeps/linux/sparc/setjmp.S index 30051418c..e01e73b04 100644 --- a/libc/sysdeps/linux/sparc/setjmp.S +++ b/libc/sysdeps/linux/sparc/setjmp.S @@ -16,22 +16,43 @@ Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. */ -#include +#include #define _ASM 1 #define _SETJMP_H #include +#define ST_FLUSH_WINDOWS 3 -ENTRY(_setjmp) +.global _setjmp; +.align 4; +.type _setjmp ,@function; + +_setjmp: b 1f set 0, %o1 -END(_setjmp) +.size _setjmp,.-_setjmp; + + + + + + +.global setjmp; +.align 4; +.type setjmp ,@function; -ENTRY(setjmp) +setjmp: set 1, %o1 -END(setjmp) +.size setjmp,.-setjmp; -ENTRY (__sigsetjmp) + + + +.global __sigsetjmp; +.align 4; +.type __sigsetjmp ,@function; + +__sigsetjmp: 1: /* Save our PC, SP and FP. Save the signal mask if requested with a tail-call for simplicity; it always returns zero. */ @@ -44,7 +65,9 @@ ENTRY (__sigsetjmp) mov %o7, %g1 call __sigjmp_save mov %g1, %o7 -END(__sigsetjmp) +.size __sigsetjmp,.-__sigsetjmp; + + .weak _setjmp .weak setjmp diff --git a/libc/sysdeps/linux/sparc/sysdep.h b/libc/sysdeps/linux/sparc/sysdep.h deleted file mode 100644 index 1553ff06d..000000000 --- a/libc/sysdeps/linux/sparc/sysdep.h +++ /dev/null @@ -1,146 +0,0 @@ -/* Copyright (C) 1991, 1992 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 Library General Public License as -published by the Free Software Foundation; either version 2 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 -Library General Public License for more details. - -You should have received a copy of the GNU Library General Public -License along with the GNU C Library; see the file COPYING.LIB. If -not, write to the Free Software Foundation, Inc., 675 Mass Ave, -Cambridge, MA 02139, USA. */ - -#include - -/* Not that using a `PASTE' macro loses. */ -#ifdef __STDC__ - -#ifdef __ELF__ - -#define SYSCALL_WEAK_ALIAS(alias,orig) \ - .weak alias; \ - alias=__libc_##orig - -/* -#ifdef _POSIX_THREADS -*/ - -#if 1 - -#ifdef PTHREAD_KERNEL - -/* Use the regular ELF conventions about underscores, and provide the - weak symbol, as required */ -#define SYSCALL__(name,args) PSEUDO (__machdep_sys_##name, name, args) \ -.weak machdep_sys_##name; \ - machdep_sys_##name = __machdep_sys_##name; \ -.type __machdep_sys_##name,@function; \ -.type machdep_sys_##name,@function; \ -.L__machdep_sys_##name##end: .size __machdep_sys_##name,.L__machdep_sys_##name##end - __machdep_sys_##name - -#define SYSCALL(name,args) PSEUDO (__machdep_sys_##name, name, args) \ -.weak machdep_sys_##name; \ - machdep_sys_##name = __machdep_sys_##name; \ -.type __machdep_sys_##name,@function; \ -.type machdep_sys_##name,@function; \ -.L__machdep_sys_##name##end: .size __machdep_sys_##name,.L__machdep_sys_##name##end - __machdep_sys_##name - -#else /* PTHREAD_KERNEL */ - -/* Use the regular ELF conventions about underscores, and provide the - weak symbol, as required */ -#define SYSCALL__(name,args) PSEUDO (__libc_##name, name, args) \ -.weak __##name; \ -.weak name; \ - __##name = __libc_##name; \ - name = __libc_##name; \ -.type __libc_##name,@function; \ -.type name,@function; \ -.type __##name,@function; \ -.L__libc_##name##end: .size __libc_##name,.L__libc_##name##end - __libc_##name - -#define SYSCALL(name,args) PSEUDO (__libc_##name, name, args) \ -.weak name; \ - name = __libc_##name; \ -.type __libc_##name,@function; \ -.type name,@function; \ -.L__libc_##name##end: .size __libc_##name,.L__libc_##name##end - __libc_##name - -#endif /* PTHREAD_KERNEL */ - -#else /* _POSIX_THREADS */ - -/* Use the regular ELF conventions about underscores, and provide the - weak symbol, as required */ -#define SYSCALL__(name,args) PSEUDO (__libc_##name, name, args) \ -.weak name; \ - __##name = __libc_##name; \ - name = __libc_##name; \ -.type __libc_##name,@function; \ -.type name,@function; \ -.type __##name,@function; \ -.L__libc_##name##end: .size __libc_##name,.L__libc_##name##end - __libc_##name - -#define SYSCALL(name,args) PSEUDO (__libc_##name, name, args) \ - name = __libc_##name; \ -.type __libc_##name,@function; \ -.type name,@function; \ -.L__libc_##name##end: .size __libc_##name,.L__libc_##name##end - __libc_##name - -#endif /* _POSIX_THREADS */ - -#else /* __ELF__ */ - -#define SYSCALL_WEAK_ALIAS(alias,orig) - -/* Regular a.out definition */ -#define SYSCALL__(name,args) PSEUDO (__##name, name, args) -#define SYSCALL(name,args) PSEUDO (name, name, args) - -#endif /* __ELF__ */ - -#else /* __STDC__ */ - -#define SYSCALL__(name,args) PSEUDO (__/**/name, name, args) -#define SYSCALL(name,args) PSEUDO (name, name, args) - -#endif /* __STDC__ */ - -/* Machine-dependent sysdep.h files are expected to define the macro - PSEUDO (function_name, syscall_name) to emit assembly code to define the - C-callable function FUNCTION_NAME to do system call SYSCALL_NAME. - r0 and r1 are the system call outputs. movl should be defined as - an instruction such that "movl r1, r0" works. ret should be defined - as the return instruction. */ - - -#if !defined(HAVE_GNU_LD) && !defined (__ELF__) -#define ___errno _errno -#endif - -#define HAVE_SYSCALLS - -#define ENTRY(name) - .global name; - .align 4; - -#define END(name) - .size name,.-name; - -#define PSEUDO(name, syscall_name, args) \ - .text; \ - ENTRY(name); \ - ta 0x10; \ - bcc,a 9000f; \ - nop; \ -9000:; - -#define PSEUDO_END(name) \ - .size name,.-name; - diff --git a/libc/sysdeps/linux/sparc/udiv.S b/libc/sysdeps/linux/sparc/udiv.S index e6f143118..85eeb40fc 100644 --- a/libc/sysdeps/linux/sparc/udiv.S +++ b/libc/sysdeps/linux/sparc/udiv.S @@ -37,7 +37,7 @@ -#include +#include .global .udiv; .align 4; @@ -345,4 +345,4 @@ retl mov %o2, %o0 -END(.udiv) +.size .udiv,.-.udiv; diff --git a/libc/sysdeps/linux/sparc/umul.S b/libc/sysdeps/linux/sparc/umul.S index d26ae4382..4f38d78eb 100644 --- a/libc/sysdeps/linux/sparc/umul.S +++ b/libc/sysdeps/linux/sparc/umul.S @@ -14,7 +14,7 @@ * bnz overflow (or tnz) */ -#include +#include .global .umul; diff --git a/libc/sysdeps/linux/sparc/urem.S b/libc/sysdeps/linux/sparc/urem.S index 2e236b151..890532141 100644 --- a/libc/sysdeps/linux/sparc/urem.S +++ b/libc/sysdeps/linux/sparc/urem.S @@ -37,7 +37,7 @@ -#include +#include .global .urem; @@ -347,4 +347,4 @@ retl mov %o3, %o0 -END(.urem) +.size .urem , . -.urem diff --git a/libc/sysdeps/linux/sparc/vfork.S b/libc/sysdeps/linux/sparc/vfork.S index 2aef09ab1..0df960d65 100644 --- a/libc/sysdeps/linux/sparc/vfork.S +++ b/libc/sysdeps/linux/sparc/vfork.S @@ -3,28 +3,50 @@ Contributed by Jakub Jelinek , 1999. The GNU C Library is free software; you can redistribute it and/or - modify it under the terms of the GNU Library General Public License as - published by the Free Software Foundation; either version 2 of the - License, or (at your option) any later version. + 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 - Library General Public License for more details. + Lesser General Public License for more details. - You should have received a copy of the GNU Library General Public - License along with the GNU C Library; see the file COPYING.LIB. If not, - write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. */ + 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. */ /* Code taken from glibc2.2.2/sysdeps/unix/sysv/linux/sparc/vfork.S */ -#include "sysdep.h" +#include -PSEUDO (__vfork, vfork, 0) +#ifndef __NR_vfork +/* uClinux-2.0 only has fork which is really vfork */ +#define __NR_vfork __NR_fork +#endif + +.text; +.global vfork; +.align 4; +.type vfork,@function; + +vfork: + mov __NR_vfork, %g1 + ta 0x10 + bcc,a 9000f + nop + save %sp,-96,%sp + call __errno_location + nop + st %i0,[%o0] + jmpl %i7+8,%g0 + restore %g0,-1,%o0 + +9000: sub %o1, 1, %o1 retl - and %o0, %o1, %o0 + and %o0, %o1, %o0 + +.size vfork,.-vfork; -.size __vfork,.-__vfork -.weak vfork; vfork = __vfork; -- cgit v1.2.3