From 4504b48c6b5d1e9add3bbf58adbcdc675842d37d Mon Sep 17 00:00:00 2001 From: Howard Chu Date: Tue, 2 Mar 2004 22:12:23 +0000 Subject: [PATCH] default_passwd_hash now takes a list of schemes passwordModify exop will generate all the configured hashes --- servers/slapd/config.c | 34 +++++++---- servers/slapd/passwd.c | 114 ++++++++++++++++++++----------------- servers/slapd/proto-slap.h | 3 +- 3 files changed, 86 insertions(+), 65 deletions(-) diff --git a/servers/slapd/config.c b/servers/slapd/config.c index d791f1758e..9460263f39 100644 --- a/servers/slapd/config.c +++ b/servers/slapd/config.c @@ -70,7 +70,7 @@ int global_idletimeout = 0; char *global_host = NULL; char *global_realm = NULL; char *ldap_srvtab = ""; -char *default_passwd_hash = NULL; +char **default_passwd_hash = NULL; int cargc = 0, cargv_size = 0; char **cargv; struct berval default_search_base = { 0, NULL }; @@ -635,22 +635,34 @@ read_config( const char *fname, int depth ) return 1; } - - if ( lutil_passwd_scheme( cargv[1] ) == 0 ) { + for(i = 1; i < cargc; i++) { + if ( lutil_passwd_scheme( cargv[i] ) == 0 ) { +#ifdef NEW_LOGGING + LDAP_LOG( CONFIG, CRIT, + "%s: line %d: password scheme \"%s\" not available\n", + fname, lineno, cargv[i] ); +#else + Debug( LDAP_DEBUG_ANY, + "%s: line %d: password scheme \"%s\" not available\n", + fname, lineno, cargv[i] ); +#endif + } else { + ldap_charray_add( &default_passwd_hash, cargv[i] ); + } + } + if( !default_passwd_hash ) { #ifdef NEW_LOGGING LDAP_LOG( CONFIG, CRIT, - "%s: line %d: password scheme \"%s\" not available\n", - fname, lineno, cargv[1] ); + "%s: line %d: no valid hashes found\n", + fname, lineno, 0 ); #else Debug( LDAP_DEBUG_ANY, - "%s: line %d: password scheme \"%s\" not available\n", - fname, lineno, cargv[1] ); -#endif + "%s: line %d: no valid hashes found\n", + fname, lineno, 0 ); return 1; +#endif } - default_passwd_hash = ch_strdup( cargv[1] ); - } else if ( strcasecmp( cargv[0], "password-crypt-salt-format" ) == 0 ) { if ( cargc < 2 ) { @@ -2774,7 +2786,7 @@ config_destroy( ) if ( slapd_pid_file ) free ( slapd_pid_file ); if ( default_passwd_hash ) - free( default_passwd_hash ); + ldap_charray_free( default_passwd_hash ); acl_destroy( global_acl, NULL ); } diff --git a/servers/slapd/passwd.c b/servers/slapd/passwd.c index 24d3e0552d..3364b90acd 100644 --- a/servers/slapd/passwd.c +++ b/servers/slapd/passwd.c @@ -28,6 +28,15 @@ #include #include +static const char *defhash[] = { +#ifdef LUTIL_SHA1_BYTES + "{SSHA}", +#else + "{SMD5}", +#endif + NULL +}; + int passwd_extop( Operation *op, SlapReply *rs ) @@ -39,6 +48,8 @@ int passwd_extop( slap_callback cb = { NULL, slap_null_cb, NULL, NULL }; slap_callback cb2 = { NULL, slap_replog_cb, NULL, NULL }; cb2.sc_next = &cb; + int i, nhash; + char **hashes; assert( ber_bvcmp( &slap_EXOP_MODIFY_PASSWD, &op->ore_reqoid ) == 0 ); @@ -144,44 +155,58 @@ int passwd_extop( return LDAP_UNWILLING_TO_PERFORM; } - slap_passwd_hash( &qpw->rs_new, &hash, &rs->sr_text ); - if ( rsp ) { - free( qpw->rs_new.bv_val ); + ml = ch_malloc( sizeof(Modifications) ); + if ( !qpw->rs_modtail ) qpw->rs_modtail = &ml->sml_next; + + if ( default_passwd_hash ) { + for ( nhash = 0; default_passwd_hash[nhash]; nhash++ ); + hashes = default_passwd_hash; + } else { + nhash = 1; + hashes = (char **)defhash; } - if ( hash.bv_len == 0 ) { - if ( !rs->sr_text ) { - rs->sr_text = "password hash failed"; + ml->sml_values = ch_malloc( (nhash+1)*sizeof(struct berval) ); + for ( i=0; hashes[i]; i++ ) { + slap_passwd_hash( hashes[i], &qpw->rs_new, &hash, &rs->sr_text ); + if ( hash.bv_len == 0 ) { + if ( !rs->sr_text ) { + rs->sr_text = "password hash failed"; + } + break; } - return LDAP_OTHER; + ml->sml_values[i] = hash; } - ml = ch_malloc( sizeof(Modifications) ); - if ( !qpw->rs_modtail ) qpw->rs_modtail = &ml->sml_next; - ml->sml_values = ch_malloc( 2*sizeof(struct berval) ); - ml->sml_values[0] = hash; - ml->sml_values[1].bv_val = NULL; - ml->sml_desc = slap_schema.si_ad_userPassword; + ml->sml_values[i].bv_val = NULL; ml->sml_nvalues = NULL; + ml->sml_desc = slap_schema.si_ad_userPassword; ml->sml_op = LDAP_MOD_REPLACE; ml->sml_next = qpw->rs_mods; qpw->rs_mods = ml; + if ( rsp ) { + free( qpw->rs_new.bv_val ); + } + if ( hashes[i] ) { + rs->sr_err = LDAP_OTHER; + } else { - op2 = *op; - op2.o_tag = LDAP_REQ_MODIFY; - op2.o_callback = &cb2; - op2.orm_modlist = qpw->rs_mods; + op2 = *op; + op2.o_tag = LDAP_REQ_MODIFY; + op2.o_callback = &cb2; + op2.orm_modlist = qpw->rs_mods; - rs->sr_err = slap_mods_opattrs( &op2, ml, qpw->rs_modtail, &rs->sr_text, - NULL, 0 ); - - if ( rs->sr_err == LDAP_SUCCESS ) { - rs->sr_err = op2.o_bd->be_modify( &op2, rs ); - } - if ( rs->sr_err == LDAP_SUCCESS ) { - rs->sr_rspdata = rsp; - } else if ( rsp ) { - ber_bvfree( rsp ); + rs->sr_err = slap_mods_opattrs( &op2, ml, qpw->rs_modtail, &rs->sr_text, + NULL, 0 ); + + if ( rs->sr_err == LDAP_SUCCESS ) { + rs->sr_err = op2.o_bd->be_modify( &op2, rs ); + } + if ( rs->sr_err == LDAP_SUCCESS ) { + rs->sr_rspdata = rsp; + } else if ( rsp ) { + ber_bvfree( rsp ); + } } - slap_mods_free( ml ); + slap_mods_free( qpw->rs_mods ); return rs->sr_err; } @@ -410,56 +435,39 @@ slap_passwd_check( void slap_passwd_generate( struct berval *pass ) { - struct berval *tmp; #ifdef NEW_LOGGING LDAP_LOG( OPERATION, ENTRY, "slap_passwd_generate: begin\n", 0, 0, 0 ); #else Debug( LDAP_DEBUG_TRACE, "slap_passwd_generate\n", 0, 0, 0 ); #endif + pass->bv_val = NULL; + pass->bv_len = 0; + /* * generate passwords of only 8 characters as some getpass(3) * implementations truncate at 8 characters. */ - tmp = lutil_passwd_generate( 8 ); - if (tmp) { - *pass = *tmp; - free(tmp); - } else { - pass->bv_val = NULL; - pass->bv_len = 0; - } + lutil_passwd_generate( pass, 8 ); } void slap_passwd_hash( + char *hash, struct berval * cred, struct berval * new, const char **text ) { - struct berval *tmp; -#ifdef LUTIL_SHA1_BYTES - char* hash = default_passwd_hash ? default_passwd_hash : "{SSHA}"; -#else - char* hash = default_passwd_hash ? default_passwd_hash : "{SMD5}"; -#endif - + new->bv_len = 0; + new->bv_val = NULL; #if defined( SLAPD_CRYPT ) || defined( SLAPD_SPASSWD ) ldap_pvt_thread_mutex_lock( &passwd_mutex ); #endif - tmp = lutil_passwd_hash( cred , hash, text ); + lutil_passwd_hash( cred , hash, new, text ); #if defined( SLAPD_CRYPT ) || defined( SLAPD_SPASSWD ) ldap_pvt_thread_mutex_unlock( &passwd_mutex ); #endif - if( tmp == NULL ) { - new->bv_len = 0; - new->bv_val = NULL; - } - - *new = *tmp; - free( tmp ); - return; } diff --git a/servers/slapd/proto-slap.h b/servers/slapd/proto-slap.h index 67a6a2d859..d9e1aa0fca 100644 --- a/servers/slapd/proto-slap.h +++ b/servers/slapd/proto-slap.h @@ -862,6 +862,7 @@ LDAP_SLAPD_F (int) slap_passwd_check( LDAP_SLAPD_F (void) slap_passwd_generate( struct berval * ); LDAP_SLAPD_F (void) slap_passwd_hash( + char *type, struct berval *cred, struct berval *hash, const char **text ); @@ -1210,7 +1211,7 @@ LDAP_SLAPD_V (int) global_idletimeout; LDAP_SLAPD_V (int) global_schemacheck; LDAP_SLAPD_V (char *) global_host; LDAP_SLAPD_V (char *) global_realm; -LDAP_SLAPD_V (char *) default_passwd_hash; +LDAP_SLAPD_V (char **) default_passwd_hash; LDAP_SLAPD_V (int) lber_debug; LDAP_SLAPD_V (int) ldap_syslog; LDAP_SLAPD_V (struct berval) default_search_base; -- 2.39.5