+ switch ( *scope ) {
+ case LDAP_X_SCOPE_EXACT:
+ case LDAP_X_SCOPE_CHILDREN:
+ case LDAP_X_SCOPE_SUBTREE:
+ case LDAP_X_SCOPE_ONELEVEL:
+ rc = dnNormalize( 0, NULL, NULL, &bv, nbase, op->o_tmpmemctx );
+ if( rc != LDAP_SUCCESS ) {
+ *scope = -1;
+ }
+ break;
+
+ case LDAP_X_SCOPE_REGEX:
+ ber_dupbv_x( nbase, &bv, op->o_tmpmemctx );
+
+ case LDAP_X_SCOPE_USERS:
+ rc = LDAP_SUCCESS;
+ break;
+
+ default:
+ *scope = -1;
+ break;
+ }
+
+ return rc;
+
+ /*
+ * u:<uid>
+ */
+ } else if ( ( uri->bv_val[ 0 ] == 'u' || uri->bv_val[ 0 ] == 'U' )
+ && ( uri->bv_val[ 1 ] == ':'
+ || uri->bv_val[ 1 ] == '/'
+ || uri->bv_val[ 1 ] == '.' ) )
+ {
+ Connection c = *op->o_conn;
+ char buf[ SLAP_LDAPDN_MAXLEN ];
+ struct berval id,
+ user = BER_BVNULL,
+ realm = BER_BVNULL,
+ mech = BER_BVNULL;
+
+ if ( sizeof( buf ) <= uri->bv_len ) {
+ return LDAP_INVALID_SYNTAX;
+ }
+
+ id.bv_len = uri->bv_len;
+ id.bv_val = buf;
+ strncpy( buf, uri->bv_val, sizeof( buf ) );
+
+ rc = slap_parse_user( &id, &user, &realm, &mech );
+ if ( rc != LDAP_SUCCESS ) {
+ return rc;
+ }
+
+ if ( !BER_BVISNULL( &mech ) ) {
+ c.c_sasl_bind_mech = mech;
+ } else {
+ BER_BVSTR( &c.c_sasl_bind_mech, "AUTHZ" );
+ }
+
+ rc = slap_sasl_getdn( &c, op, &user,
+ realm.bv_val, nbase, SLAP_GETDN_AUTHZID );
+
+ if ( rc == LDAP_SUCCESS ) {
+ *scope = LDAP_X_SCOPE_EXACT;
+ }
+
+ return rc;
+
+ /*
+ * group[/<groupoc>[/<groupat>]]:<groupdn>
+ *
+ * groupoc defaults to "groupOfNames"
+ * groupat defaults to "member"
+ *
+ * <groupdn> must pass DN normalization
+ */
+ } else if ( strncasecmp( uri->bv_val, "group", STRLENOF( "group" ) ) == 0 )
+ {
+ struct berval group_dn = BER_BVNULL,
+ group_oc = BER_BVNULL,
+ member_at = BER_BVNULL;
+ char *tmp;
+
+ bv.bv_val = uri->bv_val + STRLENOF( "group" );
+ group_dn.bv_val = strchr( bv.bv_val, ':' );
+ if ( group_dn.bv_val == NULL ) {
+ /* last chance: assume it's a(n exact) DN ... */
+ bv.bv_val = uri->bv_val;
+ *scope = LDAP_X_SCOPE_EXACT;
+ goto is_dn;
+ }
+
+ if ( bv.bv_val[ 0 ] == '/' ) {
+ group_oc.bv_val = &bv.bv_val[ 1 ];
+
+ member_at.bv_val = strchr( group_oc.bv_val, '/' );
+ if ( member_at.bv_val ) {
+ group_oc.bv_len = member_at.bv_val - group_oc.bv_val;
+ member_at.bv_val++;
+ member_at.bv_len = group_dn.bv_val - member_at.bv_val;
+
+ } else {
+ group_oc.bv_len = group_dn.bv_val - group_oc.bv_val;
+ BER_BVSTR( &member_at, "member" );
+ }
+
+ } else {
+ BER_BVSTR( &group_oc, "groupOfNames" );
+ }
+ group_dn.bv_val++;
+ group_dn.bv_len = uri->bv_len - ( group_dn.bv_val - uri->bv_val );
+
+ rc = dnNormalize( 0, NULL, NULL, &group_dn, nbase, op->o_tmpmemctx );
+ if ( rc != LDAP_SUCCESS ) {
+ *scope = -1;
+ return rc;