X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=servers%2Fslapd%2Fback-bdb%2Foperational.c;h=f30fb001c87029919c38f5f5600a84fd665e8259;hb=7d13ef7e42f1514dd99878835a13a700da4f4b69;hp=33b8f93784c173386cda01572cf0f4e9080dfef9;hpb=3dadeb3efe31c72dacc2e0e11ee25c271dffe44d;p=openldap diff --git a/servers/slapd/back-bdb/operational.c b/servers/slapd/back-bdb/operational.c index 33b8f93784..f30fb001c8 100644 --- a/servers/slapd/back-bdb/operational.c +++ b/servers/slapd/back-bdb/operational.c @@ -2,7 +2,7 @@ /* $OpenLDAP$ */ /* This work is part of OpenLDAP Software . * - * Copyright 2000-2010 The OpenLDAP Foundation. + * Copyright 2000-2012 The OpenLDAP Foundation. * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -39,6 +39,7 @@ bdb_hasSubordinates( OpExtra *oex; DB_TXN *rtxn; int rc; + int release = 0; assert( e != NULL ); @@ -48,7 +49,18 @@ bdb_hasSubordinates( * let's disable the hasSubordinate feature for back-relay. */ if ( BEI( e ) == NULL ) { - return LDAP_OTHER; + Entry *ee = NULL; + rc = be_entry_get_rw( op, &e->e_nname, NULL, NULL, 0, &ee ); + if ( rc != LDAP_SUCCESS || ee == NULL ) { + rc = LDAP_OTHER; + goto done; + } + e = ee; + release = 1; + if ( BEI( ee ) == NULL ) { + rc = LDAP_OTHER; + goto done; + } } /* Check for a txn in a parent op, otherwise use reader txn */ @@ -61,7 +73,10 @@ bdb_hasSubordinates( rtxn = opinfo->boi_txn; } else { rc = bdb_reader_get(op, bdb->bi_dbenv, &rtxn); - if ( rc ) return LDAP_OTHER; + if ( rc ) { + rc = LDAP_OTHER; + goto done; + } } retry: @@ -92,6 +107,8 @@ retry: rc = LDAP_OTHER; } +done:; + if ( release && e != NULL ) be_entry_release_r( op, e ); return rc; } @@ -107,11 +124,16 @@ bdb_operational( assert( rs->sr_entry != NULL ); - for ( ap = &rs->sr_operational_attrs; *ap; ap = &(*ap)->a_next ) - /* just count */ ; + for ( ap = &rs->sr_operational_attrs; *ap; ap = &(*ap)->a_next ) { + if ( (*ap)->a_desc == slap_schema.si_ad_hasSubordinates ) { + break; + } + } - if ( SLAP_OPATTRS( rs->sr_attr_flags ) || - ad_inlist( slap_schema.si_ad_hasSubordinates, rs->sr_attrs ) ) + if ( *ap == NULL && + attr_find( rs->sr_entry->e_attrs, slap_schema.si_ad_hasSubordinates ) == NULL && + ( SLAP_OPATTRS( rs->sr_attr_flags ) || + ad_inlist( slap_schema.si_ad_hasSubordinates, rs->sr_attrs ) ) ) { int hasSubordinates, rc;