2 * Prototypes for the kadmin password strength checking plugin.
4 * Developed by Derrick Brashear and Ken Hornstein of Sine Nomine Associates,
5 * on behalf of Stanford University
6 * Extensive modifications by Russ Allbery <eagle@eyrie.org>
7 * Copyright 2006, 2007, 2009, 2012, 2013, 2014
8 * The Board of Trustees of the Leland Stanford Junior University
10 * See LICENSE for licensing terms.
13 #ifndef PLUGIN_INTERNAL_H
14 #define PLUGIN_INTERNAL_H 1
17 #include <portable/krb5.h>
18 #include <portable/macros.h>
25 #ifdef HAVE_KRB5_PWQUAL_PLUGIN_H
26 # include <krb5/pwqual_plugin.h>
28 typedef struct krb5_pwqual_moddata_st *krb5_pwqual_moddata;
31 /* Error strings returned (and displayed to the user) for various failures. */
32 #define ERROR_ASCII "password contains non-ASCII or control characters"
33 #define ERROR_DICT "password found in list of common passwords"
34 #define ERROR_LETTER "password is only letters and spaces"
35 #define ERROR_MINDIFF "password does not contain enough unique characters"
36 #define ERROR_SHORT "password is too short"
37 #define ERROR_USERNAME "password based on username or principal"
40 * A character class rule, which consists of a minimum length to which the
41 * rule is applied, a maximum length to which the rule is applied, and a set
42 * of flags for which character classes are required. The symbol class
43 * includes everything that isn't in one of the other classes, including
53 struct class_rule *next;
56 /* Used to store a list of strings, managed by the sync_vector_* functions. */
64 * MIT Kerberos uses this type as an abstract data type for any data that a
65 * password quality check needs to carry. Reuse it since then we get type
66 * checking for at least the MIT plugin.
68 struct krb5_pwqual_moddata_st {
69 long minimum_different; /* Minimum number of different characters */
70 long minimum_length; /* Minimum password length */
71 bool ascii; /* Whether to require printable ASCII */
72 bool nonletter; /* Whether to require a non-letter */
73 struct class_rule *rules; /* Linked list of character class rules */
74 char *dictionary; /* Base path to CrackLib dictionary */
75 bool have_cdb; /* Whether we have a CDB dictionary */
76 int cdb_fd; /* File descriptor of CDB dictionary */
78 struct cdb cdb; /* Open CDB dictionary data */
84 /* Default to a hidden visibility for all internal functions. */
85 #pragma GCC visibility push(hidden)
87 /* Initialize the plugin and set up configuration. */
88 krb5_error_code strength_init(krb5_context, const char *dictionary,
89 krb5_pwqual_moddata *);
92 * Check a password. Returns 0 if okay. On error, sets the Kerberos error
93 * message and returns a Kerberos status code.
95 krb5_error_code strength_check(krb5_context, krb5_pwqual_moddata,
96 const char *principal, const char *password);
98 /* Free the internal plugin state. */
99 void strength_close(krb5_context, krb5_pwqual_moddata);
102 * CDB handling. strength_init_cdb gets the dictionary configuration and sets
103 * up the CDB database, strength_check_cdb checks it, and strength_close_cdb
104 * handles freeing resources.
106 * If not built with CDB support, provide some stubs for check and close.
107 * init is always a real function, which reports an error if CDB is
110 krb5_error_code strength_init_cdb(krb5_context, krb5_pwqual_moddata);
112 krb5_error_code strength_check_cdb(krb5_context, krb5_pwqual_moddata,
113 const char *password);
114 void strength_close_cdb(krb5_context, krb5_pwqual_moddata);
116 # define strength_check_cdb(c, d, p) 0
117 # define strength_close_cdb(c, d) /* empty */
121 * CrackLib handling. strength_init_cracklib gets the dictionary
122 * configuration does some sanity checks on it, and strength_check_cracklib
123 * checks the password against CrackLib.
125 krb5_error_code strength_init_cracklib(krb5_context, krb5_pwqual_moddata,
126 const char *dictionary);
127 krb5_error_code strength_check_cracklib(krb5_context, krb5_pwqual_moddata,
128 const char *password);
130 /* Check whether the password statisfies character class requirements. */
131 krb5_error_code strength_check_classes(krb5_context, krb5_pwqual_moddata,
132 const char *password);
134 /* Check whether the password is based on the principal in some way. */
135 krb5_error_code strength_check_principal(krb5_context, krb5_pwqual_moddata,
136 const char *principal,
137 const char *password);
140 * Manage vectors, which are counted lists of strings. The functions that
141 * return a boolean return false if memory allocation fails.
143 struct vector *strength_vector_new(void)
144 __attribute__((__malloc__));
145 bool strength_vector_add(struct vector *, const char *string)
146 __attribute__((__nonnull__));
147 void strength_vector_free(struct vector *);
150 * vector_split_multi splits on a set of characters. If the vector argument
151 * is NULL, a new vector is allocated; otherwise, the provided one is reused.
152 * Returns NULL on memory allocation failure, after which the provided vector
153 * may have been modified to only have partial results.
155 * Empty strings will yield zero-length vectors. Adjacent delimiters are
156 * treated as a single delimiter by vector_split_multi. Any leading or
157 * trailing delimiters are ignored, so this function will never create
158 * zero-length strings (similar to the behavior of strtok).
160 struct vector *strength_vector_split_multi(const char *string,
161 const char *seps, struct vector *)
162 __attribute__((__nonnull__(1, 2)));
165 * Obtain configuration settings from krb5.conf. These are wrappers around
166 * the krb5_appdefault_* APIs that handle setting the section name, obtaining
167 * the local default realm and using it to find settings, and doing any
168 * necessary conversion.
170 void strength_config_boolean(krb5_context, const char *, bool *)
171 __attribute__((__nonnull__));
172 krb5_error_code strength_config_list(krb5_context, const char *,
174 __attribute__((__nonnull__));
175 void strength_config_number(krb5_context, const char *, long *)
176 __attribute__((__nonnull__));
177 void strength_config_string(krb5_context, const char *, char **)
178 __attribute__((__nonnull__));
180 /* Parse the more complex configuration of required character classes. */
181 krb5_error_code strength_config_classes(krb5_context, const char *,
182 struct class_rule **)
183 __attribute__((__nonnull__));
186 * Store a particular password quality error in the Kerberos context. The
187 * _system variant uses errno for the error code and appends the strerror
188 * results to the message. All versions return the error code set.
190 krb5_error_code strength_error_class(krb5_context, const char *format, ...)
191 __attribute__((__nonnull__, __format__(printf, 2, 3)));
192 krb5_error_code strength_error_config(krb5_context, const char *format, ...)
193 __attribute__((__nonnull__, __format__(printf, 2, 3)));
194 krb5_error_code strength_error_dict(krb5_context, const char *format, ...)
195 __attribute__((__nonnull__, __format__(printf, 2, 3)));
196 krb5_error_code strength_error_generic(krb5_context, const char *format, ...)
197 __attribute__((__nonnull__, __format__(printf, 2, 3)));
198 krb5_error_code strength_error_system(krb5_context, const char *format, ...)
199 __attribute__((__nonnull__, __format__(printf, 2, 3)));
200 krb5_error_code strength_error_tooshort(krb5_context, const char *format, ...)
201 __attribute__((__nonnull__, __format__(printf, 2, 3)));
203 /* Undo default visibility change. */
204 #pragma GCC visibility pop
208 #endif /* !PLUGIN_INTERNAL_H */