summaryrefslogtreecommitdiffstats
path: root/libc/sysdeps/linux/powerpc
diff options
context:
space:
mode:
Diffstat (limited to 'libc/sysdeps/linux/powerpc')
-rw-r--r--libc/sysdeps/linux/powerpc/__longjmp.S2
-rw-r--r--libc/sysdeps/linux/powerpc/__syscall_error.c25
-rw-r--r--libc/sysdeps/linux/powerpc/bits/fcntl.h15
-rw-r--r--libc/sysdeps/linux/powerpc/bits/kernel_types.h4
-rw-r--r--libc/sysdeps/linux/powerpc/bits/mman.h21
-rw-r--r--libc/sysdeps/linux/powerpc/bits/msq.h3
-rw-r--r--libc/sysdeps/linux/powerpc/bits/sem.h9
-rw-r--r--libc/sysdeps/linux/powerpc/bits/shm.h6
-rw-r--r--libc/sysdeps/linux/powerpc/bits/stat.h32
-rw-r--r--libc/sysdeps/linux/powerpc/bits/termios.h87
-rw-r--r--libc/sysdeps/linux/powerpc/bits/uClibc_arch_features.h44
-rw-r--r--libc/sysdeps/linux/powerpc/bits/wordsize.h32
-rw-r--r--libc/sysdeps/linux/powerpc/brk.S15
-rw-r--r--libc/sysdeps/linux/powerpc/clone.S13
-rw-r--r--libc/sysdeps/linux/powerpc/ioctl.c12
-rw-r--r--libc/sysdeps/linux/powerpc/mmap.c11
-rw-r--r--libc/sysdeps/linux/powerpc/ppc_asm.h54
-rw-r--r--libc/sysdeps/linux/powerpc/pread_write.c105
-rw-r--r--libc/sysdeps/linux/powerpc/sys/procfs.h15
-rw-r--r--libc/sysdeps/linux/powerpc/sys/ucontext.h144
-rw-r--r--libc/sysdeps/linux/powerpc/vfork.S21
-rw-r--r--libc/sysdeps/linux/powerpc/vfork.c49
22 files changed, 470 insertions, 249 deletions
diff --git a/libc/sysdeps/linux/powerpc/__longjmp.S b/libc/sysdeps/linux/powerpc/__longjmp.S
index 874354e5a..83f094c15 100644
--- a/libc/sysdeps/linux/powerpc/__longjmp.S
+++ b/libc/sysdeps/linux/powerpc/__longjmp.S
@@ -80,3 +80,5 @@ FP( lfd fp31,((JB_FPRS+17*2)*4)(r3))
mr r3,r4
blr
.size __longjmp,.-__longjmp
+
+libc_hidden_def(__longjmp)
diff --git a/libc/sysdeps/linux/powerpc/__syscall_error.c b/libc/sysdeps/linux/powerpc/__syscall_error.c
index de65a1f39..5e109a83b 100644
--- a/libc/sysdeps/linux/powerpc/__syscall_error.c
+++ b/libc/sysdeps/linux/powerpc/__syscall_error.c
@@ -1,28 +1,17 @@
/* 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. */
+ *
+ * Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
#include <errno.h>
#include <features.h>
/* 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)
+int __syscall_error(int err_no) attribute_hidden;
+int __syscall_error(int err_no)
{
__set_errno(err_no);
return -1;
diff --git a/libc/sysdeps/linux/powerpc/bits/fcntl.h b/libc/sysdeps/linux/powerpc/bits/fcntl.h
index 8a709841b..19649c01c 100644
--- a/libc/sysdeps/linux/powerpc/bits/fcntl.h
+++ b/libc/sysdeps/linux/powerpc/bits/fcntl.h
@@ -1,5 +1,6 @@
/* O_*, F_*, FD_* bit values for Linux/PowerPC.
- Copyright (C) 1995,1996,1997,1998,2000,2003 Free Software Foundation, Inc.
+ Copyright (C) 1995, 1996, 1997, 1998, 2000, 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
@@ -45,7 +46,7 @@
# define O_DIRECT 0400000 /* Direct disk access. */
# define O_DIRECTORY 040000 /* Must be a directory. */
# define O_NOFOLLOW 0100000 /* Do not follow links. */
-# define O_STREAMING 04000000 /* streaming access */
+# define O_NOATIME 01000000 /* Do not set atime. */
#endif
#ifdef __USE_LARGEFILE64
@@ -79,7 +80,7 @@
#define F_SETLK64 13 /* Set record locking info (non-blocking). */
#define F_SETLKW64 14 /* Set record locking info (blocking). */
-#if defined __USE_BSD || defined __USE_XOPEN2K
+#if defined __USE_BSD || defined __USE_UNIX98
# define F_SETOWN 8 /* Get owner of socket (receiver of SIGIO). */
# define F_GETOWN 9 /* Set owner of socket (receiver of SIGIO). */
#endif
@@ -178,3 +179,11 @@ struct flock64
# define POSIX_FADV_DONTNEED 4 /* Don't need these pages. */
# define POSIX_FADV_NOREUSE 5 /* Data will be accessed once. */
#endif
+
+__BEGIN_DECLS
+
+/* Provide kernel hint to read ahead. */
+extern ssize_t readahead (int __fd, __off64_t __offset, size_t __count)
+ __THROW;
+
+__END_DECLS
diff --git a/libc/sysdeps/linux/powerpc/bits/kernel_types.h b/libc/sysdeps/linux/powerpc/bits/kernel_types.h
index 711ca4f21..223037545 100644
--- a/libc/sysdeps/linux/powerpc/bits/kernel_types.h
+++ b/libc/sysdeps/linux/powerpc/bits/kernel_types.h
@@ -4,9 +4,11 @@
* our private content, and not the kernel header, will win.
* -Erik
*/
-#if ! defined _PPC_POSIX_TYPES_H && ! defined _PPC64_POSIX_TYPES_H
+#if ! defined _PPC_POSIX_TYPES_H && ! defined _PPC64_POSIX_TYPES_H && \
+ ! defined _ASM_POWERPC_POSIX_TYPES_H
#define _PPC_POSIX_TYPES_H
#define _PPC64_POSIX_TYPES_H
+#define _ASM_POWERPC_POSIX_TYPES_H
# if __WORDSIZE == 64
typedef unsigned int __kernel_dev_t;
diff --git a/libc/sysdeps/linux/powerpc/bits/mman.h b/libc/sysdeps/linux/powerpc/bits/mman.h
index f92bc7fc3..580e93886 100644
--- a/libc/sysdeps/linux/powerpc/bits/mman.h
+++ b/libc/sysdeps/linux/powerpc/bits/mman.h
@@ -1,5 +1,5 @@
/* Definitions for POSIX memory map interface. Linux/PowerPC version.
- Copyright (C) 1997, 2000 Free Software Foundation, Inc.
+ Copyright (C) 1997, 2000, 2003, 2005, 2006 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
@@ -34,6 +34,10 @@
#define PROT_WRITE 0x2 /* Page can be written. */
#define PROT_EXEC 0x4 /* Page can be executed. */
#define PROT_NONE 0x0 /* Page can not be accessed. */
+#define PROT_GROWSDOWN 0x01000000 /* Extend change to start of
+ growsdown vma (mprotect only). */
+#define PROT_GROWSUP 0x02000000 /* Extend change to start of
+ growsup vma (mprotect only). */
/* Sharing types (must choose one and only one of these). */
#define MAP_SHARED 0x001 /* Share changes. */
@@ -52,11 +56,13 @@
/* These are Linux-specific. */
#ifdef __USE_MISC
-# define MAP_GROWSDOWN 0x0100 /* Stack-like segment. */
-# define MAP_DENYWRITE 0x0800 /* ETXTBSY */
-# define MAP_EXECUTABLE 0x1000 /* Mark it as an executable. */
-# define MAP_LOCKED 0x0080 /* Lock the mapping. */
-# define MAP_NORESERVE 0x0040 /* Don't check for reservations. */
+# define MAP_GROWSDOWN 0x00100 /* Stack-like segment. */
+# define MAP_DENYWRITE 0x00800 /* ETXTBSY */
+# define MAP_EXECUTABLE 0x01000 /* Mark it as an executable. */
+# define MAP_LOCKED 0x00080 /* Lock the mapping. */
+# define MAP_NORESERVE 0x00040 /* Don't check for reservations. */
+# define MAP_POPULATE 0x08000 /* Populate (prefault) pagetables. */
+# define MAP_NONBLOCK 0x10000 /* Do not block on IO. */
#endif
/* Flags to `msync'. */
@@ -83,6 +89,9 @@
# define MADV_SEQUENTIAL 2 /* Expect sequential page references. */
# define MADV_WILLNEED 3 /* Will need these pages. */
# define MADV_DONTNEED 4 /* Don't need these pages. */
+# define MADV_REMOVE 5 /* Remove these pages and resources. */
+# define MADV_DONTFORK 10 /* Do not inherit across fork. */
+# define MADV_DOFORK 11 /* Do inherit across fork. */
#endif
/* The POSIX people had to invent similar names for the same things. */
diff --git a/libc/sysdeps/linux/powerpc/bits/msq.h b/libc/sysdeps/linux/powerpc/bits/msq.h
index 45173a4cb..f19884437 100644
--- a/libc/sysdeps/linux/powerpc/bits/msq.h
+++ b/libc/sysdeps/linux/powerpc/bits/msq.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 1995, 1996, 1997, 2000 Free Software Foundation, Inc.
+/* Copyright (C) 1995, 1996, 1997, 2000, 2002 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
@@ -21,7 +21,6 @@
#endif
#include <bits/types.h>
-#include <bits/wordsize.h>
/* Define options for message queue functions. */
#define MSG_NOERROR 010000 /* no error if message is too big */
diff --git a/libc/sysdeps/linux/powerpc/bits/sem.h b/libc/sysdeps/linux/powerpc/bits/sem.h
index 6a615f154..1c648cd19 100644
--- a/libc/sysdeps/linux/powerpc/bits/sem.h
+++ b/libc/sysdeps/linux/powerpc/bits/sem.h
@@ -22,7 +22,6 @@
#endif
#include <sys/types.h>
-#include <bits/wordsize.h>
/* Flags for `semop'. */
#define SEM_UNDO 0x1000 /* undo the operation on exit */
@@ -31,8 +30,8 @@
#define GETPID 11 /* get sempid */
#define GETVAL 12 /* get semval */
#define GETALL 13 /* get all semval's */
-#define GETNCNT 14 /* get semncnt */
-#define GETZCNT 15 /* get semzcnt */
+#define GETNCNT 14 /* get semncnt */
+#define GETZCNT 15 /* get semzcnt */
#define SETVAL 16 /* set semval */
#define SETALL 17 /* set all semval's */
@@ -44,11 +43,11 @@ struct semid_ds
#if __WORDSIZE == 32
unsigned int __unused1;
#endif
- __time_t sem_otime; /* last semop() time */
+ __time_t sem_otime; /* last semop() time */
#if __WORDSIZE == 32
unsigned int __unused2;
#endif
- __time_t sem_ctime; /* last time changed by semctl() */
+ __time_t sem_ctime; /* last time changed by semctl() */
unsigned long int sem_nsems; /* number of semaphores in set */
unsigned long __unused3;
unsigned long __unused4;
diff --git a/libc/sysdeps/linux/powerpc/bits/shm.h b/libc/sysdeps/linux/powerpc/bits/shm.h
index 6477df634..62560c0ca 100644
--- a/libc/sysdeps/linux/powerpc/bits/shm.h
+++ b/libc/sysdeps/linux/powerpc/bits/shm.h
@@ -22,7 +22,6 @@
#endif
#include <bits/types.h>
-#include <bits/wordsize.h>
/* Permission flag for shmget. */
#define SHM_R 0400 /* or S_IRUGO from <linux/stat.h> */
@@ -81,9 +80,10 @@ struct shmid_ds
# define SHM_INFO 14
/* shm_mode upper byte flags */
-# define SHM_DEST 01000 /* segment will be destroyed on last detach */
-# define SHM_LOCKED 02000 /* segment will not be swapped */
+# define SHM_DEST 01000 /* segment will be destroyed on last detach */
+# define SHM_LOCKED 02000 /* segment will not be swapped */
# define SHM_HUGETLB 04000 /* segment is mapped via hugetlb */
+# define SHM_NORESERVE 010000 /* don't check for reservations */
struct shminfo
{
diff --git a/libc/sysdeps/linux/powerpc/bits/stat.h b/libc/sysdeps/linux/powerpc/bits/stat.h
index c85695e51..af71f275e 100644
--- a/libc/sysdeps/linux/powerpc/bits/stat.h
+++ b/libc/sysdeps/linux/powerpc/bits/stat.h
@@ -27,11 +27,11 @@
#define _STAT_VER_LINUX_OLD 1
#define _STAT_VER_KERNEL 1
#define _STAT_VER_SVR4 2
+#define _STAT_VER_LINUX 3
#if __WORDSIZE == 32
-# define _STAT_VER_LINUX 3
-# define _STAT_VER _STAT_VER_LINUX /* The one defined below. */
+# define _STAT_VER _STAT_VER_LINUX
#else
-# define _STAT_VER _STAT_VER_KERNEL /* The one defined below. */
+# define _STAT_VER _STAT_VER_KERNEL
#endif
/* Versions of the `xmknod' interface. */
@@ -70,11 +70,11 @@ struct stat
__blkcnt64_t st_blocks; /* Number 512-byte blocks allocated. */
# endif
__time_t st_atime; /* Time of last access. */
- unsigned long int __unused1; /* Reserved for atime.nanoseconds. */
+ unsigned long int st_atimensec; /* Nscecs of last access. */
__time_t st_mtime; /* Time of last modification. */
- unsigned long int __unused2; /* Reserved for mtime.nanoseconds. */
+ unsigned long int st_mtimensec; /* Nsecs of last modification. */
__time_t st_ctime; /* Time of last status change. */
- unsigned long int __unused3; /* Reserved for ctime.nanoseconds. */
+ unsigned long int st_ctimensec; /* Nsecs of last status change. */
unsigned long int __unused4;
unsigned long int __unused5;
};
@@ -95,11 +95,11 @@ struct stat64
__blksize_t st_blksize; /* Optimal block size for I/O. */
__blkcnt64_t st_blocks; /* Number 512-byte blocks allocated. */
__time_t st_atime; /* Time of last access. */
- unsigned long int __unused1; /* Reserved for atime.nanoseconds. */
+ unsigned long int st_atimensec; /* Nscecs of last access. */
__time_t st_mtime; /* Time of last modification. */
- unsigned long int __unused2; /* Reserved for mtime.nanoseconds. */
+ unsigned long int st_mtimensec; /* Nsecs of last modification. */
__time_t st_ctime; /* Time of last status change. */
- unsigned long int __unused3; /* Reserved for ctime.nanoseconds. */
+ unsigned long int st_ctimensec; /* Nsecs of last status change. */
unsigned long int __unused4;
unsigned long int __unused5;
};
@@ -134,11 +134,11 @@ struct stat
__blkcnt64_t st_blocks; /* Number 512-byte blocks allocated. */
# endif
__time_t st_atime; /* Time of last access. */
- unsigned long int __unused1; /* Reserved for atime.nanoseconds. */
+ unsigned long int st_atimensec; /* Nscecs of last access. */
__time_t st_mtime; /* Time of last modification. */
- unsigned long int __unused2; /* Reserved for mtime.nanoseconds. */
+ unsigned long int st_mtimensec; /* Nsecs of last modification. */
__time_t st_ctime; /* Time of last status change. */
- unsigned long int __unused3; /* Reserved for ctime.nanoseconds. */
+ unsigned long int st_ctimensec; /* Nsecs of last status change. */
unsigned long int __unused4;
unsigned long int __unused5;
unsigned long int __unused6;
@@ -159,11 +159,11 @@ struct stat64
__blksize_t st_blksize; /* Optimal block size for I/O. */
__blkcnt64_t st_blocks; /* Number 512-byte blocks allocated. */
__time_t st_atime; /* Time of last access. */
- unsigned long int __unused1; /* Reserved for atime.nanoseconds. */
+ unsigned long int st_atimensec; /* Nscecs of last access. */
__time_t st_mtime; /* Time of last modification. */
- unsigned long int __unused2; /* Reserved for mtime.nanoseconds. */
+ unsigned long int st_mtimensec; /* Nsecs of last modification. */
__time_t st_ctime; /* Time of last status change. */
- unsigned long int __unused3; /* Reserved for ctime.nanoseconds. */
+ unsigned long int st_ctimensec; /* Nsecs of last status change. */
unsigned long int __unused4;
unsigned long int __unused5;
unsigned long int __unused6;
@@ -175,6 +175,8 @@ struct stat64
/* Tell code we have these members. */
#define _STATBUF_ST_BLKSIZE
#define _STATBUF_ST_RDEV
+/* Nanosecond resolution time values are supported. */
+#define _STATBUF_ST_NSEC
/* Encoding of the file mode. */
diff --git a/libc/sysdeps/linux/powerpc/bits/termios.h b/libc/sysdeps/linux/powerpc/bits/termios.h
index f7b89ae59..7aac02dc5 100644
--- a/libc/sysdeps/linux/powerpc/bits/termios.h
+++ b/libc/sysdeps/linux/powerpc/bits/termios.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 1997, 1999, 2001 Free Software Foundation, Inc.
+/* Copyright (C) 1997,1999,2001,2003,2004,2005 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
@@ -40,6 +40,8 @@ struct termios {
cc_t c_cc[NCCS]; /* control characters */
speed_t c_ispeed; /* input speed */
speed_t c_ospeed; /* output speed */
+#define _HAVE_STRUCT_TERMIOS_C_ISPEED 1
+#define _HAVE_STRUCT_TERMIOS_C_OSPEED 1
};
/* c_cc characters */
@@ -77,6 +79,7 @@ struct termios {
#define IXANY 0004000
#define IUCLC 0010000
#define IMAXBEL 0020000
+#define IUTF8 0040000
/* c_oflag bits */
#define OPOST 0000001
@@ -89,34 +92,41 @@ struct termios {
#define OFILL 00000100
#define OFDEL 00000200
-#define NLDLY 00001400
-#define NL0 00000000
-#define NL1 00000400
-#define NL2 00001000
-#define NL3 00001400
-#define TABDLY 00006000
-#define TAB0 00000000
-#define TAB1 00002000
-#define TAB2 00004000
-#define TAB3 00006000
-#define CRDLY 00030000
-#define CR0 00000000
-#define CR1 00010000
-#define CR2 00020000
-#define CR3 00030000
-#define FFDLY 00040000
-#define FF0 00000000
-#define FF1 00040000
-#define BSDLY 00100000
-#define BS0 00000000
-#define BS1 00100000
+#if defined __USE_MISC || defined __USE_XOPEN
+# define NLDLY 00001400
+# define NL0 00000000
+# define NL1 00000400
+# define NL2 00001000
+# define NL3 00001400
+# define TABDLY 00006000
+# define TAB0 00000000
+# define TAB1 00002000
+# define TAB2 00004000
+# define TAB3 00006000
+# define CRDLY 00030000
+# define CR0 00000000
+# define CR1 00010000
+# define CR2 00020000
+# define CR3 00030000
+# define FFDLY 00040000
+# define FF0 00000000
+# define FF1 00040000
+# define BSDLY 00100000
+# define BS0 00000000
+# define BS1 00100000
+#endif
#define VTDLY 00200000
#define VT0 00000000
#define VT1 00200000
-#define XTABS 01000000 /* Hmm.. Linux/i386 considers this part of TABDLY.. */
+
+#ifdef __USE_MISC
+# define XTABS 00006000
+#endif
/* c_cflag bit meaning */
-#define CBAUD 0000377
+#ifdef __USE_MISC
+# define CBAUD 0000377
+#endif
#define B0 0000000 /* hang up */
#define B50 0000001
#define B75 0000002
@@ -133,9 +143,11 @@ struct termios {
#define B9600 0000015
#define B19200 0000016
#define B38400 0000017
-#define EXTA B19200
-#define EXTB B38400
-#define CBAUDEX 0000020
+#ifdef __USE_MISC
+# define EXTA B19200
+# define EXTB B38400
+# define CBAUDEX 0000020
+#endif
#define B57600 00020
#define B115200 00021
#define B230400 00022
@@ -166,23 +178,30 @@ struct termios {
#define HUPCL 00040000
#define CLOCAL 00100000
-#define CRTSCTS 020000000000 /* flow control */
+#ifdef __USE_MISC
+# define CMSPAR 010000000000 /* mark or space (stick) parity */
+# define CRTSCTS 020000000000 /* flow control */
+#endif
/* c_lflag bits */
#define ISIG 0x00000080
#define ICANON 0x00000100
-#define XCASE 0x00004000
+#if defined __USE_MISC || defined __USE_XOPEN
+# define XCASE 0x00004000
+#endif
#define ECHO 0x00000008
#define ECHOE 0x00000002
#define ECHOK 0x00000004
#define ECHONL 0x00000010
#define NOFLSH 0x80000000
#define TOSTOP 0x00400000
-#define ECHOCTL 0x00000040
-#define ECHOPRT 0x00000020
-#define ECHOKE 0x00000001
-#define FLUSHO 0x00800000
-#define PENDIN 0x20000000
+#ifdef __USE_MISC
+# define ECHOCTL 0x00000040
+# define ECHOPRT 0x00000020
+# define ECHOKE 0x00000001
+# define FLUSHO 0x00800000
+# define PENDIN 0x20000000
+#endif
#define IEXTEN 0x00000400
/* Values for the ACTION argument to `tcflow'. */
diff --git a/libc/sysdeps/linux/powerpc/bits/uClibc_arch_features.h b/libc/sysdeps/linux/powerpc/bits/uClibc_arch_features.h
new file mode 100644
index 000000000..1e994ec68
--- /dev/null
+++ b/libc/sysdeps/linux/powerpc/bits/uClibc_arch_features.h
@@ -0,0 +1,44 @@
+/*
+ * Track misc arch-specific features that aren't config options
+ */
+
+#ifndef _BITS_UCLIBC_ARCH_FEATURES_H
+#define _BITS_UCLIBC_ARCH_FEATURES_H
+
+/* instruction used when calling abort() to kill yourself */
+#define __UCLIBC_ABORT_INSTRUCTION__ ".long 0"
+
+/* can your target use syscall6() for mmap ? */
+#define __UCLIBC_MMAP_HAS_6_ARGS__
+
+/* does your target use syscall4() for truncate64 ? (32bit arches only) */
+#define __UCLIBC_TRUNCATE64_HAS_4_ARGS__
+
+/* does your target have a broken create_module() ? */
+#undef __UCLIBC_BROKEN_CREATE_MODULE__
+
+/* does your target have to worry about older [gs]etrlimit() ? */
+#define __UCLIBC_HANDLE_OLDER_RLIMIT__
+
+/* does your target prefix all symbols with an _ ? */
+#define __UCLIBC_NO_UNDERSCORES__
+
+/* does your target have an asm .set ? */
+#define __UCLIBC_HAVE_ASM_SET_DIRECTIVE__
+
+/* define if target doesn't like .global */
+#undef __UCLIBC_ASM_GLOBAL_DIRECTIVE__
+
+/* define if target supports .weak */
+#define __UCLIBC_HAVE_ASM_WEAK_DIRECTIVE__
+
+/* define if target supports .weakext */
+#undef __UCLIBC_HAVE_ASM_WEAKEXT_DIRECTIVE__
+
+/* needed probably only for ppc64 */
+#undef __UCLIBC_HAVE_ASM_GLOBAL_DOT_NAME__
+
+/* define if target supports IEEE signed zero floats */
+#define __UCLIBC_HAVE_SIGNED_ZERO__
+
+#endif /* _BITS_UCLIBC_ARCH_FEATURES_H */
diff --git a/libc/sysdeps/linux/powerpc/bits/wordsize.h b/libc/sysdeps/linux/powerpc/bits/wordsize.h
index ba643b60a..cf934234f 100644
--- a/libc/sysdeps/linux/powerpc/bits/wordsize.h
+++ b/libc/sysdeps/linux/powerpc/bits/wordsize.h
@@ -1,19 +1,19 @@
-/* Copyright (C) 1999 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
+/* Determine the wordsize from the preprocessor defines. */
- 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.
+#if defined __powerpc64__
+# define __WORDSIZE 64
+# define __WORDSIZE_COMPAT32 1
+#else
+# define __WORDSIZE 32
+#endif
- 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.
+#if !defined __NO_LONG_DOUBLE_MATH && !defined __LONG_DOUBLE_MATH_OPTIONAL
- 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. */
-
-#define __WORDSIZE 32
+/* Signal the glibc ABI didn't used to have a `long double'.
+ The changes all the `long double' function variants to be redirects
+ to the double functions. */
+# define __LONG_DOUBLE_MATH_OPTIONAL 1
+# ifndef __LONG_DOUBLE_128__
+# define __NO_LONG_DOUBLE_MATH 1
+# endif
+#endif
diff --git a/libc/sysdeps/linux/powerpc/brk.S b/libc/sysdeps/linux/powerpc/brk.S
index b718c0de4..b7b19d153 100644
--- a/libc/sysdeps/linux/powerpc/brk.S
+++ b/libc/sysdeps/linux/powerpc/brk.S
@@ -17,6 +17,7 @@
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
02111-1307 USA. */
+#include <features.h>
#include "ppc_asm.h"
#define _ERRNO_H 1
#include <bits/errno.h>
@@ -25,12 +26,11 @@
#ifdef __NR_brk
.comm __curbrk,4,4
.text
- .globl __brk
- .hidden __brk
- .type __brk,@function
+ .globl brk
+ .type brk,@function
.align 2
-__brk:
+brk:
stwu r1,-16(r1)
stw r3,8(r1)
li 0, __NR_brk;
@@ -55,8 +55,9 @@ __brk:
b __syscall_error
- .size __brk,.-__brk
+ .size brk,.-brk
- .weak brk
- brk=__brk
+libc_hidden_def(brk)
+/* won't help too much, HIDDEN_JUMPTARGET should be used here as well, now the reloc remains */
+libc_hidden_data_def(__curbrk)
#endif
diff --git a/libc/sysdeps/linux/powerpc/clone.S b/libc/sysdeps/linux/powerpc/clone.S
index 9e8a1ca53..15d03f679 100644
--- a/libc/sysdeps/linux/powerpc/clone.S
+++ b/libc/sysdeps/linux/powerpc/clone.S
@@ -17,6 +17,7 @@
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
02111-1307 USA. */
+#include <features.h>
#include "ppc_asm.h"
#define _ERRNO_H 1
#include <bits/errno.h>
@@ -30,11 +31,11 @@
int flags [r5], void *arg [r6]); */
#ifdef __NR_clone
- .globl __clone
- .type __clone,@function
+ .globl clone
+ .type clone,@function
.align 2
-__clone:
+clone:
/* Check for child_stack == NULL || fn == NULL. */
cmpwi cr0,r4,0
cmpwi cr1,r3,0
@@ -78,7 +79,7 @@ __clone:
mr r3,r31
bctrl
/* Call _exit with result from procedure. */
- b _exit_internal
+ b HIDDEN_JUMPTARGET(_exit)
.Lparent:
/* Parent. Restore registers & return. */
@@ -93,7 +94,5 @@ __clone:
b __syscall_error
- .size __clone,.-__clone
- .weak clone
- clone=__clone
+ .size clone,.-clone
#endif
diff --git a/libc/sysdeps/linux/powerpc/ioctl.c b/libc/sysdeps/linux/powerpc/ioctl.c
index bb8842bb6..7f92be410 100644
--- a/libc/sysdeps/linux/powerpc/ioctl.c
+++ b/libc/sysdeps/linux/powerpc/ioctl.c
@@ -16,15 +16,17 @@
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
02111-1307 USA. */
-#define tcsetattr __tcsetattr
-#define tcgetattr __tcgetattr
-
#include <stdarg.h>
#include <termios.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <sys/syscall.h>
+libc_hidden_proto(ioctl)
+
+libc_hidden_proto(tcsetattr)
+libc_hidden_proto(tcgetattr)
+
/* The user-visible size of struct termios has changed. Catch ioctl calls
using the new-style struct termios, and translate them to old-style. */
@@ -33,7 +35,7 @@ static inline
_syscall3(int, __syscall_ioctl, int, fd, unsigned long int, request, void *, arg);
-int attribute_hidden __ioctl (int fd, unsigned long int request, ...)
+int ioctl (int fd, unsigned long int request, ...)
{
void *arg;
va_list ap;
@@ -69,4 +71,4 @@ int attribute_hidden __ioctl (int fd, unsigned long int request, ...)
return result;
}
-strong_alias(__ioctl,ioctl)
+libc_hidden_def(ioctl)
diff --git a/libc/sysdeps/linux/powerpc/mmap.c b/libc/sysdeps/linux/powerpc/mmap.c
index cac08ba65..62c97c1c5 100644
--- a/libc/sysdeps/linux/powerpc/mmap.c
+++ b/libc/sysdeps/linux/powerpc/mmap.c
@@ -1,16 +1,23 @@
+/*
+ * Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
#include <unistd.h>
#include <sys/mman.h>
#include <errno.h>
#include <sys/syscall.h>
+libc_hidden_proto(mmap)
+
#define __syscall_clobbers \
"r9", "r10", "r11", "r12"
#define __syscall_return(type) \
return (__sc_err & 0x10000000 ? errno = __sc_ret, __sc_ret = -1 : 0), \
(type) __sc_ret
-void attribute_hidden * __mmap(void *start, size_t length, int prot, int flags, int fd,
+void * mmap(void *start, size_t length, int prot, int flags, int fd,
off_t offset)
{
unsigned long __sc_ret, __sc_err;
@@ -45,4 +52,4 @@ void attribute_hidden * __mmap(void *start, size_t length, int prot, int flags,
__syscall_return (void *);
}
-strong_alias(__mmap,mmap)
+libc_hidden_def(mmap)
diff --git a/libc/sysdeps/linux/powerpc/ppc_asm.h b/libc/sysdeps/linux/powerpc/ppc_asm.h
index ad34e3e62..e51d88f73 100644
--- a/libc/sysdeps/linux/powerpc/ppc_asm.h
+++ b/libc/sysdeps/linux/powerpc/ppc_asm.h
@@ -1,3 +1,23 @@
+/* Copyright (C) 1999, 2001, 2002 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. */
+
+#ifdef __ASSEMBLER__
+
/* Symbolic names for the registers. The only portable way to write asm
code is to use number but this produces really unreadable code.
Therefore these symbolic names. */
@@ -80,4 +100,38 @@
#define cr6 6
#define cr7 7
+/* Vector registers. */
+#define v0 0
+#define v1 1
+#define v2 2
+#define v3 3
+#define v4 4
+#define v5 5
+#define v6 6
+#define v7 7
+#define v8 8
+#define v9 9
+#define v10 10
+#define v11 11
+#define v12 12
+#define v13 13
+#define v14 14
+#define v15 15
+#define v16 16
+#define v17 17
+#define v18 18
+#define v19 19
+#define v20 20
+#define v21 21
+#define v22 22
+#define v23 23
+#define v24 24
+#define v25 25
+#define v26 26
+#define v27 27
+#define v28 28
+#define v29 29
+#define v30 30
+#define v31 31
+#endif /* __ASSEMBLER__ */
diff --git a/libc/sysdeps/linux/powerpc/pread_write.c b/libc/sysdeps/linux/powerpc/pread_write.c
index 8115d4d01..353143907 100644
--- a/libc/sysdeps/linux/powerpc/pread_write.c
+++ b/libc/sysdeps/linux/powerpc/pread_write.c
@@ -1,50 +1,27 @@
/* vi: set sw=4 ts=4:
*
- * Copyright (C) 2002 by Erik Andersen <andersen@uclibc.org>
- * Based in part on the files
+ * Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+/* Based in part on the files
* ./sysdeps/unix/sysv/linux/pwrite.c,
* ./sysdeps/unix/sysv/linux/pread.c,
* sysdeps/posix/pread.c
* sysdeps/posix/pwrite.c
* from GNU libc 2.2.5, but reworked considerably...
- *
- * This program 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.
- *
- * This program 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 this program; if not, write to the Free Software Foundation,
- * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
-#define _GNU_SOURCE
-#define _LARGEFILE64_SOURCE
-#include <features.h>
-#undef __OPTIMIZE__
-/* We absolutely do _NOT_ want interfaces silently
- * * * renamed under us or very bad things will happen... */
-#ifdef __USE_FILE_OFFSET64
-# undef __USE_FILE_OFFSET64
-#endif
-
-
-#include <errno.h>
-#include <sys/types.h>
-#include <sys/syscall.h>
+#include "../common/syscalls.h"
#include <unistd.h>
-#if ! defined __UCLIBC_HAS_LFS__
-#define off64_t off_t
+#ifndef __UCLIBC_HAS_LFS__
+# define off64_t off_t
#endif
#ifdef __NR_pread
-#define __NR___syscall_pread __NR_pread
+extern __typeof(pread) __libc_pread;
+# define __NR___syscall_pread __NR_pread
static inline _syscall4(ssize_t, __syscall_pread, int, fd,
void *, buf, size_t, count, off64_t, offset);
@@ -52,20 +29,22 @@ ssize_t __libc_pread(int fd, void *buf, size_t count, off_t offset)
{
return(__syscall_pread(fd, buf, count, (off64_t)offset));
}
-weak_alias (__libc_pread, pread)
+weak_alias(__libc_pread,pread)
-#if defined __UCLIBC_HAS_LFS__
+# ifdef __UCLIBC_HAS_LFS__
+extern __typeof(pread64) __libc_pread64;
ssize_t __libc_pread64(int fd, void *buf, size_t count, off64_t offset)
{
return(__syscall_pread(fd, buf, count, offset));
}
-weak_alias (__libc_pread64, pread64)
-#endif /* __UCLIBC_HAS_LFS__ */
+weak_alias(__libc_pread64,pread64)
+# endif /* __UCLIBC_HAS_LFS__ */
#endif /* __NR_pread */
#ifdef __NR_pwrite
-#define __NR___syscall_pwrite __NR_pwrite
+extern __typeof(pwrite) __libc_pwrite;
+# define __NR___syscall_pwrite __NR_pwrite
static inline _syscall4(ssize_t, __syscall_pwrite, int, fd,
const void *, buf, size_t, count, off64_t, offset);
@@ -73,20 +52,25 @@ ssize_t __libc_pwrite(int fd, const void *buf, size_t count, off_t offset)
{
return(__syscall_pwrite(fd, buf, count, (off64_t)offset));
}
-weak_alias (__libc_pwrite, pwrite)
+weak_alias(__libc_pwrite,pwrite)
-#if defined __UCLIBC_HAS_LFS__
+# ifdef __UCLIBC_HAS_LFS__
+extern __typeof(pwrite64) __libc_pwrite64;
ssize_t __libc_pwrite64(int fd, const void *buf, size_t count, off64_t offset)
{
return(__syscall_pwrite(fd, buf, count, offset));
}
-weak_alias (__libc_pwrite64, pwrite64)
-#endif /* __UCLIBC_HAS_LFS__ */
+weak_alias(__libc_pwrite64,pwrite64)
+# endif /* __UCLIBC_HAS_LFS__ */
#endif /* __NR_pwrite */
#if ! defined __NR_pread || ! defined __NR_pwrite
+libc_hidden_proto(read)
+libc_hidden_proto(write)
+libc_hidden_proto(lseek)
+
static ssize_t __fake_pread_write(int fd, void *buf,
size_t count, off_t offset, int do_pwrite)
{
@@ -96,11 +80,11 @@ static ssize_t __fake_pread_write(int fd, void *buf,
/* Since we must not change the file pointer preserve the
* value so that we can restore it later. */
- if ((old_offset=__lseek(fd, 0, SEEK_CUR)) == (off_t) -1)
+ if ((old_offset=lseek(fd, 0, SEEK_CUR)) == (off_t) -1)
return -1;
/* Set to wanted position. */
- if (__lseek (fd, offset, SEEK_SET) == (off_t) -1)
+ if (lseek (fd, offset, SEEK_SET) == (off_t) -1)
return -1;
if (do_pwrite==1) {
@@ -114,7 +98,7 @@ static ssize_t __fake_pread_write(int fd, void *buf,
/* Now we have to restore the position. If this fails we
* have to return this as an error. */
save_errno = errno;
- if (__lseek(fd, old_offset, SEEK_SET) == (off_t) -1)
+ if (lseek(fd, old_offset, SEEK_SET) == (off_t) -1)
{
if (result == -1)
__set_errno(save_errno);
@@ -124,7 +108,9 @@ static ssize_t __fake_pread_write(int fd, void *buf,
return(result);
}
-#if defined __UCLIBC_HAS_LFS__
+# ifdef __UCLIBC_HAS_LFS__
+libc_hidden_proto(lseek64)
+
static ssize_t __fake_pread_write64(int fd, void *buf,
size_t count, off64_t offset, int do_pwrite)
{
@@ -134,11 +120,11 @@ static ssize_t __fake_pread_write64(int fd, void *buf,
/* Since we must not change the file pointer preserve the
* value so that we can restore it later. */
- if ((old_offset=__lseek64(fd, 0, SEEK_CUR)) == (off64_t) -1)
+ if ((old_offset=lseek64(fd, 0, SEEK_CUR)) == (off64_t) -1)
return -1;
/* Set to wanted position. */
- if (__lseek64(fd, offset, SEEK_SET) == (off64_t) -1)
+ if (lseek64(fd, offset, SEEK_SET) == (off64_t) -1)
return -1;
if (do_pwrite==1) {
@@ -151,7 +137,7 @@ static ssize_t __fake_pread_write64(int fd, void *buf,
/* Now we have to restore the position. */
save_errno = errno;
- if (__lseek64 (fd, old_offset, SEEK_SET) == (off64_t) -1) {
+ if (lseek64 (fd, old_offset, SEEK_SET) == (off64_t) -1) {
if (result == -1)
__set_errno (save_errno);
return -1;
@@ -159,7 +145,7 @@ static ssize_t __fake_pread_write64(int fd, void *buf,
__set_errno (save_errno);
return result;
}
-#endif /* __UCLIBC_HAS_LFS__ */
+# endif /* __UCLIBC_HAS_LFS__ */
#endif /* ! defined __NR_pread || ! defined __NR_pwrite */
#ifndef __NR_pread
@@ -167,31 +153,30 @@ ssize_t __libc_pread(int fd, void *buf, size_t count, off_t offset)
{
return(__fake_pread_write(fd, buf, count, offset, 0));
}
-weak_alias (__libc_pread, pread)
+weak_alias(__libc_pread,pread)
-#if defined __UCLIBC_HAS_LFS__
+# ifdef __UCLIBC_HAS_LFS__
ssize_t __libc_pread64(int fd, void *buf, size_t count, off64_t offset)
{
return(__fake_pread_write64(fd, buf, count, offset, 0));
}
-weak_alias (__libc_pread64, pread64)
-#endif /* __UCLIBC_HAS_LFS__ */
+weak_alias(__libc_pread64,pread64)
+# endif /* __UCLIBC_HAS_LFS__ */
#endif /* ! __NR_pread */
#ifndef __NR_pwrite
ssize_t __libc_pwrite(int fd, const void *buf, size_t count, off_t offset)
{
- return(__fake_pread_write(fd, buf, count, offset, 1));
+ return(__fake_pread_write(fd, (void*)buf, count, offset, 1));
}
-weak_alias (__libc_pwrite, pwrite)
+weak_alias(__libc_pwrite,pwrite)
-#if defined __UCLIBC_HAS_LFS__
+# ifdef __UCLIBC_HAS_LFS__
ssize_t __libc_pwrite64(int fd, const void *buf, size_t count, off64_t offset)
{
return(__fake_pread_write64(fd, (void*)buf, count, offset, 1));
}
-weak_alias (__libc_pwrite64, pwrite64)
-#endif /* __UCLIBC_HAS_LFS__ */
+weak_alias(__libc_pwrite64,pwrite64)
+# endif /* __UCLIBC_HAS_LFS__ */
#endif /* ! __NR_pwrite */
-
diff --git a/libc/sysdeps/linux/powerpc/sys/procfs.h b/libc/sysdeps/linux/powerpc/sys/procfs.h
index ff85f09f9..d2d597241 100644
--- a/libc/sysdeps/linux/powerpc/sys/procfs.h
+++ b/libc/sysdeps/linux/powerpc/sys/procfs.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 1996, 1997, 1999 Free Software Foundation, Inc.
+/* Copyright (C) 1996, 1997, 1999, 2002, 2006 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,9 +32,17 @@
__BEGIN_DECLS
+/* These definitions are normally provided by ucontext.h via
+ asm/sigcontext.h, asm/ptrace.h, and asm/elf.h. Otherwise we define
+ them here. */
+#ifndef __PPC64_ELF_H
#define ELF_NGREG 48 /* includes nip, msr, lr, etc. */
#define ELF_NFPREG 33 /* includes fpscr */
-#define ELF_NVRREG 33 /* includes vscr */
+#if __WORDSIZE == 32
+# define ELF_NVRREG 33 /* includes vscr */
+#else
+# define ELF_NVRREG 34 /* includes vscr */
+#endif
typedef unsigned long elf_greg_t;
typedef elf_greg_t elf_gregset_t[ELF_NGREG];
@@ -45,8 +53,9 @@ typedef elf_fpreg_t elf_fpregset_t[ELF_NFPREG];
/* Altivec registers */
typedef struct {
unsigned int u[4];
-} __attribute((aligned (16))) elf_vrreg_t;
+} __attribute__ ((aligned (16))) elf_vrreg_t;
typedef elf_vrreg_t elf_vrregset_t[ELF_NVRREG];
+#endif
struct elf_siginfo
{
diff --git a/libc/sysdeps/linux/powerpc/sys/ucontext.h b/libc/sysdeps/linux/powerpc/sys/ucontext.h
index 07f0933ff..9eb50aa96 100644
--- a/libc/sysdeps/linux/powerpc/sys/ucontext.h
+++ b/libc/sysdeps/linux/powerpc/sys/ucontext.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 1997, 1998, 1999 Free Software Foundation, Inc.
+/* Copyright (C) 1998, 1999, 2002, 2004, 2005 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
@@ -26,7 +26,110 @@
included in <signal.h>. */
#include <bits/sigcontext.h>
-typedef struct sigcontext mcontext_t;
+#if __WORDSIZE == 32
+
+/* Number of general registers. */
+# define NGREG 48
+
+/* Container for all general registers. */
+typedef unsigned long gregset_t[NGREG];
+
+/* Container for floating-point registers and status */
+typedef struct _libc_fpstate
+{
+ double fpregs[32];
+ double fpscr;
+ unsigned int _pad[2];
+} fpregset_t;
+
+/* Container for Altivec/VMX registers and status.
+ Needs to be aligned on a 16-byte boundary. */
+typedef struct _libc_vrstate
+{
+ unsigned int vrregs[32][4];
+ unsigned int vrsave;
+ unsigned int _pad[2];
+ unsigned int vscr;
+} vrregset_t;
+
+/* Context to describe whole processor state. */
+typedef struct
+{
+ gregset_t gregs;
+ fpregset_t fpregs;
+ vrregset_t vrregs __attribute__((__aligned__(16)));
+} mcontext_t;
+
+#else
+
+/* For 64-bit kernels with Altivec support, a machine context is exactly
+ * a sigcontext. For older kernel (without Altivec) the sigcontext matches
+ * the mcontext upto but not including the v_regs field. For kernels that
+ * don't AT_HWCAP or return AT_HWCAP without PPC_FEATURE_HAS_ALTIVEC the
+ * v_regs field may not exit and should not be referenced. The v_regd field
+ * can be refernced safely only after verifying that PPC_FEATURE_HAS_ALTIVEC
+ * is set in AT_HWCAP. */
+
+/* Number of general registers. */
+# define NGREG 48 /* includes r0-r31, nip, msr, lr, etc. */
+# define NFPREG 33 /* includes fp0-fp31 &fpscr. */
+# define NVRREG 34 /* includes v0-v31, vscr, & vrsave in split vectors */
+
+typedef unsigned long gregset_t[NGREG];
+typedef double fpregset_t[NFPREG];
+
+/* Container for Altivec/VMX Vector Status and Control Register. Only 32-bits
+ but can only be copied to/from a 128-bit vector register. So we allocated
+ a whole quadword speedup save/restore. */
+typedef struct _libc_vscr
+{
+ unsigned int __pad[3];
+ unsigned int vscr_word;
+} vscr_t;
+
+/* Container for Altivec/VMX registers and status.
+ Must to be aligned on a 16-byte boundary. */
+typedef struct _libc_vrstate
+{
+ unsigned int vrregs[32][4];
+ vscr_t vscr;
+ unsigned int vrsave;
+ unsigned int __pad[3];
+} vrregset_t __attribute__((__aligned__(16)));
+
+typedef struct {
+ unsigned long __unused[4];
+ int signal;
+ int __pad0;
+ unsigned long handler;
+ unsigned long oldmask;
+ struct pt_regs *regs;
+ gregset_t gp_regs;
+ fpregset_t fp_regs;
+/*
+ * To maintain compatibility with current implementations the sigcontext is
+ * extended by appending a pointer (v_regs) to a quadword type (elf_vrreg_t)
+ * followed by an unstructured (vmx_reserve) field of 69 doublewords. This
+ * allows the array of vector registers to be quadword aligned independent of
+ * the alignment of the containing sigcontext or ucontext. It is the
+ * responsibility of the code setting the sigcontext to set this pointer to
+ * either NULL (if this processor does not support the VMX feature) or the
+ * address of the first quadword within the allocated (vmx_reserve) area.
+ *
+ * The pointer (v_regs) of vector type (elf_vrreg_t) is essentually
+ * an array of 34 quadword entries. The entries with
+ * indexes 0-31 contain the corresponding vector registers. The entry with
+ * index 32 contains the vscr as the last word (offset 12) within the
+ * quadword. This allows the vscr to be stored as either a quadword (since
+ * it must be copied via a vector register to/from storage) or as a word.
+ * The entry with index 33 contains the vrsave as the first word (offset 0)
+ * within the quadword.
+ */
+ vrregset_t *v_regs;
+ long vmx_reserve[NVRREG+NVRREG+1];
+} mcontext_t;
+
+#endif
/* Userlevel context. */
typedef struct ucontext
@@ -34,8 +137,41 @@ typedef struct ucontext
unsigned long int uc_flags;
struct ucontext *uc_link;
stack_t uc_stack;
- mcontext_t uc_mcontext;
- __sigset_t uc_sigmask;
+#if __WORDSIZE == 32
+ /*
+ * These fields are set up this way to maximize source and
+ * binary compatibility with code written for the old
+ * ucontext_t definition, which didn't include space for the
+ * registers.
+ *
+ * Different versions of the kernel have stored the registers on
+ * signal delivery at different offsets from the ucontext struct.
+ * Programs should thus use the uc_mcontext.uc_regs pointer to
+ * find where the registers are actually stored. The registers
+ * will be stored within the ucontext_t struct but not necessarily
+ * at a fixed address. As a side-effect, this lets us achieve
+ * 16-byte alignment for the register storage space if the
+ * Altivec registers are to be saved, without requiring 16-byte
+ * alignment on the whole ucontext_t.
+ *
+ * The uc_mcontext.regs field is included for source compatibility
+ * with programs written against the older ucontext_t definition,
+ * and its name should therefore not change. The uc_pad field
+ * is for binary compatibility with programs compiled against the
+ * old ucontext_t; it ensures that uc_mcontext.regs and uc_sigmask
+ * are at the same offset as previously.
+ */
+ int uc_pad[7];
+ union uc_regs_ptr {
+ struct pt_regs *regs;
+ mcontext_t *uc_regs;
+ } uc_mcontext;
+ sigset_t uc_sigmask;
+ char uc_reg_space[sizeof(mcontext_t) + 12]; /* last for extensibility */
+#else /* 64-bit */
+ sigset_t uc_sigmask;
+ mcontext_t uc_mcontext; /* last for extensibility */
+#endif
} ucontext_t;
#endif /* sys/ucontext.h */
diff --git a/libc/sysdeps/linux/powerpc/vfork.S b/libc/sysdeps/linux/powerpc/vfork.S
index 7cf5eaa16..600c980a8 100644
--- a/libc/sysdeps/linux/powerpc/vfork.S
+++ b/libc/sysdeps/linux/powerpc/vfork.S
@@ -1,17 +1,19 @@
-#include <features.h>
+/*
+ * Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+
#include <sys/syscall.h>
#ifndef __NR_vfork
-
/* No vfork so use fork instead */
-hidden_strong_alias(__fork,__vfork)
-weak_alias(vfork,__libc_fork)
-
-#else
+# define __NR_vfork __NR_fork
+#endif
.text
.global __vfork
-.hidden __vfork
+.hidden __vfork
.type __vfork,@function
.type __syscall_error,@function
@@ -22,5 +24,6 @@ __vfork:
b __syscall_error
.size __vfork,.-__vfork
-#endif
-strong_alias(__vfork,vfork)
+
+weak_alias(__vfork,vfork)
+libc_hidden_weak(vfork)
diff --git a/libc/sysdeps/linux/powerpc/vfork.c b/libc/sysdeps/linux/powerpc/vfork.c
deleted file mode 100644
index 39f992513..000000000
--- a/libc/sysdeps/linux/powerpc/vfork.c
+++ /dev/null
@@ -1,49 +0,0 @@
-#include <unistd.h>
-#include <sys/types.h>
-#include <errno.h>
-#include <sys/syscall.h>
-
-#define __syscall_clobbers \
- "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12"
-#define __syscall_return(type) \
- return (__sc_err & 0x10000000 ? errno = __sc_ret, __sc_ret = -1 : 0), \
- (type) __sc_ret
-
-pid_t attribute_hidden __vfork(void)
-{
- unsigned long __sc_ret, __sc_err;
- register unsigned long __sc_0 __asm__ ("r0");
- register unsigned long __sc_3 __asm__ ("r3");
-
-#if 0
- /* Sigh. The vfork system call on powerpc
- * seems to be completely broken. So just
- * use fork instead */
-
- __sc_0 = __NR_vfork;
- __asm__ __volatile__
- ("sc \n\t"
- "mfcr %1 "
- : "=&r" (__sc_3), "=&r" (__sc_0)
- : "0" (__sc_3), "1" (__sc_0)
- : __syscall_clobbers);
- __sc_ret = __sc_3;
- __sc_err = __sc_0;
-
- if((__sc_err & 0x10000000) && (__sc_ret == ENOSYS))
-#endif
- {
- __sc_0 = __NR_fork;
- __asm__ __volatile__
- ("sc \n\t"
- "mfcr %1 "
- : "=&r" (__sc_3), "=&r" (__sc_0)
- : "0" (__sc_3), "1" (__sc_0)
- : __syscall_clobbers);
- __sc_ret = __sc_3;
- __sc_err = __sc_0;
- }
-
- __syscall_return (pid_t);
-}
-strong_alias(__vfork,vfork)