[SCM] Samba Shared Repository - branch master updated -
release-4-0-0alpha7-1943-gc021330
Andrew Tridgell
tridge at samba.org
Mon Jun 1 06:44:01 GMT 2009
The branch, master has been updated
via c0213308bbde59270f681ce7c55a44bda34a980f (commit)
via ce1045983fd294b95dfe91524b5d8b80a35df448 (commit)
via 5a39817212aa34ef181e9ed72851b077ba088260 (commit)
from ae1c2415e23b56db7ffb8dc96425a8588401b03d (commit)
http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master
- Log -----------------------------------------------------------------
commit c0213308bbde59270f681ce7c55a44bda34a980f
Author: Andrew Tridgell <tridge at samba.org>
Date: Mon Jun 1 16:37:28 2009 +1000
we don't need the unique checks in the samldb code now
These attributes now use the unique indexing flag
commit ce1045983fd294b95dfe91524b5d8b80a35df448
Author: Andrew Tridgell <tridge at samba.org>
Date: Mon Jun 1 16:36:56 2009 +1000
mark samAccountName, objectGUID and objectSID as unique indexed
commit 5a39817212aa34ef181e9ed72851b077ba088260
Author: Andrew Tridgell <tridge at samba.org>
Date: Mon Jun 1 16:36:21 2009 +1000
added support for unique indexing in ldb
When a attribute is marked as LDB_ATTR_FLAG_UNIQUE_INDEX then attempts
to add a 2nd record that has the same attribute value for this
attribute as another record will fail.
This provides a much more efficient mechanism for ensuring that
attributes like objectGUID are unique
-----------------------------------------------------------------------
Summary of changes:
source4/dsdb/samdb/ldb_modules/samldb.c | 164 +------------------------------
source4/dsdb/schema/schema_init.c | 20 ++++
source4/lib/ldb/include/ldb.h | 6 +
source4/lib/ldb/ldb_tdb/ldb_index.c | 33 +++++--
4 files changed, 54 insertions(+), 169 deletions(-)
Changeset truncated at 500 lines:
diff --git a/source4/dsdb/samdb/ldb_modules/samldb.c b/source4/dsdb/samdb/ldb_modules/samldb.c
index 65e3641..dad5ff2 100644
--- a/source4/dsdb/samdb/ldb_modules/samldb.c
+++ b/source4/dsdb/samdb/ldb_modules/samldb.c
@@ -466,91 +466,19 @@ static int samldb_generate_samAccountName(struct ldb_message *msg)
return ldb_msg_add_steal_string(msg, "samAccountName", name);
}
-static int samldb_check_samAccountName_callback(struct ldb_request *req,
- struct ldb_reply *ares)
-{
- struct samldb_ctx *ac;
- int ret;
-
- ac = talloc_get_type(req->context, struct samldb_ctx);
-
- if (!ares) {
- ret = LDB_ERR_OPERATIONS_ERROR;
- goto done;
- }
- if (ares->error != LDB_SUCCESS) {
- return ldb_module_done(ac->req, ares->controls,
- ares->response, ares->error);
- }
-
- switch (ares->type) {
- case LDB_REPLY_ENTRY:
-
- /* if we get an entry it means this samAccountName
- * already exists */
- return ldb_module_done(ac->req, NULL, NULL,
- LDB_ERR_ENTRY_ALREADY_EXISTS);
-
- case LDB_REPLY_REFERRAL:
- /* ignore */
- talloc_free(ares);
- ret = LDB_SUCCESS;
- break;
-
- case LDB_REPLY_DONE:
-
- /* not found, go on */
- talloc_free(ares);
- ret = samldb_next_step(ac);
- break;
- }
-
-done:
- if (ret != LDB_SUCCESS) {
- return ldb_module_done(ac->req, NULL, NULL, ret);
- }
-
- return LDB_SUCCESS;
-}
static int samldb_check_samAccountName(struct samldb_ctx *ac)
{
- struct ldb_context *ldb;
- struct ldb_request *req;
- const char *name;
- char *filter;
int ret;
- ldb = ldb_module_get_ctx(ac->module);
-
if (ldb_msg_find_element(ac->msg, "samAccountName") == NULL) {
ret = samldb_generate_samAccountName(ac->msg);
if (ret != LDB_SUCCESS) {
return ret;
}
}
-
- name = ldb_msg_find_attr_as_string(ac->msg, "samAccountName", NULL);
- if (name == NULL) {
- return LDB_ERR_OPERATIONS_ERROR;
- }
- filter = talloc_asprintf(ac, "samAccountName=%s", name);
- if (filter == NULL) {
- return LDB_ERR_OPERATIONS_ERROR;
- }
-
- ret = ldb_build_search_req(&req, ldb, ac,
- ac->domain_dn, LDB_SCOPE_SUBTREE,
- filter, NULL,
- NULL,
- ac, samldb_check_samAccountName_callback,
- ac->req);
- talloc_free(filter);
- if (ret != LDB_SUCCESS) {
- return ret;
- }
- ac->ares = NULL;
- return ldb_next_request(ac->module, req);
+
+ return samldb_next_step(ac);
}
static int samldb_check_samAccountType(struct samldb_ctx *ac)
@@ -768,87 +696,6 @@ static int samldb_new_sid(struct samldb_ctx *ac)
return samldb_next_step(ac);
}
-static int samldb_check_sid_callback(struct ldb_request *req,
- struct ldb_reply *ares)
-{
- struct samldb_ctx *ac;
- int ret;
-
- ac = talloc_get_type(req->context, struct samldb_ctx);
-
- if (!ares) {
- ret = LDB_ERR_OPERATIONS_ERROR;
- goto done;
- }
- if (ares->error != LDB_SUCCESS) {
- return ldb_module_done(ac->req, ares->controls,
- ares->response, ares->error);
- }
-
- switch (ares->type) {
- case LDB_REPLY_ENTRY:
-
- /* if we get an entry it means an object with the
- * requested sid exists */
- return ldb_module_done(ac->req, NULL, NULL,
- LDB_ERR_CONSTRAINT_VIOLATION);
-
- case LDB_REPLY_REFERRAL:
- /* ignore */
- talloc_free(ares);
- break;
-
- case LDB_REPLY_DONE:
-
- /* not found, go on */
- talloc_free(ares);
- ret = samldb_next_step(ac);
- break;
- }
-
-done:
- if (ret != LDB_SUCCESS) {
- return ldb_module_done(ac->req, NULL, NULL, ret);
- }
-
- return LDB_SUCCESS;
-}
-
-static int samldb_check_sid(struct samldb_ctx *ac)
-{
- struct ldb_context *ldb;
- const char *const attrs[2] = { "objectSid", NULL };
- struct ldb_request *req;
- char *filter;
- int ret;
-
- if (ac->sid == NULL) {
- return LDB_ERR_OPERATIONS_ERROR;
- }
-
- ldb = ldb_module_get_ctx(ac->module);
-
- filter = talloc_asprintf(ac, "(objectSid=%s)",
- ldap_encode_ndr_dom_sid(ac, ac->sid));
- if (filter == NULL) {
- return LDB_ERR_OPERATIONS_ERROR;
- }
-
- ret = ldb_build_search_req(&req, ldb, ac,
- ldb_get_default_basedn(ldb),
- LDB_SCOPE_SUBTREE,
- filter, attrs,
- NULL,
- ac, samldb_check_sid_callback,
- ac->req);
-
- if (ret != LDB_SUCCESS) {
- return ret;
- }
-
- return ldb_next_request(ac->module, req);
-}
-
static int samldb_notice_sid_callback(struct ldb_request *req,
struct ldb_reply *ares)
{
@@ -1051,9 +898,6 @@ static int samldb_fill_object(struct samldb_ctx *ac, const char *type)
if (ret != LDB_SUCCESS) return ret;
}
- ret = samldb_add_step(ac, samldb_check_sid);
- if (ret != LDB_SUCCESS) return ret;
-
ret = samldb_add_step(ac, samldb_notice_sid);
if (ret != LDB_SUCCESS) return ret;
@@ -1228,10 +1072,6 @@ static int samldb_fill_foreignSecurityPrincipal_object(struct samldb_ctx *ac)
ret = samldb_add_step(ac, samldb_apply_template);
if (ret != LDB_SUCCESS) return ret;
- /* check we do not already have this SID */
- ret = samldb_add_step(ac, samldb_check_sid);
- if (ret != LDB_SUCCESS) return ret;
-
/* check if we need to notice this SID */
ret = samldb_add_step(ac, samldb_foreign_notice_sid);
if (ret != LDB_SUCCESS) return ret;
diff --git a/source4/dsdb/schema/schema_init.c b/source4/dsdb/schema/schema_init.c
index 3a65c47..76e7891 100644
--- a/source4/dsdb/schema/schema_init.c
+++ b/source4/dsdb/schema/schema_init.c
@@ -583,6 +583,22 @@ WERROR dsdb_read_prefixes_from_ldb(TALLOC_CTX *mem_ctx, struct ldb_context *ldb,
return WERR_OK;
}
+/*
+ this will be replaced with something that looks at the right part of
+ the schema once we know where unique indexing information is hidden
+ */
+static bool dsdb_schema_unique_attribute(const char *attr)
+{
+ const char *attrs[] = { "samAccountName", "objectGUID", "objectSID" , NULL };
+ int i;
+ for (i=0;attrs[i];i++) {
+ if (strcasecmp(attr, attrs[i]) == 0) {
+ return true;
+ }
+ }
+ return false;
+}
+
/*
setup the ldb_schema_attribute field for a dsdb_attribute
@@ -619,6 +635,10 @@ static int dsdb_schema_setup_ldb_schema_attribute(struct ldb_context *ldb,
a->name = attr->lDAPDisplayName;
a->flags = 0;
a->syntax = s;
+
+ if (dsdb_schema_unique_attribute(a->name)) {
+ a->flags |= LDB_ATTR_FLAG_UNIQUE_INDEX;
+ }
return LDB_SUCCESS;
}
diff --git a/source4/lib/ldb/include/ldb.h b/source4/lib/ldb/include/ldb.h
index 1b6b41a..8e4e2e0 100644
--- a/source4/lib/ldb/include/ldb.h
+++ b/source4/lib/ldb/include/ldb.h
@@ -375,6 +375,12 @@ const struct ldb_dn_extended_syntax *ldb_dn_extended_syntax_by_name(struct ldb_c
*/
#define LDB_ATTR_FLAG_FIXED (1<<2)
+/*
+ when this is set, attempts to create two records which have the same
+ value for this attribute will return LDB_ERR_ENTRY_ALREADY_EXISTS
+ */
+#define LDB_ATTR_FLAG_UNIQUE_INDEX (1<<3)
+
/**
LDAP attribute syntax for a DN
diff --git a/source4/lib/ldb/ldb_tdb/ldb_index.c b/source4/lib/ldb/ldb_tdb/ldb_index.c
index db0c315..300cf7c 100644
--- a/source4/lib/ldb/ldb_tdb/ldb_index.c
+++ b/source4/lib/ldb/ldb_tdb/ldb_index.c
@@ -426,7 +426,8 @@ struct dn_list {
caller frees
*/
static struct ldb_dn *ltdb_index_key(struct ldb_context *ldb,
- const char *attr, const struct ldb_val *value)
+ const char *attr, const struct ldb_val *value,
+ const struct ldb_schema_attribute **ap)
{
struct ldb_dn *ret;
struct ldb_val v;
@@ -440,6 +441,9 @@ static struct ldb_dn *ltdb_index_key(struct ldb_context *ldb,
}
a = ldb_schema_attribute_by_name(ldb, attr);
+ if (ap) {
+ *ap = a;
+ }
r = a->syntax->canonicalise_fn(ldb, ldb, value, &v);
if (r != LDB_SUCCESS) {
const char *errstr = ldb_errstring(ldb);
@@ -531,7 +535,7 @@ static int ltdb_index_dn_simple(struct ldb_module *module,
/* the attribute is indexed. Pull the list of DNs that match the
search criterion */
- dn = ltdb_index_key(ldb, tree->u.equality.attr, &tree->u.equality.value);
+ dn = ltdb_index_key(ldb, tree->u.equality.attr, &tree->u.equality.value, NULL);
if (!dn) return LDB_ERR_OPERATIONS_ERROR;
msg = talloc(list, struct ldb_message);
@@ -851,6 +855,11 @@ static int ltdb_index_dn_and(struct ldb_module *module,
talloc_free(list->dn);
return LDB_ERR_NO_SUCH_OBJECT;
}
+
+ if (list->count == 1) {
+ /* it isn't worth loading the next part of the tree */
+ break;
+ }
}
return ret;
@@ -882,7 +891,7 @@ static int ltdb_index_dn_one(struct ldb_module *module,
search criterion */
val.data = (uint8_t *)((uintptr_t)ldb_dn_get_casefold(parent_dn));
val.length = strlen((char *)val.data);
- key = ltdb_index_key(ldb, LTDB_IDXONE, &val);
+ key = ltdb_index_key(ldb, LTDB_IDXONE, &val, NULL);
if (!key) {
talloc_free(list2);
return LDB_ERR_OPERATIONS_ERROR;
@@ -1181,7 +1190,8 @@ static int ltdb_index_add1_new(struct ldb_context *ldb,
static int ltdb_index_add1_add(struct ldb_context *ldb,
struct ldb_message *msg,
int idx,
- const char *dn)
+ const char *dn,
+ const struct ldb_schema_attribute *a)
{
struct ldb_val *v2;
unsigned int i;
@@ -1193,6 +1203,10 @@ static int ltdb_index_add1_add(struct ldb_context *ldb,
}
}
+ if (a->flags & LDB_ATTR_FLAG_UNIQUE_INDEX) {
+ return LDB_ERR_ENTRY_ALREADY_EXISTS;
+ }
+
v2 = talloc_realloc(msg->elements, msg->elements[idx].values,
struct ldb_val,
msg->elements[idx].num_values+1);
@@ -1219,6 +1233,7 @@ static int ltdb_index_add1(struct ldb_module *module, const char *dn,
struct ldb_dn *dn_key;
int ret;
unsigned int i;
+ const struct ldb_schema_attribute *a;
ldb = ldb_module_get_ctx(module);
@@ -1228,7 +1243,7 @@ static int ltdb_index_add1(struct ldb_module *module, const char *dn,
return LDB_ERR_OPERATIONS_ERROR;
}
- dn_key = ltdb_index_key(ldb, el->name, &el->values[v_idx]);
+ dn_key = ltdb_index_key(ldb, el->name, &el->values[v_idx], &a);
if (!dn_key) {
talloc_free(msg);
return LDB_ERR_OPERATIONS_ERROR;
@@ -1256,7 +1271,7 @@ static int ltdb_index_add1(struct ldb_module *module, const char *dn,
if (i == msg->num_elements) {
ret = ltdb_index_add1_new(ldb, msg, dn);
} else {
- ret = ltdb_index_add1_add(ldb, msg, i, dn);
+ ret = ltdb_index_add1_add(ldb, msg, i, dn, a);
}
if (ret == LDB_SUCCESS) {
@@ -1339,7 +1354,7 @@ int ltdb_index_del_value(struct ldb_module *module, const char *dn,
return LDB_SUCCESS;
}
- dn_key = ltdb_index_key(ldb, el->name, &el->values[v_idx]);
+ dn_key = ltdb_index_key(ldb, el->name, &el->values[v_idx], NULL);
if (!dn_key) {
return LDB_ERR_OPERATIONS_ERROR;
}
@@ -1455,6 +1470,10 @@ int ltdb_index_one(struct ldb_module *module, const struct ldb_message *msg, int
const char *dn;
int ret;
+ if (ldb_dn_is_special(msg->dn)) {
+ return LDB_SUCCESS;
+ }
+
/* We index for ONE Level only if requested */
ret = ldb_msg_find_idx(ltdb->cache->indexlist, NULL, NULL, LTDB_IDXONE);
if (ret != 0) {
--
Samba Shared Repository
More information about the samba-cvs
mailing list