Imported Upstream version 1.8.7
[debian/sudo] / plugins / sudoers / tsgetgrpw.c
index 7b9ad790e9038bc13a3fc9376ff9fc07f22773bb..edfc3837dbcc9fff52003116eef89a99d82fb1cd 100644 (file)
@@ -1,5 +1,6 @@
 /*
- * Copyright (c) 2005, 2008, 2010-2011 Todd C. Miller <Todd.Miller@courtesan.com>
+ * Copyright (c) 2005, 2008, 2010-2013
+ *     Todd C. Miller <Todd.Miller@courtesan.com>
  *
  * Permission to use, copy, modify, and distribute this software for any
  * purpose with or without fee is hereby granted, provided that the above
@@ -23,7 +24,6 @@
 #include <config.h>
 
 #include <sys/types.h>
-#include <sys/param.h>
 #include <stdio.h>
 #ifdef STDC_HEADERS
 # include <stdlib.h>
@@ -42,6 +42,7 @@
 #ifdef HAVE_STRINGS_H
 # include <strings.h>
 #endif /* HAVE_STRINGS_H */
+#include <errno.h>
 #include <fcntl.h>
 #include <limits.h>
 
 #undef GRMEM_MAX
 #define GRMEM_MAX 200
 
+#ifndef UID_MAX
+# define UID_MAX 0xffffffffU
+#endif
+
+#ifndef GID_MAX
+# define GID_MAX UID_MAX
+#endif
+
 static FILE *pwf;
 static const char *pwfile = "/etc/passwd";
 static int pw_stayopen;
@@ -114,34 +123,46 @@ getpwent(void)
     static struct passwd pw;
     static char pwbuf[LINE_MAX];
     size_t len;
-    char *cp, *colon;
+    unsigned long id;
+    char *cp, *colon, *ep;
 
+next_entry:
     if ((colon = fgets(pwbuf, sizeof(pwbuf), pwf)) == NULL)
        return NULL;
 
     zero_bytes(&pw, sizeof(pw));
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
     pw.pw_name = cp;
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
     pw.pw_passwd = cp;
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
-    pw.pw_uid = atoi(cp);
+    id = strtoul(cp, &ep, 10);
+    if (*cp == '\0' || *ep != '\0')
+       goto next_entry;
+    if (id > UID_MAX || (id == ULONG_MAX && errno == ERANGE))
+       goto next_entry;
+    pw.pw_uid = (uid_t)id;
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
-    pw.pw_gid = atoi(cp);
+    id = strtoul(cp, &ep, 10);
+    if (*cp == '\0' || *ep != '\0')
+       goto next_entry;
+    if (id > GID_MAX || (id == ULONG_MAX && errno == ERANGE))
+       goto next_entry;
+    pw.pw_gid = (gid_t)id;
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
     pw.pw_gecos = cp;
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
     pw.pw_dir = cp;
     pw.pw_shell = colon;
@@ -234,25 +255,32 @@ getgrent(void)
     static struct group gr;
     static char grbuf[LINE_MAX], *gr_mem[GRMEM_MAX+1];
     size_t len;
-    char *cp, *colon;
+    unsigned long id;
+    char *cp, *colon, *ep;
     int n;
 
+next_entry:
     if ((colon = fgets(grbuf, sizeof(grbuf), grf)) == NULL)
        return NULL;
 
     zero_bytes(&gr, sizeof(gr));
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
     gr.gr_name = cp;
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
     gr.gr_passwd = cp;
     if ((colon = strchr(cp = colon, ':')) == NULL)
-       return NULL;
+       goto next_entry;
     *colon++ = '\0';
-    gr.gr_gid = atoi(cp);
+    id = strtoul(cp, &ep, 10);
+    if (*cp == '\0' || *ep != '\0')
+       goto next_entry;
+    if (id > GID_MAX || (id == ULONG_MAX && errno == ERANGE))
+       goto next_entry;
+    gr.gr_gid = (gid_t)id;
     len = strlen(colon);
     if (len > 0 && colon[len - 1] == '\n')
        colon[len - 1] = '\0';