]> git.sur5r.net Git - openldap/commitdiff
Don't decode entries until we know they're in scope
authorHoward Chu <hyc@openldap.org>
Mon, 27 Aug 2012 21:08:06 +0000 (14:08 -0700)
committerHoward Chu <hyc@openldap.org>
Mon, 27 Aug 2012 21:08:06 +0000 (14:08 -0700)
servers/slapd/back-mdb/id2entry.c
servers/slapd/back-mdb/proto-mdb.h
servers/slapd/back-mdb/search.c

index 29ff9c80ed0203933c2757707746277b328c3ac5..9927411bbd3eec1428b8879f22a4f7dc26f01ff0 100644 (file)
@@ -114,6 +114,21 @@ int mdb_id2entry_update(
        return mdb_id2entry_put(op, txn, mc, e, 0);
 }
 
+int mdb_id2edata(
+       Operation *op,
+       MDB_cursor *mc,
+       ID id,
+       MDB_val *data )
+{
+       MDB_val key;
+
+       key.mv_data = &id;
+       key.mv_size = sizeof(ID);
+
+       /* fetch it */
+       return mdb_cursor_get( mc, &key, data, MDB_SET );
+}
+
 int mdb_id2entry(
        Operation *op,
        MDB_cursor *mc,
index 799e8171700f277ceaa3d4946ab613add6d084b8..e989f0f75b27750b32be9c2e59731829de311900 100644 (file)
@@ -175,6 +175,12 @@ int mdb_id2entry(
        ID id,
        Entry **e);
 
+int mdb_id2edata(
+       Operation *op,
+       MDB_cursor *mc,
+       ID id,
+       MDB_val *data);
+
 int mdb_entry_return( Operation *op, Entry *e );
 BI_entry_release_rw mdb_entry_release;
 BI_entry_get_rw mdb_entry_get;
index fda36ebf11d898a312741c75b3a04365987484a0..f3d51cb5505e69ee2124656c54168acd1d655d3e 100644 (file)
@@ -129,7 +129,7 @@ static Entry * deref_base (
 static int search_aliases(
        Operation *op,
        SlapReply *rs,
-       Entry *e,
+       ID e_id,
        MDB_txn *txn,
        MDB_cursor *mci,
        ID2L scopes,
@@ -164,7 +164,7 @@ static int search_aliases(
                return rs->sr_err;
        }
        oldsubs[0] = 1;
-       oldsubs[1] = e->e_id;
+       oldsubs[1] = e_id;
 
        MDB_IDL_ZERO( visited );
        MDB_IDL_ZERO( newsubs );
@@ -176,13 +176,7 @@ static int search_aliases(
                /* Set curscop to only the aliases in the current scope. Start with
                 * all the aliases, then get the intersection with the scope.
                 */
-               rs->sr_err = mdb_idscope( op, txn, e->e_id, aliases, curscop );
-
-               if (first) {
-                       first = 0;
-               } else {
-                       mdb_entry_return( op, e );
-               }
+               rs->sr_err = mdb_idscope( op, txn, e_id, aliases, curscop );
 
                /* Dereference all of the aliases in the current scope. */
                cursora = 0;
@@ -248,9 +242,13 @@ nextido:
                 * be found, ignore it and move on. This should never happen;
                 * we should never see the ID of an entry that doesn't exist.
                 */
-               rs->sr_err = mdb_id2entry(op, mci, ido, &e);
-               if ( rs->sr_err != LDAP_SUCCESS ) {
-                       goto nextido;
+               {
+                       MDB_val edata;
+                       rs->sr_err = mdb_id2edata(op, mci, ido, &edata);
+                       if ( rs->sr_err != MDB_SUCCESS ) {
+                               goto nextido;
+                       }
+                       e_id = ido;
                }
        }
        return rs->sr_err;
@@ -605,6 +603,7 @@ dn2entry_retry:
                  id != NOID ; id = mdb_idl_next( candidates, &cursor ) )
        {
                int scopeok;
+               MDB_val edata;
 
 loop_begin:
 
@@ -640,20 +639,8 @@ loop_begin:
                } else {
 
                        /* get the entry */
-                       rs->sr_err = mdb_id2entry( op, mci, id, &e );
-
-                       if (rs->sr_err == LDAP_BUSY) {
-                               rs->sr_text = "ldap server busy";
-                               send_ldap_result( op, rs );
-                               goto done;
-
-                       } else if ( rs->sr_err == LDAP_OTHER ) {
-                               rs->sr_text = "internal error";
-                               send_ldap_result( op, rs );
-                               goto done;
-                       }
-
-                       if ( e == NULL ) {
+                       rs->sr_err = mdb_id2edata( op, mci, id, &edata );
+                       if ( rs->sr_err  == MDB_NOTFOUND ) {
                                if( !MDB_IDL_IS_RANGE(candidates) ) {
                                        /* only complain for non-range IDLs */
                                        Debug( LDAP_DEBUG_TRACE,
@@ -676,28 +663,14 @@ loop_begin:
                                }
 
                                goto loop_continue;
+                       } else if ( rs->sr_err ) {
+                               rs->sr_err = LDAP_OTHER;
+                               rs->sr_text = "internal error in mdb_id2edata";
+                               send_ldap_result( op, rs );
+                               goto done;
                        }
                }
 
-               if ( is_entry_subentry( e ) ) {
-                       if( op->oq_search.rs_scope != LDAP_SCOPE_BASE ) {
-                               if(!get_subentries_visibility( op )) {
-                                       /* only subentries are visible */
-                                       goto loop_continue;
-                               }
-
-                       } else if ( get_subentries( op ) &&
-                               !get_subentries_visibility( op ))
-                       {
-                               /* only subentries are visible */
-                               goto loop_continue;
-                       }
-
-               } else if ( get_subentries_visibility( op )) {
-                       /* only subentries are visible */
-                       goto loop_continue;
-               }
-
                /* Does this candidate actually satisfy the search scope?
                 */
                scopeok = 0;
@@ -725,6 +698,45 @@ loop_begin:
                        break;
                }
 
+               /* Not in scope, ignore it */
+               if ( !scopeok )
+               {
+                       Debug( LDAP_DEBUG_TRACE,
+                               LDAP_XSTRING(mdb_search)
+                               ": %ld scope not okay\n",
+                               (long) id, 0, 0 );
+                       goto loop_continue;
+               }
+
+               if ( id != base->e_id ) {
+                       rs->sr_err = mdb_entry_decode( op, &edata, &e );
+                       if ( rs->sr_err ) {
+                               rs->sr_err = LDAP_OTHER;
+                               rs->sr_text = "internal error in mdb_endtry_decode";
+                               send_ldap_result( op, rs );
+                               goto done;
+                       }
+               }
+
+               if ( is_entry_subentry( e ) ) {
+                       if( op->oq_search.rs_scope != LDAP_SCOPE_BASE ) {
+                               if(!get_subentries_visibility( op )) {
+                                       /* only subentries are visible */
+                                       goto loop_continue;
+                               }
+
+                       } else if ( get_subentries( op ) &&
+                               !get_subentries_visibility( op ))
+                       {
+                               /* only subentries are visible */
+                               goto loop_continue;
+                       }
+
+               } else if ( get_subentries_visibility( op )) {
+                       /* only subentries are visible */
+                       goto loop_continue;
+               }
+
                /* aliases were already dereferenced in candidate list */
                if ( op->ors_deref & LDAP_DEREF_SEARCHING ) {
                        /* but if the search base is an alias, and we didn't
@@ -738,16 +750,6 @@ loop_begin:
                        }
                }
 
-               /* Not in scope, ignore it */
-               if ( !scopeok )
-               {
-                       Debug( LDAP_DEBUG_TRACE,
-                               LDAP_XSTRING(mdb_search)
-                               ": %ld scope not okay\n",
-                               (long) id, 0, 0 );
-                       goto loop_continue;
-               }
-
                if ( !manageDSAit && is_entry_glue( e )) {
                        goto loop_continue;
                }