X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=servers%2Fslapd%2Fback-bdb%2Fattr.c;h=15a28a91ba2bf6b9363365a168195811061c4a00;hb=0af1940f3fb59fe57b2281ef253fe1341c505c2c;hp=f058c1f59672ddcda65b19638977d5d8ee64b923;hpb=b746066b9b75c4f77d69e0dd5004584a67a2be8b;p=openldap diff --git a/servers/slapd/back-bdb/attr.c b/servers/slapd/back-bdb/attr.c index f058c1f596..15a28a91ba 100644 --- a/servers/slapd/back-bdb/attr.c +++ b/servers/slapd/back-bdb/attr.c @@ -2,7 +2,7 @@ /* $OpenLDAP$ */ /* This work is part of OpenLDAP Software . * - * Copyright 2000-2005 The OpenLDAP Foundation. + * Copyright 2000-2006 The OpenLDAP Foundation. * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -25,26 +25,56 @@ #include "back-bdb.h" #include "lutil.h" - -static int -ainfo_type_cmp( - const void *v_desc, - const void *v_a -) +/* Find the ad, return -1 if not found, + * set point for insertion if ins is non-NULL + */ +int +bdb_attr_slot( struct bdb_info *bdb, AttributeDescription *ad, unsigned *ins ) { - const AttributeDescription *desc = v_desc; - const AttrInfo *a = v_a; - return SLAP_PTRCMP(desc, a->ai_desc); + unsigned base = 0, cursor = 0; + unsigned n = bdb->bi_nattrs; + int val = 0; + + while ( 0 < n ) { + int pivot = n >> 1; + cursor = base + pivot; + + val = SLAP_PTRCMP( ad, bdb->bi_attrs[cursor]->ai_desc ); + if ( val < 0 ) { + n = pivot; + } else if ( val > 0 ) { + base = cursor + 1; + n -= pivot + 1; + } else { + return cursor; + } + } + if ( ins ) { + if ( val > 0 ) + ++cursor; + *ins = cursor; + } + return -1; } static int -ainfo_cmp( - const void *v_a, - const void *v_b -) +ainfo_insert( struct bdb_info *bdb, AttrInfo *a ) { - const AttrInfo *a = v_a, *b = v_b; - return SLAP_PTRCMP(a->ai_desc, b->ai_desc); + unsigned x; + int i = bdb_attr_slot( bdb, a->ai_desc, &x ); + + /* Is it a dup? */ + if ( i >= 0 ) + return -1; + + bdb->bi_attrs = ch_realloc( bdb->bi_attrs, ( bdb->bi_nattrs+1 ) * + sizeof( AttrInfo * )); + if ( x < bdb->bi_nattrs ) + AC_MEMCPY( &bdb->bi_attrs[x+1], &bdb->bi_attrs[x], + ( bdb->bi_nattrs - x ) * sizeof( AttrInfo *)); + bdb->bi_attrs[x] = a; + bdb->bi_nattrs++; + return 0; } AttrInfo * @@ -52,8 +82,8 @@ bdb_attr_mask( struct bdb_info *bdb, AttributeDescription *desc ) { - - return avl_find( bdb->bi_attrs, desc, ainfo_type_cmp ); + int i = bdb_attr_slot( bdb, desc, NULL ); + return i < 0 ? NULL : bdb->bi_attrs[i]; } int @@ -64,7 +94,7 @@ bdb_attr_index_config( int argc, char **argv ) { - int rc; + int rc = 0; int i; slap_mask_t mask; char **attrs; @@ -86,7 +116,8 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "no indexes specified: %s\n", fname, lineno, argv[1] ); - return LDAP_PARAM_ERROR; + rc = LDAP_PARAM_ERROR; + goto done; } } @@ -104,7 +135,8 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "index type \"%s\" undefined\n", fname, lineno, indexes[i] ); - return LDAP_PARAM_ERROR; + rc = LDAP_PARAM_ERROR; + goto done; } mask |= index; @@ -115,7 +147,8 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "no indexes selected\n", fname, lineno ); - return LDAP_PARAM_ERROR; + rc = LDAP_PARAM_ERROR; + goto done; } for ( i = 0; attrs[i] != NULL; i++ ) { @@ -139,7 +172,7 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "index component reference\"%s\" undefined\n", fname, lineno, attrs[i] ); - return rc; + goto done; } cr->cr_indexmask = mask; /* @@ -149,11 +182,6 @@ bdb_attr_index_config( } else { cr = NULL; } -#endif - a = (AttrInfo *) ch_malloc( sizeof(AttrInfo) ); - -#ifdef LDAP_COMP_MATCH - a->ai_cr = NULL; #endif ad = NULL; rc = slap_str2ad( attrs[i], &ad, &text ); @@ -162,14 +190,15 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "index attribute \"%s\" undefined\n", fname, lineno, attrs[i] ); - return rc; + goto done; } if( slap_ad_is_binary( ad ) ) { fprintf( stderr, "%s: line %d: " "index of attribute \"%s\" disallowed\n", fname, lineno, attrs[i] ); - return LDAP_UNWILLING_TO_PERFORM; + rc = LDAP_UNWILLING_TO_PERFORM; + goto done; } if( IS_SLAP_INDEX( mask, SLAP_INDEX_APPROX ) && !( @@ -180,7 +209,8 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "approx index of attribute \"%s\" disallowed\n", fname, lineno, attrs[i] ); - return LDAP_INAPPROPRIATE_MATCHING; + rc = LDAP_INAPPROPRIATE_MATCHING; + goto done; } if( IS_SLAP_INDEX( mask, SLAP_INDEX_EQUALITY ) && !( @@ -191,7 +221,8 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "equality index of attribute \"%s\" disallowed\n", fname, lineno, attrs[i] ); - return LDAP_INAPPROPRIATE_MATCHING; + rc = LDAP_INAPPROPRIATE_MATCHING; + goto done; } if( IS_SLAP_INDEX( mask, SLAP_INDEX_SUBSTR ) && !( @@ -202,12 +233,18 @@ bdb_attr_index_config( fprintf( stderr, "%s: line %d: " "substr index of attribute \"%s\" disallowed\n", fname, lineno, attrs[i] ); - return LDAP_INAPPROPRIATE_MATCHING; + rc = LDAP_INAPPROPRIATE_MATCHING; + goto done; } Debug( LDAP_DEBUG_CONFIG, "index %s 0x%04lx\n", ad->ad_cname.bv_val, mask, 0 ); + a = (AttrInfo *) ch_malloc( sizeof(AttrInfo) ); + +#ifdef LDAP_COMP_MATCH + a->ai_cr = NULL; +#endif a->ai_desc = ad; if ( bdb->bi_flags & BDB_IS_OPEN ) { @@ -220,7 +257,7 @@ bdb_attr_index_config( #ifdef LDAP_COMP_MATCH if ( cr ) { - a_cr = avl_find( bdb->bi_attrs, ad, ainfo_type_cmp ); + a_cr = bdb_attr_mask( bdb, ad ); if ( a_cr ) { /* * AttrInfo is already in AVL @@ -230,24 +267,24 @@ bdb_attr_index_config( rc = insert_component_reference( cr, &a_cr->ai_cr ); if ( rc != LDAP_SUCCESS) { fprintf( stderr, " error during inserting component reference in %s ", attrs[i]); - return LDAP_PARAM_ERROR; + rc = LDAP_PARAM_ERROR; + goto done; } continue; } else { rc = insert_component_reference( cr, &a->ai_cr ); if ( rc != LDAP_SUCCESS) { fprintf( stderr, " error during inserting component reference in %s ", attrs[i]); - return LDAP_PARAM_ERROR; + rc = LDAP_PARAM_ERROR; + goto done; } } } #endif - rc = avl_insert( &bdb->bi_attrs, (caddr_t) a, - ainfo_cmp, avl_dup_error ); - + rc = ainfo_insert( bdb, a ); if( rc ) { if ( bdb->bi_flags & BDB_IS_OPEN ) { - AttrInfo *b = avl_find( bdb->bi_attrs, ad, ainfo_type_cmp ); + AttrInfo *b = bdb_attr_mask( bdb, ad ); /* If we were editing this attr, reset it */ b->ai_indexmask &= ~BDB_INDEX_DELETING; /* If this is leftover from a previous add, commit it */ @@ -257,18 +294,20 @@ bdb_attr_index_config( ch_free( a ); continue; } - fprintf( stderr, "%s: line %d: duplicate index definition " - "for attr \"%s\"" SLAPD_CONF_UNKNOWN_IGNORED ".\n", + fprintf( stderr, + "%s: line %d: duplicate index definition for attr \"%s\".\n", fname, lineno, attrs[i] ); - return LDAP_PARAM_ERROR; + rc = LDAP_PARAM_ERROR; + goto done; } } +done: ldap_charray_free( attrs ); if ( indexes != NULL ) ldap_charray_free( indexes ); - return LDAP_SUCCESS; + return rc; } static int @@ -298,17 +337,19 @@ static AttrInfo aidef = { &addef }; void bdb_attr_index_unparse( struct bdb_info *bdb, BerVarray *bva ) { + int i; + if ( bdb->bi_defaultmask ) { aidef.ai_indexmask = bdb->bi_defaultmask; bdb_attr_index_unparser( &aidef, bva ); } - avl_apply( bdb->bi_attrs, bdb_attr_index_unparser, bva, -1, AVL_INORDER ); + for ( i=0; ibi_nattrs; i++ ) + bdb_attr_index_unparser( bdb->bi_attrs[i], bva ); } -static void -bdb_attrinfo_free( void *v ) +void +bdb_attr_info_free( AttrInfo *ai ) { - AttrInfo *ai = v; #ifdef LDAP_COMP_MATCH free( ai->ai_cr ); #endif @@ -316,52 +357,41 @@ bdb_attrinfo_free( void *v ) } void -bdb_attr_index_destroy( Avlnode *tree ) +bdb_attr_index_destroy( struct bdb_info *bdb ) { - avl_free( tree, bdb_attrinfo_free ); -} + int i; -void bdb_attr_index_free( struct bdb_info *bdb, AttributeDescription *ad ) -{ - AttrInfo *ai; + for ( i=0; ibi_nattrs; i++ ) + bdb_attr_info_free( bdb->bi_attrs[i] ); - ai = avl_delete( &bdb->bi_attrs, ad, ainfo_type_cmp ); - if ( ai ) - bdb_attrinfo_free( ai ); + free( bdb->bi_attrs ); } -/* Get a list of AttrInfo's to delete */ - -typedef struct Alist { - struct Alist *next; - AttrInfo *ptr; -} Alist; - -static int -bdb_attrinfo_flush( void *v1, void *arg ) +void bdb_attr_index_free( struct bdb_info *bdb, AttributeDescription *ad ) { - AttrInfo *ai = v1; - - if ( ai->ai_indexmask & BDB_INDEX_DELETING ) { - Alist **al = arg; - Alist *a = ch_malloc( sizeof( Alist )); - a->ptr = ai; - a->next = *al; - *al = a; + int i; + + i = bdb_attr_slot( bdb, ad, NULL ); + if ( i >= 0 ) { + bdb_attr_info_free( bdb->bi_attrs[i] ); + bdb->bi_nattrs--; + for (; ibi_nattrs; i++) + bdb->bi_attrs[i] = bdb->bi_attrs[i+1]; } - return 0; } void bdb_attr_flush( struct bdb_info *bdb ) { - Alist *al = NULL, *a2; - - avl_apply( bdb->bi_attrs, bdb_attrinfo_flush, &al, -1, AVL_INORDER ); - - while (( a2 = al )) { - al = al->next; - avl_delete( &bdb->bi_attrs, a2->ptr, ainfo_cmp ); - bdb_attrinfo_free( a2->ptr ); - ch_free( a2 ); + int i; + + for ( i=0; ibi_nattrs; i++ ) { + if ( bdb->bi_attrs[i]->ai_indexmask & BDB_INDEX_DELETING ) { + int j; + bdb_attr_info_free( bdb->bi_attrs[i] ); + bdb->bi_nattrs--; + for (j=i; jbi_nattrs; j++) + bdb->bi_attrs[j] = bdb->bi_attrs[j+1]; + i--; + } } }