From e84da6fb397bfc780582271e3722d7073f9ba4a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Dag-Erling=20Sm=C3=B8rgrav?= Date: Sat, 12 Mar 2011 11:12:30 +0000 Subject: [PATCH] Add "ruser" and "luser" options. The former corresponds to the current behavior, where the module checks that the supplicant is a member of the required group. The latter checks the target user instead. If neither option was specified, pam_group(8) assumes "ruser" and issues a warning. I intend to eventually change the default to "luser" to match the behavior of similarly-named service modules in other operating systems. MFC after: 1 month --- lib/libpam/modules/pam_group/pam_group.8 | 16 +++++++++++++++- lib/libpam/modules/pam_group/pam_group.c | 24 ++++++++++++++++++++---- 2 files changed, 35 insertions(+), 5 deletions(-) diff --git a/lib/libpam/modules/pam_group/pam_group.8 b/lib/libpam/modules/pam_group/pam_group.8 index 832841b4c699..985094b1ed24 100644 --- a/lib/libpam/modules/pam_group/pam_group.8 +++ b/lib/libpam/modules/pam_group/pam_group.8 @@ -1,4 +1,5 @@ .\" Copyright (c) 2003 Networks Associates Technology, Inc. +.\" Copyright (c) 2004-2011 Dag-Erling Smørgrav .\" All rights reserved. .\" .\" Portions of this software were developed for the FreeBSD Project by @@ -32,7 +33,7 @@ .\" .\" $FreeBSD$ .\" -.Dd February 6, 2003 +.Dd March 9, 2011 .Dt PAM_GROUP 8 .Os .Sh NAME @@ -64,10 +65,23 @@ it does exist and the applicant is a member. Specify the name of the group to check. The default is .Dq Li wheel . +.It Cm luser +Accept or reject based on the target user's group membership. .It Cm root_only Skip this module entirely if the target account is not the superuser account. +.It Cm ruser +Accept or reject based on the supplicant's group membership. +This is the default. .El +.Pp +Note that the +.Cm luser +and +.Cm ruser +options are mutually exclusive, and that +.Nm +will fail if both are specified. .Sh SEE ALSO .Xr pam.conf 5 , .Xr pam 8 diff --git a/lib/libpam/modules/pam_group/pam_group.c b/lib/libpam/modules/pam_group/pam_group.c index a9d5fc32df1c..f09d51829c92 100644 --- a/lib/libpam/modules/pam_group/pam_group.c +++ b/lib/libpam/modules/pam_group/pam_group.c @@ -1,5 +1,6 @@ /*- * Copyright (c) 2003 Networks Associates Technology, Inc. + * Copyright (c) 2004-2011 Dag-Erling Smørgrav * All rights reserved. * * Portions of this software were developed for the FreeBSD Project by @@ -56,6 +57,7 @@ PAM_EXTERN int pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, int argc __unused, const char *argv[] __unused) { + int local, remote; const char *group, *user; const void *ruser; char *const *list; @@ -69,10 +71,24 @@ pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, if (pwd->pw_uid != 0 && openpam_get_option(pamh, "root_only")) return (PAM_IGNORE); - /* get applicant */ - if (pam_get_item(pamh, PAM_RUSER, &ruser) != PAM_SUCCESS - || ruser == NULL || (pwd = getpwnam(ruser)) == NULL) - return (PAM_AUTH_ERR); + /* check local / remote */ + local = openpam_get_option(pamh, "luser") ? 1 : 0; + remote = openpam_get_option(pamh, "ruser") ? 1 : 0; + if (local && remote) { + openpam_log(PAM_LOG_ERROR, + "the luser and ruser options are mutually exclusive"); + return (PAM_SERVICE_ERR); + } else if (local) { + /* we already have the correct struct passwd */ + } else { + if (!remote) + openpam_log(PAM_LOG_NOTICE, + "neither luser nor ruser specified, assuming ruser"); + /* default / historical behavior */ + if (pam_get_item(pamh, PAM_RUSER, &ruser) != PAM_SUCCESS || + ruser == NULL || (pwd = getpwnam(ruser)) == NULL) + return (PAM_AUTH_ERR); + } /* get regulating group */ if ((group = openpam_get_option(pamh, "group")) == NULL)