X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=servers%2Fslapd%2Fback-ldap%2Fchain.c;h=8f37efb236c30ac0f6a80f2ba4f0756f5855fef0;hb=473e2c997f6b1f226d35da186db8033c922001f3;hp=2334c11052dde4871a03aa032f0c9d5558384c7e;hpb=001b30ebc61944581e59129b7a3ba9774a1f30cf;p=openldap diff --git a/servers/slapd/back-ldap/chain.c b/servers/slapd/back-ldap/chain.c index 2334c11052..8f37efb236 100644 --- a/servers/slapd/back-ldap/chain.c +++ b/servers/slapd/back-ldap/chain.c @@ -2,7 +2,7 @@ /* $OpenLDAP$ */ /* This work is part of OpenLDAP Software . * - * Copyright 2003-2010 The OpenLDAP Foundation. + * Copyright 2003-2011 The OpenLDAP Foundation. * Portions Copyright 2003 Howard Chu. * All rights reserved. * @@ -225,7 +225,6 @@ ldap_chain_uri_cmp( const void *c1, const void *c2 ) assert( !BER_BVISNULL( &li2->li_bvuri[ 0 ] ) ); assert( BER_BVISNULL( &li2->li_bvuri[ 1 ] ) ); - /* If local DNs don't match, it is definitely not a match */ return ber_bvcmp( &li1->li_bvuri[ 0 ], &li2->li_bvuri[ 0 ] ); } @@ -243,11 +242,10 @@ ldap_chain_uri_dup( void *c1, void *c2 ) assert( !BER_BVISNULL( &li2->li_bvuri[ 0 ] ) ); assert( BER_BVISNULL( &li2->li_bvuri[ 1 ] ) ); - /* Cannot have more than one shared session with same DN */ if ( ber_bvcmp( &li1->li_bvuri[ 0 ], &li2->li_bvuri[ 0 ] ) == 0 ) { return -1; } - + return 0; } @@ -448,6 +446,9 @@ Document: RFC 4511 * proto://[host][:port]/ only */ rc = ldap_url_parse_ext( ref->bv_val, &srv, LDAP_PVT_URL_PARSE_NONE ); if ( rc != LDAP_URL_SUCCESS ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: unable to parse ref=\"%s\"\n", + op->o_log_prefix, ref->bv_val, 0 ); + /* try next */ rc = LDAP_OTHER; continue; @@ -501,6 +502,8 @@ Document: RFC 4511 filter2bv_x( op, tmp_oq_search.rs_filter, &tmp_oq_search.rs_filterstr ); } else { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: ref=\"%s\": unable to parse filter=\"%s\"\n", + op->o_log_prefix, ref->bv_val, srv->lud_filter ); rc = LDAP_OTHER; } } @@ -522,11 +525,17 @@ Document: RFC 4511 } if ( li.li_uri == NULL ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: ref=\"%s\" unable to reconstruct URI\n", + op->o_log_prefix, ref->bv_val, 0 ); + /* try next */ rc = LDAP_OTHER; goto further_cleanup; } + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: ref=\"%s\" -> \"%s\"\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); + op->o_req_dn = pdn; op->o_req_ndn = ndn; @@ -549,9 +558,14 @@ Document: RFC 4511 if ( lip != NULL ) { op->o_bd->be_private = (void *)lip; + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: ref=\"%s\": URI=\"%s\" found in cache\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); + } else { rc = ldap_chain_db_init_one( op->o_bd ); if ( rc != 0 ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: ref=\"%s\" unable to init back-ldap for URI=\"%s\"\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); goto cleanup; } lip = (ldapinfo_t *)op->o_bd->be_private; @@ -559,6 +573,8 @@ Document: RFC 4511 lip->li_bvuri = bvuri; rc = ldap_chain_db_open_one( op->o_bd ); if ( rc != 0 ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: ref=\"%s\" unable to open back-ldap for URI=\"%s\"\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); lip->li_uri = NULL; lip->li_bvuri = NULL; (void)ldap_chain_db_destroy_one( op->o_bd, NULL); @@ -580,6 +596,9 @@ Document: RFC 4511 } else { temporary = 1; } + + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_op: ref=\"%s\" %s\n", + op->o_log_prefix, ref->bv_val, temporary ? "temporary" : "caching" ); } lb->lb_op_f = op_f; @@ -682,7 +701,7 @@ ldap_chain_search( * to be set once for all (correct?) */ li.li_bvuri = bvuri; for ( ; !BER_BVISNULL( &ref[0] ); ref++ ) { - SlapReply rs2 = { 0 }; + SlapReply rs2 = { REP_RESULT }; LDAPURLDesc *srv; req_search_s save_oq_search = op->oq_search, tmp_oq_search = { 0 }; @@ -697,6 +716,9 @@ ldap_chain_search( * proto://[host][:port]/ only */ rc = ldap_url_parse_ext( ref[0].bv_val, &srv, LDAP_PVT_URL_PARSE_NONE ); if ( rc != LDAP_URL_SUCCESS ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: unable to parse ref=\"%s\"\n", + op->o_log_prefix, ref->bv_val, 0 ); + /* try next */ rs->sr_err = LDAP_OTHER; continue; @@ -759,6 +781,8 @@ ldap_chain_search( filter2bv_x( op, tmp_oq_search.rs_filter, &tmp_oq_search.rs_filterstr ); } else { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: ref=\"%s\": unable to parse filter=\"%s\"\n", + op->o_log_prefix, ref->bv_val, srv->lud_filter ); rc = LDAP_OTHER; } } @@ -774,11 +798,17 @@ ldap_chain_search( ldap_free_urldesc( srv ); if ( rc != LDAP_SUCCESS || li.li_uri == NULL ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: ref=\"%s\" unable to reconstruct URI\n", + op->o_log_prefix, ref->bv_val, 0 ); + /* try next */ rc = LDAP_OTHER; goto further_cleanup; } + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: ref=\"%s\" -> \"%s\"\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); + op->o_req_dn = pdn; op->o_req_ndn = ndn; op->ors_scope = tmp_oq_search.rs_scope; @@ -798,10 +828,15 @@ ldap_chain_search( if ( lip != NULL ) { op->o_bd->be_private = (void *)lip; + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: ref=\"%s\": URI=\"%s\" found in cache\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); + } else { /* if none is found, create a temporary... */ rc = ldap_chain_db_init_one( op->o_bd ); if ( rc != 0 ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: ref=\"%s\" unable to init back-ldap for URI=\"%s\"\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); goto cleanup; } lip = (ldapinfo_t *)op->o_bd->be_private; @@ -809,6 +844,8 @@ ldap_chain_search( lip->li_bvuri = bvuri; rc = ldap_chain_db_open_one( op->o_bd ); if ( rc != 0 ) { + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: ref=\"%s\" unable to open back-ldap for URI=\"%s\"\n", + op->o_log_prefix, ref->bv_val, li.li_uri ); lip->li_uri = NULL; lip->li_bvuri = NULL; (void)ldap_chain_db_destroy_one( op->o_bd, NULL ); @@ -830,6 +867,9 @@ ldap_chain_search( } else { temporary = 1; } + + Debug( LDAP_DEBUG_TRACE, "%s ldap_chain_search: ref=\"%s\" %s\n", + op->o_log_prefix, ref->bv_val, temporary ? "temporary" : "caching" ); } lb->lb_op_f = lback->bi_op_search; @@ -1181,6 +1221,9 @@ enum { static ConfigDriver chain_cf_gen; static ConfigCfAdd chain_cfadd; static ConfigLDAPadd chain_ldadd; +#ifdef SLAP_CONFIG_DELETE +static ConfigLDAPdel chain_lddel; +#endif static ConfigTable chaincfg[] = { #ifdef LDAP_CONTROL_X_CHAINING_BEHAVIOR @@ -1228,7 +1271,11 @@ static ConfigOCs chainocs[] = { "NAME 'olcChainDatabase' " "DESC 'Chain remote server configuration' " "AUXILIARY )", - Cft_Misc, olcDatabaseDummy, chain_ldadd }, + Cft_Misc, olcDatabaseDummy, chain_ldadd +#ifdef SLAP_CONFIG_DELETE + , NULL, chain_lddel +#endif + }, { NULL, 0, NULL } }; @@ -1392,6 +1439,45 @@ chain_cfadd( Operation *op, SlapReply *rs, Entry *p, ConfigArgs *ca ) return 0; } +#ifdef SLAP_CONFIG_DELETE +static int +chain_lddel( CfEntryInfo *ce, Operation *op ) +{ + CfEntryInfo *pe = ce->ce_parent; + slap_overinst *on = (slap_overinst *)pe->ce_bi; + ldap_chain_t *lc = (ldap_chain_t *)on->on_bi.bi_private; + ldapinfo_t *li = (ldapinfo_t *) ce->ce_be->be_private; + + if ( li != lc->lc_common_li ) { + if (! avl_delete( &lc->lc_lai.lai_tree, li, ldap_chain_uri_cmp ) ) { + Debug( LDAP_DEBUG_ANY, "slapd-chain: avl_delete failed. " + "\"%s\" not found.\n", li->li_uri, 0, 0 ); + return -1; + } + } else if ( lc->lc_lai.lai_tree ) { + Debug( LDAP_DEBUG_ANY, "slapd-chain: cannot delete first underlying " + "LDAP database when other databases are still present.\n", 0, 0, 0 ); + return -1; + } else { + lc->lc_common_li = NULL; + } + + ce->ce_be->bd_info = lback; + + if ( ce->ce_be->bd_info->bi_db_close ) { + ce->ce_be->bd_info->bi_db_close( ce->ce_be, NULL ); + } + if ( ce->ce_be->bd_info->bi_db_destroy ) { + ce->ce_be->bd_info->bi_db_destroy( ce->ce_be, NULL ); + } + + ch_free(ce->ce_be); + ce->ce_be = NULL; + + return LDAP_SUCCESS; +} +#endif /* SLAP_CONFIG_DELETE */ + #ifdef LDAP_CONTROL_X_CHAINING_BEHAVIOR static slap_verbmasks chaining_mode[] = { { BER_BVC("referralsRequired"), LDAP_REFERRALS_REQUIRED }, @@ -1679,20 +1765,17 @@ ldap_chain_db_config( ldap_chain_t *lc = (ldap_chain_t *)on->on_bi.bi_private; int rc = SLAP_CONF_UNKNOWN; - + if ( lc->lc_common_li == NULL ) { - void *be_private = be->be_private; - ldap_chain_db_init_common( be ); - lc->lc_common_li = lc->lc_cfg_li = (ldapinfo_t *)be->be_private; - be->be_private = be_private; + BackendDB db = *be; + ldap_chain_db_init_common( &db ); + lc->lc_common_li = lc->lc_cfg_li = (ldapinfo_t *)db.be_private; } /* Something for the chain database? */ if ( strncasecmp( argv[ 0 ], "chain-", STRLENOF( "chain-" ) ) == 0 ) { char *save_argv0 = argv[ 0 ]; - BackendInfo *bd_info = be->bd_info; - void *be_private = be->be_private; - ConfigOCs *be_cf_ocs = be->be_cf_ocs; + BackendDB db = *be; static char *allowed_argv[] = { /* special: put URI here, so in the meanwhile * it detects whether a new URI is being provided */ @@ -1731,14 +1814,14 @@ ldap_chain_db_config( } if ( which_argv == 0 ) { - rc = ldap_chain_db_init_one( be ); + rc = ldap_chain_db_init_one( &db ); if ( rc != 0 ) { Debug( LDAP_DEBUG_ANY, "%s: line %d: " "underlying slapd-ldap initialization failed.\n.", fname, lineno, 0 ); return 1; } - lc->lc_cfg_li = be->be_private; + lc->lc_cfg_li = db.be_private; } /* TODO: add checks on what other slapd-ldap(5) args @@ -1748,27 +1831,21 @@ ldap_chain_db_config( * be warned. */ - be->bd_info = lback; - be->be_private = (void *)lc->lc_cfg_li; - be->be_cf_ocs = lback->bi_cf_ocs; + db.bd_info = lback; + db.be_private = (void *)lc->lc_cfg_li; + db.be_cf_ocs = lback->bi_cf_ocs; - rc = config_generic_wrapper( be, fname, lineno, argc, argv ); + rc = config_generic_wrapper( &db, fname, lineno, argc, argv ); argv[ 0 ] = save_argv0; - be->be_cf_ocs = be_cf_ocs; - be->be_private = be_private; - be->bd_info = bd_info; if ( which_argv == 0 ) { private_destroy:; if ( rc != 0 ) { - BackendDB db = *be; - db.bd_info = lback; db.be_private = (void *)lc->lc_cfg_li; ldap_chain_db_destroy_one( &db, NULL ); lc->lc_cfg_li = NULL; - } else { if ( lc->lc_cfg_li->li_bvuri == NULL || BER_BVISNULL( &lc->lc_cfg_li->li_bvuri[ 0 ] ) @@ -1794,7 +1871,7 @@ private_destroy:; } } } - + return rc; }