diff options
author | Ulrich Drepper <drepper@redhat.com> | 2000-07-24 01:26:01 +0000 |
---|---|---|
committer | Ulrich Drepper <drepper@redhat.com> | 2000-07-24 01:26:01 +0000 |
commit | cf9e9ad98feb55d11f93aa4e069c81ee06c2a6a3 (patch) | |
tree | 2da802067a7b55b2580a49786505794ace48ac0c /hesiod | |
parent | 945b22ed04767342dac1654f7e92ad5f8870361b (diff) | |
download | glibc-cf9e9ad98feb55d11f93aa4e069c81ee06c2a6a3.tar glibc-cf9e9ad98feb55d11f93aa4e069c81ee06c2a6a3.tar.gz glibc-cf9e9ad98feb55d11f93aa4e069c81ee06c2a6a3.tar.bz2 glibc-cf9e9ad98feb55d11f93aa4e069c81ee06c2a6a3.zip |
Update.
* grp/initgroups.c (initgroups): Don't limit the possible number
of groups to NGROUPS_MAX. Allow dynamic resizing. Loop around
the setgroups call while the call fails and descrease the number
of groups each round.
The name of the initgroups function in the NSS modules changed.
(compat_call): Adapt for dynamic resizing.
* hesiod/nss_hesiod/hesiod-grp.c (_nss_hesiod_initgroups_dyn):
Implement dynamic resizing.
* nis/nss_compat/compat-initgroups.c (_nss_compat_initgroups_dyn):
Likewise.
* nis/nss_nis/compat-initgroups.c (_nss_nis_initgroups_dyn): Likewise.
* hesiod/Versions: Change exported interface name.
* nis/Versions: Change exported interface name.
2000-07-23 Ulrich Drepper <drepper@redhat.com>
Diffstat (limited to 'hesiod')
-rw-r--r-- | hesiod/Versions | 2 | ||||
-rw-r--r-- | hesiod/nss_hesiod/hesiod-grp.c | 41 |
2 files changed, 35 insertions, 8 deletions
diff --git a/hesiod/Versions b/hesiod/Versions index c51dee9c50..180befb5b3 100644 --- a/hesiod/Versions +++ b/hesiod/Versions @@ -8,7 +8,7 @@ libnss_hesiod { _nss_hesiod_getservbyname_r; } GLIBC_2.2 { - _nss_hesiod_initgroups; + _nss_hesiod_initgroups_dyn; _nss_hesiod_getservbyport_r; _nss_hesiod_setprotoent; _nss_hesiod_endprotoent; _nss_hesiod_getprotobyname_r; _nss_hesiod_getprotobynumber_r; diff --git a/hesiod/nss_hesiod/hesiod-grp.c b/hesiod/nss_hesiod/hesiod-grp.c index 2d5b96b7f9..a89ed4edaf 100644 --- a/hesiod/nss_hesiod/hesiod-grp.c +++ b/hesiod/nss_hesiod/hesiod-grp.c @@ -164,14 +164,14 @@ internal_gid_from_group (void *context, const char *groupname, gid_t *group) } enum nss_status -_nss_hesiod_initgroups (const char *user, gid_t group, long int *start, - long int *size, gid_t *groups, long int limit, - int *errnop) +_nss_hesiod_initgroups_dyn (const char *user, gid_t group, long int *start, + long int *size, gid_t **groupsp, int *errnop) { enum nss_status status = NSS_STATUS_SUCCESS; char **list = NULL; char *p; void *context; + gid_t *groups = *groupsp; context = _nss_hesiod_init (); if (context == NULL) @@ -185,11 +185,24 @@ _nss_hesiod_initgroups (const char *user, gid_t group, long int *start, return errno == ENOENT ? NSS_STATUS_NOTFOUND : NSS_STATUS_UNAVAIL; } - if (!internal_gid_in_list (groups, group, *start) && *start < limit) - groups[(*start)++] = group; + if (!internal_gid_in_list (groups, group, *start)) + { + if (__builtin_expect (*start == *size, 0)) + { + /* Need a bigger buffer. */ + gid_t *newgroups; + newgroups = realloc (groups, 2 * *size * sizeof (*groups)); + if (newgroups == NULL) + goto done; + *groupsp = groups = newgroups; + *size *= 2; + } + + groups[(*start)++] = group; + } p = *list; - while (*p != '\0' && *start < limit) + while (*p != '\0') { char *endp; char *q; @@ -214,12 +227,26 @@ _nss_hesiod_initgroups (const char *user, gid_t group, long int *start, if (status == NSS_STATUS_SUCCESS && !internal_gid_in_list (groups, group, *start)) - groups[(*start)++] = group; + { + if (__builtin_expect (*start == *size, 0)) + { + /* Need a bigger buffer. */ + gid_t *newgroups; + newgroups = realloc (groups, 2 * *size * sizeof (*groups)); + if (newgroups == NULL) + goto done; + *groupsp = groups = newgroups; + *size *= 2; + } + + groups[(*start)++] = group; + } } p = q; } + done: hesiod_free_list (context, list); hesiod_end (context); |