ITS#7284 slappasswd: Add support loading a dynamically loadable module

Add "-o module-path=<pathspec>" and "-o module-load=<filename>"
options to load a dynamically loadable password hash module
(e.g., slapd-sha2).
This commit is contained in:
SATOH Fumiyasu 2012-05-31 13:13:41 +09:00 committed by Howard Chu
parent 5cf4fbc74d
commit 4272551a01
2 changed files with 99 additions and 8 deletions

View file

@ -18,7 +18,8 @@ slappasswd \- OpenLDAP password utility
.BI \-c \ salt-format\fR]
[\c
.BR \-n ]
.B
[\c
.BI \-o \ option\fR[ = value\fR]]
.LP
.SH DESCRIPTION
.LP
@ -154,6 +155,21 @@ which provides 31 characters of salt.
.BI \-n
Omit the trailing newline; useful to pipe the credentials
into a command.
.TP
.BI \-o \ option\fR[ = value\fR]
Specify an
.I option
with a(n optional)
.IR value .
Possible generic options/values are:
.LP
.nf
module\-path=<pathspec> (see `\fBmodulepath\fP' in slapd.conf(5))
module\-load=<filename> (see `\fBmoduleload\fP' in slapd.conf(5))
.in
You can load a dynamically loadable password hash module by
using this option.
.SH LIMITATIONS
The practice of storing hashed passwords in userPassword violates
Standard Track (RFC 4519) schema specifications and may hinder

View file

@ -40,6 +40,8 @@
#include "slap.h"
static int verbose = 0;
static char *modulepath = NULL;
static char *moduleload = NULL;
static void
usage(const char *s)
@ -50,6 +52,9 @@ usage(const char *s)
" -g\t\tgenerate random password\n"
" -h hash\tpassword scheme\n"
" -n\t\tomit trailing newline\n"
" -o <opt>[=val] specify an option with a(n optional) value\n"
" \tmodule-path=<pathspec>\n"
" \tmodule-load=<filename>\n"
" -s secret\tnew password\n"
" -u\t\tgenerate RFC2307 values (default)\n"
" -v\t\tincrease verbosity\n"
@ -59,9 +64,39 @@ usage(const char *s)
exit( EXIT_FAILURE );
}
static int
parse_slappasswdopt( void )
{
size_t len = 0;
char *p;
p = strchr( optarg, '=' );
if ( p != NULL ) {
len = p - optarg;
p++;
}
if ( strncasecmp( optarg, "module-path", len ) == 0 ) {
if ( modulepath )
ch_free( modulepath );
modulepath = ch_strdup( p );
} else if ( strncasecmp( optarg, "module-load", len ) == 0 ) {
if ( moduleload )
ch_free( moduleload );
moduleload = ch_strdup( p );
} else {
return -1;
}
return 0;
}
int
slappasswd( int argc, char *argv[] )
{
int rc = EXIT_SUCCESS;
#ifdef LUTIL_SHA1_BYTES
char *default_scheme = "{SSHA}";
#else
@ -79,8 +114,15 @@ slappasswd( int argc, char *argv[] )
struct berval passwd = BER_BVNULL;
struct berval hash;
#ifdef LDAP_DEBUG
/* tools default to "none", so that at least LDAP_DEBUG_ANY
* messages show up; use -d 0 to reset */
slap_debug = LDAP_DEBUG_NONE;
#endif
ldap_syslog = 0;
while( (i = getopt( argc, argv,
"c:d:gh:ns:T:vu" )) != EOF )
"c:d:gh:no:s:T:vu" )) != EOF )
{
switch (i) {
case 'c': /* crypt salt format */
@ -117,6 +159,12 @@ slappasswd( int argc, char *argv[] )
newline = "";
break;
case 'o':
if ( parse_slappasswdopt() ) {
usage ( progname );
}
break;
case 's': /* new password (secret) */
if ( pwfile != NULL ) {
fprintf( stderr, "Option -s incompatible with -T\n" );
@ -163,11 +211,29 @@ slappasswd( int argc, char *argv[] )
if( argc - optind != 0 ) {
usage( progname );
}
}
#ifdef SLAPD_MODULES
if ( module_init() != 0 ) {
fprintf( stderr, "%s: module_init failed\n", progname );
return EXIT_FAILURE;
}
if ( modulepath && module_path(modulepath) ) {
rc = EXIT_FAILURE;
goto destroy;
}
if ( moduleload && module_load(moduleload, 0, NULL) ) {
rc = EXIT_FAILURE;
goto destroy;
}
#endif
if( pwfile != NULL ) {
if( lutil_get_filed_password( pwfile, &passwd )) {
return EXIT_FAILURE;
rc = EXIT_FAILURE;
goto destroy;
}
} else if ( BER_BVISEMPTY( &passwd )) {
if( newpw == NULL ) {
@ -178,7 +244,8 @@ slappasswd( int argc, char *argv[] )
if( strcmp( newpw, cknewpw )) {
fprintf( stderr, "Password values do not match\n" );
return EXIT_FAILURE;
rc = EXIT_FAILURE;
goto destroy;
}
}
@ -194,16 +261,24 @@ slappasswd( int argc, char *argv[] )
fprintf( stderr,
"Password generation failed for scheme %s: %s\n",
scheme, text ? text : "" );
return EXIT_FAILURE;
rc = EXIT_FAILURE;
goto destroy;
}
if( lutil_passwd( &hash, &passwd, NULL, &text ) ) {
fprintf( stderr, "Password verification failed. %s\n",
text ? text : "" );
return EXIT_FAILURE;
rc = EXIT_FAILURE;
goto destroy;
}
print_pw:;
printf( "%s%s" , hash.bv_val, newline );
return EXIT_SUCCESS;
destroy:;
#ifdef SLAPD_MODULES
module_kill();
#endif
return rc;
}