*/
#include "libbb.h"
-#include <features.h>
+//#include <features.h>
#include <assert.h>
#ifndef _PATH_SHADOW
}
#endif
+#ifdef THIS_ONE_IS_UNUSED
/* This one doesn't use static buffers */
int getpw(uid_t uid, char *buf)
{
return -1;
}
+#endif
/**********************************************************************/
*result = NULL; /* In case of error... */
if (!pwf) {
- pwf = fopen(_PATH_PASSWD, "r");
+ pwf = fopen_for_read(_PATH_PASSWD);
if (!pwf) {
rv = errno;
goto ERR;
*result = NULL; /* In case of error... */
if (!grf) {
- grf = fopen(_PATH_GROUP, "r");
+ grf = fopen_for_read(_PATH_GROUP);
if (!grf) {
rv = errno;
goto ERR;
*result = NULL; /* In case of error... */
if (!spf) {
- spf = fopen(_PATH_SHADOW, "r");
+ spf = fopen_for_read(_PATH_SHADOW);
if (!spf) {
rv = errno;
goto ERR;
}
#endif
-int initgroups(const char *user, gid_t gid)
+static gid_t *getgrouplist_internal(int *ngroups_ptr, const char *user, gid_t gid)
{
FILE *grfile;
gid_t *group_list;
- int num_groups, rv;
- char **m;
+ int ngroups;
struct group group;
char buff[PWD_BUFFER_SIZE];
- rv = -1;
-
/* We alloc space for 8 gids at a time. */
- group_list = (gid_t *) malloc(8*sizeof(gid_t *));
- if (group_list
- && ((grfile = fopen(_PATH_GROUP, "r")) != NULL)
- ) {
- *group_list = gid;
- num_groups = 1;
+ group_list = xmalloc(8 * sizeof(group_list[0]));
+ group_list[0] = gid;
+ ngroups = 1;
+ grfile = fopen_for_read(_PATH_GROUP);
+ if (grfile) {
while (!bb__pgsreader(bb__parsegrent, &group, buff, sizeof(buff), grfile)) {
+ char **m;
assert(group.gr_mem); /* Must have at least a NULL terminator. */
- if (group.gr_gid != gid) {
- for (m = group.gr_mem; *m; m++) {
- if (!strcmp(*m, user)) {
- if (!(num_groups & 7)) {
- gid_t *tmp = (gid_t *)
- realloc(group_list,
- (num_groups+8) * sizeof(gid_t *));
- if (!tmp) {
- rv = -1;
- goto DO_CLOSE;
- }
- group_list = tmp;
- }
- group_list[num_groups++] = group.gr_gid;
- break;
- }
- }
+ if (group.gr_gid == gid)
+ continue;
+ for (m = group.gr_mem; *m; m++) {
+ if (strcmp(*m, user) != 0)
+ continue;
+ group_list = xrealloc_vector(group_list, 3, ngroups);
+ group_list[ngroups++] = group.gr_gid;
+ break;
}
}
-
- rv = setgroups(num_groups, group_list);
- DO_CLOSE:
fclose(grfile);
}
+ *ngroups_ptr = ngroups;
+ return group_list;
+}
- /* group_list will be NULL if initial malloc failed, which may trigger
- * warnings from various malloc debuggers. */
+int initgroups(const char *user, gid_t gid)
+{
+ int ngroups;
+ gid_t *group_list = getgrouplist_internal(&ngroups, user, gid);
+
+ ngroups = setgroups(ngroups, group_list);
free(group_list);
- return rv;
+ return ngroups;
+}
+
+int getgrouplist(const char *user, gid_t gid, gid_t *groups, int *ngroups)
+{
+ int ngroups_old = *ngroups;
+ gid_t *group_list = getgrouplist_internal(ngroups, user, gid);
+
+ if (*ngroups <= ngroups_old) {
+ ngroups_old = *ngroups;
+ memcpy(groups, group_list, ngroups_old * sizeof(groups[0]));
+ } else {
+ ngroups_old = -1;
+ }
+ free(group_list);
+ return ngroups_old;
}
int putpwent(const struct passwd *__restrict p, FILE *__restrict f)
int rv = -1;
if (!p || !f) {
- errno=EINVAL;
+ errno = EINVAL;
} else {
/* No extra thread locking is needed above what fprintf does. */
if (fprintf(f, "%s:%s:%lu:%lu:%s:%s:%s\n",
int putgrent(const struct group *__restrict p, FILE *__restrict f)
{
- static const char format[] = ",%s";
+ static const char format[] ALIGN1 = ",%s";
+
char **m;
const char *fmt;
int rv = -1;
if (!p || !f) { /* Sigh... glibc checks. */
- errno=EINVAL;
+ errno = EINVAL;
} else {
if (fprintf(f, "%s:%s:%lu:",
p->gr_name, p->gr_passwd,
}
#if ENABLE_USE_BB_SHADOW
-static const unsigned char _sp_off[] = {
- offsetof(struct spwd, sp_lstchg), /* 2 - not a char ptr */
- offsetof(struct spwd, sp_min), /* 3 - not a char ptr */
- offsetof(struct spwd, sp_max), /* 4 - not a char ptr */
- offsetof(struct spwd, sp_warn), /* 5 - not a char ptr */
- offsetof(struct spwd, sp_inact), /* 6 - not a char ptr */
- offsetof(struct spwd, sp_expire), /* 7 - not a char ptr */
+static const unsigned char _sp_off[] ALIGN1 = {
+ offsetof(struct spwd, sp_lstchg), /* 2 - not a char ptr */
+ offsetof(struct spwd, sp_min), /* 3 - not a char ptr */
+ offsetof(struct spwd, sp_max), /* 4 - not a char ptr */
+ offsetof(struct spwd, sp_warn), /* 5 - not a char ptr */
+ offsetof(struct spwd, sp_inact), /* 6 - not a char ptr */
+ offsetof(struct spwd, sp_expire) /* 7 - not a char ptr */
};
int putspent(const struct spwd *p, FILE *stream)
{
- static const char ld_format[] = "%ld:";
+ static const char ld_format[] ALIGN1 = "%ld:";
+
const char *f;
long x;
int i;
/* Internal uClibc functions. */
/**********************************************************************/
-static const unsigned char pw_off[] = {
- offsetof(struct passwd, pw_name), /* 0 */
- offsetof(struct passwd, pw_passwd), /* 1 */
- offsetof(struct passwd, pw_uid), /* 2 - not a char ptr */
- offsetof(struct passwd, pw_gid), /* 3 - not a char ptr */
- offsetof(struct passwd, pw_gecos), /* 4 */
- offsetof(struct passwd, pw_dir), /* 5 */
- offsetof(struct passwd, pw_shell) /* 6 */
+static const unsigned char pw_off[] ALIGN1 = {
+ offsetof(struct passwd, pw_name), /* 0 */
+ offsetof(struct passwd, pw_passwd), /* 1 */
+ offsetof(struct passwd, pw_uid), /* 2 - not a char ptr */
+ offsetof(struct passwd, pw_gid), /* 3 - not a char ptr */
+ offsetof(struct passwd, pw_gecos), /* 4 */
+ offsetof(struct passwd, pw_dir), /* 5 */
+ offsetof(struct passwd, pw_shell) /* 6 */
};
static int bb__parsepwent(void *data, char *line)
/**********************************************************************/
-static const unsigned char gr_off[] = {
- offsetof(struct group, gr_name), /* 0 */
- offsetof(struct group, gr_passwd), /* 1 */
- offsetof(struct group, gr_gid) /* 2 - not a char ptr */
+static const unsigned char gr_off[] ALIGN1 = {
+ offsetof(struct group, gr_name), /* 0 */
+ offsetof(struct group, gr_passwd), /* 1 */
+ offsetof(struct group, gr_gid) /* 2 - not a char ptr */
};
static int bb__parsegrent(void *data, char *line)
/**********************************************************************/
#if ENABLE_USE_BB_SHADOW
-static const unsigned char sp_off[] = {
- offsetof(struct spwd, sp_namp), /* 0 */
- offsetof(struct spwd, sp_pwdp), /* 1 */
- offsetof(struct spwd, sp_lstchg), /* 2 - not a char ptr */
- offsetof(struct spwd, sp_min), /* 3 - not a char ptr */
- offsetof(struct spwd, sp_max), /* 4 - not a char ptr */
- offsetof(struct spwd, sp_warn), /* 5 - not a char ptr */
- offsetof(struct spwd, sp_inact), /* 6 - not a char ptr */
- offsetof(struct spwd, sp_expire), /* 7 - not a char ptr */
- offsetof(struct spwd, sp_flag) /* 8 - not a char ptr */
+static const unsigned char sp_off[] ALIGN1 = {
+ offsetof(struct spwd, sp_namp), /* 0 */
+ offsetof(struct spwd, sp_pwdp), /* 1 */
+ offsetof(struct spwd, sp_lstchg), /* 2 - not a char ptr */
+ offsetof(struct spwd, sp_min), /* 3 - not a char ptr */
+ offsetof(struct spwd, sp_max), /* 4 - not a char ptr */
+ offsetof(struct spwd, sp_warn), /* 5 - not a char ptr */
+ offsetof(struct spwd, sp_inact), /* 6 - not a char ptr */
+ offsetof(struct spwd, sp_expire), /* 7 - not a char ptr */
+ offsetof(struct spwd, sp_flag) /* 8 - not a char ptr */
};
static int bb__parsespent(void *data, char * line)