summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNathan Kinder <nkinder@redhat.com>2008-11-26 22:42:12 +0000
committerNathan Kinder <nkinder@redhat.com>2008-11-26 22:42:12 +0000
commit6e5a17f5264a20d504a6e98dfc31f1cf278f363b (patch)
tree333761f60d17e4a1afbfca7e90cc82028feb06e1
parent97f52d81060f75b0f8a2411b69f6f427665765b6 (diff)
downloadds-6e5a17f5264a20d504a6e98dfc31f1cf278f363b.tar.gz
ds-6e5a17f5264a20d504a6e98dfc31f1cf278f363b.tar.xz
ds-6e5a17f5264a20d504a6e98dfc31f1cf278f363b.zip
Resolves: 220532
Summary: Add access to RUV by users other than "cn=Directory Manager".
-rw-r--r--ldap/servers/slapd/back-ldbm/ldbm_search.c10
-rw-r--r--ldap/servers/slapd/filter.c51
-rw-r--r--ldap/servers/slapd/plugin_internal_op.c6
-rw-r--r--ldap/servers/slapd/slapi-private.h1
-rw-r--r--ldap/servers/slapd/str2filter.c8
5 files changed, 63 insertions, 13 deletions
diff --git a/ldap/servers/slapd/back-ldbm/ldbm_search.c b/ldap/servers/slapd/back-ldbm/ldbm_search.c
index d8b7f063..600a9c47 100644
--- a/ldap/servers/slapd/back-ldbm/ldbm_search.c
+++ b/ldap/servers/slapd/back-ldbm/ldbm_search.c
@@ -1203,11 +1203,17 @@ ldbm_back_next_search_entry_ext( Slapi_PBlock *pb, int use_extension )
if((slapi_entry_flag_is_set(e->ep_entry,SLAPI_ENTRY_LDAPSUBENTRY)
&& !filter_flag_is_set(filter,SLAPI_FILTER_LDAPSUBENTRY)) ||
(slapi_entry_flag_is_set(e->ep_entry,SLAPI_ENTRY_FLAG_TOMBSTONE)
- && (!isroot || !filter_flag_is_set(filter, SLAPI_FILTER_TOMBSTONE))))
+ && ((!isroot && !filter_flag_is_set(filter, SLAPI_FILTER_RUV)) ||
+ !filter_flag_is_set(filter, SLAPI_FILTER_TOMBSTONE))))
{
/* If the entry is an LDAP subentry and filter don't filter subentries OR
* the entry is a TombStone and filter don't filter Tombstone
- * don't return the entry
+ * don't return the entry. We make a special case to allow a non-root user
+ * to search for the RUV entry using a filter of:
+ *
+ * "(&(objectclass=nstombstone)(nsuniqueid=ffffffff-ffffffff-ffffffff-ffffffff))"
+ *
+ * For this RUV case, we let the ACL check apply.
*/
/* ugaston - we don't want to mistake this filter failure with the one below due to ACL,
* because whereas the former should be read as 'no entry must be returned', the latter
diff --git a/ldap/servers/slapd/filter.c b/ldap/servers/slapd/filter.c
index 14fee9ff..a3ec29c9 100644
--- a/ldap/servers/slapd/filter.c
+++ b/ldap/servers/slapd/filter.c
@@ -54,14 +54,15 @@
static int
get_filter_list( Connection *conn, BerElement *ber,
struct slapi_filter **f, char **fstr, int maxdepth, int curdepth,
- int *subentry_dont_rewrite, int *has_tombstone_filter);
+ int *subentry_dont_rewrite, int *has_tombstone_filter, int *has_ruv_filter);
static int get_substring_filter();
static int get_extensible_filter( BerElement *ber, mr_filter_t* );
static int get_filter_internal( Connection *conn, BerElement *ber,
struct slapi_filter **filt, char **fstr, int maxdepth, int curdepth,
- int *subentry_dont_rewrite, int *has_tombstone_filter);
+ int *subentry_dont_rewrite, int *has_tombstone_filter, int *has_ruv_filter);
static int tombstone_check_filter(Slapi_Filter *f);
+static int ruv_check_filter(Slapi_Filter *f);
static void filter_optimize(Slapi_Filter *f);
@@ -83,20 +84,23 @@ get_filter( Connection *conn, BerElement *ber, int scope,
{
int subentry_dont_rewrite = 0; /* Re-write unless we're told not to */
int has_tombstone_filter = 0; /* Check if nsTombstone appears */
+ int has_ruv_filter = 0; /* Check if searching for RUV */
int return_value = 0;
char *logbuf = NULL;
size_t logbufsize = 0;
return_value = get_filter_internal(conn, ber, filt, fstr,
config_get_max_filter_nest_level(), /* maximum depth */
- 0, /* current depth */
- &subentry_dont_rewrite, &has_tombstone_filter);
+ 0, /* current depth */ &subentry_dont_rewrite,
+ &has_tombstone_filter, &has_ruv_filter);
if (0 == return_value) { /* Don't try to re-write if there was an error */
if (subentry_dont_rewrite || scope == LDAP_SCOPE_BASE)
(*filt)->f_flags |= SLAPI_FILTER_LDAPSUBENTRY;
if (has_tombstone_filter)
(*filt)->f_flags |= SLAPI_FILTER_TOMBSTONE;
+ if (has_ruv_filter)
+ (*filt)->f_flags |= SLAPI_FILTER_RUV;
}
if (LDAPDebugLevelIsSet( LDAP_DEBUG_FILTER ) && *filt != NULL
@@ -175,7 +179,7 @@ filter_escape_filter_value(struct slapi_filter *f, const char *fmt, size_t len)
static int
get_filter_internal( Connection *conn, BerElement *ber,
struct slapi_filter **filt, char **fstr, int maxdepth, int curdepth,
- int *subentry_dont_rewrite, int *has_tombstone_filter )
+ int *subentry_dont_rewrite, int *has_tombstone_filter, int *has_ruv_filter )
{
ber_len_t len;
int err;
@@ -272,6 +276,18 @@ get_filter_internal( Connection *conn, BerElement *ber,
*has_tombstone_filter = tombstone_check_filter(f);
}
}
+
+ if ( 0 == strcasecmp ( f->f_avtype, "nsuniqueid")) {
+ /*
+ * Check if it's a RUV filter.
+ * We need to do it once per filter, so if flag is already set,
+ * don't bother doing it
+ */
+ if (!(*has_ruv_filter)) {
+ *has_ruv_filter = ruv_check_filter(f);
+ }
+ }
+
*fstr=filter_escape_filter_value(f, FILTER_EQ_FMT, FILTER_EQ_LEN);
}
break;
@@ -342,7 +358,8 @@ get_filter_internal( Connection *conn, BerElement *ber,
case LDAP_FILTER_AND:
LDAPDebug( LDAP_DEBUG_FILTER, "AND\n", 0, 0, 0 );
if ( (err = get_filter_list( conn, ber, &f->f_and, &ftmp, maxdepth,
- curdepth, subentry_dont_rewrite, has_tombstone_filter ))
+ curdepth, subentry_dont_rewrite,
+ has_tombstone_filter, has_ruv_filter ))
== 0 ) {
filter_compute_hash(f);
*fstr = slapi_ch_smprintf( "(&%s)", ftmp );
@@ -353,7 +370,8 @@ get_filter_internal( Connection *conn, BerElement *ber,
case LDAP_FILTER_OR:
LDAPDebug( LDAP_DEBUG_FILTER, "OR\n", 0, 0, 0 );
if ( (err = get_filter_list( conn, ber, &f->f_or, &ftmp, maxdepth,
- curdepth, subentry_dont_rewrite, has_tombstone_filter ))
+ curdepth, subentry_dont_rewrite,
+ has_tombstone_filter, has_ruv_filter ))
== 0 ) {
filter_compute_hash(f);
*fstr = slapi_ch_smprintf( "(|%s)", ftmp );
@@ -365,7 +383,8 @@ get_filter_internal( Connection *conn, BerElement *ber,
LDAPDebug( LDAP_DEBUG_FILTER, "NOT\n", 0, 0, 0 );
(void) ber_skip_tag( ber, &len );
if ( (err = get_filter_internal( conn, ber, &f->f_not, &ftmp, maxdepth,
- curdepth, subentry_dont_rewrite, has_tombstone_filter ))
+ curdepth, subentry_dont_rewrite,
+ has_tombstone_filter, has_ruv_filter ))
== 0 ) {
filter_compute_hash(f);
*fstr = slapi_ch_smprintf( "(!%s)", ftmp );
@@ -394,7 +413,7 @@ static int
get_filter_list( Connection *conn, BerElement *ber,
struct slapi_filter **f, char **fstr, int maxdepth,
int curdepth, int *subentry_dont_rewrite,
- int *has_tombstone_filter)
+ int *has_tombstone_filter, int* has_ruv_filter)
{
struct slapi_filter **new;
int err;
@@ -411,7 +430,8 @@ get_filter_list( Connection *conn, BerElement *ber,
tag = ber_next_element( ber, &len, last ) ) {
char *ftmp;
if ( (err = get_filter_internal( conn, ber, new, &ftmp, maxdepth,
- curdepth, subentry_dont_rewrite, has_tombstone_filter))
+ curdepth, subentry_dont_rewrite,
+ has_tombstone_filter, has_ruv_filter))
!= 0 ) {
if ( *fstr != NULL ) {
slapi_ch_free((void**)fstr );
@@ -1450,6 +1470,17 @@ tombstone_check_filter(Slapi_Filter *f)
return 0; /* Not nsTombstone filter */
}
+
+static int
+ruv_check_filter(Slapi_Filter *f)
+{
+ if ( 0 == strcasecmp ( f->f_avvalue.bv_val, "ffffffff-ffffffff-ffffffff-ffffffff")) {
+ return 1; /* Contains a RUV filter */
+ }
+ return 0; /* Not a RUV filter */
+}
+
+
/* filter_optimize
* ---------------
* takes a filter and optimizes it for fast evaluation
diff --git a/ldap/servers/slapd/plugin_internal_op.c b/ldap/servers/slapd/plugin_internal_op.c
index 4b36ede4..2707149e 100644
--- a/ldap/servers/slapd/plugin_internal_op.c
+++ b/ldap/servers/slapd/plugin_internal_op.c
@@ -720,7 +720,11 @@ static int search_internal_callback_pb (Slapi_PBlock *pb, void *callback_data,
op->o_search_referral_handler = internal_ref_entry_callback;
filter = slapi_str2filter(ifstr ? (fstr = slapi_ch_strdup(ifstr)) : NULL);
- if(scope == LDAP_SCOPE_BASE) filter->f_flags |= (SLAPI_FILTER_LDAPSUBENTRY | SLAPI_FILTER_TOMBSTONE);
+ if(scope == LDAP_SCOPE_BASE) {
+ filter->f_flags |= (SLAPI_FILTER_LDAPSUBENTRY |
+ SLAPI_FILTER_TOMBSTONE | SLAPI_FILTER_RUV);
+ }
+
if (NULL == filter)
{
send_ldap_result(pb, LDAP_FILTER_ERROR, NULL, NULL, 0, NULL);
diff --git a/ldap/servers/slapd/slapi-private.h b/ldap/servers/slapd/slapi-private.h
index ccd98554..eaab8d7a 100644
--- a/ldap/servers/slapd/slapi-private.h
+++ b/ldap/servers/slapd/slapi-private.h
@@ -68,6 +68,7 @@ extern "C" {
/* filter */
#define SLAPI_FILTER_LDAPSUBENTRY 1
#define SLAPI_FILTER_TOMBSTONE 2
+#define SLAPI_FILTER_RUV 4
#define SLAPI_ENTRY_LDAPSUBENTRY 2
/*
diff --git a/ldap/servers/slapd/str2filter.c b/ldap/servers/slapd/str2filter.c
index 744b8fa3..0dd91a56 100644
--- a/ldap/servers/slapd/str2filter.c
+++ b/ldap/servers/slapd/str2filter.c
@@ -162,6 +162,7 @@ str2list( char *str, unsigned long ftype )
str = next;
f->f_flags |= ((*fp)->f_flags & SLAPI_FILTER_LDAPSUBENTRY);
f->f_flags |= ((*fp)->f_flags & SLAPI_FILTER_TOMBSTONE);
+ f->f_flags |= ((*fp)->f_flags & SLAPI_FILTER_RUV);
fp = &(*fp)->f_next;
}
*fp = NULL;
@@ -331,6 +332,13 @@ str2simple( char *str , int unescape_filter)
if (0 == strcasecmp (unqstr,SLAPI_ATTR_VALUE_TOMBSTONE))
f->f_flags |= SLAPI_FILTER_TOMBSTONE;
}
+
+ if((f->f_choice == LDAP_FILTER_EQUALITY) &&
+ (0 == strncasecmp (str,"nsuniqueid",strlen("nsuniqueid")))) {
+ if (0 == strcasecmp (unqstr, "ffffffff-ffffffff-ffffffff-ffffffff"))
+ f->f_flags |= SLAPI_FILTER_RUV;
+ }
+
} if ( !unescape_filter ) {
f->f_avtype = slapi_ch_strdup( str );
f->f_avvalue.bv_val = slapi_ch_strdup ( value );