diff options
author | Steve Langasek <steve.langasek@ubuntu.com> | 2019-01-03 12:44:11 -0800 |
---|---|---|
committer | Steve Langasek <steve.langasek@ubuntu.com> | 2019-01-03 12:44:11 -0800 |
commit | efd31890b5ed496a5a00c08a262da240e66a4ddc (patch) | |
tree | 22a7aab22b3a491bb58df250d7d6409e0c160bcc /modules/pam_cracklib/pam_cracklib.c | |
parent | 067affee9267fa0d1c21835182ba639ba33e820f (diff) | |
download | pam-efd31890b5ed496a5a00c08a262da240e66a4ddc.tar.gz pam-efd31890b5ed496a5a00c08a262da240e66a4ddc.tar.bz2 pam-efd31890b5ed496a5a00c08a262da240e66a4ddc.zip |
New upstream version 0.76
Diffstat (limited to 'modules/pam_cracklib/pam_cracklib.c')
-rw-r--r-- | modules/pam_cracklib/pam_cracklib.c | 888 |
1 files changed, 0 insertions, 888 deletions
diff --git a/modules/pam_cracklib/pam_cracklib.c b/modules/pam_cracklib/pam_cracklib.c deleted file mode 100644 index bc98d2f6..00000000 --- a/modules/pam_cracklib/pam_cracklib.c +++ /dev/null @@ -1,888 +0,0 @@ -/* - * pam_cracklib module - * $Id$ - */ - -/* - * 0.9. switch to using a distance algorithm in similar() - * 0.86. added support for setting minimum numbers of digits, uppers, - * lowers, and others - * 0.85. added six new options to use this with long passwords. - * 0.8. tidied output and improved D(()) usage for debugging. - * 0.7. added support for more obscure checks for new passwd. - * 0.6. root can reset user passwd to any values (it's only warned) - * 0.5. supports retries - 'retry=N' argument - * 0.4. added argument 'type=XXX' for 'New XXX password' prompt - * 0.3. Added argument 'debug' - * 0.2. new password is feeded to cracklib for verify after typed once - * 0.1. First release - */ - -/* - * Written by Cristian Gafton <gafton@redhat.com> 1996/09/10 - * Long password support by Philip W. Dalrymple <pwd@mdtsoft.com> 1997/07/18 - * See the end of the file for Copyright Information - * - * Modification for long password systems (>8 chars). The original - * module had problems when used in a md5 password system in that it - * allowed too short passwords but required that at least half of the - * bytes in the new password did not appear in the old one. this - * action is still the default and the changes should not break any - * current user. This modification adds 6 new options, one to set the - * number of bytes in the new password that are not in the old one, - * the other five to control the length checking, these are all - * documented (or will be before anyone else sees this code) in the PAM - * S.A.G. in the section on the cracklib module. - */ - -#include <security/_pam_aconf.h> - -#include <stdio.h> -#ifdef HAVE_CRYPT_H -# include <crypt.h> -#endif -#include <unistd.h> -#include <stdlib.h> -#include <string.h> -#include <syslog.h> -#include <stdarg.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <ctype.h> - -extern char *FascistCheck(char *pw, const char *dictpath); - -#ifndef CRACKLIB_DICTPATH -#define CRACKLIB_DICTPATH "/usr/share/dict/cracklib_dict" -#endif - -#define PROMPT1 "New %s%spassword: " -#define PROMPT2 "Retype new %s%spassword: " -#define MISTYPED_PASS "Sorry, passwords do not match" - -#ifdef MIN -#undef MIN -#endif -#define MIN(_a, _b) (((_a) < (_b)) ? (_a) : (_b)) - -/* - * here, we make a definition for the externally accessible function - * in this file (this definition is required for static a module - * but strongly encouraged generally) it is used to instruct the - * modules include file to define the function prototypes. - */ - -#define PAM_SM_PASSWORD - -#include <security/pam_modules.h> -#include <security/_pam_macros.h> - -#ifndef LINUX_PAM -#include <security/pam_appl.h> -#endif /* LINUX_PAM */ - -/* some syslogging */ - -static void _pam_log(int err, const char *format, ...) -{ - va_list args; - - va_start(args, format); - openlog("PAM-Cracklib", LOG_CONS|LOG_PID, LOG_AUTH); - vsyslog(err, format, args); - va_end(args); - closelog(); -} - -/* argument parsing */ -#define PAM_DEBUG_ARG 0x0001 - -struct cracklib_options { - int retry_times; - int diff_ok; - int diff_ignore; - int min_length; - int dig_credit; - int up_credit; - int low_credit; - int oth_credit; - int use_authtok; - char prompt_type[BUFSIZ]; -}; - -#define CO_RETRY_TIMES 1 -#define CO_DIFF_OK 5 -#define CO_DIFF_IGNORE 23 -#define CO_MIN_LENGTH 9 -# define CO_MIN_LENGTH_BASE 5 -#define CO_DIG_CREDIT 1 -#define CO_UP_CREDIT 1 -#define CO_LOW_CREDIT 1 -#define CO_OTH_CREDIT 1 -#define CO_USE_AUTHTOK 0 - -static int _pam_parse(struct cracklib_options *opt, int argc, const char **argv) -{ - int ctrl=0; - - /* step through arguments */ - for (ctrl=0; argc-- > 0; ++argv) { - char *ep = NULL; - - /* generic options */ - - if (!strcmp(*argv,"debug")) - ctrl |= PAM_DEBUG_ARG; - else if (!strncmp(*argv,"type=",5)) - strncpy(opt->prompt_type, *argv+5, sizeof(opt->prompt_type) - 1); - else if (!strncmp(*argv,"retry=",6)) { - opt->retry_times = strtol(*argv+6,&ep,10); - if (!ep || (opt->retry_times < 1)) - opt->retry_times = CO_RETRY_TIMES; - } else if (!strncmp(*argv,"difok=",6)) { - opt->diff_ok = strtol(*argv+6,&ep,10); - if (!ep || (opt->diff_ok < 0)) - opt->diff_ok = CO_DIFF_OK; - } else if (!strncmp(*argv,"difignore=",10)) { - opt->diff_ignore = strtol(*argv+10,&ep,10); - if (!ep || (opt->diff_ignore < 0)) - opt->diff_ignore = CO_DIFF_IGNORE; - } else if (!strncmp(*argv,"minlen=",7)) { - opt->min_length = strtol(*argv+7,&ep,10); - if (!ep || (opt->min_length < CO_MIN_LENGTH_BASE)) - opt->min_length = CO_MIN_LENGTH_BASE; - } else if (!strncmp(*argv,"dcredit=",8)) { - opt->dig_credit = strtol(*argv+8,&ep,10); - if (!ep) - opt->dig_credit = 0; - } else if (!strncmp(*argv,"ucredit=",8)) { - opt->up_credit = strtol(*argv+8,&ep,10); - if (!ep) - opt->up_credit = 0; - } else if (!strncmp(*argv,"lcredit=",8)) { - opt->low_credit = strtol(*argv+8,&ep,10); - if (!ep) - opt->low_credit = 0; - } else if (!strncmp(*argv,"ocredit=",8)) { - opt->oth_credit = strtol(*argv+8,&ep,10); - if (!ep) - opt->oth_credit = 0; - } else if (!strncmp(*argv,"use_authtok",11)) { - opt->use_authtok = 1; - } else { - _pam_log(LOG_ERR,"pam_parse: unknown option; %s",*argv); - } - } - opt->prompt_type[sizeof(opt->prompt_type) - 1] = '\0'; - - return ctrl; -} - -/* Helper functions */ - -/* this is a front-end for module-application conversations */ -static int converse(pam_handle_t *pamh, int ctrl, int nargs, - struct pam_message **message, - struct pam_response **response) -{ - int retval; - struct pam_conv *conv; - - retval = pam_get_item(pamh, PAM_CONV, (const void **) &conv); - - if ( retval == PAM_SUCCESS ) { - retval = conv->conv(nargs, (const struct pam_message **)message, - response, conv->appdata_ptr); - if (retval != PAM_SUCCESS && (ctrl && PAM_DEBUG_ARG)) { - _pam_log(LOG_DEBUG, "conversation failure [%s]", - pam_strerror(pamh, retval)); - } - } else { - _pam_log(LOG_ERR, "couldn't obtain coversation function [%s]", - pam_strerror(pamh, retval)); - } - - return retval; /* propagate error status */ -} - -static int make_remark(pam_handle_t *pamh, unsigned int ctrl, - int type, const char *text) -{ - struct pam_message *pmsg[1], msg[1]; - struct pam_response *resp; - int retval; - - pmsg[0] = &msg[0]; - msg[0].msg = text; - msg[0].msg_style = type; - resp = NULL; - - retval = converse(pamh, ctrl, 1, pmsg, &resp); - if (retval == PAM_SUCCESS) - _pam_drop_reply(resp, 1); - - return retval; -} - -/* use this to free strings. ESPECIALLY password strings */ -static char *_pam_delete(register char *xx) -{ - _pam_overwrite(xx); - free(xx); - return NULL; -} - -/* - * can't be a palindrome - like `R A D A R' or `M A D A M' - */ -static int palindrome(const char *old, const char *new) -{ - int i, j; - - i = strlen (new); - - for (j = 0;j < i;j++) - if (new[i - j - 1] != new[j]) - return 0; - - return 1; -} - -/* - * Calculate how different two strings are in terms of the number of - * character removals, additions, and changes needed to go from one to - * the other - */ - -static int distdifferent(const char *old, const char *new, int i, int j) -{ - char c, d; - - if ((i == 0) || (strlen(old) <= i)) { - c = 0; - } else { - c = old[i - 1]; - } - if ((j == 0) || (strlen(new) <= i)) { - d = 0; - } else { - d = new[j - 1]; - } - return (c != d); -} - -static int distcalculate(int **distances, const char *old, const char *new, - int i, int j) -{ - int tmp = 0; - - if (distances[i][j] != -1) { - return distances[i][j]; - } - - tmp = distcalculate(distances, old, new, i - 1, j - 1); - tmp = MIN(tmp, distcalculate(distances, old, new, i, j - 1)); - tmp = MIN(tmp, distcalculate(distances, old, new, i - 1, j)); - tmp += distdifferent(old, new, i, j); - - distances[i][j] = tmp; - - return tmp; -} - -static int distance(const char *old, const char *new) -{ - int **distances = NULL; - int m, n, i, j, r; - - m = strlen(old); - n = strlen(new); - distances = malloc(sizeof(int*) * (m + 1)); - - for (i = 0; i <= m; i++) { - distances[i] = malloc(sizeof(int) * (n + 1)); - for(j = 0; j <= n; j++) { - distances[i][j] = -1; - } - } - for (i = 0; i <= m; i++) { - distances[i][0] = i; - } - for (j = 0; j <= n; j++) { - distances[0][j] = j; - } - distances[0][0] = 0; - - r = distcalculate(distances, old, new, m, n); - - for (i = 0; i <= m; i++) { - memset(distances[i], 0, sizeof(int) * (n + 1)); - free(distances[i]); - } - free(distances); - - return r; -} - -static int similar(struct cracklib_options *opt, - const char *old, const char *new) -{ - if (distance(old, new) >= opt->diff_ok) { - return 0; - } - - if (strlen(new) >= (strlen(old) * 2)) { - return 0; - } - - /* passwords are too similar */ - return 1; -} - -/* - * a nice mix of characters. - */ -static int simple(struct cracklib_options *opt, - const char *old, const char *new) -{ - int digits = 0; - int uppers = 0; - int lowers = 0; - int others = 0; - int size; - int i; - - for (i = 0;new[i];i++) { - if (isdigit (new[i])) - digits++; - else if (isupper (new[i])) - uppers++; - else if (islower (new[i])) - lowers++; - else - others++; - } - - /* - * The scam was this - a password of only one character type - * must be 8 letters long. Two types, 7, and so on. - * This is now changed, the base size and the credits or defaults - * see the docs on the module for info on these parameters, the - * defaults cause the effect to be the same as before the change - */ - - if ((opt->dig_credit >= 0) && (digits > opt->dig_credit)) - digits = opt->dig_credit; - - if ((opt->up_credit >= 0) && (uppers > opt->up_credit)) - uppers = opt->up_credit; - - if ((opt->low_credit >= 0) && (lowers > opt->low_credit)) - lowers = opt->low_credit; - - if ((opt->oth_credit >= 0) && (others > opt->oth_credit)) - others = opt->oth_credit; - - size = opt->min_length; - - if (opt->dig_credit >= 0) - size -= digits; - else if (digits < opt->dig_credit * -1) - return 1; - - if (opt->up_credit >= 0) - size -= uppers; - else if (uppers < opt->up_credit * -1) - return 1; - - if (opt->low_credit >= 0) - size -= lowers; - else if (lowers < opt->low_credit * -1) - return 1; - - if (opt->oth_credit >= 0) - size -= others; - else if (others < opt->oth_credit * -1) - return 1; - - if (size <= i) - return 0; - - return 1; -} - -static char * str_lower(char *string) -{ - char *cp; - - for (cp = string; *cp; cp++) - *cp = tolower(*cp); - return string; -} - -static const char * password_check(struct cracklib_options *opt, const char *old, const char *new) -{ - const char *msg = NULL; - char *oldmono, *newmono, *wrapped; - - if (strcmp(new, old) == 0) { - msg = "is the same as the old one"; - return msg; - } - - newmono = str_lower(x_strdup(new)); - oldmono = str_lower(x_strdup(old)); - wrapped = malloc(strlen(oldmono) * 2 + 1); - strcpy (wrapped, oldmono); - strcat (wrapped, oldmono); - - if (palindrome(oldmono, newmono)) - msg = "is a palindrome"; - - if (!msg && strcmp(oldmono, newmono) == 0) - msg = "case changes only"; - - if (!msg && similar(opt, oldmono, newmono)) - msg = "is too similar to the old one"; - - if (!msg && simple(opt, old, new)) - msg = "is too simple"; - - if (!msg && strstr(wrapped, newmono)) - msg = "is rotated"; - - memset(newmono, 0, strlen(newmono)); - memset(oldmono, 0, strlen(oldmono)); - memset(wrapped, 0, strlen(wrapped)); - free(newmono); - free(oldmono); - free(wrapped); - - return msg; -} - - -#define OLD_PASSWORDS_FILE "/etc/security/opasswd" - -static const char * check_old_password(const char *forwho, const char *newpass) -{ - static char buf[16384]; - char *s_luser, *s_uid, *s_npas, *s_pas; - const char *msg = NULL; - FILE *opwfile; - - opwfile = fopen(OLD_PASSWORDS_FILE, "r"); - if (opwfile == NULL) - return NULL; - - while (fgets(buf, 16380, opwfile)) { - if (!strncmp(buf, forwho, strlen(forwho))) { - buf[strlen(buf)-1] = '\0'; - s_luser = strtok(buf, ":,"); - s_uid = strtok(NULL, ":,"); - s_npas = strtok(NULL, ":,"); - s_pas = strtok(NULL, ":,"); - while (s_pas != NULL) { - if (!strcmp(crypt(newpass, s_pas), s_pas)) { - msg = "has been already used"; - break; - } - s_pas = strtok(NULL, ":,"); - } - break; - } - } - fclose(opwfile); - - return msg; -} - - -static int _pam_unix_approve_pass(pam_handle_t *pamh, - unsigned int ctrl, - struct cracklib_options *opt, - const char *pass_old, - const char *pass_new) -{ - const char *msg = NULL; - const char *user; - int retval; - - if (pass_new == NULL || (pass_old && !strcmp(pass_old,pass_new))) { - if (ctrl && PAM_DEBUG_ARG) - _pam_log(LOG_DEBUG, "bad authentication token"); - make_remark(pamh, ctrl, PAM_ERROR_MSG, - pass_new == NULL ? - "No password supplied":"Password unchanged" ); - return PAM_AUTHTOK_ERR; - } - - /* - * if one wanted to hardwire authentication token strength - * checking this would be the place - */ - msg = password_check(opt, pass_old,pass_new); - if (!msg) { - retval = pam_get_item(pamh, PAM_USER, (const void **)&user); - if (retval != PAM_SUCCESS) { - if (ctrl & PAM_DEBUG_ARG) { - _pam_log(LOG_ERR,"Can not get username"); - return PAM_AUTHTOK_ERR; - } - } - msg = check_old_password(user, pass_new); - } - - if (msg) { - char remark[BUFSIZ]; - - memset(remark,0,sizeof(remark)); - snprintf(remark,sizeof(remark),"BAD PASSWORD: %s",msg); - if (ctrl && PAM_DEBUG_ARG) - _pam_log(LOG_NOTICE, "new passwd fails strength check: %s", - msg); - make_remark(pamh, ctrl, PAM_ERROR_MSG, remark); - return PAM_AUTHTOK_ERR; - }; - return PAM_SUCCESS; - -} - -/* The Main Thing (by Cristian Gafton, CEO at this module :-) - * (stolen from http://home.netscape.com) - */ -PAM_EXTERN int pam_sm_chauthtok(pam_handle_t *pamh, int flags, - int argc, const char **argv) -{ - unsigned int ctrl; - struct cracklib_options options; - - D(("called.")); - - options.retry_times = CO_RETRY_TIMES; - options.diff_ok = CO_DIFF_OK; - options.diff_ignore = CO_DIFF_IGNORE; - options.min_length = CO_MIN_LENGTH; - options.dig_credit = CO_DIG_CREDIT; - options.up_credit = CO_UP_CREDIT; - options.low_credit = CO_LOW_CREDIT; - options.oth_credit = CO_OTH_CREDIT; - options.use_authtok = CO_USE_AUTHTOK; - memset(options.prompt_type, 0, BUFSIZ); - strcpy(options.prompt_type,"UNIX"); - - ctrl = _pam_parse(&options, argc, argv); - - if (flags & PAM_PRELIM_CHECK) { - /* Check for passwd dictionary */ - struct stat st; - char buf[sizeof(CRACKLIB_DICTPATH)+10]; - - D(("prelim check")); - - memset(buf,0,sizeof(buf)); /* zero the buffer */ - snprintf(buf,sizeof(buf),"%s.pwd",CRACKLIB_DICTPATH); - - if (!stat(buf,&st) && st.st_size) - return PAM_SUCCESS; - else { - if (ctrl & PAM_DEBUG_ARG) - _pam_log(LOG_NOTICE,"dict path '%s'[.pwd] is invalid", - CRACKLIB_DICTPATH); - return PAM_ABORT; - } - - /* Not reached */ - return PAM_SERVICE_ERR; - - } else if (flags & PAM_UPDATE_AUTHTOK) { - int retval; - char *token1, *token2, *oldtoken; - struct pam_message msg[1],*pmsg[1]; - struct pam_response *resp; - const char *cracklib_dictpath = CRACKLIB_DICTPATH; - char prompt[BUFSIZ]; - - D(("do update")); - retval = pam_get_item(pamh, PAM_OLDAUTHTOK, - (const void **)&oldtoken); - if (retval != PAM_SUCCESS) { - if (ctrl & PAM_DEBUG_ARG) - _pam_log(LOG_ERR,"Can not get old passwd"); - oldtoken=NULL; - retval = PAM_SUCCESS; - } - - do { - /* - * make sure nothing inappropriate gets returned - */ - token1 = token2 = NULL; - - if (!options.retry_times) { - D(("returning %s because maxtries reached", - pam_strerror(pamh, retval))); - return retval; - } - - /* Planned modus operandi: - * Get a passwd. - * Verify it against cracklib. - * If okay get it a second time. - * Check to be the same with the first one. - * set PAM_AUTHTOK and return - */ - - if (options.use_authtok == 1) { - const char *item = NULL; - - retval = pam_get_item(pamh, PAM_AUTHTOK, (const void **) &item); - if (retval != PAM_SUCCESS) { - /* very strange. */ - _pam_log(LOG_ALERT - ,"pam_get_item returned error to pam_cracklib" - ); - } else if (item != NULL) { /* we have a password! */ - token1 = x_strdup(item); - item = NULL; - } else { - retval = PAM_AUTHTOK_RECOVER_ERR; /* didn't work */ - } - - } else { - /* Prepare to ask the user for the first time */ - memset(prompt,0,sizeof(prompt)); - snprintf(prompt,sizeof(prompt),PROMPT1, - options.prompt_type, options.prompt_type[0]?" ":""); - pmsg[0] = &msg[0]; - msg[0].msg_style = PAM_PROMPT_ECHO_OFF; - msg[0].msg = prompt; - - resp = NULL; - retval = converse(pamh, ctrl, 1, pmsg, &resp); - if (resp != NULL) { - /* interpret the response */ - if (retval == PAM_SUCCESS) { /* a good conversation */ - token1 = x_strdup(resp[0].resp); - if (token1 == NULL) { - _pam_log(LOG_NOTICE, - "could not recover authentication token 1"); - retval = PAM_AUTHTOK_RECOVER_ERR; - } - } - /* - * tidy up the conversation (resp_retcode) is ignored - */ - _pam_drop_reply(resp, 1); - } else { - retval = (retval == PAM_SUCCESS) ? - PAM_AUTHTOK_RECOVER_ERR:retval ; - } - } - - if (retval != PAM_SUCCESS) { - if (ctrl && PAM_DEBUG_ARG) - _pam_log(LOG_DEBUG,"unable to obtain a password"); - continue; - } - - D(("testing password, retval = %s", pam_strerror(pamh, retval))); - /* now test this passwd against cracklib */ - { - char *crack_msg; - char remark[BUFSIZ]; - - bzero(remark,sizeof(remark)); - D(("against cracklib")); - if ((crack_msg = FascistCheck(token1, cracklib_dictpath))) { - if (ctrl && PAM_DEBUG_ARG) - _pam_log(LOG_DEBUG,"bad password: %s",crack_msg); - snprintf(remark,sizeof(remark),"BAD PASSWORD: %s", crack_msg); - make_remark(pamh, ctrl, PAM_ERROR_MSG, remark); - if (getuid() || (flags & PAM_CHANGE_EXPIRED_AUTHTOK)) - retval = PAM_AUTHTOK_ERR; - else - retval = PAM_SUCCESS; - } else { - /* check it for strength too... */ - D(("for strength")); - if (oldtoken) { - retval = _pam_unix_approve_pass(pamh,ctrl,&options, - oldtoken,token1); - if (retval != PAM_SUCCESS) { - if (getuid() || (flags & PAM_CHANGE_EXPIRED_AUTHTOK)) - retval = PAM_AUTHTOK_ERR; - else - retval = PAM_SUCCESS; - } - } - } - } - - D(("after testing: retval = %s", pam_strerror(pamh, retval))); - /* if cracklib/strength check said it is a bad passwd... */ - if ((retval != PAM_SUCCESS) && (retval != PAM_IGNORE)) { - int temp_unused; - - temp_unused = pam_set_item(pamh, PAM_AUTHTOK, NULL); - token1 = _pam_delete(token1); - continue; - } - - /* Now we have a good passwd. Ask for it once again */ - - if (options.use_authtok == 0) { - bzero(prompt,sizeof(prompt)); - snprintf(prompt,sizeof(prompt),PROMPT2, - options.prompt_type, options.prompt_type[0]?" ":""); - pmsg[0] = &msg[0]; - msg[0].msg_style = PAM_PROMPT_ECHO_OFF; - msg[0].msg = prompt; - - resp = NULL; - retval = converse(pamh, ctrl, 1, pmsg, &resp); - if (resp != NULL) { - /* interpret the response */ - if (retval == PAM_SUCCESS) { /* a good conversation */ - token2 = x_strdup(resp[0].resp); - if (token2 == NULL) { - _pam_log(LOG_NOTICE, - "could not recover authentication token 2"); - retval = PAM_AUTHTOK_RECOVER_ERR; - } - } - /* - * tidy up the conversation (resp_retcode) is ignored - */ - _pam_drop_reply(resp, 1); - } else { - retval = (retval == PAM_SUCCESS) ? - PAM_AUTHTOK_RECOVER_ERR:retval ; - } - - if (retval != PAM_SUCCESS) { - if (ctrl && PAM_DEBUG_ARG) - _pam_log(LOG_DEBUG - ,"unable to obtain the password a second time"); - continue; - } - - /* Hopefully now token1 and token2 the same password ... */ - if (strcmp(token1,token2) != 0) { - /* tell the user */ - make_remark(pamh, ctrl, PAM_ERROR_MSG, MISTYPED_PASS); - token1 = _pam_delete(token1); - token2 = _pam_delete(token2); - pam_set_item(pamh, PAM_AUTHTOK, NULL); - if (ctrl & PAM_DEBUG_ARG) - _pam_log(LOG_NOTICE,"Password mistyped"); - retval = PAM_AUTHTOK_RECOVER_ERR; - continue; - } - - /* Yes, the password was typed correct twice - * we store this password as an item - */ - - { - const char *item = NULL; - - retval = pam_set_item(pamh, PAM_AUTHTOK, token1); - - /* clean up */ - token1 = _pam_delete(token1); - token2 = _pam_delete(token2); - - if ( (retval != PAM_SUCCESS) || - ((retval = pam_get_item(pamh, PAM_AUTHTOK, - (const void **)&item) - ) != PAM_SUCCESS) ) { - _pam_log(LOG_CRIT, "error manipulating password"); - continue; - } - item = NULL; /* break link to password */ - return PAM_SUCCESS; - } - } - - } while (options.retry_times--); - - } else { - if (ctrl & PAM_DEBUG_ARG) - _pam_log(LOG_NOTICE, "UNKNOWN flags setting %02X",flags); - return PAM_SERVICE_ERR; - } - - /* Not reached */ - return PAM_SERVICE_ERR; -} - - - -#ifdef PAM_STATIC -/* static module data */ -struct pam_module _pam_cracklib_modstruct = { - "pam_cracklib", - NULL, - NULL, - NULL, - NULL, - NULL, - pam_sm_chauthtok -}; -#endif - -/* - * Copyright (c) Cristian Gafton <gafton@redhat.com>, 1996. - * All rights reserved - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, and the entire permission notice in its entirety, - * including the disclaimer of warranties. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. The name of the author may not be used to endorse or promote - * products derived from this software without specific prior - * written permission. - * - * ALTERNATIVELY, this product may be distributed under the terms of - * the GNU Public License, in which case the provisions of the GPL are - * required INSTEAD OF the above restrictions. (This clause is - * necessary due to a potential bad interaction between the GPL and - * the restrictions contained in a BSD-style copyright.) - * - * THIS SOFTWARE IS PROVIDED `AS IS'' AND ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES - * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, - * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED - * OF THE POSSIBILITY OF SUCH DAMAGE. - * - * The following copyright was appended for the long password support - * added with the libpam 0.58 release: - * - * Modificaton Copyright (c) Philip W. Dalrymple III <pwd@mdtsoft.com> - * 1997. All rights reserved - * - * THE MODIFICATION THAT PROVIDES SUPPORT FOR LONG PASSWORD TYPE CHECKING TO - * THIS SOFTWARE IS PROVIDED `AS IS'' AND ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES - * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, - * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED - * OF THE POSSIBILITY OF SUCH DAMAGE. - */ |