--- servers/slapd/root_dse.c 2005/03/24 04:13:31 1.101 +++ servers/slapd/root_dse.c 2005/05/04 22:22:43 1.104 @@ -1,5 +1,5 @@ /* root_dse.c - Provides the Root DSA-Specific Entry */ -/* $OpenLDAP: pkg/ldap/servers/slapd/root_dse.c,v 1.100 2005/03/14 22:21:00 hyc Exp $ */ +/* $OpenLDAP: pkg/ldap/servers/slapd/root_dse.c,v 1.103 2005/04/22 12:34:10 hyc Exp $ */ /* This work is part of OpenLDAP Software . * * Copyright 1999-2005 The OpenLDAP Foundation. @@ -52,8 +52,8 @@ root_dse_info( const char **text ) { Entry *e; - struct berval vals[2], *bv; - struct berval nvals[2]; + struct berval val, *bv; + struct berval nval; int i, j; char ** supportedSASLMechanisms; BackendDB *be; @@ -79,9 +79,6 @@ root_dse_info( AttributeDescription *ad_ref = slap_schema.si_ad_ref; - vals[1].bv_val = NULL; - nvals[1].bv_val = NULL; - e = (Entry *) SLAP_CALLOC( 1, sizeof(Entry) ); if( e == NULL ) { @@ -102,18 +99,16 @@ root_dse_info( e->e_private = NULL; - vals[0].bv_val = "top"; - vals[0].bv_len = sizeof("top")-1; - if( attr_merge( e, ad_objectClass, vals, NULL ) ) { + BER_BVSTR( &val, "top" ); + if( attr_merge_one( e, ad_objectClass, &val, NULL ) ) { return LDAP_OTHER; } - vals[0].bv_val = "OpenLDAProotDSE"; - vals[0].bv_len = sizeof("OpenLDAProotDSE")-1; - if( attr_merge( e, ad_objectClass, vals, NULL ) ) { + BER_BVSTR( &val, "OpenLDAProotDSE" ); + if( attr_merge_one( e, ad_objectClass, &val, NULL ) ) { return LDAP_OTHER; } - if( attr_merge( e, ad_structuralObjectClass, vals, NULL ) ) { + if( attr_merge_one( e, ad_structuralObjectClass, &val, NULL ) ) { return LDAP_OTHER; } @@ -124,17 +119,19 @@ root_dse_info( continue; } if ( SLAP_MONITOR( be )) { - vals[0] = be->be_suffix[0]; - nvals[0] = be->be_nsuffix[0]; - if( attr_merge( e, ad_monitorContext, vals, nvals ) ) { + if( attr_merge_one( e, ad_monitorContext, + &be->be_suffix[0], + &be->be_nsuffix[0] ) ) + { return LDAP_OTHER; } continue; } if ( SLAP_CONFIG( be )) { - vals[0] = be->be_suffix[0]; - nvals[0] = be->be_nsuffix[0]; - if( attr_merge( e, ad_configContext, vals, nvals ) ) { + if( attr_merge_one( e, ad_configContext, + &be->be_suffix[0], + & be->be_nsuffix[0] ) ) + { return LDAP_OTHER; } continue; @@ -143,9 +140,10 @@ root_dse_info( continue; } for ( j = 0; be->be_suffix[j].bv_val != NULL; j++ ) { - vals[0] = be->be_suffix[j]; - nvals[0] = be->be_nsuffix[0]; - if( attr_merge( e, ad_namingContexts, vals, nvals ) ) { + if( attr_merge_one( e, ad_namingContexts, + &be->be_suffix[j], + &be->be_nsuffix[0] ) ) + { return LDAP_OTHER; } } @@ -166,8 +164,7 @@ root_dse_info( #ifdef LDAP_SLAPI /* netscape supportedExtension */ for ( i = 0; (bv = slapi_int_get_supported_extop(i)) != NULL; i++ ) { - vals[0] = *bv; - if( attr_merge( e, ad_supportedExtension, vals, NULL )) { + if( attr_merge_one( e, ad_supportedExtension, bv, NULL ) ) { return LDAP_OTHER; } } @@ -188,9 +185,9 @@ root_dse_info( continue; } snprintf(buf, sizeof buf, "%d", i); - vals[0].bv_val = buf; - vals[0].bv_len = strlen( vals[0].bv_val ); - if( attr_merge( e, ad_supportedLDAPVersion, vals, NULL ) ) { + val.bv_val = buf; + val.bv_len = strlen( val.bv_val ); + if( attr_merge_one( e, ad_supportedLDAPVersion, &val, NULL ) ) { return LDAP_OTHER; } } @@ -200,9 +197,9 @@ root_dse_info( if( supportedSASLMechanisms != NULL ) { for ( i=0; supportedSASLMechanisms[i] != NULL; i++ ) { - vals[0].bv_val = supportedSASLMechanisms[i]; - vals[0].bv_len = strlen( vals[0].bv_val ); - if( attr_merge( e, ad_supportedSASLMechanisms, vals, NULL ) ) { + val.bv_val = supportedSASLMechanisms[i]; + val.bv_len = strlen( val.bv_val ); + if( attr_merge_one( e, ad_supportedSASLMechanisms, &val, NULL ) ) { return LDAP_OTHER; } } @@ -311,3 +308,78 @@ int read_root_dse_file( const char *fnam Debug(LDAP_DEBUG_CONFIG, "rootDSE file %s read.\n", fname, 0, 0); return rc; } + +int +slap_discover_feature( + const char *uri, + int version, + const char *attr, + const char *val ) +{ + LDAP *ld; + LDAPMessage *res = NULL, *entry; + int rc, i; + struct berval cred = BER_BVC( "" ), + bv_val, + **values = NULL; + char *attrs[ 2 ] = { NULL, NULL }; + + ber_str2bv( val, 0, 0, &bv_val ); + attrs[ 0 ] = attr; + + rc = ldap_initialize( &ld, uri ); + if ( rc != LDAP_SUCCESS ) { + return rc; + } + + rc = ldap_set_option( ld, LDAP_OPT_PROTOCOL_VERSION, &version ); + if ( rc != LDAP_SUCCESS ) { + goto done; + } + + rc = ldap_sasl_bind_s( ld, "", LDAP_SASL_SIMPLE, + &cred, NULL, NULL, NULL ); + if ( rc != LDAP_SUCCESS ) { + goto done; + } + + rc = ldap_search_ext_s( ld, "", LDAP_SCOPE_BASE, "(objectClass=*)", + attrs, 0, NULL, NULL, NULL, 0, &res ); + if ( rc != LDAP_SUCCESS ) { + goto done; + } + + entry = ldap_first_entry( ld, res ); + if ( entry == NULL ) { + goto done; + } + + values = ldap_get_values_len( ld, entry, attrs[ 0 ] ); + if ( values == NULL ) { + rc = LDAP_NO_SUCH_ATTRIBUTE; + goto done; + } + + for ( i = 0; values[ i ] != NULL; i++ ) { + if ( bvmatch( &bv_val, values[ i ] ) ) { + rc = LDAP_COMPARE_TRUE; + goto done; + } + } + + rc = LDAP_COMPARE_FALSE; + +done:; + if ( values != NULL ) { + ldap_value_free_len( values ); + } + + if ( res != NULL ) { + ldap_msgfree( res ); + } + + ldap_unbind_ext( ld, NULL, NULL ); + + return rc; +} +