1 /* filter.c - routines for parsing and dealing with filters */
3 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
5 * Copyright 1998-2007 The OpenLDAP Foundation.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted only as authorized by the OpenLDAP
12 * A copy of this license is available in the file LICENSE in the
13 * top-level directory of the distribution or, alternatively, at
14 * <http://www.OpenLDAP.org/license.html>.
16 /* Portions Copyright (c) 1995 Regents of the University of Michigan.
17 * All rights reserved.
19 * Redistribution and use in source and binary forms are permitted
20 * provided that this notice is preserved and that due credit is given
21 * to the University of Michigan at Ann Arbor. The name of the University
22 * may not be used to endorse or promote products derived from this
23 * software without specific prior written permission. This software
24 * is provided ``as is'' without express or implied warranty.
31 #include <ac/socket.h>
32 #include <ac/string.h>
36 static int get_filter_list(
48 static void simple_vrFilter2bv(
50 ValuesReturnFilter *f,
51 struct berval *fstr );
53 static int get_simple_vrFilter(
56 ValuesReturnFilter **f,
71 Debug( LDAP_DEBUG_FILTER, "begin get_filter\n", 0, 0, 0 );
73 * A filter looks like this coming in:
75 * and [0] SET OF Filter,
76 * or [1] SET OF Filter,
78 * equalityMatch [3] AttributeValueAssertion,
79 * substrings [4] SubstringFilter,
80 * greaterOrEqual [5] AttributeValueAssertion,
81 * lessOrEqual [6] AttributeValueAssertion,
82 * present [7] AttributeType,
83 * approxMatch [8] AttributeValueAssertion,
84 * extensibleMatch [9] MatchingRuleAssertion
87 * SubstringFilter ::= SEQUENCE {
89 * SEQUENCE OF CHOICE {
90 * initial [0] IA5String,
96 * MatchingRuleAssertion ::= SEQUENCE {
97 * matchingRule [1] MatchingRuleId OPTIONAL,
98 * type [2] AttributeDescription OPTIONAL,
99 * matchValue [3] AssertionValue,
100 * dnAttributes [4] BOOLEAN DEFAULT FALSE
105 tag = ber_peek_tag( ber, &len );
107 if( tag == LBER_ERROR ) {
108 *text = "error decoding filter";
109 return SLAPD_DISCONNECT;
117 switch ( f.f_choice ) {
118 case LDAP_FILTER_EQUALITY:
119 Debug( LDAP_DEBUG_FILTER, "EQUALITY\n", 0, 0, 0 );
120 err = get_ava( op, ber, &f, SLAP_MR_EQUALITY, text );
121 if ( err != LDAP_SUCCESS ) {
125 assert( f.f_ava != NULL );
128 case LDAP_FILTER_SUBSTRINGS:
129 Debug( LDAP_DEBUG_FILTER, "SUBSTRINGS\n", 0, 0, 0 );
130 err = get_ssa( op, ber, &f, text );
131 if( err != LDAP_SUCCESS ) {
134 assert( f.f_sub != NULL );
138 Debug( LDAP_DEBUG_FILTER, "GE\n", 0, 0, 0 );
139 err = get_ava( op, ber, &f, SLAP_MR_ORDERING, text );
140 if ( err != LDAP_SUCCESS ) {
143 assert( f.f_ava != NULL );
147 Debug( LDAP_DEBUG_FILTER, "LE\n", 0, 0, 0 );
148 err = get_ava( op, ber, &f, SLAP_MR_ORDERING, text );
149 if ( err != LDAP_SUCCESS ) {
152 assert( f.f_ava != NULL );
155 case LDAP_FILTER_PRESENT: {
158 Debug( LDAP_DEBUG_FILTER, "PRESENT\n", 0, 0, 0 );
159 if ( ber_scanf( ber, "m", &type ) == LBER_ERROR ) {
160 err = SLAPD_DISCONNECT;
161 *text = "error decoding filter";
166 err = slap_bv2ad( &type, &f.f_desc, text );
168 if( err != LDAP_SUCCESS ) {
169 f.f_choice |= SLAPD_FILTER_UNDEFINED;
170 err = slap_bv2undef_ad( &type, &f.f_desc, text,
171 SLAP_AD_PROXIED|SLAP_AD_NOINSERT );
173 if ( err != LDAP_SUCCESS ) {
174 /* unrecognized attribute description or other error */
175 Debug( LDAP_DEBUG_ANY,
176 "get_filter: conn %lu unknown attribute "
178 op->o_connid, type.bv_val, err );
181 f.f_desc = slap_bv2tmp_ad( &type, op->o_tmpmemctx );
186 assert( f.f_desc != NULL );
189 case LDAP_FILTER_APPROX:
190 Debug( LDAP_DEBUG_FILTER, "APPROX\n", 0, 0, 0 );
191 err = get_ava( op, ber, &f, SLAP_MR_EQUALITY_APPROX, text );
192 if ( err != LDAP_SUCCESS ) {
195 assert( f.f_ava != NULL );
198 case LDAP_FILTER_AND:
199 Debug( LDAP_DEBUG_FILTER, "AND\n", 0, 0, 0 );
200 err = get_filter_list( op, ber, &f.f_and, text );
201 if ( err != LDAP_SUCCESS ) {
204 if ( f.f_and == NULL ) {
205 f.f_choice = SLAPD_FILTER_COMPUTED;
206 f.f_result = LDAP_COMPARE_TRUE;
208 /* no assert - list could be empty */
212 Debug( LDAP_DEBUG_FILTER, "OR\n", 0, 0, 0 );
213 err = get_filter_list( op, ber, &f.f_or, text );
214 if ( err != LDAP_SUCCESS ) {
217 if ( f.f_or == NULL ) {
218 f.f_choice = SLAPD_FILTER_COMPUTED;
219 f.f_result = LDAP_COMPARE_FALSE;
221 /* no assert - list could be empty */
224 case LDAP_FILTER_NOT:
225 Debug( LDAP_DEBUG_FILTER, "NOT\n", 0, 0, 0 );
226 (void) ber_skip_tag( ber, &len );
227 err = get_filter( op, ber, &f.f_not, text );
228 if ( err != LDAP_SUCCESS ) {
232 assert( f.f_not != NULL );
233 if ( f.f_not->f_choice == SLAPD_FILTER_COMPUTED ) {
234 int fresult = f.f_not->f_result;
235 f.f_choice = SLAPD_FILTER_COMPUTED;
236 op->o_tmpfree( f.f_not, op->o_tmpmemctx );
240 case LDAP_COMPARE_TRUE:
241 f.f_result = LDAP_COMPARE_FALSE;
243 case LDAP_COMPARE_FALSE:
244 f.f_result = LDAP_COMPARE_TRUE;
247 /* (!Undefined) is Undefined */
252 case LDAP_FILTER_EXT:
253 Debug( LDAP_DEBUG_FILTER, "EXTENSIBLE\n", 0, 0, 0 );
255 err = get_mra( op, ber, &f, text );
256 if ( err != LDAP_SUCCESS ) {
260 assert( f.f_mra != NULL );
264 (void) ber_scanf( ber, "x" ); /* skip the element */
265 Debug( LDAP_DEBUG_ANY, "get_filter: unknown filter type=%lu\n",
267 f.f_choice = SLAPD_FILTER_COMPUTED;
268 f.f_result = SLAPD_COMPARE_UNDEFINED;
272 if( err != LDAP_SUCCESS && err != SLAPD_DISCONNECT ) {
275 f.f_choice = SLAPD_FILTER_COMPUTED;
276 f.f_result = SLAPD_COMPARE_UNDEFINED;
280 if ( err == LDAP_SUCCESS ) {
281 *filt = op->o_tmpalloc( sizeof(f), op->o_tmpmemctx );
285 Debug( LDAP_DEBUG_FILTER, "end get_filter %d\n", err, 0, 0 );
291 get_filter_list( Operation *op, BerElement *ber,
301 Debug( LDAP_DEBUG_FILTER, "begin get_filter_list\n", 0, 0, 0 );
303 for ( tag = ber_first_element( ber, &len, &last );
305 tag = ber_next_element( ber, &len, last ) )
307 err = get_filter( op, ber, new, text );
308 if ( err != LDAP_SUCCESS )
310 new = &(*new)->f_next;
314 Debug( LDAP_DEBUG_FILTER, "end get_filter_list\n", 0, 0, 0 );
315 return( LDAP_SUCCESS );
328 struct berval desc, value, nvalue;
330 SubstringsAssertion ssa;
332 *text = "error decoding filter";
334 Debug( LDAP_DEBUG_FILTER, "begin get_ssa\n", 0, 0, 0 );
335 if ( ber_scanf( ber, "{m" /*}*/, &desc ) == LBER_ERROR ) {
336 return SLAPD_DISCONNECT;
342 ssa.sa_initial.bv_val = NULL;
344 ssa.sa_final.bv_val = NULL;
346 rc = slap_bv2ad( &desc, &ssa.sa_desc, text );
348 if( rc != LDAP_SUCCESS ) {
349 f->f_choice |= SLAPD_FILTER_UNDEFINED;
350 rc = slap_bv2undef_ad( &desc, &ssa.sa_desc, text,
351 SLAP_AD_PROXIED|SLAP_AD_NOINSERT );
353 if( rc != LDAP_SUCCESS ) {
354 Debug( LDAP_DEBUG_ANY,
355 "get_ssa: conn %lu unknown attribute type=%s (%ld)\n",
356 op->o_connid, desc.bv_val, (long) rc );
358 ssa.sa_desc = slap_bv2tmp_ad( &desc, op->o_tmpmemctx );
362 rc = LDAP_PROTOCOL_ERROR;
364 for ( tag = ber_first_element( ber, &len, &last );
366 tag = ber_next_element( ber, &len, last ) )
370 rc = ber_scanf( ber, "m", &value );
371 if ( rc == LBER_ERROR ) {
372 rc = SLAPD_DISCONNECT;
376 if ( value.bv_val == NULL || value.bv_len == 0 ) {
377 rc = LDAP_INVALID_SYNTAX;
382 case LDAP_SUBSTRING_INITIAL:
383 if ( ssa.sa_initial.bv_val != NULL
384 || ssa.sa_any != NULL
385 || ssa.sa_final.bv_val != NULL )
387 rc = LDAP_PROTOCOL_ERROR;
390 usage = SLAP_MR_SUBSTR_INITIAL;
393 case LDAP_SUBSTRING_ANY:
394 if ( ssa.sa_final.bv_val != NULL ) {
395 rc = LDAP_PROTOCOL_ERROR;
398 usage = SLAP_MR_SUBSTR_ANY;
401 case LDAP_SUBSTRING_FINAL:
402 if ( ssa.sa_final.bv_val != NULL ) {
403 rc = LDAP_PROTOCOL_ERROR;
407 usage = SLAP_MR_SUBSTR_FINAL;
411 Debug( LDAP_DEBUG_FILTER,
412 " unknown substring choice=%ld\n",
415 rc = LDAP_PROTOCOL_ERROR;
419 /* validate/normalize using equality matching rule validator! */
420 rc = asserted_value_validate_normalize(
421 ssa.sa_desc, ssa.sa_desc->ad_type->sat_equality,
422 usage, &value, &nvalue, text, op->o_tmpmemctx );
423 if( rc != LDAP_SUCCESS ) goto return_error;
426 case LDAP_SUBSTRING_INITIAL:
427 Debug( LDAP_DEBUG_FILTER, " INITIAL\n", 0, 0, 0 );
428 ssa.sa_initial = nvalue;
431 case LDAP_SUBSTRING_ANY:
432 Debug( LDAP_DEBUG_FILTER, " ANY\n", 0, 0, 0 );
433 ber_bvarray_add_x( &ssa.sa_any, &nvalue, op->o_tmpmemctx );
436 case LDAP_SUBSTRING_FINAL:
437 Debug( LDAP_DEBUG_FILTER, " FINAL\n", 0, 0, 0 );
438 ssa.sa_final = nvalue;
443 slap_sl_free( nvalue.bv_val, op->o_tmpmemctx );
444 rc = LDAP_PROTOCOL_ERROR;
447 Debug( LDAP_DEBUG_FILTER, " error=%ld\n",
449 slap_sl_free( ssa.sa_initial.bv_val, op->o_tmpmemctx );
450 ber_bvarray_free_x( ssa.sa_any, op->o_tmpmemctx );
451 if ( ssa.sa_desc->ad_flags & SLAP_DESC_TEMPORARY )
452 op->o_tmpfree( ssa.sa_desc, op->o_tmpmemctx );
453 slap_sl_free( ssa.sa_final.bv_val, op->o_tmpmemctx );
460 if( rc == LDAP_SUCCESS ) {
461 f->f_sub = op->o_tmpalloc( sizeof( ssa ), op->o_tmpmemctx );
465 Debug( LDAP_DEBUG_FILTER, "end get_ssa\n", 0, 0, 0 );
466 return rc /* LDAP_SUCCESS */ ;
470 filter_free_x( Operation *op, Filter *f )
478 f->f_choice &= SLAPD_FILTER_MASK;
480 switch ( f->f_choice ) {
481 case LDAP_FILTER_PRESENT:
484 case LDAP_FILTER_EQUALITY:
487 case LDAP_FILTER_APPROX:
488 ava_free( op, f->f_ava, 1 );
491 case LDAP_FILTER_SUBSTRINGS:
492 if ( f->f_sub_initial.bv_val != NULL ) {
493 op->o_tmpfree( f->f_sub_initial.bv_val, op->o_tmpmemctx );
495 ber_bvarray_free_x( f->f_sub_any, op->o_tmpmemctx );
496 if ( f->f_sub_final.bv_val != NULL ) {
497 op->o_tmpfree( f->f_sub_final.bv_val, op->o_tmpmemctx );
499 if ( f->f_sub->sa_desc->ad_flags & SLAP_DESC_TEMPORARY )
500 op->o_tmpfree( f->f_sub->sa_desc, op->o_tmpmemctx );
501 op->o_tmpfree( f->f_sub, op->o_tmpmemctx );
504 case LDAP_FILTER_AND:
506 case LDAP_FILTER_NOT:
507 for ( p = f->f_list; p != NULL; p = next ) {
509 filter_free_x( op, p );
513 case LDAP_FILTER_EXT:
514 mra_free( op, f->f_mra, 1 );
517 case SLAPD_FILTER_COMPUTED:
521 Debug( LDAP_DEBUG_ANY, "filter_free: unknown filter type=%lu\n",
526 op->o_tmpfree( f, op->o_tmpmemctx );
530 filter_free( Filter *f )
536 op.o_tmpmemctx = slap_sl_context( f );
537 op.o_tmpmfuncs = &slap_sl_mfuncs;
538 filter_free_x( &op, f );
542 filter2bv_x( Operation *op, Filter *f, struct berval *fstr )
548 ber_bvfalse = BER_BVC( "(?=false)" ),
549 ber_bvtrue = BER_BVC( "(?=true)" ),
550 ber_bvundefined = BER_BVC( "(?=undefined)" ),
551 ber_bverror = BER_BVC( "(?=error)" ),
552 ber_bvunknown = BER_BVC( "(?=unknown)" ),
553 ber_bvnone = BER_BVC( "(?=none)" );
560 ber_dupbv_x( fstr, &ber_bvnone, op->o_tmpmemctx );
564 undef = f->f_choice & SLAPD_FILTER_UNDEFINED;
565 choice = f->f_choice & SLAPD_FILTER_MASK;
568 case LDAP_FILTER_EQUALITY:
569 fstr->bv_len = STRLENOF("(=)");
573 fstr->bv_len = STRLENOF("(>=)");
577 fstr->bv_len = STRLENOF("(<=)");
580 case LDAP_FILTER_APPROX:
581 fstr->bv_len = STRLENOF("(~=)");
585 filter_escape_value_x( &f->f_av_value, &tmp, op->o_tmpmemctx );
586 /* NOTE: tmp can legitimately be NULL (meaning empty)
587 * since in a Filter values in AVAs are supposed
588 * to have been normalized, meaning that an empty value
589 * is legal for that attribute's syntax */
591 fstr->bv_len += f->f_av_desc->ad_cname.bv_len + tmp.bv_len;
594 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
596 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s%s%s%s)",
598 f->f_av_desc->ad_cname.bv_val, sign,
599 tmp.bv_len ? tmp.bv_val : "" );
601 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
604 case LDAP_FILTER_SUBSTRINGS:
605 fstr->bv_len = f->f_sub_desc->ad_cname.bv_len +
609 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 128, op->o_tmpmemctx );
611 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s%s=*)",
613 f->f_sub_desc->ad_cname.bv_val );
615 if ( f->f_sub_initial.bv_val != NULL ) {
620 filter_escape_value_x( &f->f_sub_initial, &tmp, op->o_tmpmemctx );
623 fstr->bv_len += tmplen;
624 fstr->bv_val = op->o_tmprealloc( fstr->bv_val,
625 fstr->bv_len + 1, op->o_tmpmemctx );
627 snprintf( &fstr->bv_val[len - 2],
628 tmplen + STRLENOF( /*(*/ "*)" ) + 1,
629 /* "(attr=" */ "%s*)",
630 tmp.bv_len ? tmp.bv_val : "");
632 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
635 if ( f->f_sub_any != NULL ) {
636 for ( i = 0; f->f_sub_any[i].bv_val != NULL; i++ ) {
640 filter_escape_value_x( &f->f_sub_any[i],
641 &tmp, op->o_tmpmemctx );
644 fstr->bv_len += tmplen + STRLENOF( /*(*/ ")" );
645 fstr->bv_val = op->o_tmprealloc( fstr->bv_val,
646 fstr->bv_len + 1, op->o_tmpmemctx );
648 snprintf( &fstr->bv_val[len - 1],
649 tmplen + STRLENOF( /*(*/ "*)" ) + 1,
650 /* "(attr=[init]*[any*]" */ "%s*)",
651 tmp.bv_len ? tmp.bv_val : "");
652 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
656 if ( f->f_sub_final.bv_val != NULL ) {
661 filter_escape_value_x( &f->f_sub_final, &tmp, op->o_tmpmemctx );
664 fstr->bv_len += tmplen;
665 fstr->bv_val = op->o_tmprealloc( fstr->bv_val,
666 fstr->bv_len + 1, op->o_tmpmemctx );
668 snprintf( &fstr->bv_val[len - 1],
669 tmplen + STRLENOF( /*(*/ ")" ) + 1,
670 /* "(attr=[init*][any*]" */ "%s)",
671 tmp.bv_len ? tmp.bv_val : "");
673 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
678 case LDAP_FILTER_PRESENT:
679 fstr->bv_len = f->f_desc->ad_cname.bv_len +
684 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
686 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s%s=*)",
688 f->f_desc->ad_cname.bv_val );
691 case LDAP_FILTER_AND:
693 case LDAP_FILTER_NOT:
694 fstr->bv_len = STRLENOF("(%)");
695 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 128, op->o_tmpmemctx );
697 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%c)",
698 f->f_choice == LDAP_FILTER_AND ? '&' :
699 f->f_choice == LDAP_FILTER_OR ? '|' : '!' );
701 for ( p = f->f_list; p != NULL; p = p->f_next ) {
704 filter2bv_x( op, p, &tmp );
706 fstr->bv_len += tmp.bv_len;
707 fstr->bv_val = op->o_tmprealloc( fstr->bv_val, fstr->bv_len + 1,
710 snprintf( &fstr->bv_val[len-1],
711 tmp.bv_len + STRLENOF( /*(*/ ")" ) + 1,
712 /*"("*/ "%s)", tmp.bv_val );
714 op->o_tmpfree( tmp.bv_val, op->o_tmpmemctx );
719 case LDAP_FILTER_EXT: {
722 filter_escape_value_x( &f->f_mr_value, &tmp, op->o_tmpmemctx );
723 /* NOTE: tmp can legitimately be NULL (meaning empty)
724 * since in a Filter values in MRAs are supposed
725 * to have been normalized, meaning that an empty value
726 * is legal for that attribute's syntax */
728 if ( f->f_mr_desc ) {
729 ad = f->f_mr_desc->ad_cname;
735 fstr->bv_len = ad.bv_len +
736 ( f->f_mr_dnattrs ? STRLENOF(":dn") : 0 ) +
737 ( f->f_mr_rule_text.bv_len ? f->f_mr_rule_text.bv_len+1 : 0 ) +
738 tmp.bv_len + STRLENOF("(:=)");
739 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
741 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s%s%s%s%s:=%s)",
744 f->f_mr_dnattrs ? ":dn" : "",
745 f->f_mr_rule_text.bv_len ? ":" : "",
746 f->f_mr_rule_text.bv_len ? f->f_mr_rule_text.bv_val : "",
747 tmp.bv_len ? tmp.bv_val : "" );
748 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
751 case SLAPD_FILTER_COMPUTED:
752 switch ( f->f_result ) {
753 case LDAP_COMPARE_FALSE:
757 case LDAP_COMPARE_TRUE:
761 case SLAPD_COMPARE_UNDEFINED:
762 tmp = ber_bvundefined;
770 ber_dupbv_x( fstr, &tmp, op->o_tmpmemctx );
774 ber_dupbv_x( fstr, &ber_bvunknown, op->o_tmpmemctx );
780 filter2bv( Filter *f, struct berval *fstr )
786 op.o_tmpmemctx = NULL;
787 op.o_tmpmfuncs = &ch_mfuncs;
789 filter2bv_x( &op, f, fstr );
793 filter_dup( Filter *f, void *memctx )
795 BerMemoryFunctions *mf = &slap_sl_mfuncs;
801 n = mf->bmf_malloc( sizeof(Filter), memctx );
802 n->f_choice = f->f_choice;
805 switch( f->f_choice & SLAPD_FILTER_MASK ) {
806 case SLAPD_FILTER_COMPUTED:
807 n->f_result = f->f_result;
809 case LDAP_FILTER_PRESENT:
810 if ( f->f_desc->ad_flags & SLAP_DESC_TEMPORARY )
811 n->f_desc = slap_bv2tmp_ad( &f->f_desc->ad_cname, memctx );
813 n->f_desc = f->f_desc;
815 case LDAP_FILTER_EQUALITY:
818 case LDAP_FILTER_APPROX:
819 /* Should this be ava_dup() ? */
820 n->f_ava = mf->bmf_calloc( 1, sizeof(AttributeAssertion), memctx );
821 *n->f_ava = *f->f_ava;
822 if ( f->f_av_desc->ad_flags & SLAP_DESC_TEMPORARY )
823 n->f_av_desc = slap_bv2tmp_ad( &f->f_av_desc->ad_cname, memctx );
824 ber_dupbv_x( &n->f_av_value, &f->f_av_value, memctx );
826 case LDAP_FILTER_SUBSTRINGS:
827 n->f_sub = mf->bmf_calloc( 1, sizeof(SubstringsAssertion), memctx );
828 if ( f->f_sub_desc->ad_flags & SLAP_DESC_TEMPORARY )
829 n->f_sub_desc = slap_bv2tmp_ad( &f->f_sub_desc->ad_cname, memctx );
831 n->f_sub_desc = f->f_sub_desc;
832 if ( !BER_BVISNULL( &f->f_sub_initial ))
833 ber_dupbv_x( &n->f_sub_initial, &f->f_sub_initial, memctx );
834 if ( f->f_sub_any ) {
836 for ( i = 0; !BER_BVISNULL( &f->f_sub_any[i] ); i++ );
837 n->f_sub_any = mf->bmf_malloc(( i+1 )*sizeof( struct berval ),
839 for ( i = 0; !BER_BVISNULL( &f->f_sub_any[i] ); i++ ) {
840 ber_dupbv_x( &n->f_sub_any[i], &f->f_sub_any[i], memctx );
842 BER_BVZERO( &n->f_sub_any[i] );
844 if ( !BER_BVISNULL( &f->f_sub_final ))
845 ber_dupbv_x( &n->f_sub_final, &f->f_sub_final, memctx );
847 case LDAP_FILTER_EXT: {
848 /* Should this be mra_dup() ? */
850 length = sizeof(MatchingRuleAssertion);
851 if ( !BER_BVISNULL( &f->f_mr_rule_text ))
852 length += f->f_mr_rule_text.bv_len + 1;
853 n->f_mra = mf->bmf_calloc( 1, length, memctx );
854 *n->f_mra = *f->f_mra;
855 if ( f->f_mr_desc && ( f->f_sub_desc->ad_flags & SLAP_DESC_TEMPORARY ))
856 n->f_mr_desc = slap_bv2tmp_ad( &f->f_mr_desc->ad_cname, memctx );
857 ber_dupbv_x( &n->f_mr_value, &f->f_mr_value, memctx );
858 if ( !BER_BVISNULL( &f->f_mr_rule_text )) {
859 n->f_mr_rule_text.bv_val = (char *)(n->f_mra+1);
860 AC_MEMCPY(n->f_mr_rule_text.bv_val,
861 f->f_mr_rule_text.bv_val, f->f_mr_rule_text.bv_len );
864 case LDAP_FILTER_AND:
866 case LDAP_FILTER_NOT: {
868 for ( p = &n->f_list, f = f->f_list; f; f = f->f_next ) {
869 *p = filter_dup( f, memctx );
881 ValuesReturnFilter **filt,
887 ValuesReturnFilter vrf;
889 Debug( LDAP_DEBUG_FILTER, "begin get_simple_vrFilter\n", 0, 0, 0 );
891 tag = ber_peek_tag( ber, &len );
893 if( tag == LBER_ERROR ) {
894 *text = "error decoding filter";
895 return SLAPD_DISCONNECT;
901 vrf.vrf_choice = tag;
903 switch ( vrf.vrf_choice ) {
904 case LDAP_FILTER_EQUALITY:
905 Debug( LDAP_DEBUG_FILTER, "EQUALITY\n", 0, 0, 0 );
906 err = get_ava( op, ber, (Filter *)&vrf, SLAP_MR_EQUALITY, text );
907 if ( err != LDAP_SUCCESS ) {
911 assert( vrf.vrf_ava != NULL );
914 case LDAP_FILTER_SUBSTRINGS:
915 Debug( LDAP_DEBUG_FILTER, "SUBSTRINGS\n", 0, 0, 0 );
916 err = get_ssa( op, ber, (Filter *)&vrf, text );
920 Debug( LDAP_DEBUG_FILTER, "GE\n", 0, 0, 0 );
921 err = get_ava( op, ber, (Filter *)&vrf, SLAP_MR_ORDERING, text );
922 if ( err != LDAP_SUCCESS ) {
928 Debug( LDAP_DEBUG_FILTER, "LE\n", 0, 0, 0 );
929 err = get_ava( op, ber, (Filter *)&vrf, SLAP_MR_ORDERING, text );
930 if ( err != LDAP_SUCCESS ) {
935 case LDAP_FILTER_PRESENT: {
938 Debug( LDAP_DEBUG_FILTER, "PRESENT\n", 0, 0, 0 );
939 if ( ber_scanf( ber, "m", &type ) == LBER_ERROR ) {
940 err = SLAPD_DISCONNECT;
941 *text = "error decoding filter";
946 err = slap_bv2ad( &type, &vrf.vrf_desc, text );
948 if( err != LDAP_SUCCESS ) {
949 vrf.vrf_choice |= SLAPD_FILTER_UNDEFINED;
950 err = slap_bv2undef_ad( &type, &vrf.vrf_desc, text,
953 if( err != LDAP_SUCCESS ) {
954 /* unrecognized attribute description or other error */
955 Debug( LDAP_DEBUG_ANY,
956 "get_simple_vrFilter: conn %lu unknown "
957 "attribute type=%s (%d)\n",
958 op->o_connid, type.bv_val, err );
960 vrf.vrf_choice = SLAPD_FILTER_COMPUTED;
961 vrf.vrf_result = LDAP_COMPARE_FALSE;
968 case LDAP_FILTER_APPROX:
969 Debug( LDAP_DEBUG_FILTER, "APPROX\n", 0, 0, 0 );
970 err = get_ava( op, ber, (Filter *)&vrf, SLAP_MR_EQUALITY_APPROX, text );
971 if ( err != LDAP_SUCCESS ) {
976 case LDAP_FILTER_EXT:
977 Debug( LDAP_DEBUG_FILTER, "EXTENSIBLE\n", 0, 0, 0 );
979 err = get_mra( op, ber, (Filter *)&vrf, text );
980 if ( err != LDAP_SUCCESS ) {
984 assert( vrf.vrf_mra != NULL );
988 (void) ber_scanf( ber, "x" ); /* skip the element */
989 Debug( LDAP_DEBUG_ANY, "get_simple_vrFilter: unknown filter type=%lu\n",
990 vrf.vrf_choice, 0, 0 );
991 vrf.vrf_choice = SLAPD_FILTER_COMPUTED;
992 vrf.vrf_result = SLAPD_COMPARE_UNDEFINED;
996 if ( err != LDAP_SUCCESS && err != SLAPD_DISCONNECT ) {
998 vrf.vrf_choice = SLAPD_FILTER_COMPUTED;
999 vrf.vrf_result = SLAPD_COMPARE_UNDEFINED;
1003 if ( err == LDAP_SUCCESS ) {
1004 *filt = op->o_tmpalloc( sizeof vrf, op->o_tmpmemctx );
1008 Debug( LDAP_DEBUG_FILTER, "end get_simple_vrFilter %d\n", err, 0, 0 );
1014 get_vrFilter( Operation *op, BerElement *ber,
1015 ValuesReturnFilter **vrf,
1019 * A ValuesReturnFilter looks like this:
1021 * ValuesReturnFilter ::= SEQUENCE OF SimpleFilterItem
1022 * SimpleFilterItem ::= CHOICE {
1023 * equalityMatch [3] AttributeValueAssertion,
1024 * substrings [4] SubstringFilter,
1025 * greaterOrEqual [5] AttributeValueAssertion,
1026 * lessOrEqual [6] AttributeValueAssertion,
1027 * present [7] AttributeType,
1028 * approxMatch [8] AttributeValueAssertion,
1029 * extensibleMatch [9] SimpleMatchingAssertion -- LDAPv3
1032 * SubstringFilter ::= SEQUENCE {
1033 * type AttributeType,
1034 * SEQUENCE OF CHOICE {
1035 * initial [0] IA5String,
1036 * any [1] IA5String,
1037 * final [2] IA5String
1041 * SimpleMatchingAssertion ::= SEQUENCE { -- LDAPv3
1042 * matchingRule [1] MatchingRuleId OPTIONAL,
1043 * type [2] AttributeDescription OPTIONAL,
1044 * matchValue [3] AssertionValue }
1047 ValuesReturnFilter **n;
1052 Debug( LDAP_DEBUG_FILTER, "begin get_vrFilter\n", 0, 0, 0 );
1054 tag = ber_peek_tag( ber, &len );
1056 if( tag == LBER_ERROR ) {
1057 *text = "error decoding vrFilter";
1058 return SLAPD_DISCONNECT;
1061 if( tag != LBER_SEQUENCE ) {
1062 *text = "error decoding vrFilter, expect SEQUENCE tag";
1063 return SLAPD_DISCONNECT;
1067 for ( tag = ber_first_element( ber, &len, &last );
1068 tag != LBER_DEFAULT;
1069 tag = ber_next_element( ber, &len, last ) )
1071 int err = get_simple_vrFilter( op, ber, n, text );
1073 if ( err != LDAP_SUCCESS ) return( err );
1075 n = &(*n)->vrf_next;
1079 Debug( LDAP_DEBUG_FILTER, "end get_vrFilter\n", 0, 0, 0 );
1080 return( LDAP_SUCCESS );
1084 vrFilter_free( Operation *op, ValuesReturnFilter *vrf )
1086 ValuesReturnFilter *p, *next;
1088 if ( vrf == NULL ) {
1092 for ( p = vrf; p != NULL; p = next ) {
1095 switch ( vrf->vrf_choice & SLAPD_FILTER_MASK ) {
1096 case LDAP_FILTER_PRESENT:
1099 case LDAP_FILTER_EQUALITY:
1100 case LDAP_FILTER_GE:
1101 case LDAP_FILTER_LE:
1102 case LDAP_FILTER_APPROX:
1103 ava_free( op, vrf->vrf_ava, 1 );
1106 case LDAP_FILTER_SUBSTRINGS:
1107 if ( vrf->vrf_sub_initial.bv_val != NULL ) {
1108 op->o_tmpfree( vrf->vrf_sub_initial.bv_val, op->o_tmpmemctx );
1110 ber_bvarray_free_x( vrf->vrf_sub_any, op->o_tmpmemctx );
1111 if ( vrf->vrf_sub_final.bv_val != NULL ) {
1112 op->o_tmpfree( vrf->vrf_sub_final.bv_val, op->o_tmpmemctx );
1114 op->o_tmpfree( vrf->vrf_sub, op->o_tmpmemctx );
1117 case LDAP_FILTER_EXT:
1118 mra_free( op, vrf->vrf_mra, 1 );
1121 case SLAPD_FILTER_COMPUTED:
1125 Debug( LDAP_DEBUG_ANY, "filter_free: unknown filter type=%lu\n",
1126 vrf->vrf_choice, 0, 0 );
1130 op->o_tmpfree( vrf, op->o_tmpmemctx );
1135 vrFilter2bv( Operation *op, ValuesReturnFilter *vrf, struct berval *fstr )
1137 ValuesReturnFilter *p;
1141 if ( vrf == NULL ) {
1142 ber_str2bv_x( "No filter!", STRLENOF("No filter!"),
1143 1, fstr, op->o_tmpmemctx );
1147 fstr->bv_len = STRLENOF("()");
1148 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 128, op->o_tmpmemctx );
1150 snprintf( fstr->bv_val, fstr->bv_len + 1, "()");
1152 for ( p = vrf; p != NULL; p = p->vrf_next ) {
1155 simple_vrFilter2bv( op, p, &tmp );
1157 fstr->bv_len += tmp.bv_len;
1158 fstr->bv_val = op->o_tmprealloc( fstr->bv_val, fstr->bv_len + 1,
1161 snprintf( &fstr->bv_val[len-1], tmp.bv_len + 2,
1162 /*"("*/ "%s)", tmp.bv_val );
1164 op->o_tmpfree( tmp.bv_val, op->o_tmpmemctx );
1169 simple_vrFilter2bv( Operation *op, ValuesReturnFilter *vrf, struct berval *fstr )
1175 if ( vrf == NULL ) {
1176 ber_str2bv_x( "No filter!", STRLENOF("No filter!"), 1, fstr,
1180 undef = vrf->vrf_choice & SLAPD_FILTER_UNDEFINED;
1182 switch ( vrf->vrf_choice & SLAPD_FILTER_MASK ) {
1183 case LDAP_FILTER_EQUALITY:
1184 filter_escape_value_x( &vrf->vrf_av_value, &tmp, op->o_tmpmemctx );
1186 fstr->bv_len = vrf->vrf_av_desc->ad_cname.bv_len +
1187 tmp.bv_len + STRLENOF("(=)");
1188 if ( undef ) fstr->bv_len++;
1189 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
1191 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s=%s)",
1192 vrf->vrf_av_desc->ad_cname.bv_val,
1195 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1198 case LDAP_FILTER_GE:
1199 filter_escape_value_x( &vrf->vrf_av_value, &tmp, op->o_tmpmemctx );
1201 fstr->bv_len = vrf->vrf_av_desc->ad_cname.bv_len +
1202 tmp.bv_len + STRLENOF("(>=)");
1203 if ( undef ) fstr->bv_len++;
1204 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
1206 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s>=%s)",
1207 vrf->vrf_av_desc->ad_cname.bv_val,
1210 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1213 case LDAP_FILTER_LE:
1214 filter_escape_value_x( &vrf->vrf_av_value, &tmp, op->o_tmpmemctx );
1216 fstr->bv_len = vrf->vrf_av_desc->ad_cname.bv_len +
1217 tmp.bv_len + STRLENOF("(<=)");
1218 if ( undef ) fstr->bv_len++;
1219 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
1221 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s<=%s)",
1222 vrf->vrf_av_desc->ad_cname.bv_val,
1225 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1228 case LDAP_FILTER_APPROX:
1229 filter_escape_value_x( &vrf->vrf_av_value, &tmp, op->o_tmpmemctx );
1231 fstr->bv_len = vrf->vrf_av_desc->ad_cname.bv_len +
1232 tmp.bv_len + STRLENOF("(~=)");
1233 if ( undef ) fstr->bv_len++;
1234 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
1236 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s~=%s)",
1237 vrf->vrf_av_desc->ad_cname.bv_val,
1239 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1242 case LDAP_FILTER_SUBSTRINGS:
1243 fstr->bv_len = vrf->vrf_sub_desc->ad_cname.bv_len +
1245 if ( undef ) fstr->bv_len++;
1246 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 128, op->o_tmpmemctx );
1248 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s=*)",
1249 vrf->vrf_sub_desc->ad_cname.bv_val );
1251 if ( vrf->vrf_sub_initial.bv_val != NULL ) {
1254 filter_escape_value_x( &vrf->vrf_sub_initial, &tmp, op->o_tmpmemctx );
1256 fstr->bv_len += tmp.bv_len;
1257 fstr->bv_val = op->o_tmprealloc( fstr->bv_val, fstr->bv_len + 1,
1260 snprintf( &fstr->bv_val[len-2], tmp.bv_len+3,
1261 /* "(attr=" */ "%s*)",
1264 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1267 if ( vrf->vrf_sub_any != NULL ) {
1269 for ( i = 0; vrf->vrf_sub_any[i].bv_val != NULL; i++ ) {
1271 filter_escape_value_x( &vrf->vrf_sub_any[i], &tmp,
1274 fstr->bv_len += tmp.bv_len + 1;
1275 fstr->bv_val = op->o_tmprealloc( fstr->bv_val,
1276 fstr->bv_len + 1, op->o_tmpmemctx );
1278 snprintf( &fstr->bv_val[len-1], tmp.bv_len+3,
1279 /* "(attr=[init]*[any*]" */ "%s*)",
1281 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1285 if ( vrf->vrf_sub_final.bv_val != NULL ) {
1288 filter_escape_value_x( &vrf->vrf_sub_final, &tmp, op->o_tmpmemctx );
1290 fstr->bv_len += tmp.bv_len;
1291 fstr->bv_val = op->o_tmprealloc( fstr->bv_val, fstr->bv_len + 1,
1294 snprintf( &fstr->bv_val[len-1], tmp.bv_len+3,
1295 /* "(attr=[init*][any*]" */ "%s)",
1298 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1303 case LDAP_FILTER_PRESENT:
1304 fstr->bv_len = vrf->vrf_desc->ad_cname.bv_len +
1306 if ( undef ) fstr->bv_len++;
1307 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
1309 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s=*)",
1310 vrf->vrf_desc->ad_cname.bv_val );
1313 case LDAP_FILTER_EXT: {
1315 filter_escape_value_x( &vrf->vrf_mr_value, &tmp, op->o_tmpmemctx );
1317 if ( vrf->vrf_mr_desc ) {
1318 ad = vrf->vrf_mr_desc->ad_cname;
1324 fstr->bv_len = ad.bv_len +
1325 ( vrf->vrf_mr_dnattrs ? STRLENOF(":dn") : 0 ) +
1326 ( vrf->vrf_mr_rule_text.bv_len
1327 ? vrf->vrf_mr_rule_text.bv_len+1 : 0 ) +
1328 tmp.bv_len + STRLENOF("(:=)");
1329 if ( undef ) fstr->bv_len++;
1330 fstr->bv_val = op->o_tmpalloc( fstr->bv_len + 1, op->o_tmpmemctx );
1332 snprintf( fstr->bv_val, fstr->bv_len + 1, "(%s%s%s%s:=%s)",
1334 vrf->vrf_mr_dnattrs ? ":dn" : "",
1335 vrf->vrf_mr_rule_text.bv_len ? ":" : "",
1336 vrf->vrf_mr_rule_text.bv_len ? vrf->vrf_mr_rule_text.bv_val : "",
1339 ber_memfree_x( tmp.bv_val, op->o_tmpmemctx );
1342 case SLAPD_FILTER_COMPUTED:
1344 vrf->vrf_result == LDAP_COMPARE_FALSE ? "(?=false)" :
1345 vrf->vrf_result == LDAP_COMPARE_TRUE ? "(?=true)" :
1346 vrf->vrf_result == SLAPD_COMPARE_UNDEFINED
1347 ? "(?=undefined)" : "(?=error)",
1348 vrf->vrf_result == LDAP_COMPARE_FALSE ? STRLENOF("(?=false)") :
1349 vrf->vrf_result == LDAP_COMPARE_TRUE ? STRLENOF("(?=true)") :
1350 vrf->vrf_result == SLAPD_COMPARE_UNDEFINED
1351 ? STRLENOF("(?=undefined)") : STRLENOF("(?=error)"),
1352 1, fstr, op->o_tmpmemctx );
1356 ber_str2bv_x( "(?=unknown)", STRLENOF("(?=unknown)"),
1357 1, fstr, op->o_tmpmemctx );