Thanks for reviewing the patch. Here's an updated version with your
suggestions incorporated.

Shaun

-- 
Shaun Amott // PGP: 0x6B387A9A
"A foolish consistency is the hobgoblin
of little minds." - Ralph Waldo Emerson
Index: pam_krb5.8
===================================================================
RCS file: /home/ncvs/src/lib/libpam/modules/pam_krb5/pam_krb5.8,v
retrieving revision 1.6
diff -u -r1.6 pam_krb5.8
--- pam_krb5.8  24 Nov 2001 23:41:32 -0000      1.6
+++ pam_krb5.8  9 Nov 2006 01:14:18 -0000
@@ -1,7 +1,7 @@
 .\"
 .\" $Id: pam_krb5.5,v 1.5 2000/01/05 00:59:56 fcusack Exp $
 .\" $FreeBSD: src/lib/libpam/modules/pam_krb5/pam_krb5.8,v 1.6 2001/11/24 
23:41:32 dd Exp $
-.Dd January 15, 1999
+.Dd Thursday 09, 2006
 .Dt PAM_KRB5 8
 .Os
 .Sh NAME
@@ -108,6 +108,13 @@
 .Ql %p ,
 to designate the current process ID; can be used in
 .Ar name .
+.It Cm minimum_uid Ns = Ns Ar id
+Do not attempt to authenticate users with a UID below
+.Ar id .
+Instead, simply return; thus allowing a later module to authenticate
+the user.
+.It Cm minimum_gid Ns = Ns Ar id
+As above, but specifies a minimum primary GID.
 .El
 .Ss Kerberos 5 Account Management Module
 The Kerberos 5 account management component
Index: pam_krb5.c
===================================================================
RCS file: /home/ncvs/src/lib/libpam/modules/pam_krb5/pam_krb5.c,v
retrieving revision 1.23
diff -u -r1.23 pam_krb5.c
--- pam_krb5.c  7 Jul 2005 14:16:38 -0000       1.23
+++ pam_krb5.c  9 Nov 2006 01:14:19 -0000
@@ -88,6 +88,8 @@
 #define PAM_OPT_CCACHE         "ccache"
 #define PAM_OPT_DEBUG          "debug"
 #define PAM_OPT_FORWARDABLE    "forwardable"
+#define PAM_OPT_MINIMUM_GID    "minimum_gid"
+#define PAM_OPT_MINIMUM_UID    "minimum_uid"
 #define PAM_OPT_NO_CCACHE      "no_ccache"
 #define PAM_OPT_REUSE_CCACHE   "reuse_ccache"
 
@@ -110,6 +112,9 @@
        const char *user, *pass;
        const void *sourceuser, *service;
        char *principal, *princ_name, *ccache_name, luser[32], *srvdup;
+       const char *retstr;
+       uid_t minuid = 0;
+       gid_t mingid = 0;
 
        retval = pam_get_user(pamh, &user, USER_PROMPT);
        if (retval != PAM_SUCCESS)
@@ -222,6 +227,39 @@
 
        PAM_LOG("Done getpwnam()");
 
+       retstr = openpam_get_option(pamh, PAM_OPT_MINIMUM_UID);
+       if (retstr != NULL) {
+               if ((minuid = (uid_t)strtoul(retstr, NULL, 10)) == 0) {
+                       if (errno == ERANGE || errno == EINVAL) {
+                               PAM_LOG("Error in minimum_uid: %s",
+                                   strerror(errno));
+                               return (PAM_SERVICE_ERR);
+                       }
+               } else if (minuid > UID_MAX) {
+                       PAM_LOG("Error in minimum_uid: invalid UID");
+                       return (PAM_SERVICE_ERR);
+               }
+       }
+
+       retstr = openpam_get_option(pamh, PAM_OPT_MINIMUM_GID);
+       if (retstr != NULL) {
+               if ((mingid = (gid_t)strtoul(retstr, NULL, 10)) == 0) {
+                       if (errno == ERANGE || errno == EINVAL) {
+                               PAM_LOG("Error in minimum_gid: %s",
+                                   strerror(errno));
+                               return (PAM_SERVICE_ERR);
+                       }
+               } else if (mingid > GID_MAX) {
+                       PAM_LOG("Error in minimum_gid: invalid GID");
+                       return (PAM_SERVICE_ERR);
+               }
+       }
+
+       if (pwd->pw_uid < minuid || pwd->pw_gid < mingid)
+               return (PAM_IGNORE);
+
+       PAM_LOG("Checked uid and gid bounds");
+
        /* Get a TGT */
        memset(&creds, 0, sizeof(krb5_creds));
        krbret = krb5_get_init_creds_password(pam_context, &creds, princ,
@@ -349,6 +387,9 @@
        const void *user;
        void *cache_data;
        char *cache_name_buf = NULL, *p;
+       const char *retstr;
+       uid_t minuid = 0;
+       gid_t mingid = 0;
 
        uid_t euid;
        gid_t egid;
@@ -391,6 +432,48 @@
 
        PAM_LOG("Got euid, egid: %d %d", euid, egid);
 
+       /* Get the uid. This should exist. */
+       pwd = getpwnam(user);
+       if (pwd == NULL) {
+               retval = PAM_USER_UNKNOWN;
+               goto cleanup3;
+       }
+
+       PAM_LOG("Done getpwnam()");
+
+       retstr = openpam_get_option(pamh, PAM_OPT_MINIMUM_UID);
+       if (retstr != NULL) {
+               if ((minuid = (uid_t)strtoul(retstr, NULL, 10)) == 0) {
+                       if (errno == ERANGE || errno == EINVAL) {
+                               PAM_LOG("Error in minimum_uid: %s",
+                                   strerror(errno));
+                               return (PAM_SERVICE_ERR);
+                       }
+               } else if (minuid > UID_MAX) {
+                       PAM_LOG("Error in minimum_uid: invalid UID");
+                       return (PAM_SERVICE_ERR);
+               }
+       }
+
+       retstr = openpam_get_option(pamh, PAM_OPT_MINIMUM_GID);
+       if (retstr != NULL) {
+               if ((mingid = (gid_t)strtoul(retstr, NULL, 10)) == 0) {
+                       if (errno == ERANGE || errno == EINVAL) {
+                               PAM_LOG("Error in minimum_gid: %s",
+                                   strerror(errno));
+                               return (PAM_SERVICE_ERR);
+                       }
+               } else if (mingid > GID_MAX) {
+                       PAM_LOG("Error in minimum_gid: invalid GID");
+                       return (PAM_SERVICE_ERR);
+               }
+       }
+
+       if (pwd->pw_uid < minuid || pwd->pw_gid < mingid)
+               return (PAM_IGNORE);
+
+       PAM_LOG("Checked uid and gid bounds");
+
        /* Retrieve the temporary cache */
        retval = pam_get_data(pamh, "ccache", &cache_data);
        if (retval != PAM_SUCCESS) {
@@ -405,15 +488,6 @@
                goto cleanup3;
        }
 
-       /* Get the uid. This should exist. */
-       pwd = getpwnam(user);
-       if (pwd == NULL) {
-               retval = PAM_USER_UNKNOWN;
-               goto cleanup3;
-       }
-
-       PAM_LOG("Done getpwnam()");
-
        /* Avoid following a symlink as root */
        if (setegid(pwd->pw_gid)) {
                retval = PAM_SERVICE_ERR;

Attachment: pgp8oPpZj3DES.pgp
Description: PGP signature

Reply via email to