On Wed, Nov 08, 2006 at 09:28:30PM +0000, Shaun Amott wrote:
> While fiddling with PAM, it came to my attention that the pam_krb5
> module in some other (Linux?) PAM implementations supports, amongst
> other things, a minimum_uid option. This makes it possible to skip over
> Kerberos authentication for local system accounts, like so:
> 
>   auth    required    pam_krb5.so    no_warn minimum_uid=1000
>   auth    required    pam_unix.so    no_warn try_first_pass
> 
> I think it'd a nice addition to our pam_krb5 at least.
> 
> I've attached an initial patch. Comments/review welcome.
> 
OK.

> 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        8 Nov 2006 20:50:35 -0000
> @@ -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
                                               ^^^ UID
> +.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 group.
                                     ^^^^^ "group ID" or GID

Also, it could be explicit about this being a primary GID.

>  .El
>  .Ss Kerberos 5 Account Management Module
>  The Kerberos 5 account management component
> 
Document date should be bumped (the .Dd macro).

> 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        8 Nov 2006 20:50:36 -0000
> @@ -90,6 +90,8 @@
>  #define PAM_OPT_FORWARDABLE  "forwardable"
>  #define PAM_OPT_NO_CCACHE    "no_ccache"
>  #define PAM_OPT_REUSE_CCACHE "reuse_ccache"
> +#define PAM_OPT_MINIMUM_UID  "minimum_uid"
> +#define PAM_OPT_MINIMUM_GID  "minimum_gid"
>  
Defines were sorted alphabetically by a defined name.

>  /*
>   * authentication management
> @@ -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,21 @@
>  
>       PAM_LOG("Done getpwnam()");
>  
> +     retstr = openpam_get_option(pamh, PAM_OPT_MINIMUM_UID);
> +
Extraneous empty line.

> +     if (retstr)
                  ^ missing "!= NULL"

> +             minuid = (uid_t)strtoul(retstr, NULL, 10);
> 
Errors are silently ignored; limit (UID_MAX) isn't checked.

> +
> +     retstr = openpam_get_option(pamh, PAM_OPT_MINIMUM_GID);
> +
> +     if (retstr)
> +             mingid = (gid_t)strtoul(retstr, NULL, 10);
> +
> 
Ditto but s/UID_MAX/GID_MAX/.

> +     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 +369,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 +414,30 @@
>  
>       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)
> +             minuid = (uid_t)strtoul(retstr, NULL, 10);
> +
> +     retstr = openpam_get_option(pamh, PAM_OPT_MINIMUM_GID);
> +
> +     if (retstr)
> +             mingid = (gid_t)strtoul(retstr, NULL, 10);
> +
> +     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 +452,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;


Cheers,
-- 
Ruslan Ermilov
[EMAIL PROTECTED]
FreeBSD committer

Attachment: pgpEGzGpWOdwY.pgp
Description: PGP signature

Reply via email to