On Thu, Jan 22, 2009 at 10:48:59AM +0000, Daniel P. Berrange wrote: > On Fri, Jan 16, 2009 at 12:25:02PM +0000, Daniel P. Berrange wrote: > > On Fri, Jan 16, 2009 at 12:21:59PM +0000, Richard W.M. Jones wrote: > > > On Tue, Jan 13, 2009 at 05:46:37PM +0000, Daniel P. Berrange wrote: > > > > + char buf[1024]; > > > > > > sysconf (_SC_GETPW_R_SIZE_MAX)? > > > > > > Looking at glibc's implementation of getpwuid (which uses getpwuid_r), > > > I see that glibc dynamically reallocates the buffer as necessary to > > > the correct size for the return value. The logic of this is fairly > > > simple so maybe we should do the same? > > > > > > From glibc: > > > > > > buffer = malloc (/*some_initial_size*/); > > > > > > while (buffer != NULL > > > && (getpwuid_r (const char *name, &resbuf, buffer, > > > buffer_size, &result) > > > == ERANGE)) > > > { > > > char *new_buf; > > > buffer_size *= 2; > > > new_buf = (char *) realloc (buffer, buffer_size); > > > if (new_buf == NULL) > > > { > > > free (buffer); > > > errno = ENOMEM; > > > } > > > buffer = new_buf; > > > } > > > > > > > > > Anyhow, +1 but I'd be happier if these functions were centralized in > > > somewhere like src/utils.c. > > > > That's a good idea - in all the cases where we currently use getpwuid > > all we actually want is the home directory path. So we could add a > > simple func: > > > > char *virUserHomeDirectory(uid_t uid); > > > > and hide all the horrific code in there. > > Here's an update with that usage in it > > diff --git a/src/util.c b/src/util.c > --- a/src/util.c > +++ b/src/util.c > @@ -49,6 +49,9 @@ > #include <paths.h> > #endif > #include <netdb.h> > +#ifdef HAVE_GETPWUID_R > +#include <pwd.h> > +#endif > > #include "virterror_internal.h" > #include "logging.h" > @@ -1431,3 +1434,37 @@ int virKillProcess(pid_t pid, int sig) > return kill(pid, sig); > #endif > } > + > + > +#ifdef HAVE_GETPWUID_R > +char *virGetUserDirectory(virConnectPtr conn, > + uid_t uid) > +{ > + char *strbuf; > + char *ret; > + struct passwd pwbuf; > + struct passwd *pw; > + size_t strbuflen = sysconf(_SC_GETPW_R_SIZE_MAX); > + > + if (VIR_ALLOC_N(strbuf, strbuflen) < 0) { > + virReportOOMError(conn); > + return NULL; > + } > + > + if (getpwuid_r(uid, &pwbuf, strbuf, strbuflen, &pw) != 0) { > + virReportSystemError(conn, errno, > + _("Failed to find user record for uid '%d'"), > + uid); > + VIR_FREE(strbuf); > + return NULL; > + } > + > + ret = strdup(pw->pw_dir); > + > + VIR_FREE(strbuf); > + if (!ret) > + virReportOOMError(conn); > + > + return NULL; > +} > +#endif Delibrate mistake here :-) s/return NULL/return ret/ Otherwise it always returns NULL :-) Daniel -- |: Red Hat, Engineering, London -o- http://people.redhat.com/berrange/ :| |: http://libvirt.org -o- http://virt-manager.org -o- http://ovirt.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: GnuPG: 7D3B9505 -o- F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 :| -- Libvir-list mailing list Libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list