]> git.sur5r.net Git - openldap/blobdiff - servers/slapd/mr.c
Add a safety check to bvcasechr
[openldap] / servers / slapd / mr.c
index 52bdbe96eb252a759c0e66e12c63b11f72bad2e8..316ff13641621edf58ff5d7b8038e12b28e8ecb7 100644 (file)
@@ -1,7 +1,7 @@
 /* mr.c - routines to manage matching rule definitions */
 /* $OpenLDAP$ */
 /*
- * Copyright 1998-2000 The OpenLDAP Foundation, All Rights Reserved.
+ * Copyright 1998-2002 The OpenLDAP Foundation, All Rights Reserved.
  * COPYING RESTRICTIONS APPLY, see COPYRIGHT file
  */
 
@@ -18,7 +18,7 @@
 
 
 struct mindexrec {
-       char            *mir_name;
+       struct berval   mir_name;
        MatchingRule    *mir_mr;
 };
 
@@ -31,20 +31,34 @@ mr_index_cmp(
     struct mindexrec   *mir2
 )
 {
-       return (strcmp( mir1->mir_name, mir2->mir_name ));
+       int i = mir1->mir_name.bv_len - mir2->mir_name.bv_len;
+       if (i) return i;
+       return (strcmp( mir1->mir_name.bv_val, mir2->mir_name.bv_val ));
 }
 
 static int
 mr_index_name_cmp(
-    char               *name,
+    struct berval      *name,
     struct mindexrec   *mir
 )
 {
-       return (strcmp( name, mir->mir_name ));
+       int i = name->bv_len - mir->mir_name.bv_len;
+       if (i) return i;
+       return (strncmp( name->bv_val, mir->mir_name.bv_val, name->bv_len ));
 }
 
 MatchingRule *
 mr_find( const char *mrname )
+{
+       struct berval bv;
+
+       bv.bv_val = (char *)mrname;
+       bv.bv_len = strlen( mrname );
+       return mr_bvfind( &bv );
+}
+
+MatchingRule *
+mr_bvfind( struct berval *mrname )
 {
        struct mindexrec        *mir = NULL;
 
@@ -86,7 +100,8 @@ mr_insert(
        if ( smr->smr_oid ) {
                mir = (struct mindexrec *)
                        ch_calloc( 1, sizeof(struct mindexrec) );
-               mir->mir_name = smr->smr_oid;
+               mir->mir_name.bv_val = smr->smr_oid;
+               mir->mir_name.bv_len = strlen( smr->smr_oid );
                mir->mir_mr = smr;
                if ( avl_insert( &mr_index, (caddr_t) mir,
                                 (AVL_CMP) mr_index_cmp,
@@ -96,13 +111,14 @@ mr_insert(
                        return SLAP_SCHERR_DUP_RULE;
                }
                /* FIX: temporal consistency check */
-               mr_find(mir->mir_name);
+               mr_bvfind(&mir->mir_name);
        }
        if ( (names = smr->smr_names) ) {
                while ( *names ) {
                        mir = (struct mindexrec *)
                                ch_calloc( 1, sizeof(struct mindexrec) );
-                       mir->mir_name = *names;
+                       mir->mir_name.bv_val = *names;
+                       mir->mir_name.bv_len = strlen( *names );
                        mir->mir_mr = smr;
                        if ( avl_insert( &mr_index, (caddr_t) mir,
                                         (AVL_CMP) mr_index_cmp,
@@ -112,7 +128,7 @@ mr_insert(
                                return SLAP_SCHERR_DUP_RULE;
                        }
                        /* FIX: temporal consistency check */
-                       mr_find(mir->mir_name);
+                       mr_bvfind(&mir->mir_name);
                        names++;
                }
        }
@@ -139,6 +155,7 @@ mr_add(
        smr = (MatchingRule *) ch_calloc( 1, sizeof(MatchingRule) );
        AC_MEMCPY( &smr->smr_mrule, mr, sizeof(LDAPMatchingRule));
 
+       smr->smr_oidlen = strlen( mr->mr_oid );
        smr->smr_usage = usage;
        smr->smr_convert = convert;
        smr->smr_normalize = normalize;
@@ -255,34 +272,33 @@ register_matching_rule(
 
 int mr_schema_info( Entry *e )
 {
-       struct berval   val;
-       struct berval   *vals[2];
+       struct berval   vals[2];
        MatchingRule    *mr;
 
        AttributeDescription *ad_matchingRules = slap_schema.si_ad_matchingRules;
 
-       vals[0] = &val;
-       vals[1] = NULL;
+       vals[1].bv_val = NULL;
 
        for ( mr = mr_list; mr; mr = mr->smr_next ) {
+               if ( mr->smr_usage & SLAP_MR_HIDE ) {
+                       /* skip hidden rules */
+                       continue;
+               }
+
                if ( ! mr->smr_match ) {
                        /* skip rules without matching functions */
                        continue;
                }
 
-               val.bv_val = ldap_matchingrule2str( &mr->smr_mrule );
-
-               if ( val.bv_val == NULL ) {
+               if ( ldap_matchingrule2bv( &mr->smr_mrule, vals ) == NULL ) {
                        return -1;
                }
-
-               val.bv_len = strlen( val.bv_val );
 #if 0
                Debug( LDAP_DEBUG_TRACE, "Merging mr [%ld] %s\n",
-              (long) val.bv_len, val.bv_val, 0 );
+              (long) vals[0].bv_len, vals[0].bv_val, 0 );
 #endif
                attr_merge( e, ad_matchingRules, vals );
-               ldap_memfree( val.bv_val );
+               ldap_memfree( vals[0].bv_val );
        }
        return 0;
 }