From ee5a5ba6725ee949483f043cd0cf2a1579b6b509 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 10:00:28 -0800 Subject: [PATCH 01/11] Define week, first_weekday, and first_workday for hsb_DE locale. --- localedata/ChangeLog | 4 ++++ localedata/locales/hsb_DE | 24 ++++++++++++++---------- 2 files changed, 18 insertions(+), 10 deletions(-) diff --git a/localedata/ChangeLog b/localedata/ChangeLog index 077182b4c2..88284268a9 100644 --- a/localedata/ChangeLog +++ b/localedata/ChangeLog @@ -1,3 +1,7 @@ +2009-11-24 Ulrich Drepper + + * locales/hsb_DE: Define week, first_weekday, and first_workday. + 2009-11-23 Ulrich Drepper * locales/en_DK: Define week, first_weekday, and first_workday. diff --git a/localedata/locales/hsb_DE b/localedata/locales/hsb_DE index 50355af35a..0929897c8a 100644 --- a/localedata/locales/hsb_DE +++ b/localedata/locales/hsb_DE @@ -197,7 +197,7 @@ collating-symbol % letter;accent;case;specials order_start forward;backward/ - ;forward;position + ;forward;position % or letters first: @@ -2136,16 +2136,16 @@ END LC_NUMERIC LC_TIME abday "";"";/ - "";"";/ - "";"";/ - "" + "";"";/ + "";"";/ + "" day "";/ - "";/ - "";/ - "";/ - "";/ - "";/ - "" + "";/ + "";/ + "";/ + "";/ + "";/ + "" abmon "";"";/ "";"";/ "";"";/ @@ -2172,6 +2172,10 @@ t_fmt_ampm "" date_fmt "/ / " + +week 7;19971130;4 +first_weekday 2 +first_workday 2 END LC_TIME LC_PAPER From 1c3c269b55c84c29ec1e2c70f122c5e33fef4257 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 11:17:06 -0800 Subject: [PATCH 02/11] Fix startup to security-relevant statically linked binaries. Before the change they crash on startup. Perform IREL relocations earlier to prevent this. --- ChangeLog | 7 +++++++ csu/elf-init.c | 21 +++++++++++++++------ csu/libc-start.c | 6 ++++++ 3 files changed, 28 insertions(+), 6 deletions(-) diff --git a/ChangeLog b/ChangeLog index 3d22169a7c..dd68e5bb90 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,10 @@ +2009-11-24 Ulrich Drepper + + * csu/elf-init.c (__libc_csu_irel): New function. Code to perform + irel relocations split out from... + (__libc_csu_init): ...here. + * csu/libc-start.c [!SHARED]: Call __libc_csu_irel early. + 2009-11-23 Andreas Schwab * sysdeps/unix/sysv/linux/x86_64/bits/stat.h: Use struct timespec diff --git a/csu/elf-init.c b/csu/elf-init.c index 1d2df62ca3..1e3d6d6cd8 100644 --- a/csu/elf-init.c +++ b/csu/elf-init.c @@ -72,15 +72,14 @@ extern void _fini (void); /* These functions are passed to __libc_start_main by the startup code. These get statically linked into each program. For dynamically linked programs, this module will come from libc_nonshared.a and differs from - the libc.a module in that it doesn't call the preinit array. */ + the libc.a module in that it doesn't call the preinit array and performs + explicit IREL{,A} relocations. */ -void -__libc_csu_init (int argc, char **argv, char **envp) -{ - /* For dynamically linked executables the preinit array is executed by - the dynamic linker (before initializing any shared object. */ #ifndef LIBC_NONSHARED +void +__libc_csu_irel (void) +{ # ifdef USE_MULTIARCH # ifdef ELF_MACHINE_IRELA { @@ -98,7 +97,17 @@ __libc_csu_init (int argc, char **argv, char **envp) } # endif # endif +} +#endif + +void +__libc_csu_init (int argc, char **argv, char **envp) +{ + /* For dynamically linked executables the preinit array is executed by + the dynamic linker (before initializing any shared object. */ + +#ifndef LIBC_NONSHARED /* For static executables, preinit happens right before init. */ { const size_t size = __preinit_array_end - __preinit_array_start; diff --git a/csu/libc-start.c b/csu/libc-start.c index 80b672f88d..dc7ca55f09 100644 --- a/csu/libc-start.c +++ b/csu/libc-start.c @@ -24,6 +24,9 @@ #include extern void __libc_init_first (int argc, char **argv, char **envp); +#ifndef SHARED +extern void __libc_csu_irel (void); +#endif extern int __libc_multiple_libcs; @@ -134,6 +137,9 @@ LIBC_START_MAIN (int (*main) (int, char **, char ** MAIN_AUXVEC_DECL), } # endif + /* Performe IREL{,A} relocations. */ + __libc_csu_irel (); + /* Initialize the thread library at least a bit since the libgcc functions are using thread functions if these are available and we need to setup errno. */ From 80b3a4ea1c4eb5641aa4c0cac57fe9df65ddba86 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 16:37:29 -0800 Subject: [PATCH 03/11] New NPTL POSIX semaphore test. --- nptl/ChangeLog | 5 +++++ nptl/Makefile | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/nptl/ChangeLog b/nptl/ChangeLog index 2dd5dac2d5..d0e1abcff5 100644 --- a/nptl/ChangeLog +++ b/nptl/ChangeLog @@ -1,3 +1,8 @@ +2009-11-24 Ulrich Drepper + + * tst-sem13.c: New file. + * Makefile (tests): Add tst-sem13. + 2009-11-22 Roland McGrath * sysdeps/unix/sysv/linux/i386/dl-sysdep.h: # include "i686/dl-sysdep.h" diff --git a/nptl/Makefile b/nptl/Makefile index f96ed458e6..a7b53ed15d 100644 --- a/nptl/Makefile +++ b/nptl/Makefile @@ -216,7 +216,7 @@ tests = tst-typesizes \ tst-once1 tst-once2 tst-once3 tst-once4 \ tst-key1 tst-key2 tst-key3 tst-key4 \ tst-sem1 tst-sem2 tst-sem3 tst-sem4 tst-sem5 tst-sem6 tst-sem7 \ - tst-sem8 tst-sem9 tst-sem10 tst-sem11 tst-sem12 \ + tst-sem8 tst-sem9 tst-sem10 tst-sem11 tst-sem12 tst-sem13 \ tst-barrier1 tst-barrier2 tst-barrier3 tst-barrier4 \ tst-align tst-align2 tst-align3 \ tst-basic1 tst-basic2 tst-basic3 tst-basic4 tst-basic5 tst-basic6 \ From 21f2c22320c00c1627dd734794af7353ad7637b2 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 17:50:27 -0800 Subject: [PATCH 04/11] Don't get tty group info multiple times in grantpt. This is a minor optimization. The tty group mustn't change so a successful call to getgrnam will always return the same information. Cache it and reuse it. --- ChangeLog | 3 +++ sysdeps/unix/grantpt.c | 46 +++++++++++++++++++++++------------------- 2 files changed, 28 insertions(+), 21 deletions(-) diff --git a/ChangeLog b/ChangeLog index dd68e5bb90..c78e1905e0 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,8 @@ 2009-11-24 Ulrich Drepper + * sysdeps/unix/grantpt.c (grantpt): Only get tty group information + once. + * csu/elf-init.c (__libc_csu_irel): New function. Code to perform irel relocations split out from... (__libc_csu_init): ...here. diff --git a/sysdeps/unix/grantpt.c b/sysdeps/unix/grantpt.c index 8c299e9147..e140fb2850 100644 --- a/sysdeps/unix/grantpt.c +++ b/sysdeps/unix/grantpt.c @@ -107,14 +107,6 @@ grantpt (int fd) char _buf[512]; #endif char *buf = _buf; - struct stat64 st; - char *grtmpbuf; - struct group grbuf; - size_t grbuflen = __sysconf (_SC_GETGR_R_SIZE_MAX); - struct group *p; - uid_t uid; - gid_t gid; - pid_t pid; if (__builtin_expect (pts_name (fd, &buf, sizeof (_buf)), 0)) { @@ -126,34 +118,46 @@ grantpt (int fd) return -1; /* If the filedescriptor is no TTY, grantpt has to set errno - to EINVAL. */ + to EINVAL. */ if (save_errno == ENOTTY) - __set_errno (EINVAL); + __set_errno (EINVAL); else __set_errno (save_errno); return -1; } + struct stat64 st; if (__xstat64 (_STAT_VER, buf, &st) < 0) goto cleanup; /* Make sure that we own the device. */ - uid = __getuid (); + uid_t uid = __getuid (); if (st.st_uid != uid) { if (__chown (buf, uid, st.st_gid) < 0) goto helper; } - /* Get the group ID of the special `tty' group. */ - if (grbuflen == (size_t) -1L) - /* `sysconf' does not support _SC_GETGR_R_SIZE_MAX. - Try a moderate value. */ - grbuflen = 1024; - grtmpbuf = (char *) __alloca (grbuflen); - __getgrnam_r (TTY_GROUP, &grbuf, grtmpbuf, grbuflen, &p); - gid = p ? p->gr_gid : __getgid (); + static int tty_gid = -1; + if (__builtin_expect (tty_gid == -1, 0)) + { + char *grtmpbuf; + struct group grbuf; + size_t grbuflen = __sysconf (_SC_GETGR_R_SIZE_MAX); + struct group *p; + + /* Get the group ID of the special `tty' group. */ + if (grbuflen == (size_t) -1L) + /* `sysconf' does not support _SC_GETGR_R_SIZE_MAX. + Try a moderate value. */ + grbuflen = 1024; + grtmpbuf = (char *) __alloca (grbuflen); + __getgrnam_r (TTY_GROUP, &grbuf, grtmpbuf, grbuflen, &p); + if (p != NULL) + tty_gid = p->gr_gid; + } + gid_t gid = tty_gid == -1 ? __getgid () : tty_gid; /* Make sure the group of the device is that special group. */ if (st.st_gid != gid) @@ -174,9 +178,9 @@ grantpt (int fd) goto cleanup; /* We have to use the helper program. */ - helper: + helper:; - pid = __fork (); + pid_t pid = __fork (); if (pid == -1) goto cleanup; else if (pid == 0) From fa214705b957d20621cb1190b467aa88bc9b69a3 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 18:22:30 -0800 Subject: [PATCH 05/11] Once again forgot to add new test file. --- nptl/tst-sem13.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 46 insertions(+) create mode 100644 nptl/tst-sem13.c diff --git a/nptl/tst-sem13.c b/nptl/tst-sem13.c new file mode 100644 index 0000000000..8756b2262f --- /dev/null +++ b/nptl/tst-sem13.c @@ -0,0 +1,46 @@ +#include +#include +#include +#include +#include +#include + + +static int +do_test (void) +{ + union + { + sem_t s; + struct new_sem ns; + } u; + + if (sem_init (&u.s, 0, 0) != 0) + { + puts ("sem_init failed"); + return 1; + } + + struct timespec ts = { 0, 1000000001 }; /* Invalid. */ + errno = 0; + if (sem_timedwait (&u.s, &ts) >= 0) + { + puts ("sem_timedwait did not fail"); + return 1; + } + if (errno != EINVAL) + { + puts ("sem_timedwait did not fail with EINVAL"); + return 1; + } + if (u.ns.nwaiters != 0) + { + puts ("nwaiters modified"); + return 1; + } + + return 0; +} + +#define TEST_FUNCTION do_test () +#include "../test-skeleton.c" From 139ee080b6b428240bf49f3e6361f3ac729f891a Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 18:24:14 -0800 Subject: [PATCH 06/11] Prevent unintended file desriptor leak in grantpt. The pt_chown program is completely transparently called. It might not be able to live with the various file descriptors the program has open at the time of the call (e.g., under SELinux). Close all but the needed descriptor and connect stdin, stdout, and stderr with /dev/null. pt_chown shouldn't print anything when called to do real work. --- ChangeLog | 6 +++++ login/programs/pt_chown.c | 5 ++-- sysdeps/unix/grantpt.c | 4 +++ sysdeps/unix/sysv/linux/grantpt.c | 42 +++++++++++++++++++++++++++++++ 4 files changed, 54 insertions(+), 3 deletions(-) create mode 100644 sysdeps/unix/sysv/linux/grantpt.c diff --git a/ChangeLog b/ChangeLog index c78e1905e0..173fe780f8 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,11 @@ 2009-11-24 Ulrich Drepper + * sysdeps/unix/grantpt.c (grantpt): Use CLOSE_ALL_FDS is available + before the exec. + * sysdeps/unix/sysv/linux/grantpt.c: New file. + * login/programs/pt_chown.c (main): Don't print message on errors + when doing real work. + * sysdeps/unix/grantpt.c (grantpt): Only get tty group information once. diff --git a/login/programs/pt_chown.c b/login/programs/pt_chown.c index 7e279a5f3b..4c36f2ceac 100644 --- a/login/programs/pt_chown.c +++ b/login/programs/pt_chown.c @@ -154,8 +154,7 @@ main (int argc, char *argv[]) # define ncap_list (sizeof (cap_list) / sizeof (cap_list[0])) cap_t caps = cap_init (); if (caps == NULL) - error (FAIL_ENOMEM, errno, - _("Failed to initialize drop of capabilities")); + return FAIL_ENOMEM; /* There is no reason why these should not work. */ cap_set_flag (caps, CAP_PERMITTED, ncap_list, cap_list, CAP_SET); @@ -166,7 +165,7 @@ main (int argc, char *argv[]) cap_free (caps); if (__builtin_expect (res != 0, 0)) - error (FAIL_EXEC, errno, _("cap_set_proc failed")); + return FAIL_EXEC; } #endif diff --git a/sysdeps/unix/grantpt.c b/sysdeps/unix/grantpt.c index e140fb2850..2a7a963162 100644 --- a/sysdeps/unix/grantpt.c +++ b/sysdeps/unix/grantpt.c @@ -194,6 +194,10 @@ grantpt (int fd) if (__dup2 (fd, PTY_FILENO) < 0) _exit (FAIL_EBADF); +#ifdef CLOSE_ALL_FDS + CLOSE_ALL_FDS (); +#endif + execle (_PATH_PT_CHOWN, basename (_PATH_PT_CHOWN), NULL, NULL); _exit (FAIL_EXEC); } diff --git a/sysdeps/unix/sysv/linux/grantpt.c b/sysdeps/unix/sysv/linux/grantpt.c new file mode 100644 index 0000000000..6305ed4944 --- /dev/null +++ b/sysdeps/unix/sysv/linux/grantpt.c @@ -0,0 +1,42 @@ +#include +#include +#include +#include +#include +#include +#include +#include + +#include "not-cancel.h" +#include "pty-private.h" + + +/* Close all file descriptors except the one specified. */ +static void +close_all_fds (void) +{ + DIR *dir = opendir ("/proc/self/fd"); + if (dir != NULL) + { + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (isdigit (d->d_name[0])) + { + char *endp; + long int fd = strtol (d->d_name, &endp, 10); + if (*endp == '\0' && fd != PTY_FILENO && fd != dirfd (dir)) + close_not_cancel_no_status (fd); + } + + closedir (dir); + + int nullfd = open_not_cancel_2 (_PATH_DEVNULL, O_RDONLY); + assert (nullfd == STDIN_FILENO); + nullfd = open_not_cancel_2 (_PATH_DEVNULL, O_WRONLY); + assert (nullfd == STDOUT_FILENO); + __dup2 (STDOUT_FILENO, STDERR_FILENO); + } +} +#define CLOSE_ALL_FDS() close_all_fds() + +#include From 0f622686af3ae5a8f03dae886b08c260b38bda16 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 18:47:26 -0800 Subject: [PATCH 07/11] Avoid local PLTs. --- sysdeps/unix/sysv/linux/grantpt.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/sysdeps/unix/sysv/linux/grantpt.c b/sysdeps/unix/sysv/linux/grantpt.c index 6305ed4944..f2fc60f83a 100644 --- a/sysdeps/unix/sysv/linux/grantpt.c +++ b/sysdeps/unix/sysv/linux/grantpt.c @@ -15,11 +15,11 @@ static void close_all_fds (void) { - DIR *dir = opendir ("/proc/self/fd"); + DIR *dir = __opendir ("/proc/self/fd"); if (dir != NULL) { struct dirent64 *d; - while ((d = readdir64 (dir)) != NULL) + while ((d = __readdir64 (dir)) != NULL) if (isdigit (d->d_name[0])) { char *endp; @@ -28,7 +28,7 @@ close_all_fds (void) close_not_cancel_no_status (fd); } - closedir (dir); + __closedir (dir); int nullfd = open_not_cancel_2 (_PATH_DEVNULL, O_RDONLY); assert (nullfd == STDIN_FILENO); From aa9890239a2aef81e64f3f22a31c7e01b6501f69 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 18:50:32 -0800 Subject: [PATCH 08/11] Optimize grantpt. grantpt was performing two consecutive calls to stat with the same file name. Avoid this by creating a special version of the ptsname function which allows to pass the stat result back to the caller. --- ChangeLog | 10 +++++++++ include/stdlib.h | 3 +++ sysdeps/unix/grantpt.c | 11 ++++------ sysdeps/unix/sysv/linux/ptsname.c | 35 ++++++++++++++++++------------- 4 files changed, 38 insertions(+), 21 deletions(-) diff --git a/ChangeLog b/ChangeLog index 173fe780f8..4f74b500f0 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,15 @@ 2009-11-24 Ulrich Drepper + * sysdeps/unix/grantpt.c (pts_name): Take additional parameter, + pass it on to __ptsname_internal. + (grantpt): Pass stat64 pointer to pts_name. Remove stat call here. + * sysdeps/unix/sysv/linux/ptsname.c (__ptsname_internal): New function. + All the code from __ptsname_r but take additional parameter. Use that + instead of pointer to local stat64 variable. + (__ptsname_r): Call __ptsname_internal with pointer to local stat64 + variable. + * include/stdlib.h: Declare __ptsname_internal. + * sysdeps/unix/grantpt.c (grantpt): Use CLOSE_ALL_FDS is available before the exec. * sysdeps/unix/sysv/linux/grantpt.c: New file. diff --git a/include/stdlib.h b/include/stdlib.h index d90e6ff4fe..f540bece9c 100644 --- a/include/stdlib.h +++ b/include/stdlib.h @@ -9,6 +9,7 @@ /* Now define the internal interfaces. */ #ifndef __Need_M_And_C +# include __BEGIN_DECLS @@ -77,6 +78,8 @@ extern int __clearenv (void); extern char *__canonicalize_file_name (__const char *__name); extern char *__realpath (__const char *__name, char *__resolved); extern int __ptsname_r (int __fd, char *__buf, size_t __buflen); +extern int __ptsname_internal (int fd, char *buf, size_t buflen, + struct stat64 *stp); extern int __getpt (void); extern int __posix_openpt (int __oflag); diff --git a/sysdeps/unix/grantpt.c b/sysdeps/unix/grantpt.c index 2a7a963162..260e8273f8 100644 --- a/sysdeps/unix/grantpt.c +++ b/sysdeps/unix/grantpt.c @@ -38,7 +38,7 @@ this buffer, a sufficiently long buffer is allocated using malloc, and returned in PTS. 0 is returned upon success, -1 otherwise. */ static int -pts_name (int fd, char **pts, size_t buf_len) +pts_name (int fd, char **pts, size_t buf_len, struct stat64 *stp) { int rv; char *buf = *pts; @@ -49,7 +49,7 @@ pts_name (int fd, char **pts, size_t buf_len) if (buf_len) { - rv = __ptsname_r (fd, buf, buf_len); + rv = __ptsname_internal (fd, buf, buf_len, stp); if (rv != 0) { if (rv == ENOTTY) @@ -107,8 +107,9 @@ grantpt (int fd) char _buf[512]; #endif char *buf = _buf; + struct stat64 st; - if (__builtin_expect (pts_name (fd, &buf, sizeof (_buf)), 0)) + if (__builtin_expect (pts_name (fd, &buf, sizeof (_buf), &st), 0)) { int save_errno = errno; @@ -127,10 +128,6 @@ grantpt (int fd) return -1; } - struct stat64 st; - if (__xstat64 (_STAT_VER, buf, &st) < 0) - goto cleanup; - /* Make sure that we own the device. */ uid_t uid = __getuid (); if (st.st_uid != uid) diff --git a/sysdeps/unix/sysv/linux/ptsname.c b/sysdeps/unix/sysv/linux/ptsname.c index 9c364b18b4..ba7c791c9f 100644 --- a/sysdeps/unix/sysv/linux/ptsname.c +++ b/sysdeps/unix/sysv/linux/ptsname.c @@ -1,4 +1,4 @@ -/* Copyright (C) 1998, 2000, 2001, 2002 Free Software Foundation, Inc. +/* Copyright (C) 1998, 2000, 2001, 2002, 2009 Free Software Foundation, Inc. This file is part of the GNU C Library. Contributed by Zack Weinberg , 1998. @@ -67,14 +67,10 @@ ptsname (int fd) } -/* Store at most BUFLEN characters of the pathname of the slave pseudo - terminal associated with the master FD is open on in BUF. - Return 0 on success, otherwise an error number. */ int -__ptsname_r (int fd, char *buf, size_t buflen) +__ptsname_internal (int fd, char *buf, size_t buflen, struct stat64 *stp) { int save_errno = errno; - struct stat64 st; unsigned int ptyno; if (buf == NULL) @@ -93,7 +89,7 @@ __ptsname_r (int fd, char *buf, size_t buflen) if (__ioctl (fd, TIOCGPTN, &ptyno) == 0) { /* Buffer we use to print the number in. For a maximum size for - `int' of 8 bytes we never need more than 20 digits. */ + `int' of 8 bytes we never need more than 20 digits. */ char numbuf[21]; const char *devpts = _PATH_DEVPTS; const size_t devptslen = strlen (_PATH_DEVPTS); @@ -121,20 +117,20 @@ __ptsname_r (int fd, char *buf, size_t buflen) return ERANGE; } - if (__fxstat64 (_STAT_VER, fd, &st) < 0) + if (__fxstat64 (_STAT_VER, fd, stp) < 0) return errno; /* Check if FD really is a master pseudo terminal. */ - if (! MASTER_P (st.st_rdev)) + if (! MASTER_P (stp->st_rdev)) { __set_errno (ENOTTY); return ENOTTY; } - ptyno = minor (st.st_rdev); + ptyno = minor (stp->st_rdev); /* This is for the old BSD pseudo terminals. As of Linux - 2.1.115 these are no longer supported. */ - if (major (st.st_rdev) == 4) + 2.1.115 these are no longer supported. */ + if (major (stp->st_rdev) == 4) ptyno -= 128; if (ptyno / 16 >= strlen (__libc_ptyname1)) @@ -149,12 +145,12 @@ __ptsname_r (int fd, char *buf, size_t buflen) p[2] = '\0'; } - if (__xstat64 (_STAT_VER, buf, &st) < 0) + if (__xstat64 (_STAT_VER, buf, stp) < 0) return errno; /* Check if the name we're about to return really corresponds to a slave pseudo terminal. */ - if (! S_ISCHR (st.st_mode) || ! SLAVE_P (st.st_rdev)) + if (! S_ISCHR (stp->st_mode) || ! SLAVE_P (stp->st_rdev)) { /* This really is a configuration problem. */ __set_errno (ENOTTY); @@ -164,4 +160,15 @@ __ptsname_r (int fd, char *buf, size_t buflen) __set_errno (save_errno); return 0; } + + +/* Store at most BUFLEN characters of the pathname of the slave pseudo + terminal associated with the master FD is open on in BUF. + Return 0 on success, otherwise an error number. */ +int +__ptsname_r (int fd, char *buf, size_t buflen) +{ + struct stat64 st; + return __ptsname_internal (fd, buf, buflen, &st); +} weak_alias (__ptsname_r, ptsname_r) From c53f6228f178f54d8a93569b88c1c3144c8a9d3a Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Tue, 24 Nov 2009 20:22:44 -0800 Subject: [PATCH 09/11] Fix comments in random_r.c. --- ChangeLog | 4 ++++ stdlib/random_r.c | 4 ++-- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/ChangeLog b/ChangeLog index 4f74b500f0..000a535f1d 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,9 @@ 2009-11-24 Ulrich Drepper + [BZ #3662] + * stdlib/random_r.c: Fix comments for __initstate_r and __setstate_r. + Patch by Christopher Neufeld . + * sysdeps/unix/grantpt.c (pts_name): Take additional parameter, pass it on to __ptsname_internal. (grantpt): Pass stat64 pointer to pts_name. Remove stat call here. diff --git a/stdlib/random_r.c b/stdlib/random_r.c index 90a157f9c1..51a2e8c812 100644 --- a/stdlib/random_r.c +++ b/stdlib/random_r.c @@ -228,7 +228,7 @@ weak_alias (__srandom_r, srandom_r) lose this information and will be able to restart with setstate. Note: The first thing we do is save the current state, if any, just like setstate so that it doesn't matter when initstate is called. - Returns a pointer to the old state. */ + Returns 0 on success, non-zero on failure. */ int __initstate_r (seed, arg_state, n, buf) unsigned int seed; @@ -296,7 +296,7 @@ weak_alias (__initstate_r, initstate_r) location into the zeroth word of the state information. Note that due to the order in which things are done, it is OK to call setstate with the same state as the current state - Returns a pointer to the old state information. */ + Returns 0 on success, non-zero on failure. */ int __setstate_r (arg_state, buf) char *arg_state; From e2c59de609151c643be697fd243ffe0b92753f43 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Thu, 26 Nov 2009 08:47:56 -0800 Subject: [PATCH 10/11] Avoid handling long-obsolete old BSD PTY handling in ptsname. Support for this type of PTY was removed in the 2.1.115 kernel. Just use __LINUX_KERNEL_VERSION to determine when we can drop the compat code. --- ChangeLog | 6 ++++++ sysdeps/unix/sysv/linux/ptsname.c | 2 ++ 2 files changed, 8 insertions(+) diff --git a/ChangeLog b/ChangeLog index 000a535f1d..1b487ec264 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2009-11-26 Ulrich Drepper + + * sysdeps/unix/sysv/linux/ptsname.c (__ptsname_internal): Avoid code + only used on truly ancient kernel if configuration requires a more + recent kernel. + 2009-11-24 Ulrich Drepper [BZ #3662] diff --git a/sysdeps/unix/sysv/linux/ptsname.c b/sysdeps/unix/sysv/linux/ptsname.c index ba7c791c9f..129d09085e 100644 --- a/sysdeps/unix/sysv/linux/ptsname.c +++ b/sysdeps/unix/sysv/linux/ptsname.c @@ -128,10 +128,12 @@ __ptsname_internal (int fd, char *buf, size_t buflen, struct stat64 *stp) } ptyno = minor (stp->st_rdev); +#if __LINUX_KERNEL_VERSION >= 131443 /* This is for the old BSD pseudo terminals. As of Linux 2.1.115 these are no longer supported. */ if (major (stp->st_rdev) == 4) ptyno -= 128; +#endif if (ptyno / 16 >= strlen (__libc_ptyname1)) { From b55ec98c6490b944593243c7da54dda1796e3f84 Mon Sep 17 00:00:00 2001 From: Andreas Schwab Date: Fri, 27 Nov 2009 21:37:30 -0800 Subject: [PATCH 11/11] Fix infloop in __pthread_disable_asynccancel on x86_64 --- nptl/ChangeLog | 5 +++++ nptl/sysdeps/unix/sysv/linux/x86_64/cancellation.S | 5 +++-- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/nptl/ChangeLog b/nptl/ChangeLog index d0e1abcff5..b964fd895a 100644 --- a/nptl/ChangeLog +++ b/nptl/ChangeLog @@ -1,3 +1,8 @@ +2009-11-27 Andreas Schwab + + * sysdeps/unix/sysv/linux/x86_64/cancellation.S: Reload + THREAD_SELF->cancelhandling after returning from futex call. + 2009-11-24 Ulrich Drepper * tst-sem13.c: New file. diff --git a/nptl/sysdeps/unix/sysv/linux/x86_64/cancellation.S b/nptl/sysdeps/unix/sysv/linux/x86_64/cancellation.S index 0d48ec6fcd..680696200a 100644 --- a/nptl/sysdeps/unix/sysv/linux/x86_64/cancellation.S +++ b/nptl/sysdeps/unix/sysv/linux/x86_64/cancellation.S @@ -96,8 +96,8 @@ ENTRY(__pthread_disable_asynccancel) cmpxchgl %r11d, %fs:CANCELHANDLING jnz 2b -3: movl %r11d, %eax - andl $(TCB_CANCELING_BITMASK|TCB_CANCELED_BITMASK), %eax + movl %r11d, %eax +3: andl $(TCB_CANCELING_BITMASK|TCB_CANCELED_BITMASK), %eax cmpl $TCB_CANCELING_BITMASK, %eax je 4f 1: ret @@ -111,5 +111,6 @@ ENTRY(__pthread_disable_asynccancel) addq $CANCELHANDLING, %rdi LOAD_PRIVATE_FUTEX_WAIT (%esi) syscall + movl %fs:CANCELHANDLING, %eax jmp 3b END(__pthread_disable_asynccancel)