From 76d80593426f5f77a51dcf694786576a37f3b208 Mon Sep 17 00:00:00 2001 From: Mike Frysinger Date: Wed, 6 Jul 2005 22:40:33 +0000 Subject: Peter S. Mazinger writes: use the __syscall_error.c trick to handle setting errno --- libc/sysdeps/linux/i386/Makefile | 2 +- libc/sysdeps/linux/i386/__syscall_error.c | 29 ++++++++++++++++ libc/sysdeps/linux/i386/mmap64.S | 30 +++++------------ libc/sysdeps/linux/i386/syscall.S | 55 ++++++++----------------------- libc/sysdeps/linux/i386/vfork.S | 23 +++---------- 5 files changed, 55 insertions(+), 84 deletions(-) create mode 100644 libc/sysdeps/linux/i386/__syscall_error.c diff --git a/libc/sysdeps/linux/i386/Makefile b/libc/sysdeps/linux/i386/Makefile index e29707f0e..fc13e6f45 100644 --- a/libc/sysdeps/linux/i386/Makefile +++ b/libc/sysdeps/linux/i386/Makefile @@ -28,7 +28,7 @@ SSRC=__longjmp.S vfork.S clone.S setjmp.S bsd-setjmp.S \ bsd-_setjmp.S syscall.S mmap64.S SOBJS=$(patsubst %.S,%.o, $(SSRC)) -CSRC=brk.c sigaction.c +CSRC=brk.c sigaction.c __syscall_error.c COBJS=$(patsubst %.c,%.o, $(CSRC)) OBJS=$(SOBJS) $(COBJS) diff --git a/libc/sysdeps/linux/i386/__syscall_error.c b/libc/sysdeps/linux/i386/__syscall_error.c new file mode 100644 index 000000000..de65a1f39 --- /dev/null +++ b/libc/sysdeps/linux/i386/__syscall_error.c @@ -0,0 +1,29 @@ +/* Wrapper for setting errno. + Copyright (C) 1997, 1998, 1999, 2000 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 +#include + +/* This routine is jumped to by all the syscall handlers, to stash + * an error number into errno. */ +int attribute_hidden __syscall_error(int err_no) +{ + __set_errno(err_no); + return -1; +} diff --git a/libc/sysdeps/linux/i386/mmap64.S b/libc/sysdeps/linux/i386/mmap64.S index 42d1bb69e..dde3b9ae1 100644 --- a/libc/sysdeps/linux/i386/mmap64.S +++ b/libc/sysdeps/linux/i386/mmap64.S @@ -65,6 +65,7 @@ mmap64: movl FD(%esp), %edi movl $__NR_mmap2, %eax /* System call number in %eax. */ + /* Do the system call trap. */ int $0x80 /* Restore registers. */ @@ -75,7 +76,8 @@ mmap64: /* If 0 > %eax > -4096 there was an error. */ cmpl $-4095,%eax - jae __syscall_error + ja __error + /* Successful; return the syscall's value. */ ret /* This means the offset value is too large. */ @@ -85,27 +87,11 @@ L_einval: popl %ebx popl %ebp movl $-EINVAL, %eax - jmp __syscall_error - - -__syscall_error: - negl %eax - pushl %eax -#ifdef __PIC__ - call .Lthere -.Lthere: - popl %ebx - addl $_GLOBAL_OFFSET_TABLE_+[.- .Lthere ], %ebx - call __errno_location@PLT -#else - call __errno_location -#endif - popl %ecx - movl %ecx, (%eax) - xorl %eax, %eax - decl %eax + jmp __error + +__error: + call __syscall_error -.Lsize: -.size mmap64,.Lsize-mmap64 +.size mmap64,.-mmap64 #endif diff --git a/libc/sysdeps/linux/i386/syscall.S b/libc/sysdeps/linux/i386/syscall.S index b65950fb5..7c49625b2 100644 --- a/libc/sysdeps/linux/i386/syscall.S +++ b/libc/sysdeps/linux/i386/syscall.S @@ -20,8 +20,6 @@ * and things will just work. */ -#include - .text .global syscall .type syscall,%function @@ -30,49 +28,22 @@ syscall: pushl %edi pushl %esi pushl %ebx - movl 36(%esp),%edi; /* Load the 5 syscall argument registers */ - movl 32(%esp),%esi; - movl 28(%esp),%edx; - movl 24(%esp),%ecx; - movl 20(%esp),%ebx; + movl 36(%esp),%edi /* Load the 5 syscall argument registers */ + movl 32(%esp),%esi + movl 28(%esp),%edx + movl 24(%esp),%ecx + movl 20(%esp),%ebx movl 16(%esp),%eax /* Load syscall number into %eax. */ -#APP int $0x80 -#NO_APP - cmpl $-4095,%eax - jbe .Ldone - -#ifdef __PIC__ - call Lhere -Lhere: - popl %ebx - addl $_GLOBAL_OFFSET_TABLE_+[.-Lhere],%ebx - negl %eax - movl %eax,%ecx -#ifdef __UCLIBC_HAS_THREADS__ - call __errno_location@PLT -#else - movl errno@GOT(%ebx),%eax -#endif /* __UCLIBC_HAS_THREADS__ */ - movl %ecx,(%eax) -#else - negl %eax -#ifdef __UCLIBC_HAS_THREADS__ - movl %eax,%ecx - call __errno_location - movl %ecx,(%eax) -#else - movl %eax,errno -#endif /* __UCLIBC_HAS_THREADS__ */ - -#endif /* __PIC__ */ - movl $-1,%eax - .p2align 4,,7 -.Ldone: popl %ebx popl %esi popl %edi - ret -.Lsize: -.size syscall,.Lsize-syscall + cmpl $-4095,%eax + jae __error + ret /* Return to caller. */ + +__error: + call __syscall_error + +.size syscall,.-syscall diff --git a/libc/sysdeps/linux/i386/vfork.S b/libc/sysdeps/linux/i386/vfork.S index d9b8ab7ca..00a2954d5 100644 --- a/libc/sysdeps/linux/i386/vfork.S +++ b/libc/sysdeps/linux/i386/vfork.S @@ -25,28 +25,13 @@ __vfork: int $0x80 pushl %ecx cmpl $-4095,%eax - jae __syscall_error + jae __error ret -__syscall_error: - negl %eax - pushl %eax -#ifdef __PIC__ - call .Lthere -.Lthere: - popl %ebx - addl $_GLOBAL_OFFSET_TABLE_+[.- .Lthere ], %ebx - call __errno_location@PLT -#else - call __errno_location -#endif - popl %ecx - movl %ecx, (%eax) - xorl %eax, %eax - decl %eax +__error: + call __syscall_error -.Lsize: -.size __vfork,.Lsize-__vfork +.size __vfork,.-__vfork .weak vfork ; vfork = __vfork -- cgit v1.2.3