summaryrefslogtreecommitdiff
path: root/usr/src/lib/pam_modules
diff options
context:
space:
mode:
authorMike Zeller <mike@mikezeller.net>2020-04-30 12:05:53 -0400
committerMike Zeller <mike@mikezeller.net>2020-04-30 12:05:53 -0400
commitac392c47376cdb46e02be40735cc74d5d100fe6c (patch)
tree450ea4b694961d00606485aa323234bb2ad69851 /usr/src/lib/pam_modules
parent95a46e0bd62ba0e68db9fa0b958dc5313920e6fe (diff)
parent0f8413a98e7949bf0a6a2c24153f2928c7eb5cfb (diff)
downloadillumos-joyent-OS-8165.tar.gz
Merge branch 'master' into OS-8165OS-8165
Diffstat (limited to 'usr/src/lib/pam_modules')
-rw-r--r--usr/src/lib/pam_modules/list/list.c56
1 files changed, 52 insertions, 4 deletions
diff --git a/usr/src/lib/pam_modules/list/list.c b/usr/src/lib/pam_modules/list/list.c
index 185a451246..234f709a36 100644
--- a/usr/src/lib/pam_modules/list/list.c
+++ b/usr/src/lib/pam_modules/list/list.c
@@ -33,6 +33,7 @@
#include <malloc.h>
#include <unistd.h>
#include <errno.h>
+#include <grp.h>
#include <security/pam_appl.h>
#include <security/pam_modules.h>
#include <security/pam_impl.h>
@@ -68,24 +69,34 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
char buf[BUFSIZ];
char hostname[MAXHOSTNAMELEN];
char *username = NULL;
+ char *grbuf = NULL;
char *bufp;
char *rhost;
- char *limit;
+ char *limit;
int userok = 0;
int hostok = 0;
int i;
int allow_deny_test = 0;
+ long grbuflen = 0;
boolean_t debug = B_FALSE;
boolean_t allow = B_FALSE;
boolean_t matched = B_FALSE;
boolean_t check_user = B_TRUE;
+ boolean_t check_group = B_FALSE;
boolean_t check_host = B_FALSE;
boolean_t check_exact = B_FALSE;
pam_list_mode_t op_mode = LIST_PLUS_CHECK;
+ // group reentrant interfaces limits
+ if ((grbuflen = sysconf(_SC_GETGR_R_SIZE_MAX)) <= 0)
+ return (PAM_BUF_ERR);
+
for (i = 0; i < argc; ++i) {
if (strncasecmp(argv[i], "debug", sizeof ("debug")) == 0) {
debug = B_TRUE;
+ } else if (strncasecmp(argv[i], "group",
+ sizeof ("group")) == 0) {
+ check_group = B_TRUE;
} else if (strncasecmp(argv[i], "user", sizeof ("user")) == 0) {
check_user = B_TRUE;
} else if (strncasecmp(argv[i], "nouser",
@@ -140,8 +151,8 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
}
}
- if (((check_user || check_host || check_exact) == B_FALSE) ||
- (allow_deny_test > 1)) {
+ if (((check_user || check_group || check_host ||
+ check_exact) == B_FALSE) || (allow_deny_test > 1)) {
__pam_log(LOG_AUTH | LOG_ERR, ILLEGAL_COMBINATION);
return (PAM_SERVICE_ERR);
}
@@ -151,6 +162,11 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
return (PAM_SERVICE_ERR);
}
+ if ((op_mode == LIST_COMPAT_MODE) && (check_group == B_TRUE)) {
+ log_illegal_combination("compat", "group");
+ return (PAM_SERVICE_ERR);
+ }
+
if (debug) {
__pam_log(LOG_AUTH | LOG_DEBUG,
"pam_list: check_user = %d, check_host = %d,"
@@ -165,7 +181,7 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
(void) pam_get_item(pamh, PAM_USER, (void**)&username);
- if ((check_user || check_exact) && ((username == NULL) ||
+ if ((check_user || check_group || check_exact) && ((username == NULL) ||
(*username == '\0'))) {
__pam_log(LOG_AUTH | LOG_ERR,
"pam_list: username not supplied, critical error");
@@ -203,6 +219,12 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
return (PAM_SERVICE_ERR);
}
+ if (check_group && ((grbuf = calloc(1, grbuflen)) == NULL)) {
+ __pam_log(LOG_AUTH | LOG_ERR,
+ "pam_list: could not allocate memory for group");
+ return (PAM_BUF_ERR);
+ }
+
while (fgets(buf, BUFSIZ, fd) != NULL) {
/* lines longer than BUFSIZ-1 */
if ((strlen(buf) == (BUFSIZ - 1)) &&
@@ -242,6 +264,7 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
"pam_list: simple minus unknown, "
"illegal line in " PF_PATH);
(void) fclose(fd);
+ free(grbuf);
return (PAM_SERVICE_ERR);
}
@@ -251,6 +274,7 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
"pam_list: @ is not allowed on the first "
"position in " PF_PATH);
(void) fclose(fd);
+ free(grbuf);
return (PAM_SERVICE_ERR);
}
@@ -282,6 +306,7 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
/*
* if -> netgroup line
+ * else if -> group line
* else -> user line
*/
if ((bufp[0] == '@') && (bufp[1] != '\0')) {
@@ -311,6 +336,28 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
break;
}
}
+ } else if ((bufp[0] == '%') && (bufp[1] != '\0')) {
+ char **member;
+ struct group grp;
+
+ if (check_group == B_FALSE)
+ continue;
+
+ bufp++;
+
+ if (getgrnam_r(bufp, &grp, grbuf, grbuflen) != NULL) {
+ for (member = grp.gr_mem; *member != NULL;
+ member++) {
+ if (strcmp(*member, username) == 0) {
+ matched = B_TRUE;
+ break;
+ }
+ }
+ } else {
+ __pam_log(LOG_AUTH | LOG_ERR,
+ "pam_list: %s is not a known group",
+ bufp);
+ }
} else {
if (check_user) {
if (strcmp(bufp, username) == 0) {
@@ -331,6 +378,7 @@ pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int argc, const char **argv)
}
}
(void) fclose(fd);
+ free(grbuf);
if (debug) {
__pam_log(LOG_AUTH | LOG_DEBUG,