This is the mail archive of the
glibc-cvs@sourceware.org
mailing list for the glibc project.
GNU C Library master sources branch, master, updated. glibc-2.11-282-gc8727fa
- From: drepper at sourceware dot org
- To: glibc-cvs at sourceware dot org
- Date: 25 Mar 2010 00:05:27 -0000
- Subject: GNU C Library master sources branch, master, updated. glibc-2.11-282-gc8727fa
This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "GNU C Library master sources".
The branch, master has been updated
via c8727fa6e5073d28ed6d0eb40a006ac2c1b9f9f3 (commit)
from fd8ccb0427569ffdfbb70c8828029122f3459160 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
http://sources.redhat.com/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=c8727fa6e5073d28ed6d0eb40a006ac2c1b9f9f3
commit c8727fa6e5073d28ed6d0eb40a006ac2c1b9f9f3
Author: Ulrich Drepper <drepper@redhat.com>
Date: Wed Mar 24 17:02:57 2010 -0700
Fix Linux getlogin{_r,} implementation
The old implementation uses fd 0 to determine the login TTY. This
was needed because using /dev/tty it is not possible to deduce the
login TTY. For some time now there is the pseudo-file
/proc/self/loginuid which directly helps us to find the user. Prefer
using this file. It also works if stdin is closed, redirected, or
re-opened.
diff --git a/ChangeLog b/ChangeLog
index 0e606dd..d3cd548 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,12 @@
2010-03-24 Ulrich Drepper <drepper@redhat.com>
+ * sysdeps/unix/sysv/linux/getlogin_r.c: New file.
+ * sysdeps/unix/sysv/linux/getlogin.c: New file.
+ * sysdeps/unix/getlogin_r.c: Allow compiling getlogin as static
+ function.
+ * sysdeps/unix/getlogin.c: Likewise. Move name variable to toplevel.
+ * include/unistd.h: Declare __getlogin_r_loginuid.
+
[BZ #11397]
* sysdeps/posix/cuserid.c (cuserid): Make sure the returned string
is NUL terminated.
diff --git a/include/unistd.h b/include/unistd.h
index ccba893..0ad2983 100644
--- a/include/unistd.h
+++ b/include/unistd.h
@@ -176,6 +176,9 @@ extern int __have_sock_cloexec;
unless it is really necessary. */
#define __have_pipe2 __have_sock_cloexec
+extern int __getlogin_r_loginuid (char *name, size_t namesize)
+ attribute_hidden;
+
__END_DECLS
#endif
diff --git a/sysdeps/unix/getlogin.c b/sysdeps/unix/getlogin.c
index 4752685..b0ad97c 100644
--- a/sysdeps/unix/getlogin.c
+++ b/sysdeps/unix/getlogin.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 1991, 1992, 1996, 1997 Free Software Foundation, Inc.
+/* Copyright (C) 1991, 1992, 1996, 1997, 2010 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
@@ -25,16 +25,20 @@
#include <utmp.h>
+static char name[UT_NAMESIZE + 1];
+
/* Return the login name of the user, or NULL if it can't be determined.
The returned pointer, if not NULL, is good only until the next call. */
+#ifdef STATIC
+STATIC
+#endif
char *
getlogin (void)
{
char tty_pathname[2 + 2 * NAME_MAX];
char *real_tty_path = tty_pathname;
char *result = NULL;
- static char name[UT_NAMESIZE + 1];
struct utmp *ut, line, buffer;
/* Get name of tty connected to fd 0. Return NULL if not a tty or
diff --git a/sysdeps/unix/getlogin_r.c b/sysdeps/unix/getlogin_r.c
index ba7badd..bf3c889 100644
--- a/sysdeps/unix/getlogin_r.c
+++ b/sysdeps/unix/getlogin_r.c
@@ -1,5 +1,5 @@
/* Reentrant function to return the current login name. Unix version.
- Copyright (C) 1991,92,96,97,98,2002 Free Software Foundation, Inc.
+ Copyright (C) 1991,92,96,97,98,2002,2010 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
@@ -31,6 +31,9 @@
If it cannot be determined or some other error occurred, return the error
code. Otherwise return 0. */
+#ifdef STATIC
+STATIC
+#endif
int
getlogin_r (name, name_len)
char *name;
@@ -96,4 +99,6 @@ getlogin_r (name, name_len)
return result;
}
+#ifndef STATIC
libc_hidden_def (getlogin_r)
+#endif
diff --git a/sysdeps/unix/sysv/linux/getlogin.c b/sysdeps/unix/sysv/linux/getlogin.c
new file mode 100644
index 0000000..4d15db0
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/getlogin.c
@@ -0,0 +1,39 @@
+/* Copyright (C) 2010 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 <pwd.h>
+#include <unistd.h>
+#include <not-cancel.h>
+
+#define STATIC static
+#define getlogin getlogin_fd0
+#include <sysdeps/unix/getlogin.c>
+#undef getlogin
+
+
+/* Return the login name of the user, or NULL if it can't be determined.
+ The returned pointer, if not NULL, is good only until the next call. */
+
+char *
+getlogin (void)
+{
+ if (__getlogin_r_loginuid (name, sizeof (name)) == 0)
+ return name;
+
+ return getlogin_fd0 ();
+}
diff --git a/sysdeps/unix/sysv/linux/getlogin_r.c b/sysdeps/unix/sysv/linux/getlogin_r.c
new file mode 100644
index 0000000..d07846c
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/getlogin_r.c
@@ -0,0 +1,100 @@
+/* Copyright (C) 2010 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 <pwd.h>
+#include <unistd.h>
+#include <not-cancel.h>
+
+#define STATIC static
+static int getlogin_r_fd0 (char *name, size_t namesize);
+#define getlogin_r getlogin_r_fd0
+#include <sysdeps/unix/getlogin_r.c>
+#undef getlogin_r
+
+
+int
+attribute_hidden
+__getlogin_r_loginuid (name, namesize)
+ char *name;
+ size_t namesize;
+{
+ int fd = open_not_cancel_2 ("/proc/self/loginuid", O_RDONLY);
+ if (fd == -1)
+ return 1;
+
+ ssize_t n = TEMP_FAILURE_RETRY (read_not_cancel (fd, name, namesize));
+ close_not_cancel_no_status (fd);
+
+ uid_t uid;
+ char *endp;
+ if (n <= 0
+ || (uid = strtoul (name, &endp, 10), endp == name || *endp != '\0'))
+ return 1;
+
+ size_t buflen = 1024;
+ char *buf = alloca (buflen);
+ bool use_malloc = false;
+ struct passwd pwd;
+ struct passwd *tpwd;
+ int res;
+
+ while ((res = __getpwuid_r (uid, &pwd, buf, buflen, &tpwd)) != 0)
+ if (__libc_use_alloca (2 * buflen))
+ extend_alloca (buf, buflen, 2 * buflen);
+ else
+ {
+ buflen *= 2;
+ char *newp = realloc (use_malloc ? buf : NULL, buflen);
+ if (newp == NULL)
+ {
+ fail:
+ if (use_malloc)
+ free (buf);
+ return 1;
+ }
+ buf = newp;
+ use_malloc = true;
+ }
+
+ if (tpwd == NULL)
+ goto fail;
+
+ strncpy (name, pwd.pw_name, namesize - 1);
+ name[namesize - 1] = '\0';
+
+ if (use_malloc)
+ free (buf);
+
+ return 0;
+}
+
+
+/* Return the login name of the user, or NULL if it can't be determined.
+ The returned pointer, if not NULL, is good only until the next call. */
+
+int
+getlogin_r (name, namesize)
+ char *name;
+ size_t namesize;
+{
+ if (__getlogin_r_loginuid (name, namesize) == 0)
+ return 0;
+
+ return getlogin_r_fd0 (name, namesize);
+}
+libc_hidden_def (getlogin_r)
-----------------------------------------------------------------------
Summary of changes:
ChangeLog | 7 ++
include/unistd.h | 3 +
sysdeps/unix/getlogin.c | 8 ++-
sysdeps/unix/getlogin_r.c | 7 ++-
{posix => sysdeps/unix/sysv/linux}/getlogin.c | 22 ++++--
sysdeps/unix/sysv/linux/getlogin_r.c | 100 +++++++++++++++++++++++++
6 files changed, 136 insertions(+), 11 deletions(-)
copy {posix => sysdeps/unix/sysv/linux}/getlogin.c (76%)
create mode 100644 sysdeps/unix/sysv/linux/getlogin_r.c
hooks/post-receive
--
GNU C Library master sources