]> git.sur5r.net Git - openldap/blobdiff - servers/slapd/back-meta/config.c
Merge remote-tracking branch 'origin/mdb.master'
[openldap] / servers / slapd / back-meta / config.c
index 54b4c8795a66c447620583d72436d8d2b6a308e8..231c583c93fbaf9d3cdc1a87483e35d54f9051df 100644 (file)
@@ -1,7 +1,7 @@
 /* $OpenLDAP$ */
 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
  *
- * Copyright 1999-2012 The OpenLDAP Foundation.
+ * Copyright 1999-2013 The OpenLDAP Foundation.
  * Portions Copyright 2001-2003 Pierangelo Masarati.
  * Portions Copyright 1999-2003 Howard Chu.
  * All rights reserved.
 #include "../back-ldap/back-ldap.h"
 #include "back-meta.h"
 
+#ifdef LDAP_DEVEL
+#define SLAP_AUTH_DN   1
+#endif
+
 static ConfigDriver meta_back_cf_gen;
 static ConfigLDAPadd meta_ldadd;
 static ConfigCfAdd meta_cfadd;
@@ -101,7 +105,7 @@ enum {
 };
 
 static ConfigTable metacfg[] = {
-       { "uri", "uri", 2, 2, 0,
+       { "uri", "uri", 2, 0, 0,
                ARG_MAGIC|LDAP_BACK_CFG_URI,
                meta_back_cf_gen, "( OLcfgDbAt:0.14 "
                        "NAME 'olcDbURI' "
@@ -315,7 +319,7 @@ static ConfigTable metacfg[] = {
                NULL, NULL },
 
        { "subtree-exclude", "pattern", 2, 2, 0,
-               ARG_STRING|ARG_MAGIC|LDAP_BACK_CFG_SUBTREE_EX,
+               ARG_MAGIC|LDAP_BACK_CFG_SUBTREE_EX,
                meta_back_cf_gen, "( OLcfgDbAt:3.103 "
                        "NAME 'olcDbSubtreeExclude' "
                        "DESC 'DN of subtree to exclude from target' "
@@ -323,7 +327,7 @@ static ConfigTable metacfg[] = {
                        "SYNTAX OMsDirectoryString )",
                NULL, NULL },
        { "subtree-include", "pattern", 2, 2, 0,
-               ARG_STRING|ARG_MAGIC|LDAP_BACK_CFG_SUBTREE_IN,
+               ARG_MAGIC|LDAP_BACK_CFG_SUBTREE_IN,
                meta_back_cf_gen, "( OLcfgDbAt:3.104 "
                        "NAME 'olcDbSubtreeInclude' "
                        "DESC 'DN of subtree to include in target' "
@@ -473,10 +477,11 @@ static ConfigOCs metaocs[] = {
 static int
 meta_ldadd( CfEntryInfo *p, Entry *e, ConfigArgs *c )
 {
-       if ( p->ce_type != Cft_Database || !p->ce_bi ||
-               p->ce_bi->bi_cf_ocs != metaocs )
+       if ( p->ce_type != Cft_Database || !p->ce_be ||
+               p->ce_be->be_cf_ocs != metaocs )
                return LDAP_CONSTRAINT_VIOLATION;
 
+       c->be = p->ce_be;
        return LDAP_SUCCESS;
 }
 
@@ -560,6 +565,8 @@ meta_back_new_target(
 static int
 meta_suffixm_config(
        ConfigArgs *c,
+       int argc,
+       char **argv,
        metatarget_t *mt
 )
 {
@@ -579,11 +586,11 @@ meta_suffixm_config(
         * current server
         */
 
-       ber_str2bv( c->argv[ 1 ], 0, 0, &dn );
+       ber_str2bv( argv[ 1 ], 0, 0, &dn );
        if ( dnPrettyNormal( NULL, &dn, &pvnc, &nvnc, NULL ) != LDAP_SUCCESS ) {
                snprintf( c->cr_msg, sizeof( c->cr_msg ),
                        "suffix \"%s\" is invalid",
-                       c->argv[1] );
+                       argv[1] );
                Debug( LDAP_DEBUG_ANY, "%s: %s.\n", c->log, c->cr_msg, 0 );
                return 1;
        }
@@ -597,18 +604,18 @@ meta_suffixm_config(
        if ( BER_BVISNULL( &c->be->be_nsuffix[ j ] ) ) {
                snprintf( c->cr_msg, sizeof( c->cr_msg ),
                        "suffix \"%s\" must be within the database naming context",
-                       c->argv[1] );
+                       argv[1] );
                Debug( LDAP_DEBUG_ANY, "%s: %s.\n", c->log, c->cr_msg, 0 );
                free( pvnc.bv_val );
                free( nvnc.bv_val );
                return 1;
        }
 
-       ber_str2bv( c->argv[ 2 ], 0, 0, &dn );
+       ber_str2bv( argv[ 2 ], 0, 0, &dn );
        if ( dnPrettyNormal( NULL, &dn, &prnc, &nrnc, NULL ) != LDAP_SUCCESS ) {
                snprintf( c->cr_msg, sizeof( c->cr_msg ),
                        "massaged suffix \"%s\" is invalid",
-                       c->argv[2] );
+                       argv[2] );
                Debug( LDAP_DEBUG_ANY, "%s: %s.\n", c->log, c->cr_msg, 0 );
                free( pvnc.bv_val );
                free( nvnc.bv_val );
@@ -680,12 +687,8 @@ slap_bv_x_ordered_unparse( BerVarray in, BerVarray *out )
 }
 
 int
-meta_subtree_destroy( metasubtree_t *ms )
+meta_subtree_free( metasubtree_t *ms )
 {
-       if ( ms->ms_next ) {
-               meta_subtree_destroy( ms->ms_next );
-       }
-
        switch ( ms->ms_type ) {
        case META_ST_SUBTREE:
        case META_ST_SUBORDINATE:
@@ -702,10 +705,19 @@ meta_subtree_destroy( metasubtree_t *ms )
        }
 
        ch_free( ms );
-
        return 0;
 }
 
+int
+meta_subtree_destroy( metasubtree_t *ms )
+{
+       if ( ms->ms_next ) {
+               meta_subtree_destroy( ms->ms_next );
+       }
+
+       return meta_subtree_free( ms );
+}
+
 static struct berval st_styles[] = {
        BER_BVC("subtree"),
        BER_BVC("children"),
@@ -1077,9 +1089,7 @@ meta_back_cf_gen( ConfigArgs *c )
 
        assert( mi != NULL );
 
-       if ( c->op == SLAP_CONFIG_EMIT ) {
-               struct berval bv = BER_BVNULL;
-
+       if ( c->op == SLAP_CONFIG_EMIT || c->op == LDAP_MOD_DELETE ) {
                if ( !mi )
                        return 1;
 
@@ -1090,6 +1100,10 @@ meta_back_cf_gen( ConfigArgs *c )
                        mt = c->ca_private;
                        mc = &mt->mt_mc;
                }
+       }
+
+       if ( c->op == SLAP_CONFIG_EMIT ) {
+               struct berval bv = BER_BVNULL;
 
                switch( c->type ) {
                /* Base attrs */
@@ -1340,19 +1354,22 @@ meta_back_cf_gen( ConfigArgs *c )
                /* target attrs */
                case LDAP_BACK_CFG_URI: {
                        char *p2, *p1 = strchr( mt->mt_uri, ' ' );
-                       bv.bv_len = strlen( mt->mt_uri ) + 1 + mt->mt_psuffix.bv_len;
+                       bv.bv_len = strlen( mt->mt_uri ) + 3 + mt->mt_psuffix.bv_len;
                        bv.bv_val = ch_malloc( bv.bv_len + 1 );
+                       p2 = bv.bv_val;
+                       *p2++ = '"';
                        if ( p1 ) {
-                               p2 = lutil_strncopy( bv.bv_val, mt->mt_uri, p1 - mt->mt_uri );
+                               p2 = lutil_strncopy( p2, mt->mt_uri, p1 - mt->mt_uri );
                        } else {
-                               p2 = lutil_strcopy( bv.bv_val, mt->mt_uri );
+                               p2 = lutil_strcopy( p2, mt->mt_uri );
                        }
                        *p2++ = '/';
                        p2 = lutil_strcopy( p2, mt->mt_psuffix.bv_val );
+                       *p2++ = '"';
                        if ( p1 ) {
                                strcpy( p2, p1 );
                        }
-                       value_add_one( &c->rvalue_vals, &bv );
+                       ber_bvarray_add( &c->rvalue_vals, &bv );
                        } break;
 
                case LDAP_BACK_CFG_ACL_AUTHCDN:
@@ -1492,6 +1509,7 @@ meta_back_cf_gen( ConfigArgs *c )
                                        ptr = lutil_strcopy( ptr, ",proxy-authz-non-critical" );
                                }
 
+#ifdef SLAP_AUTH_DN
                                switch ( mt->mt_idassert_flags & LDAP_BACK_AUTH_DN_MASK ) {
                                case LDAP_BACK_AUTH_DN_AUTHZID:
                                        ptr = lutil_strcopy( ptr, ",dn-authzid" );
@@ -1507,6 +1525,7 @@ meta_back_cf_gen( ConfigArgs *c )
 #endif
                                        break;
                                }
+#endif
 
                                bv.bv_len = ( ptr - bv.bv_val );
                                /* end-of-flags */
@@ -1575,7 +1594,221 @@ meta_back_cf_gen( ConfigArgs *c )
                }
                return rc;
        } else if ( c->op == LDAP_MOD_DELETE ) {
-               return 1;
+               switch( c->type ) {
+               /* Base attrs */
+               case LDAP_BACK_CFG_CONN_TTL:
+                       mi->mi_conn_ttl = 0;
+                       break;
+
+               case LDAP_BACK_CFG_DNCACHE_TTL:
+                       mi->mi_cache.ttl = META_DNCACHE_DISABLED;
+                       break;
+
+               case LDAP_BACK_CFG_IDLE_TIMEOUT:
+                       mi->mi_idle_timeout = 0;
+                       break;
+
+               case LDAP_BACK_CFG_ONERR:
+                       mi->mi_flags &= ~META_BACK_F_ONERR_MASK;
+                       break;
+
+               case LDAP_BACK_CFG_PSEUDOROOT_BIND_DEFER:
+                       mi->mi_flags &= ~META_BACK_F_DEFER_ROOTDN_BIND;
+                       break;
+
+               case LDAP_BACK_CFG_SINGLECONN:
+                       mi->mi_flags &= ~LDAP_BACK_F_SINGLECONN;
+                       break;
+
+               case LDAP_BACK_CFG_USETEMP:
+                       mi->mi_flags &= ~LDAP_BACK_F_USE_TEMPORARIES;
+                       break;
+
+               case LDAP_BACK_CFG_CONNPOOLMAX:
+                       mi->mi_conn_priv_max = LDAP_BACK_CONN_PRIV_MIN;
+                       break;
+
+               /* common attrs */
+               case LDAP_BACK_CFG_BIND_TIMEOUT:
+                       mc->mc_bind_timeout.tv_sec = 0;
+                       mc->mc_bind_timeout.tv_usec = 0;
+                       break;
+
+               case LDAP_BACK_CFG_CANCEL:
+                       mc->mc_flags &= ~LDAP_BACK_F_CANCEL_MASK2;
+                       break;
+
+               case LDAP_BACK_CFG_CHASE:
+                       mc->mc_flags &= ~LDAP_BACK_F_CHASE_REFERRALS;
+                       break;
+
+#ifdef SLAPD_META_CLIENT_PR
+               case LDAP_BACK_CFG_CLIENT_PR:
+                       mc->mc_ps == META_CLIENT_PR_DISABLE;
+                       break;
+#endif /* SLAPD_META_CLIENT_PR */
+
+               case LDAP_BACK_CFG_DEFAULT_T:
+                       mi->mi_defaulttarget = META_DEFAULT_TARGET_NONE;
+                       break;
+
+               case LDAP_BACK_CFG_NETWORK_TIMEOUT:
+                       mc->mc_network_timeout = 0;
+                       break;
+
+               case LDAP_BACK_CFG_NOREFS:
+                       mc->mc_flags &= ~LDAP_BACK_F_NOREFS;
+                       break;
+
+               case LDAP_BACK_CFG_NOUNDEFFILTER:
+                       mc->mc_flags &= ~LDAP_BACK_F_NOUNDEFFILTER;
+                       break;
+
+               case LDAP_BACK_CFG_NRETRIES:
+                       mc->mc_nretries == META_RETRY_DEFAULT;
+                       break;
+
+               case LDAP_BACK_CFG_QUARANTINE:
+                       if ( META_BACK_CMN_QUARANTINE( mc )) {
+                               mi->mi_ldap_extra->retry_info_destroy( &mc->mc_quarantine );
+                               mc->mc_flags &= ~LDAP_BACK_F_QUARANTINE;
+                               if ( mc == &mt->mt_mc ) {
+                                       ldap_pvt_thread_mutex_destroy( &mt->mt_quarantine_mutex );
+                                       mt->mt_isquarantined = 0;
+                               }
+                       }
+                       break;
+
+               case LDAP_BACK_CFG_REBIND:
+                       mc->mc_flags &= ~LDAP_BACK_F_SAVECRED;
+                       break;
+
+               case LDAP_BACK_CFG_TIMEOUT:
+                       for ( i = 0; i < SLAP_OP_LAST; i++ ) {
+                               mc->mc_timeout[ i ] = 0;
+                       }
+                       break;
+
+               case LDAP_BACK_CFG_VERSION:
+                       mc->mc_version = 0;
+                       break;
+
+#ifdef SLAP_CONTROL_X_SESSION_TRACKING
+               case LDAP_BACK_CFG_ST_REQUEST:
+                       mc->mc_flags &= ~LDAP_BACK_F_ST_REQUEST;
+                       break;
+#endif /* SLAP_CONTROL_X_SESSION_TRACKING */
+
+               case LDAP_BACK_CFG_T_F:
+                       mc->mc_flags &= ~LDAP_BACK_F_T_F_MASK2;
+                       break;
+
+               case LDAP_BACK_CFG_TLS:
+                       mc->mc_flags &= ~LDAP_BACK_F_TLS_MASK;
+                       if ( mt )
+                               bindconf_free( &mt->mt_tls );
+                       break;
+
+               /* target attrs */
+               case LDAP_BACK_CFG_URI:
+                       if ( mt->mt_uri ) {
+                               ch_free( mt->mt_uri );
+                               mt->mt_uri = NULL;
+                       }
+                       /* FIXME: should have a way to close all cached
+                        * connections associated with this target.
+                        */
+                       break;
+
+               case LDAP_BACK_CFG_IDASSERT_AUTHZFROM: {
+                       BerVarray *bvp;
+
+                       bvp = &mt->mt_idassert_authz; break;
+                       if ( c->valx < 0 ) {
+                               if ( *bvp != NULL ) {
+                                       ber_bvarray_free( *bvp );
+                                       *bvp = NULL;
+                               }
+
+                       } else {
+                               if ( *bvp == NULL ) {
+                                       rc = 1;
+                                       break;
+                               }
+
+                               for ( i = 0; !BER_BVISNULL( &((*bvp)[ i ]) ); i++ )
+                                       ;
+
+                               if ( i >= c->valx ) {
+                                       rc = 1;
+                                       break;
+                               }
+                               ber_memfree( ((*bvp)[ c->valx ]).bv_val );
+                               for ( i = c->valx; !BER_BVISNULL( &((*bvp)[ i + 1 ]) ); i++ ) {
+                                       (*bvp)[ i ] = (*bvp)[ i + 1 ];
+                               }
+                               BER_BVZERO( &((*bvp)[ i ]) );
+                       }
+                       } break;
+
+               case LDAP_BACK_CFG_IDASSERT_BIND:
+                       bindconf_free( &mt->mt_idassert.si_bc );
+                       memset( &mt->mt_idassert, 0, sizeof( slap_idassert_t ) );
+                       break;
+
+               case LDAP_BACK_CFG_SUFFIXM:     /* unused */
+               case LDAP_BACK_CFG_REWRITE:
+                       if ( mt->mt_rwmap.rwm_bva_rewrite ) {
+                               ber_bvarray_free( mt->mt_rwmap.rwm_bva_rewrite );
+                               mt->mt_rwmap.rwm_bva_rewrite = NULL;
+                       }
+                       if ( mt->mt_rwmap.rwm_rw )
+                               rewrite_info_delete( &mt->mt_rwmap.rwm_rw );
+                       break;
+
+               case LDAP_BACK_CFG_MAP:
+                       if ( mt->mt_rwmap.rwm_bva_map ) {
+                               ber_bvarray_free( mt->mt_rwmap.rwm_bva_map );
+                               mt->mt_rwmap.rwm_bva_map = NULL;
+                       }
+                       meta_back_map_free( &mt->mt_rwmap.rwm_oc );
+                       meta_back_map_free( &mt->mt_rwmap.rwm_at );
+                       mt->mt_rwmap.rwm_oc.drop_missing = 0;
+                       mt->mt_rwmap.rwm_at.drop_missing = 0;
+                       break;
+
+               case LDAP_BACK_CFG_SUBTREE_EX:
+               case LDAP_BACK_CFG_SUBTREE_IN:
+                       /* can only be one of exclude or include */
+                       if (( c->type == LDAP_BACK_CFG_SUBTREE_EX ) ^ mt->mt_subtree_exclude ) {
+                               rc = 1;
+                               break;
+                       }
+                       if ( c->valx < 0 ) {
+                               meta_subtree_destroy( mt->mt_subtree );
+                               mt->mt_subtree = NULL;
+                       } else {
+                               metasubtree_t *ms, **mprev;
+                               for (i=0, mprev = &mt->mt_subtree, ms = *mprev; ms; ms = *mprev) {
+                                       if ( i == c->valx ) {
+                                               *mprev = ms->ms_next;
+                                               meta_subtree_free( ms );
+                                               break;
+                                       }
+                                       i++;
+                                       mprev = &ms->ms_next;
+                               }
+                               if ( i != c->valx )
+                                       rc = 1;
+                       }
+                       break;
+
+               default:
+                       rc = 1;
+                       break;
+               }
+
+               return rc;
        }
 
        if ( c->op == SLAP_CONFIG_ADD ) {
@@ -1670,7 +1903,7 @@ meta_back_cf_gen( ConfigArgs *c )
                                return 1;
                        }
 
-                       if ( j == 0 ) {
+                       if ( j == 1 ) {
                                uris = tmpuris;
 
                        } else {
@@ -2319,10 +2552,10 @@ idassert-authzFrom      "dn:<rootdn>"
                                config_fp_parse_line( &ca );
 
                                if ( !strcasecmp( ca.argv[0], "suffixmassage" )) {
-                                       rc = meta_suffixm_config( &ca, mt );
+                                       rc = meta_suffixm_config( &ca, ca.argc, ca.argv, mt );
                                } else {
                                        rc = rewrite_parse( mt->mt_rwmap.rwm_rw,
-                                               c->fname, c->lineno, ca.argc, argv );
+                                               c->fname, c->lineno, ca.argc, ca.argv );
                                }
                                assert( rc == 0 );
                                ch_free( ca.argv );
@@ -2331,14 +2564,14 @@ idassert-authzFrom      "dn:<rootdn>"
                }
                argc = c->argc;
                argv = c->argv;
+               if ( c->op != SLAP_CONFIG_ADD ) {
+                       argc--;
+                       argv++;
+               }
                /* add the new rule */
-               if ( c->type == LDAP_BACK_CFG_SUFFIXM ) {
-                       rc = meta_suffixm_config( c, mt );
+               if ( !strcasecmp( argv[0], "suffixmassage" )) {
+                       rc = meta_suffixm_config( c, argc, argv, mt );
                } else {
-                       if ( c->op != SLAP_CONFIG_ADD ) {
-                               argc--;
-                               argv++;
-                       }
                        rc = rewrite_parse( mt->mt_rwmap.rwm_rw,
                                                c->fname, c->lineno, argc, argv );
                }
@@ -2356,7 +2589,7 @@ idassert-authzFrom        "dn:<rootdn>"
                                config_fp_parse_line( &ca );
 
                                if ( !strcasecmp( ca.argv[0], "suffixmassage" )) {
-                                       rc = meta_suffixm_config( &ca, mt );
+                                       rc = meta_suffixm_config( &ca, ca.argc, ca.argv, mt );
                                } else {
                                        rc = rewrite_parse( mt->mt_rwmap.rwm_rw,
                                                c->fname, c->lineno, ca.argc, argv );