diff options
author | deischen <deischen@FreeBSD.org> | 2001-01-01 13:29:19 +0000 |
---|---|---|
committer | deischen <deischen@FreeBSD.org> | 2001-01-01 13:29:19 +0000 |
commit | 62702ce855fe19ce92fd197c92be0cabbbc4218b (patch) | |
tree | f417d77563d062253daef226841673fb1f1dd005 /lib/libc/gen/getlogin.c | |
parent | 95a1cabbb96cc4c8e5d7144af62395500b22cdc3 (diff) | |
download | FreeBSD-src-62702ce855fe19ce92fd197c92be0cabbbc4218b.zip FreeBSD-src-62702ce855fe19ce92fd197c92be0cabbbc4218b.tar.gz |
Change the interface of getlogin_r to return an int. The former
interface was based on a draft version of POSIX whereas the final
(1996) version of POSIX specified that the error is returned.
While I'm here, fix getlogin_r so that it works for more than just
the first time it's called.
Reviewed by: wes, wollman (man page)
Diffstat (limited to 'lib/libc/gen/getlogin.c')
-rw-r--r-- | lib/libc/gen/getlogin.c | 67 |
1 files changed, 50 insertions, 17 deletions
diff --git a/lib/libc/gen/getlogin.c b/lib/libc/gen/getlogin.c index 044689d..5adc46c 100644 --- a/lib/libc/gen/getlogin.c +++ b/lib/libc/gen/getlogin.c @@ -38,43 +38,76 @@ static char sccsid[] = "@(#)getlogin.c 8.1 (Berkeley) 6/4/93"; #endif /* LIBC_SCCS and not lint */ #include <sys/param.h> +#include <errno.h> #include <pwd.h> #include <utmp.h> #include <stdio.h> #include <string.h> #include <unistd.h> -int _logname_valid; /* known to setlogin() */ +#include <libc_private.h> -char * -getlogin() +#ifndef _THREAD_SAFE +#define THREAD_LOCK() +#define THREAD_UNLOCK() +#else +#include <pthread.h> +#include "pthread_private.h" +static struct pthread_mutex logname_lock = PTHREAD_MUTEX_STATIC_INITIALIZER; +static pthread_mutex_t logname_mutex = &logname_lock; +#define THREAD_LOCK() if (__isthreaded) pthread_mutex_lock(&logname_mutex) +#define THREAD_UNLOCK() if (__isthreaded) pthread_mutex_unlock(&logname_mutex) +#endif /* _THREAD_SAFE */ + +int _logname_valid; /* known to setlogin() */ + +static char * +getlogin_basic(int *status) { static char logname[MAXLOGNAME]; if (_logname_valid == 0) { #ifdef __NETBSD_SYSCALLS - if (__getlogin(logname, sizeof(logname) - 1) < 0) + if (__getlogin(logname, sizeof(logname) - 1) < 0) { #else - if (_getlogin(logname, sizeof(logname)) < 0) + if (_getlogin(logname, sizeof(logname)) < 0) { #endif - return ((char *)NULL); + *status = errno; + return (NULL); + } _logname_valid = 1; } - return (*logname ? logname : (char *)NULL); + *status = 0; + return (*logname ? logname : NULL); } - char * +getlogin(void) +{ + char *result; + int status; + + THREAD_LOCK(); + result = getlogin_basic(&status); + THREAD_UNLOCK(); + return (result); +} + +int getlogin_r(char *logname, int namelen) { - if (_logname_valid == 0) { -#ifdef __NETBSD_SYSCALLS - if (__getlogin(logname, namelen - 1) < 0) -#else - if (_getlogin(logname, namelen) < 0) -#endif - return ((char *)NULL); - _logname_valid = 1; + char *result; + int len; + int status; + + THREAD_LOCK(); + result = getlogin_basic(&status); + if (status == 0) { + if ((len = strlen(result) + 1) > namelen) + status = ERANGE; + else + strncpy(logname, result, len); } - return (*logname ? logname : (char *)NULL); + THREAD_UNLOCK(); + return (status); } |