diff options
Diffstat (limited to 'sysdeps/unix/sysv/linux/sh')
-rw-r--r-- | sysdeps/unix/sysv/linux/sh/bits/fcntl.h | 52 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/sh/chown.c | 70 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/sh/fchownat.c | 123 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/sh/pread.c | 96 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/sh/pread64.c | 97 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/sh/pwrite.c | 96 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/sh/pwrite64.c | 99 |
7 files changed, 605 insertions, 28 deletions
diff --git a/sysdeps/unix/sysv/linux/sh/bits/fcntl.h b/sysdeps/unix/sysv/linux/sh/bits/fcntl.h index c883002641..9065825b98 100644 --- a/sysdeps/unix/sysv/linux/sh/bits/fcntl.h +++ b/sysdeps/unix/sysv/linux/sh/bits/fcntl.h @@ -43,18 +43,18 @@ #define O_ASYNC 020000 #ifdef __USE_GNU -# define O_DIRECT 040000 /* Direct disk access. */ -# define O_DIRECTORY 0200000 /* Must be a directory. */ -# define O_NOFOLLOW 0400000 /* Do not follow links. */ +# define O_DIRECT 040000 /* Direct disk access. */ +# define O_DIRECTORY 0200000 /* Must be a directory. */ +# define O_NOFOLLOW 0400000 /* Do not follow links. */ # define O_NOATIME 01000000 /* Do not set atime. */ #endif /* For now Linux has synchronisity options for data and read operations. We define the symbols here but let them do the same as O_SYNC since - this is a superset. */ + this is a superset. */ #if defined __USE_POSIX199309 || defined __USE_UNIX98 # define O_DSYNC O_SYNC /* Synchronize data. */ -# define O_RSYNC O_SYNC /* Synchronize read operations. */ +# define O_RSYNC O_SYNC /* Synchronize read operations. */ #endif #ifdef __USE_LARGEFILE64 @@ -70,15 +70,15 @@ #ifndef __USE_FILE_OFFSET64 # define F_GETLK 5 /* Get record locking info. */ # define F_SETLK 6 /* Set record locking info (non-blocking). */ -# define F_SETLKW 7 /* Set record locking info (blocking). */ +# define F_SETLKW 7 /* Set record locking info (blocking). */ #else -# define F_GETLK F_GETLK64 /* Get record locking info. */ +# define F_GETLK F_GETLK64 /* Get record locking info. */ # define F_SETLK F_SETLK64 /* Set record locking info (non-blocking).*/ # define F_SETLKW F_SETLKW64 /* Set record locking info (blocking). */ #endif #define F_GETLK64 12 /* Get record locking info. */ #define F_SETLK64 13 /* Set record locking info (non-blocking). */ -#define F_SETLKW64 14 /* Set record locking info (blocking). */ +#define F_SETLKW64 14 /* Set record locking info (blocking). */ #if defined __USE_BSD || defined __USE_UNIX98 # define F_SETOWN 8 /* Get owner of socket (receiver of SIGIO). */ @@ -90,20 +90,26 @@ # define F_GETSIG 11 /* Get number of signal to be sent. */ #endif +#ifdef __USE_GNU +# define F_SETLEASE 1024 /* Set a lease. */ +# define F_GETLEASE 1025 /* Enquire what lease is active. */ +# define F_NOTIFY 1026 /* Request notfications on a directory. */ +#endif + /* For F_[GET|SET]FL. */ #define FD_CLOEXEC 1 /* actually anything with low bit set goes */ /* For posix fcntl() and `l_type' field of a `struct flock' for lockf(). */ #define F_RDLCK 0 /* Read lock. */ -#define F_WRLCK 1 /* Write lock. */ -#define F_UNLCK 2 /* Remove lock. */ +#define F_WRLCK 1 /* Write lock. */ +#define F_UNLCK 2 /* Remove lock. */ /* For old implementation of bsd flock(). */ #define F_EXLCK 4 /* or 3 */ #define F_SHLCK 8 /* or 4 */ #ifdef __USE_BSD -/* Operations for bsd flock(), also used by the kernel implementation. */ +/* Operations for bsd flock(), also used by the kernel implementation. */ # define LOCK_SH 1 /* shared lock */ # define LOCK_EX 2 /* exclusive lock */ # define LOCK_NB 4 /* or'd with one of the above to prevent @@ -111,9 +117,27 @@ # define LOCK_UN 8 /* remove lock */ #endif +#ifdef __USE_GNU +# define LOCK_MAND 32 /* This is a mandatory flock: */ +# define LOCK_READ 64 /* ... which allows concurrent read operations. */ +# define LOCK_WRITE 128 /* ... which allows concurrent write operations. */ +# define LOCK_RW 192 /* ... Which allows concurrent read & write operations. */ +#endif + +#ifdef __USE_GNU +/* Types of directory notifications that may be requested with F_NOTIFY. */ +# define DN_ACCESS 0x00000001 /* File accessed. */ +# define DN_MODIFY 0x00000002 /* File modified. */ +# define DN_CREATE 0x00000004 /* File created. */ +# define DN_DELETE 0x00000008 /* File removed. */ +# define DN_RENAME 0x00000010 /* File renamed. */ +# define DN_ATTRIB 0x00000020 /* File changed attibutes. */ +# define DN_MULTISHOT 0x80000000 /* Don't remove notifier. */ +#endif + struct flock { - short int l_type; /* Type of lock: F_RDLCK, F_WRLCK, or F_UNLCK. */ + short int l_type; /* Type of lock: F_RDLCK, F_WRLCK, or F_UNLCK. */ short int l_whence; /* Where `l_start' is relative to (like `lseek'). */ #ifndef __USE_FILE_OFFSET64 __off_t l_start; /* Offset where the lock begins. */ @@ -128,7 +152,7 @@ struct flock #ifdef __USE_LARGEFILE64 struct flock64 { - short int l_type; /* Type of lock: F_RDLCK, F_WRLCK, or F_UNLCK. */ + short int l_type; /* Type of lock: F_RDLCK, F_WRLCK, or F_UNLCK. */ short int l_whence; /* Where `l_start' is relative to (like `lseek'). */ __off64_t l_start; /* Offset where the lock begins. */ __off64_t l_len; /* Size of the locked area; zero means until EOF. */ @@ -150,7 +174,7 @@ struct flock64 #ifdef __USE_XOPEN2K # define POSIX_FADV_NORMAL 0 /* No further special treatment. */ # define POSIX_FADV_RANDOM 1 /* Expect random page references. */ -# define POSIX_FADV_SEQUENTIAL 2 /* Expect sequential page references. */ +# define POSIX_FADV_SEQUENTIAL 2 /* Expect sequential page references. */ # define POSIX_FADV_WILLNEED 3 /* Will need these pages. */ # define POSIX_FADV_DONTNEED 4 /* Don't need these pages. */ # define POSIX_FADV_NOREUSE 5 /* Data will be accessed once. */ diff --git a/sysdeps/unix/sysv/linux/sh/chown.c b/sysdeps/unix/sysv/linux/sh/chown.c index 1961622564..e7193dc23b 100644 --- a/sysdeps/unix/sysv/linux/sh/chown.c +++ b/sysdeps/unix/sysv/linux/sh/chown.c @@ -1 +1,69 @@ -#include <sysdeps/unix/sysv/linux/m68k/chown.c> +/* Copyright (C) 1998,2000,2002,2003,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 + 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 <errno.h> +#include <unistd.h> + +#include <sysdep.h> +#include <sys/syscall.h> +#include <bp-checks.h> + +#include <linux/posix_types.h> +#include <kernel-features.h> + +#ifdef __NR_chown32 +# if __ASSUME_32BITUIDS == 0 +/* This variable is shared with all files that need to check for 32bit + uids. */ +extern int __libc_missing_32bit_uids; +# endif +#endif /* __NR_chown32 */ + +int +__chown (const char *file, uid_t owner, gid_t group) +{ +#if __ASSUME_32BITUIDS > 0 + return INLINE_SYSCALL (chown32, 3, CHECK_STRING (file), owner, group); +#else +# ifdef __NR_chown32 + if (__libc_missing_32bit_uids <= 0) + { + int result; + int saved_errno = errno; + + result = INLINE_SYSCALL (chown32, 3, CHECK_STRING (file), owner, group); + if (result == 0 || errno != ENOSYS) + return result; + + __set_errno (saved_errno); + __libc_missing_32bit_uids = 1; + } +# endif /* __NR_chown32 */ + + if (((owner + 1) > (gid_t) ((__kernel_uid_t) -1U)) + || ((group + 1) > (gid_t) ((__kernel_gid_t) -1U))) + { + __set_errno (EINVAL); + return -1; + } + + return INLINE_SYSCALL (chown, 3, CHECK_STRING (file), owner, group); +#endif +} +libc_hidden_def (__chown) +weak_alias (__chown, chown) diff --git a/sysdeps/unix/sysv/linux/sh/fchownat.c b/sysdeps/unix/sysv/linux/sh/fchownat.c index 7acf7918ee..6cc093222d 100644 --- a/sysdeps/unix/sysv/linux/sh/fchownat.c +++ b/sysdeps/unix/sysv/linux/sh/fchownat.c @@ -1 +1,122 @@ -#include <sysdeps/unix/sysv/linux/m68k/fchownat.c> +/* Copyright (C) 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 + 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 <errno.h> +#include <fcntl.h> +#include <stdio.h> +#include <unistd.h> +#include <string.h> + +#include <sysdep.h> +#include <sys/syscall.h> +#include <bp-checks.h> + +#include <linux/posix_types.h> +#include <kernel-features.h> + +#ifdef __NR_chown32 +# if __ASSUME_32BITUIDS == 0 +/* This variable is shared with all files that need to check for 32bit + uids. */ +extern int __libc_missing_32bit_uids; +# endif +#endif /* __NR_chown32 */ + +int +fchownat (int fd, const char *file, uid_t owner, gid_t group, int flag) +{ + if (flag & ~AT_SYMLINK_NOFOLLOW) + { + __set_errno (EINVAL); + return -1; + } + + char *buf = NULL; + + if (fd != AT_FDCWD && file[0] != '/') + { + size_t filelen = strlen (file); + static const char procfd[] = "/proc/self/fd/%d/%s"; + /* Buffer for the path name we are going to use. It consists of + - the string /proc/self/fd/ + - the file descriptor number + - the file name provided. + The final NUL is included in the sizeof. A bit of overhead + due to the format elements compensates for possible negative + numbers. */ + size_t buflen = sizeof (procfd) + sizeof (int) * 3 + filelen; + buf = alloca (buflen); + + __snprintf (buf, buflen, procfd, fd, file); + file = buf; + } + + int result; + INTERNAL_SYSCALL_DECL (err); + +#if __ASSUME_32BITUIDS > 0 + if (flag & AT_SYMLINK_NOFOLLOW) + result = INTERNAL_SYSCALL (lchown32, err, 3, CHECK_STRING (file), owner, + group); + else + result = INTERNAL_SYSCALL (chown32, err, 3, CHECK_STRING (file), owner, + group); +#else +# ifdef __NR_chown32 + if (__libc_missing_32bit_uids <= 0) + { + if (flag & AT_SYMLINK_NOFOLLOW) + result = INTERNAL_SYSCALL (lchown32, err, 3, CHECK_STRING (file), + owner, group); + else + result = INTERNAL_SYSCALL (chown32, err, 3, CHECK_STRING (file), owner, + group); + + if (__builtin_expect (!INTERNAL_SYSCALL_ERROR_P (result, err), 1)) + return result; + if (INTERNAL_SYSCALL_ERRNO (result, err) != ENOSYS) + goto fail; + + __libc_missing_32bit_uids = 1; + } +# endif /* __NR_chown32 */ + + if (((owner + 1) > (gid_t) ((__kernel_uid_t) -1U)) + || ((group + 1) > (gid_t) ((__kernel_gid_t) -1U))) + { + __set_errno (EINVAL); + return -1; + } + + if (flag & AT_SYMLINK_NOFOLLOW) + result = INTERNAL_SYSCALL (lchown, err, 3, CHECK_STRING (file), owner, + group); + else + result = INTERNAL_SYSCALL (chown, err, 3, CHECK_STRING (file), owner, + group); +#endif + + if (__builtin_expect (INTERNAL_SYSCALL_ERROR_P (result, err), 0)) + { + fail: + __atfct_seterrno (INTERNAL_SYSCALL_ERRNO (result, err), fd, buf); + result = -1; + } + + return result; +} diff --git a/sysdeps/unix/sysv/linux/sh/pread.c b/sysdeps/unix/sysv/linux/sh/pread.c index 9ded53ebaa..0186e40c9c 100644 --- a/sysdeps/unix/sysv/linux/sh/pread.c +++ b/sysdeps/unix/sysv/linux/sh/pread.c @@ -1,3 +1,93 @@ -#define NO_SGIDEFS_H -#define _MIPS_SIM -1 -#include <sysdeps/unix/sysv/linux/mips/pread.c> +/* Copyright (C) 1997, 1998, 2000, 2002, 2003, 2004, 2006 + Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 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 + 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 <assert.h> +#include <errno.h> +#include <unistd.h> +#include <endian.h> + +#include <sysdep-cancel.h> +#include <sys/syscall.h> +#include <bp-checks.h> + +#include <kernel-features.h> + +#ifdef __NR_pread64 /* Newer kernels renamed but it's the same. */ +# ifdef __NR_pread +# error "__NR_pread and __NR_pread64 both defined???" +# endif +# define __NR_pread __NR_pread64 +#endif + +#if defined __NR_pread || __ASSUME_PREAD_SYSCALL > 0 + +# if __ASSUME_PREAD_SYSCALL == 0 +static ssize_t __emulate_pread (int fd, void *buf, size_t count, + off_t offset) internal_function; +# endif + +ssize_t +__libc_pread (fd, buf, count, offset) + int fd; + void *buf; + size_t count; + off_t offset; +{ + ssize_t result; + + if (SINGLE_THREAD_P) + { + /* First try the syscall. */ + result = INLINE_SYSCALL (pread, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR (offset >> 31, offset)); +# if __ASSUME_PREAD_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pread (fd, buf, count, offset); +# endif + return result; + } + + int oldtype = LIBC_CANCEL_ASYNC (); + + /* First try the syscall. */ + result = INLINE_SYSCALL (pread, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR (offset >> 31, offset)); +# if __ASSUME_PREAD_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pread (fd, buf, count, offset); +# endif + + LIBC_CANCEL_RESET (oldtype); + + return result; +} + +strong_alias (__libc_pread, __pread) +weak_alias (__libc_pread, pread) + +# define __libc_pread(fd, buf, count, offset) \ + static internal_function __emulate_pread (fd, buf, count, offset) +#endif + +#if __ASSUME_PREAD_SYSCALL == 0 +# include <sysdeps/posix/pread.c> +#endif diff --git a/sysdeps/unix/sysv/linux/sh/pread64.c b/sysdeps/unix/sysv/linux/sh/pread64.c index 5b22a395ec..f23d619090 100644 --- a/sysdeps/unix/sysv/linux/sh/pread64.c +++ b/sysdeps/unix/sysv/linux/sh/pread64.c @@ -1,3 +1,94 @@ -#define NO_SGIDEFS_H -#define _MIPS_SIM -1 -#include <sysdeps/unix/sysv/linux/mips/pread64.c> +/* Copyright (C) 1997, 1998, 2000, 2002, 2003, 2004, 2006 + Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 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 + 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 <errno.h> +#include <unistd.h> +#include <endian.h> + +#include <sysdep-cancel.h> +#include <sys/syscall.h> +#include <bp-checks.h> + +#include <kernel-features.h> + +#ifdef __NR_pread64 /* Newer kernels renamed but it's the same. */ +# ifdef __NR_pread +# error "__NR_pread and __NR_pread64 both defined???" +# endif +# define __NR_pread __NR_pread64 +#endif + +#if defined __NR_pread || __ASSUME_PREAD_SYSCALL > 0 + +# if __ASSUME_PREAD_SYSCALL == 0 +static ssize_t __emulate_pread64 (int fd, void *buf, size_t count, + off64_t offset) internal_function; +# endif + +ssize_t +__libc_pread64 (fd, buf, count, offset) + int fd; + void *buf; + size_t count; + off64_t offset; +{ + ssize_t result; + + if (SINGLE_THREAD_P) + { + /* First try the syscall. */ + result = INLINE_SYSCALL (pread, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR ((off_t) (offset >> 32), + (off_t) (offset & 0xffffffff))); +# if __ASSUME_PREAD_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pread64 (fd, buf, count, offset); +# endif + return result; + } + + int oldtype = LIBC_CANCEL_ASYNC (); + + /* First try the syscall. */ + result = INLINE_SYSCALL (pread, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR ((off_t) (offset >> 32), + (off_t) (offset & 0xffffffff))); +# if __ASSUME_PREAD_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pread64 (fd, buf, count, offset); +# endif + + LIBC_CANCEL_RESET (oldtype); + + return result; +} + +weak_alias (__libc_pread64, __pread64) +weak_alias (__libc_pread64, pread64) + +# define __libc_pread64(fd, buf, count, offset) \ + static internal_function __emulate_pread64 (fd, buf, count, offset) +#endif + +#if __ASSUME_PREAD_SYSCALL == 0 +# include <sysdeps/posix/pread64.c> +#endif diff --git a/sysdeps/unix/sysv/linux/sh/pwrite.c b/sysdeps/unix/sysv/linux/sh/pwrite.c index b75a6a968e..f0e2bc7e0f 100644 --- a/sysdeps/unix/sysv/linux/sh/pwrite.c +++ b/sysdeps/unix/sysv/linux/sh/pwrite.c @@ -1,3 +1,93 @@ -#define NO_SGIDEFS_H -#define _MIPS_SIM -1 -#include <sysdeps/unix/sysv/linux/mips/pwrite.c> +/* Copyright (C) 1997, 1998, 2000, 2002, 2003, 2004, 2006 + Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 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 + 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 <assert.h> +#include <errno.h> +#include <unistd.h> +#include <endian.h> + +#include <sysdep-cancel.h> +#include <sys/syscall.h> +#include <bp-checks.h> + +#include <kernel-features.h> + +#ifdef __NR_pwrite64 /* Newer kernels renamed but it's the same. */ +# ifdef __NR_pwrite +# error "__NR_pwrite and __NR_pwrite64 both defined???" +# endif +# define __NR_pwrite __NR_pwrite64 +#endif + +#if defined __NR_pwrite || __ASSUME_PWRITE_SYSCALL > 0 + +# if __ASSUME_PWRITE_SYSCALL == 0 +static ssize_t __emulate_pwrite (int fd, const void *buf, size_t count, + off_t offset) internal_function; +# endif + +ssize_t +__libc_pwrite (fd, buf, count, offset) + int fd; + const void *buf; + size_t count; + off_t offset; +{ + ssize_t result; + + if (SINGLE_THREAD_P) + { + /* First try the syscall. */ + result = INLINE_SYSCALL (pwrite, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR (offset >> 31, offset)); +# if __ASSUME_PWRITE_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pwrite (fd, buf, count, offset); +# endif + return result; + } + + int oldtype = LIBC_CANCEL_ASYNC (); + + /* First try the syscall. */ + result = INLINE_SYSCALL (pwrite, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR (offset >> 31, offset)); +# if __ASSUME_PWRITE_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pwrite (fd, buf, count, offset); +# endif + + LIBC_CANCEL_RESET (oldtype); + + return result; +} + +strong_alias (__libc_pwrite, __pwrite) +weak_alias (__libc_pwrite, pwrite) + +# define __libc_pwrite(fd, buf, count, offset) \ + static internal_function __emulate_pwrite (fd, buf, count, offset) +#endif + +#if __ASSUME_PWRITE_SYSCALL == 0 +# include <sysdeps/posix/pwrite.c> +#endif diff --git a/sysdeps/unix/sysv/linux/sh/pwrite64.c b/sysdeps/unix/sysv/linux/sh/pwrite64.c index ae29280f85..eb1e507287 100644 --- a/sysdeps/unix/sysv/linux/sh/pwrite64.c +++ b/sysdeps/unix/sysv/linux/sh/pwrite64.c @@ -1,3 +1,96 @@ -#define NO_SGIDEFS_H -#define _MIPS_SIM -1 -#include <sysdeps/unix/sysv/linux/mips/pwrite64.c> +/* Copyright (C) 1997, 1998, 2000, 2002, 2003, 2004, 2006 + Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ralf Baechle <ralf@gnu.org>, 1998. + + 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 <errno.h> +#include <unistd.h> +#include <endian.h> + +#include <sysdep-cancel.h> +#include <sys/syscall.h> +#include <bp-checks.h> + +#include <kernel-features.h> + +#ifdef __NR_pwrite64 /* Newer kernels renamed but it's the same. */ +# ifdef __NR_pwrite +# error "__NR_pwrite and __NR_pwrite64 both defined???" +# endif +# define __NR_pwrite __NR_pwrite64 +#endif + +#if defined __NR_pwrite || __ASSUME_PWRITE_SYSCALL > 0 + +# if __ASSUME_PWRITE_SYSCALL == 0 +static ssize_t __emulate_pwrite64 (int fd, const void *buf, size_t count, + off64_t offset) internal_function; +# endif + +ssize_t +__libc_pwrite64 (fd, buf, count, offset) + int fd; + const void *buf; + size_t count; + off64_t offset; +{ + ssize_t result; + + if (SINGLE_THREAD_P) + { + /* First try the syscall. */ + result = INLINE_SYSCALL (pwrite, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR ((off_t) (offset >> 32), + (off_t) (offset & 0xffffffff))); +# if __ASSUME_PWRITE_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pwrite64 (fd, buf, count, offset); +# endif + + return result; + } + + int oldtype = LIBC_CANCEL_ASYNC (); + + /* First try the syscall. */ + result = INLINE_SYSCALL (pwrite, 6, fd, CHECK_N (buf, count), count, 0, + __LONG_LONG_PAIR ((off_t) (offset >> 32), + (off_t) (offset & 0xffffffff))); +# if __ASSUME_PWRITE_SYSCALL == 0 + if (result == -1 && errno == ENOSYS) + /* No system call available. Use the emulation. */ + result = __emulate_pwrite64 (fd, buf, count, offset); +# endif + + LIBC_CANCEL_RESET (oldtype); + + return result; +} + +weak_alias (__libc_pwrite64, __pwrite64) +libc_hidden_weak (__pwrite64) +weak_alias (__libc_pwrite64, pwrite64) + +# define __libc_pwrite64(fd, buf, count, offset) \ + static internal_function __emulate_pwrite64 (fd, buf, count, offset) +#endif + +#if __ASSUME_PWRITE_SYSCALL == 0 +# include <sysdeps/posix/pwrite64.c> +#endif |