X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=servers%2Fslapd%2Fvalue.c;h=a1e081664d1d40f043fc7f1d652bf7c1cc186b08;hb=ed471a4d53b9bcd2cc89410743ffb4bd58b5fc05;hp=bc139e2f8e649f82fa31e99c8d94c892e5560555;hpb=185ff129b59340698f32e9e8ecf26c21fb58b446;p=openldap diff --git a/servers/slapd/value.c b/servers/slapd/value.c index bc139e2f8e..a1e081664d 100644 --- a/servers/slapd/value.c +++ b/servers/slapd/value.c @@ -1,7 +1,7 @@ /* value.c - routines for dealing with values */ /* $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 */ @@ -20,36 +20,141 @@ int value_add( - struct berval ***vals, - struct berval **addvals + BerVarray *vals, + BerVarray addvals ) { - int n, nn, i, j; + int n, nn; + BerVarray v2; - for ( nn = 0; addvals != NULL && addvals[nn] != NULL; nn++ ) + for ( nn = 0; addvals != NULL && addvals[nn].bv_val != NULL; nn++ ) ; /* NULL */ if ( *vals == NULL ) { - *vals = (struct berval **) ch_malloc( (nn + 1) - * sizeof(struct berval *) ); + *vals = (BerVarray) SLAP_MALLOC( (nn + 1) + * sizeof(struct berval) ); + if( *vals == NULL ) { +#ifdef NEW_LOGGING + LDAP_LOG( OPERATION, ERR, + "value_add: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#else + Debug(LDAP_DEBUG_TRACE, + "value_add: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#endif + return LBER_ERROR_MEMORY; + } n = 0; - } else { - for ( n = 0; (*vals)[n] != NULL; n++ ) - ; /* NULL */ - *vals = (struct berval **) ch_realloc( (char *) *vals, - (n + nn + 1) * sizeof(struct berval *) ); + for ( n = 0; (*vals)[n].bv_val != NULL; n++ ) { + ; /* Empty */ + } + *vals = (BerVarray) SLAP_REALLOC( (char *) *vals, + (n + nn + 1) * sizeof(struct berval) ); + if( *vals == NULL ) { +#ifdef NEW_LOGGING + LDAP_LOG( OPERATION, ERR, + "value_add: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#else + Debug(LDAP_DEBUG_TRACE, + "value_add: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#endif + return LBER_ERROR_MEMORY; + } } - for ( i = 0, j = 0; i < nn; i++ ) { - (*vals)[n + j] = ber_bvdup( addvals[i] ); - if( (*vals)[n + j++] == NULL ) break; + v2 = *vals + n; + for ( ; addvals->bv_val; v2++, addvals++ ) { + ber_dupbv(v2, addvals); + if (v2->bv_val == NULL) break; } - (*vals)[n + j] = NULL; + v2->bv_val = NULL; + v2->bv_len = 0; return LDAP_SUCCESS; } +int +value_add_one( + BerVarray *vals, + struct berval *addval +) +{ + int n; + BerVarray v2; + + if ( *vals == NULL ) { + *vals = (BerVarray) SLAP_MALLOC( 2 * sizeof(struct berval) ); + if( *vals == NULL ) { +#ifdef NEW_LOGGING + LDAP_LOG( OPERATION, ERR, + "value_add_one: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#else + Debug(LDAP_DEBUG_TRACE, + "value_add_one: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#endif + return LBER_ERROR_MEMORY; + } + n = 0; + } else { + for ( n = 0; (*vals)[n].bv_val != NULL; n++ ) { + ; /* Empty */ + } + *vals = (BerVarray) SLAP_REALLOC( (char *) *vals, + (n + 2) * sizeof(struct berval) ); + if( *vals == NULL ) { +#ifdef NEW_LOGGING + LDAP_LOG( OPERATION, ERR, + "value_add_one: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#else + Debug(LDAP_DEBUG_TRACE, + "value_add_one: SLAP_MALLOC failed.\n", 0, 0, 0 ); +#endif + return LBER_ERROR_MEMORY; + } + } + + v2 = *vals + n; + ber_dupbv(v2, addval); + + v2++; + v2->bv_val = NULL; + v2->bv_len = 0; + + return LDAP_SUCCESS; +} + +int +value_validate( + MatchingRule *mr, + struct berval *in, + const char **text ) +{ + int rc; + + if( mr == NULL ) { + *text = "inappropriate matching request"; + return LDAP_INAPPROPRIATE_MATCHING; + } + + if( mr->smr_syntax == NULL ) { + *text = "no assertion syntax"; + return LDAP_INVALID_SYNTAX; + } + + if( ! mr->smr_syntax->ssyn_validate ) { + *text = "no syntax validator"; + return LDAP_INVALID_SYNTAX; + } + + rc = (mr->smr_syntax->ssyn_validate)( mr->smr_syntax, in ); + + if( rc != LDAP_SUCCESS ) { + *text = "value is invalid"; + return LDAP_INVALID_SYNTAX; + } + + return LDAP_SUCCESS; +} int value_normalize( @@ -119,6 +224,91 @@ value_normalize( return LDAP_SUCCESS; } +int +value_validate_normalize( + AttributeDescription *ad, + unsigned usage, + struct berval *in, + struct berval *out, + const char **text ) +{ + int rc; + MatchingRule *mr; + + switch( usage & SLAP_MR_TYPE_MASK ) { + case SLAP_MR_NONE: + case SLAP_MR_EQUALITY: + mr = ad->ad_type->sat_equality; + break; + case SLAP_MR_ORDERING: + mr = ad->ad_type->sat_ordering; + break; + case SLAP_MR_SUBSTR: + mr = ad->ad_type->sat_substr; + break; + case SLAP_MR_EXT: + default: + assert( 0 ); + *text = "internal error"; + return LDAP_OTHER; + } + + if( mr == NULL ) { + *text = "inappropriate matching request"; + return LDAP_INAPPROPRIATE_MATCHING; + } + + if( mr->smr_syntax == NULL ) { + *text = "no assertion syntax"; + return LDAP_INVALID_SYNTAX; + } + + if( ! mr->smr_syntax->ssyn_validate ) { + *text = "no syntax validator"; + return LDAP_INVALID_SYNTAX; + } + + rc = (mr->smr_syntax->ssyn_validate)( mr->smr_syntax, in ); + + if( rc != LDAP_SUCCESS ) { + *text = "value is invalid"; + return LDAP_INVALID_SYNTAX; + } + + /* we only support equality matching of binary attributes */ + /* This is suspect, flexible certificate matching will hit this */ + if( slap_ad_is_binary( ad ) && usage != SLAP_MR_EQUALITY ) { + *text = "inappropriate binary matching"; + return LDAP_INAPPROPRIATE_MATCHING; + } + + if( mr->smr_normalize ) { + rc = (mr->smr_normalize)( usage, + ad->ad_type->sat_syntax, + mr, in, out ); + + if( rc != LDAP_SUCCESS ) { + *text = "unable to normalize value"; + return LDAP_INVALID_SYNTAX; + } + + } else if ( mr->smr_syntax->ssyn_normalize ) { + rc = (mr->smr_syntax->ssyn_normalize)( + ad->ad_type->sat_syntax, + in, out ); + + if( rc != LDAP_SUCCESS ) { + *text = "unable to normalize value"; + return LDAP_INVALID_SYNTAX; + } + + } else { + ber_dupbv( out, in ); + } + + return LDAP_SUCCESS; +} + int value_match( @@ -131,8 +321,10 @@ value_match( const char ** text ) { int rc; - struct berval nv1; - struct berval nv2; + struct berval nv1 = { 0, NULL }; + struct berval nv2 = { 0, NULL }; + + assert( mr != NULL ); if( !mr->smr_match ) { return LDAP_INAPPROPRIATE_MATCHING; @@ -165,8 +357,8 @@ value_match( nv1.bv_val != NULL ? &nv1 : v1, nv2.bv_val != NULL ? &nv2 : v2 ); - free( nv1.bv_val ); - free( nv2.bv_val ); + if (nv1.bv_val ) free( nv1.bv_val ); + if (nv2.bv_val ) free( nv2.bv_val ); return rc; } @@ -174,13 +366,12 @@ value_match( int value_find_ex( AttributeDescription *ad, unsigned flags, - struct berval **vals, + BerVarray vals, struct berval *val ) { int i; int rc; - struct berval nval; - struct berval nval_tmp; + struct berval nval = { 0, NULL }; MatchingRule *mr = ad->ad_type->sat_equality; if( mr == NULL || !mr->smr_match ) { @@ -200,9 +391,13 @@ int value_find_ex( flags |= SLAP_MR_VALUE_SYNTAX_CONVERTED_MATCH; } - if( mr->smr_syntax->ssyn_normalize ) { + if( !(flags & SLAP_MR_VALUE_NORMALIZED_MATCH) && + mr->smr_syntax->ssyn_normalize ) { + struct berval nval_tmp = { 0, NULL }; + rc = mr->smr_syntax->ssyn_normalize( - mr->smr_syntax, nval.bv_val == NULL ? val : &nval, &nval_tmp ); + mr->smr_syntax, + nval.bv_val == NULL ? val : &nval, &nval_tmp ); free(nval.bv_val); nval = nval_tmp; @@ -212,12 +407,12 @@ int value_find_ex( } } - for ( i = 0; vals[i] != NULL; i++ ) { + for ( i = 0; vals[i].bv_val != NULL; i++ ) { int match; const char *text; rc = value_match( &match, ad, mr, flags, - vals[i], nval.bv_val == NULL ? val : &nval, &text ); + &vals[i], nval.bv_val == NULL ? val : &nval, &text ); if( rc == LDAP_SUCCESS && match == 0 ) { free( nval.bv_val );