From: Todd C. Miller Date: Fri, 18 Jan 2013 19:58:12 +0000 (-0500) Subject: Use _getgroupsbymember() on Solaris to get the groups list. Fixes X-Git-Tag: SUDO_1_8_7~1^2~276 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=a06a14838f561fb737c357d30183d52396aa9f0d;p=sudo Use _getgroupsbymember() on Solaris to get the groups list. Fixes performance problems with the getgroupslist() compat on Solaris systems with network-based group databases. --- diff --git a/compat/getgrouplist.c b/compat/getgrouplist.c index 2d22714f4..cea72f511 100644 --- a/compat/getgrouplist.c +++ b/compat/getgrouplist.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2010 Todd C. Miller + * Copyright (c) 2010, 2011, 2013 Todd C. Miller * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -36,7 +36,7 @@ #include "missing.h" -#ifdef HAVE_GETGRSET +#if defined(HAVE_GETGRSET) /* * BSD-compatible getgrouplist(3) using getgrset(3) */ @@ -79,7 +79,32 @@ done: return rval; } -#else /* HAVE_GETGRSET */ +#elif defined(HAVE__GETGROUPSBYMEMBER) + +/* + * BSD-compatible getgrouplist(3) using _getgroupsbymember(3) + */ +int +getgrouplist(const char *name, gid_t basegid, gid_t *groups, int *ngroupsp) +{ + int ngroups, grpsize = *ngroupsp; + int rval = -1; + + if (grpsize > 0) { + /* We support BSD semantics where the first element is the base gid */ + groups[0] = basegid; + + /* The last arg is 1 because we already filled in the base gid. */ + ngroups = _getgroupsbymember(name, groups, grpsize, 1); + if (ngroups != -1) { + rval = 0; + *ngroupsp = ngroups; + } + } + return rval; +} + +#else /* !HAVE_GETGRSET && !HAVE__GETGROUPSBYMEMBER */ /* * BSD-compatible getgrouplist(3) using getgrent(3) @@ -128,4 +153,4 @@ done: return rval; } -#endif /* HAVE_GETGRSET */ +#endif /* !HAVE_GETGRSET && !HAVE__GETGROUPSBYMEMBER */ diff --git a/config.h.in b/config.h.in index bead6ae8c..3483ac225 100644 --- a/config.h.in +++ b/config.h.in @@ -697,6 +697,9 @@ /* Define to 1 if the system has the type `_Bool'. */ #undef HAVE__BOOL +/* Define to 1 if you have the `_getgroupsbymember' function. */ +#undef HAVE__GETGROUPSBYMEMBER + /* Define to 1 if you have the `_getpty' function. */ #undef HAVE__GETPTY diff --git a/configure b/configure index 5dbd996f8..5018c023e 100755 --- a/configure +++ b/configure @@ -13927,6 +13927,19 @@ case "$host" in OS_INIT=os_init_solaris SUDO_OBJS="${SUDO_OBJS} solaris.o" + # For implementing getgrouplist() + for ac_func in _getgroupsbymember +do : + ac_fn_c_check_func "$LINENO" "_getgroupsbymember" "ac_cv_func__getgroupsbymember" +if test "x$ac_cv_func__getgroupsbymember" = xyes; then : + cat >>confdefs.h <<_ACEOF +#define HAVE__GETGROUPSBYMEMBER 1 +_ACEOF + +fi +done + + # To get the crypt(3) prototype (so we pass -Wall) OSDEFS="${OSDEFS} -D__EXTENSIONS__" # AFS support needs -lucb diff --git a/configure.in b/configure.in index 02c4760e5..c9b589d70 100644 --- a/configure.in +++ b/configure.in @@ -1573,6 +1573,9 @@ case "$host" in OS_INIT=os_init_solaris SUDO_OBJS="${SUDO_OBJS} solaris.o" + # For implementing getgrouplist() + AC_CHECK_FUNCS(_getgroupsbymember) + # To get the crypt(3) prototype (so we pass -Wall) OSDEFS="${OSDEFS} -D__EXTENSIONS__" # AFS support needs -lucb