diff options
Diffstat (limited to 'modules/pam_pwdb')
-rw-r--r-- | modules/pam_pwdb/pwdb_chkpwd.c | 24 | ||||
-rw-r--r-- | modules/pam_pwdb/support.-c | 13 |
2 files changed, 28 insertions, 9 deletions
diff --git a/modules/pam_pwdb/pwdb_chkpwd.c b/modules/pam_pwdb/pwdb_chkpwd.c index fdd3cfa3..36cf0984 100644 --- a/modules/pam_pwdb/pwdb_chkpwd.c +++ b/modules/pam_pwdb/pwdb_chkpwd.c @@ -83,12 +83,12 @@ static int _unix_verify_passwd(const char *salt, const char *p) return retval; } -int main(void) +int main(int argc, char **argv) { const struct pwdb *pw=NULL; const struct pwdb_entry *pwe=NULL; char pass[MAXPASS+1]; - int npass; + int npass, force_failure=0; int retval=UNIX_FAILED; /* @@ -120,14 +120,26 @@ int main(void) retval = UNIX_FAILED; } if (retval != UNIX_FAILED) { - retval = pwdb_locate("user", PWDB_DEFAULT, PWDB_NAME_UNKNOWN - , getuid(), &pw); + retval = pwdb_locate("user", PWDB_DEFAULT, PWDB_NAME_UNKNOWN, + getuid(), &pw); } if (retval != PWDB_SUCCESS) { _log_err(LOG_ALERT, "could not identify user"); while (pwdb_end() != PWDB_SUCCESS); exit(UNIX_FAILED); } + if (argc == 2) { + if (pwdb_get_entry(pw, "user", &pwe) == PWDB_SUCCESS) { + if (pwe == NULL) { + force_failure = 1; + } else { + if (strcmp((const char *) pwe->value, argv[1])) { + force_failure = 1; + } + pwdb_entry_delete(&pwe); + } + } + } /* read the password from stdin (a pipe from the pam_pwdb module) */ @@ -158,6 +170,10 @@ int main(void) memset(pass, '\0', MAXPASS); /* clear memory of the password */ while (pwdb_end() != PWDB_SUCCESS); + if ((retval != UNIX_FAILED) && force_failure) { + retval = UNIX_FAILED; + } + /* return pass or fail */ exit(retval); diff --git a/modules/pam_pwdb/support.-c b/modules/pam_pwdb/support.-c index d43e0554..bbaa51ac 100644 --- a/modules/pam_pwdb/support.-c +++ b/modules/pam_pwdb/support.-c @@ -345,7 +345,8 @@ static void _cleanup_failures(pam_handle_t *pamh, void *fl, int err) #include <sys/types.h> #include <sys/wait.h> -static int pwdb_run_helper_binary(pam_handle_t *pamh, const char *passwd) +static int pwdb_run_helper_binary(pam_handle_t *pamh, const char *passwd, + const char *user) { int retval, child, fds[2]; @@ -359,7 +360,7 @@ static int pwdb_run_helper_binary(pam_handle_t *pamh, const char *passwd) /* fork */ child = fork(); if (child == 0) { - static char *args[] = { NULL, NULL }; + static char *args[] = { NULL, NULL, NULL }; static char *envp[] = { NULL }; /* XXX - should really tidy up PAM here too */ @@ -371,6 +372,8 @@ static int pwdb_run_helper_binary(pam_handle_t *pamh, const char *passwd) /* exec binary helper */ args[0] = x_strdup(CHKPWD_HELPER); + args[1] = x_strdup(user); + execve(CHKPWD_HELPER, args, envp); /* should not get here: exit with error */ @@ -398,8 +401,8 @@ static int pwdb_run_helper_binary(pam_handle_t *pamh, const char *passwd) return retval; } -static int _unix_verify_password(pam_handle_t *pamh, const char *name - , const char *p, unsigned int ctrl) +static int _unix_verify_password(pam_handle_t *pamh, const char *name, + const char *p, unsigned int ctrl) { const struct pwdb *pw=NULL; const struct pwdb_entry *pwe=NULL; @@ -465,7 +468,7 @@ static int _unix_verify_password(pam_handle_t *pamh, const char *name if (geteuid()) { /* we are not root perhaps this is the reason? Run helper */ D(("running helper binary")); - retval = pwdb_run_helper_binary(pamh, p); + retval = pwdb_run_helper_binary(pamh, p, name); } else { retval = PAM_AUTHINFO_UNAVAIL; _log_err(LOG_ALERT, "get passwd; %s", pwdb_strerror(retval)); |