diff options
author | Andrew G. Morgan <morgan@kernel.org> | 2000-11-25 03:27:39 +0000 |
---|---|---|
committer | Andrew G. Morgan <morgan@kernel.org> | 2000-11-25 03:27:39 +0000 |
commit | 4ea47216da66274357b14d5d7488ccbde27d75c4 (patch) | |
tree | 5b73492bf55a8a46c8a68e09c4e6a55479ed9028 | |
parent | ae282c2b26cfacb4e850d1258b851f125eca221a (diff) | |
download | pam-4ea47216da66274357b14d5d7488ccbde27d75c4.tar.gz pam-4ea47216da66274357b14d5d7488ccbde27d75c4.tar.bz2 pam-4ea47216da66274357b14d5d7488ccbde27d75c4.zip |
Relevant BUGIDs: 115055
Purpose of commit: bugfix
Commit summary:
---------------
fixed the bogus logic in 'similiar' (renamed it to similar) and
documented the new override argument: difignore.
-rw-r--r-- | CHANGELOG | 3 | ||||
-rw-r--r-- | doc/modules/pam_cracklib.sgml | 13 | ||||
-rw-r--r-- | modules/pam_cracklib/README | 18 | ||||
-rw-r--r-- | modules/pam_cracklib/pam_cracklib.c | 79 |
4 files changed, 79 insertions, 34 deletions
@@ -35,6 +35,9 @@ Where you should replace XXXXX with a bug-id. 0.73: please submit patches for this section with actual code/doc patches! +* replaced bogus logic in the pam_cracklib module for determining if + the replacement is too similar to the old password (Bug 115055 - + agmorgan) * added accessconf=<filename> feature to pam_access - request from Aldrin Martoq and Meelis Roos (Bugs 111927,117240 - agmorgan) * fix for pam_limit module not dealing with all limits Adam J. Richter diff --git a/doc/modules/pam_cracklib.sgml b/doc/modules/pam_cracklib.sgml index f5b2359a..031a440e 100644 --- a/doc/modules/pam_cracklib.sgml +++ b/doc/modules/pam_cracklib.sgml @@ -70,12 +70,19 @@ Is the new password the the old one with only a change of case? <item> <bf/Similar/ - -Is the new password too much like the old one? This is controlled -by one argument, <tt/difok/ which is a number of characters that if -different between the old and new are enough to accept the new +Is the new password too much like the old one? This is primarily +controlled by one argument, <tt/difok/ which is a number of characters +that if different between the old and new are enough to accept the new password, this defaults to 10 or 1/2 the size of the new password whichever is smaller. +To avoid the lockup associated with trying to change a long and +complicated password, <tt/difignore/ is available. This argument can +be used to specify the minimum length a new password needs to be +before the <tt/difok/ value is ignored. The default value for +<tt/difignore/ is 23. + + <item> <bf/Simple/ - Is the new password too small? This is controlled by 5 arguments diff --git a/modules/pam_cracklib/README b/modules/pam_cracklib/README index e4b02731..69662f73 100644 --- a/modules/pam_cracklib/README +++ b/modules/pam_cracklib/README @@ -13,9 +13,25 @@ RECOGNIZED ARGUMENTS: retry=N Prompt user at most N times before returning with error. Default N=1. + difok=N How many characters can be the same in the new + password relative to the old + difignore=N How many characters long should the password be + before we ignore difok. + + minlen=N The minimum simplicity count for a good password. + + dcredit=N + ucredit=N + lcredit=N + ocredit=N Weight, digits, upper, lower, other characters with + count N. Use these values to compute the + 'unsimplicity' of the password. + + use_authtok Get the proposed password from PAM_AUTHTOK + MODULE SERVICES PROVIDED: passwd chauthtok AUTHOR: - Cristian Gafton <gafton@sorosis.ro> + Cristian Gafton <gafton@redhat.com> diff --git a/modules/pam_cracklib/pam_cracklib.c b/modules/pam_cracklib/pam_cracklib.c index d3d74947..c79d4e76 100644 --- a/modules/pam_cracklib/pam_cracklib.c +++ b/modules/pam_cracklib/pam_cracklib.c @@ -87,11 +87,10 @@ static void _pam_log(int err, const char *format, ...) /* argument parsing */ #define PAM_DEBUG_ARG 0x0001 -/* module data - AGM: */ - struct cracklib_options { int retry_times; int diff_ok; + int diff_ignore; int min_length; int dig_credit; int up_credit; @@ -101,6 +100,17 @@ struct cracklib_options { char prompt_type[BUFSIZ]; }; +#define CO_RETRY_TIMES 1 +#define CO_DIFF_OK 10 +#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; @@ -118,15 +128,19 @@ static int _pam_parse(struct cracklib_options *opt, int argc, const char **argv) else if (!strncmp(*argv,"retry=",6)) { opt->retry_times = strtol(*argv+6,&ep,10); if (!ep || (opt->retry_times < 1)) - 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 = 10; + 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 < 5)) - opt->min_length = 5; + 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)) @@ -224,26 +238,30 @@ static int palindrome(const char *old, const char *new) } /* - * more than half of the characters are different ones. - * or at least diff_ok are different - * NOTE that the defaults are NOT the same as befor this - * change. as long as there are at least 10 different bytes - * in a new password it will now pass even if the password - * is longer than 20 bytes (MD5) + * This is a reasonably severe check for a different selection of characters + * in the old and new passwords. */ -static int similiar(struct cracklib_options *opt, const char *old, const char *new) +static int similar(struct cracklib_options *opt, + const char *old, const char *new) { - int i, j; + int i, j; - for (i = j = 0;new[i] && old[i];i++) - if (strchr (new, old[i])) - j++; + for (i = j = 0; old[i]; i++) { + if (strchr (new, old[i])) { + j++; + } + } - if (j >= opt->diff_ok || i >= j * 2) - return 0; + if (((i-j) >= opt->diff_ok) + || (strlen(new) >= (j * 2)) + || (strlen(new) >= opt->diff_ignore)) { + /* passwords are not very similar */ + return 0; + } - return 1; + /* passwords are too similar */ + return 1; } /* @@ -332,8 +350,8 @@ static const char * password_check(struct cracklib_options *opt, const char *old if (!msg && strcmp(oldmono, newmono) == 0) msg = "case changes only"; - if (!msg && similiar(opt, oldmono, newmono)) - msg = "is too similiar to the old one"; + if (!msg && similar(opt, oldmono, newmono)) + msg = "is too similar to the old one"; if (!msg && simple(opt, old, new)) msg = "is too simple"; @@ -447,14 +465,15 @@ PAM_EXTERN int pam_sm_chauthtok(pam_handle_t *pamh, int flags, unsigned int ctrl; struct cracklib_options options; - options.retry_times = 1; - options.diff_ok = 10; - options.min_length = 9; - options.dig_credit = 1; - options.up_credit = 1; - options.low_credit = 1; - options.oth_credit = 1; - options.use_authtok = 0; + 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); ctrl = _pam_parse(&options, argc, argv); |