Here's an assortment of build and run-time fixes for various architectures that we've applied in Debian. Ben. Aurelien Jarno (1): ppc64: fix struct stat Ben Hutchings (2): MIPS: Update archfcntl.h syscalls: Override detection of direct socket syscalls on i386, m68k, s390 Helge Deller (1): Add pread and pwrite 32bit syscall wrappers for parisc Mauricio Faria de Oliveira (1): ppc64: ELFv2: Load TOC value in system call stub usr/include/arch/i386/klibc/archconfig.h | 3 +++ usr/include/arch/m68k/klibc/archconfig.h | 3 +++ usr/include/arch/mips/klibc/archfcntl.h | 22 +++++++++++++++++++++- usr/include/arch/ppc64/klibc/archstat.h | 1 + usr/include/arch/s390/klibc/archconfig.h | 3 +++ usr/include/endian.h | 6 ++++++ usr/klibc/Kbuild | 1 + usr/klibc/SYSCALLS.def | 6 ++++-- usr/klibc/arch/ppc64/sysstub.ph | 3 +++ usr/klibc/pread.c | 29 +++++++++++++++++++++++++++++ usr/klibc/pwrite.c | 29 +++++++++++++++++++++++++++++ 11 files changed, 103 insertions(+), 3 deletions(-) create mode 100644 usr/klibc/pread.c create mode 100644 usr/klibc/pwrite.c -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 811 bytes Desc: Digital signature URL: <http://www.zytor.com/pipermail/klibc/attachments/20160106/34874cb3/attachment.sig>
Ben Hutchings
2016-Jan-06 00:43 UTC
[klibc] [PATCH klibc 1/5] ppc64: ELFv2: Load TOC value in system call stub
From: Mauricio Faria de Oliveira <mauricfo at linux.vnet.ibm.com> This fixes a segmentation fault in the system call's error handling path with dynamically-linked binaries on PowerPC64 little endian. The system call stub wasn't loading up r2 with the appropriate TOC value in its global entry point. The r2 setup code comes from the FUNC_START macro in gcc [1] and an equivalent one can also be found in the LOCALENTRY macro in glibc [2]. On the ELFv2 ABI (see [1]): - The global entry point is expected to load up r2 with the appropriate TOC value for this function. - The local entry point expects r2 to be set up to the current TOC. The problem happened with dynamically-linked binaries because: - the system call is an indirect call (via global entry point) from the binary to the shared library, landing in the syscall stub (which didn't load up r2 with the TOC of the shared library) - its branch to __syscall_error is a direct call (via local entry point) within the shared library, landing in the function (which expects r2 to be set up to that TOC) - when the function attempts to store errno (in an address relative to the TOC), that address incorrectly pointed to a read-only segment -- segmentation fault. The problem didn't happen with statically-linked binaries because the TOC value wasn't different on that case. Thanks and credits to Alan Modra and Ulrich Weigand, for helping with this and pointing out the solution. [1] https://gcc.gnu.org/ml/gcc-patches/2013-11/msg01141.html [2] https://www.sourceware.org/ml/libc-alpha/2013-11/msg00315.html Signed-off-by: Mauricio Faria de Oliveira <mauricfo at linux.vnet.ibm.com> Signed-off-by: Ben Hutchings <ben at decadent.org.uk> --- usr/klibc/arch/ppc64/sysstub.ph | 3 +++ 1 file changed, 3 insertions(+) diff --git a/usr/klibc/arch/ppc64/sysstub.ph b/usr/klibc/arch/ppc64/sysstub.ph index b3f6e38..a0c6d41 100644 --- a/usr/klibc/arch/ppc64/sysstub.ph +++ b/usr/klibc/arch/ppc64/sysstub.ph @@ -18,6 +18,9 @@ sub make_sysstub($$$$$@) { #if _CALL_ELF == 2 .type ${fname},\@function ${fname}: +0: addis 2,12,(.TOC.-0b)\@ha + addi 2,2,(.TOC.-0b)\@l + .localentry ${fname},.-${fname} #else .section ".opd","aw" .balign 8 -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 811 bytes Desc: Digital signature URL: <http://www.zytor.com/pipermail/klibc/attachments/20160106/77cb8a7b/attachment.sig>
Update usr/include/arch/mips/archfcntl.h from kernel headers: - Add definitions of O_PATH, O_TMPFILE - Update value of O_SYNC to include __O_SYNC - Add definitions of F_{SET,GET}OWN_EX, F_GETOWNER_UIDS, F_OFD_{GETLK,SETLK,SETLKW}, F_OWNER_{TID,PID,PGRP} Signed-off-by: Ben Hutchings <ben at decadent.org.uk> --- usr/include/arch/mips/klibc/archfcntl.h | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) diff --git a/usr/include/arch/mips/klibc/archfcntl.h b/usr/include/arch/mips/klibc/archfcntl.h index 2e57116..586afb4 100644 --- a/usr/include/arch/mips/klibc/archfcntl.h +++ b/usr/include/arch/mips/klibc/archfcntl.h @@ -19,7 +19,6 @@ #define O_WRONLY 0x0001 #define O_RDWR 0x0002 #define O_APPEND 0x0008 -#define O_SYNC 0x0010 #define O_NONBLOCK 0x0080 #define O_CREAT 0x0100 #define O_TRUNC 0x0200 @@ -27,11 +26,14 @@ #define O_NOCTTY 0x0800 #define FASYNC 0x1000 #define O_LARGEFILE 0x2000 +#define O_SYNC 0x4010 #define O_DIRECT 0x8000 #define O_DIRECTORY 0x10000 #define O_NOFOLLOW 0x20000 #define O_NOATIME 0x40000 #define O_CLOEXEC 0x80000 +#define O_PATH 0x200000 +#define O_TMPFILE 0x410000 #define O_NDELAY O_NONBLOCK @@ -53,6 +55,24 @@ #define F_SETLK64 34 #define F_SETLKW64 35 +#define F_SETOWN_EX 15 +#define F_GETOWN_EX 16 + +#define F_GETOWNER_UIDS 17 + +#define F_OFD_GETLK 36 +#define F_OFD_SETLK 37 +#define F_OFD_SETLKW 38 + +#define F_OWNER_TID 0 +#define F_OWNER_PID 1 +#define F_OWNER_PGRP 2 + +struct f_owner_ex { + int type; + pid_t pid; +}; + #define FD_CLOEXEC 1 #define F_RDLCK 0 -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 811 bytes Desc: Digital signature URL: <http://www.zytor.com/pipermail/klibc/attachments/20160106/ca55a3a2/attachment.sig>
Ben Hutchings
2016-Jan-06 00:43 UTC
[klibc] [PATCH klibc 3/5] Add pread and pwrite 32bit syscall wrappers for parisc
From: Helge Deller <deller at gmx.de> On the hppa arch (32bit userspace and 32 or 64bit kernel), the fstype program fails to detect the filesystem. The reason for this failure is, that fstype calls the pread() syscall, which has on some architectures with 32bit userspace a different calling syntax. I noticed this bug on hppa, but I assume s390 (32bit) and others might run into similiar issues. Signed-off-by: Helge Deller <deller at gmx.de> Signed-off-by: Ben Hutchings <ben at decadent.org.uk> --- usr/include/endian.h | 6 ++++++ usr/klibc/Kbuild | 1 + usr/klibc/SYSCALLS.def | 6 ++++-- usr/klibc/pread.c | 29 +++++++++++++++++++++++++++++ usr/klibc/pwrite.c | 29 +++++++++++++++++++++++++++++ 5 files changed, 69 insertions(+), 2 deletions(-) create mode 100644 usr/klibc/pread.c create mode 100644 usr/klibc/pwrite.c diff --git a/usr/include/endian.h b/usr/include/endian.h index a6cd6d9..61cda3a 100644 --- a/usr/include/endian.h +++ b/usr/include/endian.h @@ -12,4 +12,10 @@ #define PDP_ENDIAN __PDP_ENDIAN #define BYTE_ORDER __BYTE_ORDER +#if __BYTE_ORDER == __LITTLE_ENDIAN +# define __LONG_LONG_PAIR(HI, LO) LO, HI +#elif __BYTE_ORDER == __BIG_ENDIAN +# define __LONG_LONG_PAIR(HI, LO) HI, LO +#endif + #endif /* _ENDIAN_H */ diff --git a/usr/klibc/Kbuild b/usr/klibc/Kbuild index 40d43c7..d3e2b9f 100644 --- a/usr/klibc/Kbuild +++ b/usr/klibc/Kbuild @@ -35,6 +35,7 @@ klib-y += vsnprintf.o snprintf.o vsprintf.o sprintf.o \ siglongjmp.o \ sigaction.o sigpending.o sigprocmask.o sigsuspend.o \ pselect.o ppoll.o \ + pread.o pwrite.o \ brk.o sbrk.o malloc.o realloc.o zalloc.o calloc.o \ mmap.o shm_open.o shm_unlink.o \ memcpy.o memcmp.o memset.o memccpy.o memmem.o memswap.o \ diff --git a/usr/klibc/SYSCALLS.def b/usr/klibc/SYSCALLS.def index 41cfa17..c56e8f9 100644 --- a/usr/klibc/SYSCALLS.def +++ b/usr/klibc/SYSCALLS.def @@ -189,8 +189,10 @@ int fdatasync,fsync::fdatasync(int); int readv(int, const struct iovec *, int); int writev(int, const struct iovec *, int); int ftruncate64,ftruncate::ftruncate(int, off_t); -ssize_t pread64,pread::pread(int, void *, size_t, off_t); -ssize_t pwrite64,pwrite::pwrite(int, void *, size_t, off_t); +<parisc> ssize_t pread64,pread::__pread(int, void *, size_t, off_t); +<parisc> ssize_t pwrite64,pwrite::__pwrite(int, void *, size_t, off_t); +<!parisc> ssize_t pread64,pread::pread(int, void *, size_t, off_t); +<!parisc> ssize_t pwrite64,pwrite::pwrite(int, void *, size_t, off_t); int sync_file_range,fdatasync,fsync::sync_file_range(int, off_t, off_t, unsigned int); <?> int splice(int, off_t *, int, off_t *, size_t, unsigned int); <?> int tee(int, int, size_t, unsigned int); diff --git a/usr/klibc/pread.c b/usr/klibc/pread.c new file mode 100644 index 0000000..0d8c3b1 --- /dev/null +++ b/usr/klibc/pread.c @@ -0,0 +1,29 @@ +/* + * pread.c + * + * Some architectures need to wrap the system call + */ + +#include <endian.h> +#include <sys/syscall.h> + +#if defined(__hppa__) + +#if _BITSIZE == 32 +extern size_t __pread(int, void *, size_t, unsigned int, unsigned int); +#else +extern size_t __pread(int, void *, size_t, off_t); +#endif + +size_t pread(int fd, void *buf, size_t count, off_t offset) +{ +#if _BITSIZE == 32 + unsigned int hi = offset >> 32; + unsigned int lo = (unsigned int) offset; + return __pread(fd, buf, count, __LONG_LONG_PAIR(hi, lo)); +#else + return __pread(fd, buf, count, offset); +#endif +} + +#endif diff --git a/usr/klibc/pwrite.c b/usr/klibc/pwrite.c new file mode 100644 index 0000000..691d0e4 --- /dev/null +++ b/usr/klibc/pwrite.c @@ -0,0 +1,29 @@ +/* + * pwrite.c + * + * Some architectures need to wrap the system call + */ + +#include <endian.h> +#include <sys/syscall.h> + +#if defined(__hppa__) + +#if _BITSIZE == 32 +extern ssize_t __pwrite(int, const void *, size_t, unsigned int, unsigned int); +#else +extern ssize_t __pwrite(int, const void *, size_t, off_t); +#endif + +size_t pwrite(int fd, void *buf, size_t count, off_t offset) +{ +#if _BITSIZE == 32 + unsigned int hi = offset >> 32; + unsigned int lo = (unsigned int) offset; + return __pwrite(fd, buf, count, __LONG_LONG_PAIR(hi, lo)); +#else + return __pwrite(fd, buf, count, offset); +#endif +} + +#endif -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 811 bytes Desc: Digital signature URL: <http://www.zytor.com/pipermail/klibc/attachments/20160106/d938a128/attachment.sig>
From: Aurelien Jarno <aurelien at aurel32.net> On ppc64 the struct stat defined by klibc matches the kernel one. However it contains implicit padding before the st_rdev field due to the 64-bit alignement. For internal reasons, klibc defines st_rdev as a pair of 32-bit values (using the __stdev64 macro). They only need to be 32-bit aligned and as a consequence st->st_rdev is incorrectly defined. The solution is to add an explicit padding in the structure. This fixes the resume binary on ppc64 BE and LE, and probably other things. Signed-off-by: Aurelien Jarno <aurelien at aurel32.net> Signed-off-by: Ben Hutchings <ben at decadent.org.uk> --- usr/include/arch/ppc64/klibc/archstat.h | 1 + 1 file changed, 1 insertion(+) diff --git a/usr/include/arch/ppc64/klibc/archstat.h b/usr/include/arch/ppc64/klibc/archstat.h index 918d810..0bbbff3 100644 --- a/usr/include/arch/ppc64/klibc/archstat.h +++ b/usr/include/arch/ppc64/klibc/archstat.h @@ -12,6 +12,7 @@ struct stat { mode_t st_mode; uid_t st_uid; gid_t st_gid; + unsigned int __pad1; __stdev64 (st_rdev); off_t st_size; unsigned long st_blksize; -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 811 bytes Desc: Digital signature URL: <http://www.zytor.com/pipermail/klibc/attachments/20160106/9004f9c3/attachment.sig>
Ben Hutchings
2016-Jan-06 00:46 UTC
[klibc] [PATCH klibc 5/5] syscalls: Override detection of direct socket syscalls on i386, m68k, s390
The direct socket syscalls are now implemented on i386, m68k and s390, making socketcall() obsolete. We avoid using them immediately since this will break compatibility with Linux < 4.3. Signed-off-by: Ben Hutchings <ben at decadent.org.uk> --- Some sort of fix is needed here as otherwise we'll build two copies of the socket system call wrappers. In Debian we do need to retain compatibility back to 3.16 for the time being. Ben. usr/include/arch/i386/klibc/archconfig.h | 3 +++ usr/include/arch/m68k/klibc/archconfig.h | 3 +++ usr/include/arch/s390/klibc/archconfig.h | 3 +++ 3 files changed, 9 insertions(+) diff --git a/usr/include/arch/i386/klibc/archconfig.h b/usr/include/arch/i386/klibc/archconfig.h index f070f5b..6951f96 100644 --- a/usr/include/arch/i386/klibc/archconfig.h +++ b/usr/include/arch/i386/klibc/archconfig.h @@ -15,4 +15,7 @@ /* We have klibc/archinit.h and __libc_archinit() */ #define _KLIBC_HAS_ARCHINIT 1 +/* Use sys_socketcall unconditionally */ +#define _KLIBC_SYS_SOCKETCALL 1 + #endif /* _KLIBC_ARCHCONFIG_H */ diff --git a/usr/include/arch/m68k/klibc/archconfig.h b/usr/include/arch/m68k/klibc/archconfig.h index 10ef62e..1d5c034 100644 --- a/usr/include/arch/m68k/klibc/archconfig.h +++ b/usr/include/arch/m68k/klibc/archconfig.h @@ -12,4 +12,7 @@ /* On m68k, sys_mmap2 uses the current page size as the shift factor */ #define _KLIBC_MMAP2_SHIFT __getpageshift() +/* Use sys_socketcall unconditionally */ +#define _KLIBC_SYS_SOCKETCALL 1 + #endif /* _KLIBC_ARCHCONFIG_H */ diff --git a/usr/include/arch/s390/klibc/archconfig.h b/usr/include/arch/s390/klibc/archconfig.h index d7a71a4..18d30da 100644 --- a/usr/include/arch/s390/klibc/archconfig.h +++ b/usr/include/arch/s390/klibc/archconfig.h @@ -12,4 +12,7 @@ /* Both s390 and s390x use the "32-bit" version of this structure */ #define _KLIBC_STATFS_F_TYPE_64 0 +/* Use sys_socketcall unconditionally */ +#define _KLIBC_SYS_SOCKETCALL 1 + #endif /* _KLIBC_ARCHCONFIG_H */ -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 811 bytes Desc: Digital signature URL: <http://www.zytor.com/pipermail/klibc/attachments/20160106/af03a9cf/attachment.sig>