| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261 |
- /*
- * <pwd.h> wrapper functions.
- *
- * Authors:
- * Jonathan Pryor ([email protected])
- *
- * Copyright (C) 2004-2005 Jonathan Pryor
- */
- #include <pwd.h>
- #include <errno.h>
- #include <string.h>
- #include <stdio.h>
- #include <stdlib.h>
- #include "map.h"
- #include "mph.h"
- G_BEGIN_DECLS
- static const mph_string_offset_t
- passwd_offsets[] = {
- MPH_STRING_OFFSET (struct passwd, pw_name, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct passwd, pw_passwd, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct passwd, pw_gecos, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct passwd, pw_dir, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct passwd, pw_shell, MPH_STRING_OFFSET_PTR)
- };
- static const mph_string_offset_t
- mph_passwd_offsets[] = {
- MPH_STRING_OFFSET (struct Mono_Posix_Syscall__Passwd, pw_name, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct Mono_Posix_Syscall__Passwd, pw_passwd, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct Mono_Posix_Syscall__Passwd, pw_gecos, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct Mono_Posix_Syscall__Passwd, pw_dir, MPH_STRING_OFFSET_PTR),
- MPH_STRING_OFFSET (struct Mono_Posix_Syscall__Passwd, pw_shell, MPH_STRING_OFFSET_PTR)
- };
- /*
- * Copy the native `passwd' structure to it's managed representation.
- *
- * To minimize separate mallocs, all the strings are allocated within the same
- * memory block (stored in _pw_buf_).
- */
- static int
- copy_passwd (struct Mono_Posix_Syscall__Passwd *to, struct passwd *from)
- {
- char *buf;
- buf = _mph_copy_structure_strings (to, mph_passwd_offsets,
- from, passwd_offsets, sizeof(passwd_offsets)/sizeof(passwd_offsets[0]));
- to->pw_uid = from->pw_uid;
- to->pw_gid = from->pw_gid;
- to->_pw_buf_ = buf;
- if (buf == NULL) {
- return -1;
- }
- return 0;
- }
- gint32
- Mono_Posix_Syscall_getpwnam (const char *name, struct Mono_Posix_Syscall__Passwd *pwbuf)
- {
- struct passwd *pw;
- if (pwbuf == NULL) {
- errno = EFAULT;
- return -1;
- }
- errno = 0;
- pw = getpwnam (name);
- if (pw == NULL)
- return -1;
- if (copy_passwd (pwbuf, pw) == -1) {
- errno = ENOMEM;
- return -1;
- }
- return 0;
- }
- gint32
- Mono_Posix_Syscall_getpwuid (mph_uid_t uid, struct Mono_Posix_Syscall__Passwd *pwbuf)
- {
- struct passwd *pw;
- if (pwbuf == NULL) {
- errno = EFAULT;
- return -1;
- }
- errno = 0;
- pw = getpwuid (uid);
- if (pw == NULL) {
- return -1;
- }
- if (copy_passwd (pwbuf, pw) == -1) {
- errno = ENOMEM;
- return -1;
- }
- return 0;
- }
- #ifdef HAVE_GETPWNAM_R
- gint32
- Mono_Posix_Syscall_getpwnam_r (const char *name,
- struct Mono_Posix_Syscall__Passwd *pwbuf,
- void **pwbufp)
- {
- char *buf, *buf2;
- size_t buflen;
- int r;
- struct passwd _pwbuf;
- if (pwbuf == NULL) {
- errno = EFAULT;
- return -1;
- }
- buf = buf2 = NULL;
- buflen = 2;
- do {
- buf2 = realloc (buf, buflen *= 2);
- if (buf2 == NULL) {
- free (buf);
- errno = ENOMEM;
- return -1;
- }
- buf = buf2;
- errno = 0;
- } while ((r = getpwnam_r (name, &_pwbuf, buf, buflen, (struct passwd**) pwbufp)) &&
- recheck_range (r));
- if (r == 0 && !(*pwbufp))
- /* On solaris, this function returns 0 even if the entry was not found */
- r = errno = ENOENT;
- if (r == 0 && copy_passwd (pwbuf, &_pwbuf) == -1)
- r = errno = ENOMEM;
- free (buf);
- return r;
- }
- #endif /* ndef HAVE_GETPWNAM_R */
- #ifdef HAVE_GETPWUID_R
- gint32
- Mono_Posix_Syscall_getpwuid_r (mph_uid_t uid,
- struct Mono_Posix_Syscall__Passwd *pwbuf,
- void **pwbufp)
- {
- char *buf, *buf2;
- size_t buflen;
- int r;
- struct passwd _pwbuf;
- if (pwbuf == NULL) {
- errno = EFAULT;
- return -1;
- }
- buf = buf2 = NULL;
- buflen = 2;
- do {
- buf2 = realloc (buf, buflen *= 2);
- if (buf2 == NULL) {
- free (buf);
- errno = ENOMEM;
- return -1;
- }
- buf = buf2;
- errno = 0;
- } while ((r = getpwuid_r (uid, &_pwbuf, buf, buflen, (struct passwd**) pwbufp)) &&
- recheck_range (r));
- if (r == 0 && copy_passwd (pwbuf, &_pwbuf) == -1)
- r = errno = ENOMEM;
- free (buf);
- return r;
- }
- #endif /* ndef HAVE_GETPWUID_R */
- gint32
- Mono_Posix_Syscall_getpwent (struct Mono_Posix_Syscall__Passwd *pwbuf)
- {
- struct passwd *pw;
- if (pwbuf == NULL) {
- errno = EFAULT;
- return -1;
- }
- errno = 0;
- pw = getpwent ();
- if (pw == NULL)
- return -1;
- if (copy_passwd (pwbuf, pw) == -1) {
- errno = ENOMEM;
- return -1;
- }
- return 0;
- }
- #ifdef HAVE_FGETPWENT
- gint32
- Mono_Posix_Syscall_fgetpwent (void *stream, struct Mono_Posix_Syscall__Passwd *pwbuf)
- {
- struct passwd *pw;
- if (pwbuf == NULL) {
- errno = EFAULT;
- return -1;
- }
- errno = 0;
- pw = fgetpwent ((FILE*) stream);
- if (pw == NULL)
- return -1;
- if (copy_passwd (pwbuf, pw) == -1) {
- errno = ENOMEM;
- return -1;
- }
- return 0;
- }
- #endif /* ndef HAVE_FGETPWENT */
- int
- Mono_Posix_Syscall_setpwent (void)
- {
- errno = 0;
- do {
- setpwent ();
- } while (errno == EINTR);
- mph_return_if_val_in_list5(errno, EIO, EMFILE, ENFILE, ENOMEM, ERANGE);
- return 0;
- }
- int
- Mono_Posix_Syscall_endpwent (void)
- {
- errno = 0;
- endpwent ();
- if (errno == EIO)
- return -1;
- return 0;
- }
- G_END_DECLS
- /*
- * vim: noexpandtab
- */
|