X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=libraries%2Flibldap%2Ffilter.c;h=2d05d81c25dc78187d08596ecfd9b5867ff6ef84;hb=62295c0928c071685dbbfb98644cadaeb37333b8;hp=7d40d1ceb472588ee886da4c89df09f19c7a18b5;hpb=8c152396b9ff4fa0f2618435441550c1f12df461;p=openldap
diff --git a/libraries/libldap/filter.c b/libraries/libldap/filter.c
index 7d40d1ceb4..2d05d81c25 100644
--- a/libraries/libldap/filter.c
+++ b/libraries/libldap/filter.c
@@ -1,13 +1,20 @@
+/* search.c */
/* $OpenLDAP$ */
-/*
- * Copyright 1998-2002 The OpenLDAP Foundation, All Rights Reserved.
- * COPYING RESTRICTIONS APPLY, see COPYRIGHT file
- */
-/* Portions
- * Copyright (c) 1990 Regents of the University of Michigan.
- * All rights reserved.
+/* This work is part of OpenLDAP Software .
+ *
+ * Copyright 1998-2009 The OpenLDAP Foundation.
+ * All rights reserved.
*
- * search.c
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted only as authorized by the OpenLDAP
+ * Public License.
+ *
+ * A copy of this license is available in the file LICENSE in the
+ * top-level directory of the distribution or, alternatively, at
+ * .
+ */
+/* Portions Copyright (c) 1990 Regents of the University of Michigan.
+ * All rights reserved.
*/
#include "portable.h"
@@ -43,7 +50,8 @@ static int put_simple_filter LDAP_P((
static int put_substring_filter LDAP_P((
BerElement *ber,
char *type,
- char *str ));
+ char *str,
+ char *nextstar ));
static int put_filter_list LDAP_P((
BerElement *ber,
@@ -324,44 +332,39 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
int parens, balance, escape;
/*
- * A Filter looks like this:
- * Filter ::= CHOICE {
- * and [0] SET OF Filter,
- * or [1] SET OF Filter,
- * not [2] Filter,
- * equalityMatch [3] AttributeValueAssertion,
- * substrings [4] SubstringFilter,
- * greaterOrEqual [5] AttributeValueAssertion,
- * lessOrEqual [6] AttributeValueAssertion,
- * present [7] AttributeType,
- * approxMatch [8] AttributeValueAssertion,
- * extensibleMatch [9] MatchingRuleAssertion -- LDAPv3
- * }
+ * A Filter looks like this (RFC 4511 as extended by RFC 4526):
+ * Filter ::= CHOICE {
+ * and [0] SET SIZE (0..MAX) OF filter Filter,
+ * or [1] SET SIZE (0..MAX) OF filter Filter,
+ * not [2] Filter,
+ * equalityMatch [3] AttributeValueAssertion,
+ * substrings [4] SubstringFilter,
+ * greaterOrEqual [5] AttributeValueAssertion,
+ * lessOrEqual [6] AttributeValueAssertion,
+ * present [7] AttributeDescription,
+ * approxMatch [8] AttributeValueAssertion,
+ * extensibleMatch [9] MatchingRuleAssertion,
+ * ... }
*
- * SubstringFilter ::= SEQUENCE {
- * type AttributeType,
- * SEQUENCE OF CHOICE {
- * initial [0] IA5String,
- * any [1] IA5String,
- * final [2] IA5String
- * }
- * }
+ * SubstringFilter ::= SEQUENCE {
+ * type AttributeDescription,
+ * substrings SEQUENCE SIZE (1..MAX) OF substring CHOICE {
+ * initial [0] AssertionValue, -- only once
+ * any [1] AssertionValue,
+ * final [2] AssertionValue -- only once
+ * }
+ * }
*
- * MatchingRuleAssertion ::= SEQUENCE { -- LDAPv3
- * matchingRule [1] MatchingRuleId OPTIONAL,
- * type [2] AttributeDescription OPTIONAL,
- * matchValue [3] AssertionValue,
- * dnAttributes [4] BOOLEAN DEFAULT FALSE }
+ * MatchingRuleAssertion ::= SEQUENCE {
+ * matchingRule [1] MatchingRuleId OPTIONAL,
+ * type [2] AttributeDescription OPTIONAL,
+ * matchValue [3] AssertionValue,
+ * dnAttributes [4] BOOLEAN DEFAULT FALSE }
*
- * Note: tags in a choice are always explicit
+ * Note: tags in a CHOICE are always explicit
*/
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_ARGS, "ldap_pvt_put_filter: \"%s\"\n",
- str_in ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter: \"%s\"\n", str_in, 0, 0 );
-#endif
freeme = LDAP_STRDUP( str_in );
if( freeme == NULL ) return LDAP_NO_MEMORY;
@@ -379,13 +382,8 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
switch ( *str ) {
case '&':
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: AND\n" ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter: AND\n",
0, 0, 0 );
-#endif
str = put_complex_filter( ber, str,
LDAP_FILTER_AND, 0 );
@@ -398,13 +396,8 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
break;
case '|':
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: OR\n" ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter: OR\n",
0, 0, 0 );
-#endif
str = put_complex_filter( ber, str,
LDAP_FILTER_OR, 0 );
@@ -417,13 +410,8 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
break;
case '!':
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: NOT\n" ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter: NOT\n",
0, 0, 0 );
-#endif
str = put_complex_filter( ber, str,
LDAP_FILTER_NOT, 0 );
@@ -435,14 +423,13 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
parens--;
break;
+ case '(':
+ rc = -1;
+ goto done;
+
default:
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: simple\n" ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter: simple\n",
0, 0, 0 );
-#endif
balance = 1;
escape = 0;
@@ -487,13 +474,8 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
break;
case /*'('*/ ')':
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: end\n" ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter: end\n",
0, 0, 0 );
-#endif
if ( ber_printf( ber, /*"["*/ "]" ) == -1 ) {
rc = -1;
goto done;
@@ -507,13 +489,8 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
break;
default: /* assume it's a simple type=value filter */
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: default\n" ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter: default\n",
0, 0, 0 );
-#endif
next = strchr( str, '\0' );
if ( put_simple_filter( ber, str ) == -1 ) {
rc = -1;
@@ -522,9 +499,11 @@ ldap_pvt_put_filter( BerElement *ber, const char *str_in )
str = next;
break;
}
+ if ( !parens )
+ break;
}
- rc = parens ? -1 : 0;
+ rc = ( parens || *str ) ? -1 : 0;
done:
LDAP_FREE( freeme );
@@ -541,13 +520,8 @@ put_filter_list( BerElement *ber, char *str, ber_tag_t tag )
char *next = NULL;
char save;
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_ARGS,
- "put_filter_list \"%s\"\n", str ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_filter_list \"%s\"\n",
str, 0, 0 );
-#endif
while ( *str ) {
while ( *str && LDAP_SPACE( (unsigned char) *str ) ) {
@@ -586,13 +560,8 @@ put_simple_filter(
ber_tag_t ftype;
int rc = -1;
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_ARGS,
- "put_simple_filter: \"%s\"\n", str ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_simple_filter: \"%s\"\n",
str, 0, 0 );
-#endif
str = LDAP_STRDUP( str );
if( str == NULL ) return -1;
@@ -621,7 +590,7 @@ put_simple_filter(
break;
case ':':
- /* RFC2254 extensible filters are off the form:
+ /* RFC 4515 extensible filters are off the form:
* type [:dn] [:rule] := value
* or [:dn]:rule := value
*/
@@ -638,7 +607,7 @@ put_simple_filter(
if( rule == NULL ) {
/* one colon */
- if ( strcmp(dn, "dn") == 0 ) {
+ if ( strcasecmp(dn, "dn") == 0 ) {
/* must have attribute */
if( !ldap_is_desc( str ) ) {
goto done;
@@ -655,7 +624,7 @@ put_simple_filter(
/* two colons */
*rule++ = '\0';
- if ( strcmp(dn, "dn") != 0 ) {
+ if ( strcasecmp(dn, "dn") != 0 ) {
/* must have "dn" */
goto done;
}
@@ -725,7 +694,7 @@ put_simple_filter(
ftype = LDAP_FILTER_PRESENT;
} else {
- rc = put_substring_filter( ber, str, value );
+ rc = put_substring_filter( ber, str, value, nextstar );
goto done;
}
} break;
@@ -752,31 +721,26 @@ done:
}
static int
-put_substring_filter( BerElement *ber, char *type, char *val )
+put_substring_filter( BerElement *ber, char *type, char *val, char *nextstar )
{
- char *nextstar;
int gotstar = 0;
ber_tag_t ftype = LDAP_FILTER_SUBSTRINGS;
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_ARGS,
- "put_substring_filter \"%s=%s\"\n", type, val ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_substring_filter \"%s=%s\"\n",
type, val, 0 );
-#endif
if ( ber_printf( ber, "t{s{" /*"}}"*/, ftype, type ) == -1 ) {
return -1;
}
for( ; *val; val=nextstar ) {
- nextstar = ldap_pvt_find_wildcard( val );
+ if ( gotstar )
+ nextstar = ldap_pvt_find_wildcard( val );
if ( nextstar == NULL ) {
return -1;
}
-
+
if ( *nextstar == '\0' ) {
ftype = LDAP_SUBSTRING_FINAL;
} else {
@@ -791,7 +755,7 @@ put_substring_filter( BerElement *ber, char *type, char *val )
if ( *val != '\0' || ftype == LDAP_SUBSTRING_ANY ) {
ber_slen_t len = ldap_pvt_filter_value_unescape( val );
- if ( len < 0 ) {
+ if ( len <= 0 ) {
return -1;
}
@@ -808,8 +772,8 @@ put_substring_filter( BerElement *ber, char *type, char *val )
return 0;
}
-int
-ldap_pvt_put_vrFilter( BerElement *ber, const char *str_in )
+static int
+put_vrFilter( BerElement *ber, const char *str_in )
{
int rc;
char *freeme;
@@ -844,14 +808,11 @@ ldap_pvt_put_vrFilter( BerElement *ber, const char *str_in )
* matchingRule [1] MatchingRuleId OPTIONAL,
* type [2] AttributeDescription OPTIONAL,
* matchValue [3] AssertionValue }
+ *
+ * (Source: RFC 3876)
*/
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_ARGS, "ldap_pvt_put_vrFilter: \"%s\"\n",
- str_in ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_vrFilter: \"%s\"\n", str_in, 0, 0 );
-#endif
freeme = LDAP_STRDUP( str_in );
if( freeme == NULL ) return LDAP_NO_MEMORY;
@@ -891,13 +852,8 @@ ldap_pvt_put_vrFilter( BerElement *ber, const char *str_in )
default:
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_vrFilter: simple\n" ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_vrFilter: simple\n",
0, 0, 0 );
-#endif
balance = 1;
escape = 0;
@@ -942,13 +898,8 @@ ldap_pvt_put_vrFilter( BerElement *ber, const char *str_in )
break;
case /*'('*/ ')':
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: end\n" ));
-#else
- Debug( LDAP_DEBUG_TRACE, "put_filter: end\n",
+ Debug( LDAP_DEBUG_TRACE, "put_vrFilter: end\n",
0, 0, 0 );
-#endif
if ( ber_printf( ber, /*"["*/ "]" ) == -1 ) {
rc = -1;
goto done;
@@ -962,15 +913,10 @@ ldap_pvt_put_vrFilter( BerElement *ber, const char *str_in )
break;
default: /* assume it's a simple type=value filter */
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_DETAIL1,
- "ldap_pvt_put_filter: default\n" ));
-#else
- Debug( LDAP_DEBUG_TRACE, "put_filter: default\n",
+ Debug( LDAP_DEBUG_TRACE, "put_vrFilter: default\n",
0, 0, 0 );
-#endif
next = strchr( str, '\0' );
- if ( put_simple_filter( ber, str ) == -1 ) {
+ if ( put_simple_vrFilter( ber, str ) == -1 ) {
rc = -1;
goto done;
}
@@ -987,7 +933,7 @@ done:
}
int
-put_vrFilter( BerElement *ber, const char *str_in )
+ldap_put_vrFilter( BerElement *ber, const char *str_in )
{
int rc =0;
@@ -995,7 +941,7 @@ put_vrFilter( BerElement *ber, const char *str_in )
rc = -1;
}
- rc = ldap_pvt_put_vrFilter( ber, str_in );
+ rc = put_vrFilter( ber, str_in );
if ( ber_printf( ber, /*"{"*/ "N}" ) == -1 ) {
rc = -1;
@@ -1010,13 +956,8 @@ put_vrFilter_list( BerElement *ber, char *str )
char *next = NULL;
char save;
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_ARGS,
- "put_vrFilter_list \"%s\"\n", str ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_vrFilter_list \"%s\"\n",
str, 0, 0 );
-#endif
while ( *str ) {
while ( *str && LDAP_SPACE( (unsigned char) *str ) ) {
@@ -1031,7 +972,7 @@ put_vrFilter_list( BerElement *ber, char *str )
/* now we have "(filter)" with str pointing to it */
*next = '\0';
- if ( ldap_pvt_put_vrFilter( ber, str ) == -1 ) return -1;
+ if ( put_vrFilter( ber, str ) == -1 ) return -1;
*next = save;
str = next;
}
@@ -1049,13 +990,8 @@ put_simple_vrFilter(
ber_tag_t ftype;
int rc = -1;
-#ifdef NEW_LOGGING
- LDAP_LOG (( "filter", LDAP_LEVEL_ARGS,
- "put_simple_vrFilter: \"%s\"\n", str ));
-#else
Debug( LDAP_DEBUG_TRACE, "put_simple_vrFilter: \"%s\"\n",
str, 0, 0 );
-#endif
str = LDAP_STRDUP( str );
if( str == NULL ) return -1;
@@ -1094,7 +1030,6 @@ put_simple_vrFilter(
{
char *rule = strchr( str, ':' );
- *rule++ = '\0';
if( rule == NULL ) {
/* must have attribute */
@@ -1102,12 +1037,10 @@ put_simple_vrFilter(
goto done;
}
rule = "";
-
} else {
*rule++ = '\0';
}
-
if ( *str == '\0' && ( !rule || *rule == '\0' ) ) {
/* must have either type or rule */
goto done;
@@ -1165,7 +1098,7 @@ put_simple_vrFilter(
ftype = LDAP_FILTER_PRESENT;
} else {
- rc = put_substring_filter( ber, str, value );
+ rc = put_substring_filter( ber, str, value, nextstar );
goto done;
}
} break;