diff options
-rw-r--r-- | source4/dsdb/samdb/ldb_modules/kludge_acl.c | 101 | ||||
-rw-r--r-- | source4/dsdb/samdb/ldb_modules/schema_fsmo.c | 4 | ||||
-rw-r--r-- | source4/dsdb/samdb/samdb.c | 1 | ||||
-rw-r--r-- | source4/dsdb/schema/schema_init.c | 90 | ||||
-rw-r--r-- | source4/lib/db_wrap.c | 5 | ||||
-rw-r--r-- | source4/lib/ldb/common/ldb_msg.c | 12 | ||||
-rw-r--r-- | source4/lib/ldb/samba/ldif_handlers.c | 71 | ||||
-rw-r--r-- | source4/scripting/libjs/provision.js | 14 | ||||
-rwxr-xr-x | source4/setup/provision | 6 | ||||
-rw-r--r-- | source4/setup/provision_partitions.ldif | 6 | ||||
-rw-r--r-- | source4/setup/provision_schema_basedn_modify.ldif | 18 | ||||
-rwxr-xr-x | testprogs/ejs/ldap.js | 41 | ||||
-rwxr-xr-x | testprogs/ejs/samba3sam.js | 198 |
13 files changed, 402 insertions, 165 deletions
diff --git a/source4/dsdb/samdb/ldb_modules/kludge_acl.c b/source4/dsdb/samdb/ldb_modules/kludge_acl.c index ff0dd062fb..6b043aeb40 100644 --- a/source4/dsdb/samdb/ldb_modules/kludge_acl.c +++ b/source4/dsdb/samdb/ldb_modules/kludge_acl.c @@ -37,6 +37,7 @@ #include "ldb/include/ldb_private.h" #include "auth/auth.h" #include "libcli/security/security.h" +#include "dsdb/samdb/samdb.h" /* Kludge ACL rules: * @@ -105,13 +106,74 @@ struct kludge_acl_context { int (*up_callback)(struct ldb_context *, void *, struct ldb_reply *); enum user_is user_type; + bool allowedAttributes; + bool allowedAttributesEffective; + const char **attrs; }; +/* read all objectClasses */ + +static int kludge_acl_allowedAttributes(struct ldb_context *ldb, struct ldb_message *msg, + const char *attrName) +{ + struct ldb_message_element *oc_el = ldb_msg_find_element(msg, "objectClass"); + struct ldb_message_element *allowedAttributes; + const struct dsdb_schema *schema = dsdb_get_schema(ldb); + const struct dsdb_class *class; + int i, j, ret; + ret = ldb_msg_add_empty(msg, attrName, 0, &allowedAttributes); + if (ret != LDB_SUCCESS) { + return ret; + } + + for (i=0; i < oc_el->num_values; i++) { + class = dsdb_class_by_lDAPDisplayName(schema, (const char *)oc_el->values[i].data); + if (!class) { + /* We don't know this class? what is going on? */ + continue; + } + for (j=0; class->mayContain && class->mayContain[j]; j++) { + ldb_msg_add_string(msg, attrName, class->mayContain[j]); + } + for (j=0; class->mustContain && class->mustContain[j]; j++) { + ldb_msg_add_string(msg, attrName, class->mustContain[j]); + } + for (j=0; class->systemMayContain && class->systemMayContain[j]; j++) { + ldb_msg_add_string(msg, attrName, class->systemMayContain[j]); + } + for (j=0; class->systemMustContain && class->systemMustContain[j]; j++) { + ldb_msg_add_string(msg, attrName, class->systemMustContain[j]); + } + } + + if (allowedAttributes->num_values > 1) { + qsort(allowedAttributes->values, + allowedAttributes->num_values, + sizeof(*allowedAttributes->values), + data_blob_cmp); + + for (i=1 ; i < allowedAttributes->num_values; i++) { + struct ldb_val *val1 = &allowedAttributes->values[i-1]; + struct ldb_val *val2 = &allowedAttributes->values[i]; + if (data_blob_cmp(val1, val2) == 0) { + memmove(val1, val2, (allowedAttributes->num_values - i) * sizeof( struct ldb_val)); + allowedAttributes->num_values--; + i--; + } + } + } + + return 0; + +} + +/* find all attributes allowed by all these objectClasses */ + static int kludge_acl_callback(struct ldb_context *ldb, void *context, struct ldb_reply *ares) { struct kludge_acl_context *ac; struct kludge_private_data *data; - int i; + int i, ret; if (!context || !ares) { ldb_set_errstring(ldb, "NULL Context or Result in callback"); @@ -121,12 +183,28 @@ static int kludge_acl_callback(struct ldb_context *ldb, void *context, struct ld ac = talloc_get_type(context, struct kludge_acl_context); data = talloc_get_type(ac->module->private_data, struct kludge_private_data); - if (ares->type == LDB_REPLY_ENTRY - && data && data->password_attrs) /* if we are not initialized just get through */ + if (ares->type != LDB_REPLY_ENTRY) { + return ac->up_callback(ldb, ac->up_context, ares); + } + + if (ac->allowedAttributes) { + ret = kludge_acl_allowedAttributes(ldb, ares->message, "allowedAttributes"); + if (ret != LDB_SUCCESS) { + return ret; + } + } + + if (data && data->password_attrs) /* if we are not initialized just get through */ { switch (ac->user_type) { case SYSTEM: case ADMINISTRATOR: + if (ac->allowedAttributesEffective) { + ret = kludge_acl_allowedAttributes(ldb, ares->message, "allowedAttributesEffective"); + if (ret != LDB_SUCCESS) { + return ret; + } + } break; default: /* remove password attributes */ @@ -136,6 +214,12 @@ static int kludge_acl_callback(struct ldb_context *ldb, void *context, struct ld } } + if ((ac->allowedAttributes || ac->allowedAttributesEffective) && + (!ldb_attr_in_list(ac->attrs, "objectClass") && + !ldb_attr_in_list(ac->attrs, "*"))) { + ldb_msg_remove_attr(ares->message, "objectClass"); + } + return ac->up_callback(ldb, ac->up_context, ares); error: @@ -163,6 +247,7 @@ static int kludge_acl_search(struct ldb_module *module, struct ldb_request *req) ac->up_context = req->context; ac->up_callback = req->callback; ac->user_type = what_is_user(module); + ac->attrs = req->op.search.attrs; down_req = talloc_zero(req, struct ldb_request); if (down_req == NULL) { @@ -174,7 +259,15 @@ static int kludge_acl_search(struct ldb_module *module, struct ldb_request *req) down_req->op.search.scope = req->op.search.scope; down_req->op.search.tree = req->op.search.tree; down_req->op.search.attrs = req->op.search.attrs; - + + ac->allowedAttributes = ldb_attr_in_list(req->op.search.attrs, "allowedAttributes"); + + ac->allowedAttributesEffective = ldb_attr_in_list(req->op.search.attrs, "allowedAttributesEffective"); + + if (ac->allowedAttributes || ac->allowedAttributesEffective) { + down_req->op.search.attrs + = ldb_attr_list_copy_add(down_req, down_req->op.search.attrs, "objectClass"); + } /* FIXME: I hink we should copy the tree and keep the original * unmodified. SSS */ diff --git a/source4/dsdb/samdb/ldb_modules/schema_fsmo.c b/source4/dsdb/samdb/ldb_modules/schema_fsmo.c index eb5d7e8e8e..3df887acb6 100644 --- a/source4/dsdb/samdb/ldb_modules/schema_fsmo.c +++ b/source4/dsdb/samdb/ldb_modules/schema_fsmo.c @@ -54,6 +54,10 @@ static int schema_fsmo_init(struct ldb_module *module) NULL }; + if (dsdb_get_schema(module->ldb)) { + return ldb_next_init(module); + } + schema_dn = samdb_schema_dn(module->ldb); if (!schema_dn) { ldb_debug(module->ldb, LDB_DEBUG_WARNING, diff --git a/source4/dsdb/samdb/samdb.c b/source4/dsdb/samdb/samdb.c index 2208bb9333..2ae0fe25ac 100644 --- a/source4/dsdb/samdb/samdb.c +++ b/source4/dsdb/samdb/samdb.c @@ -50,6 +50,7 @@ struct ldb_context *samdb_connect(TALLOC_CTX *mem_ctx, if (!ldb) { return NULL; } + dsdb_make_schema_global(ldb); return ldb; } diff --git a/source4/dsdb/schema/schema_init.c b/source4/dsdb/schema/schema_init.c index b609478f94..c7a7b59754 100644 --- a/source4/dsdb/schema/schema_init.c +++ b/source4/dsdb/schema/schema_init.c @@ -323,6 +323,34 @@ WERROR dsdb_map_int2oid(const struct dsdb_schema *schema, uint32_t in, TALLOC_CT talloc_steal(mem_ctx, (p)->elem); \ } while (0) +#define GET_STRING_LIST_LDB(msg, attr, mem_ctx, p, elem, strict) do { \ + int get_string_list_counter; \ + struct ldb_message_element *get_string_list_el = ldb_msg_find_element(msg, attr); \ + if (get_string_list_el == NULL) { \ + if (strict) { \ + d_printf("%s: %s == NULL\n", __location__, attr); \ + return WERR_INVALID_PARAM; \ + } else { \ + (p)->elem = NULL; \ + break; \ + } \ + } \ + (p)->elem = talloc_array(mem_ctx, const char *, get_string_list_el->num_values + 1); \ + for (get_string_list_counter=0; \ + get_string_list_counter < get_string_list_el->num_values; \ + get_string_list_counter++) { \ + (p)->elem[get_string_list_counter] = talloc_strndup((p)->elem, \ + (const char *)get_string_list_el->values[get_string_list_counter].data, \ + get_string_list_el->values[get_string_list_counter].length); \ + if (!(p)->elem[get_string_list_counter]) { \ + d_printf("%s: talloc_strndup failed for %s\n", __location__, attr); \ + return WERR_NOMEM; \ + } \ + (p)->elem[get_string_list_counter+1] = NULL; \ + } \ + talloc_steal(mem_ctx, (p)->elem); \ +} while (0) + #define GET_BOOL_LDB(msg, attr, p, elem, strict) do { \ const char *str; \ str = samdb_result_string(msg, attr, NULL);\ @@ -466,13 +494,14 @@ WERROR dsdb_class_from_ldb(const struct dsdb_schema *schema, obj->systemAuxiliaryClass = NULL; obj->systemPossSuperiors = NULL; - obj->systemMustContain = NULL; - obj->systemMayContain = NULL; obj->auxiliaryClass = NULL; obj->possSuperiors = NULL; - obj->mustContain = NULL; - obj->mayContain = NULL; + + GET_STRING_LIST_LDB(msg, "systemMustContain", mem_ctx, obj, systemMustContain, False); + GET_STRING_LIST_LDB(msg, "systemMayContain", mem_ctx, obj, systemMayContain, False); + GET_STRING_LIST_LDB(msg, "mustContain", mem_ctx, obj, mustContain, False); + GET_STRING_LIST_LDB(msg, "mayContain", mem_ctx, obj, mayContain, False); GET_STRING_LDB(msg, "defaultSecurityDescriptor", mem_ctx, obj, defaultSecurityDescriptor, False); @@ -930,6 +959,23 @@ const struct dsdb_class *dsdb_class_by_lDAPDisplayName(const struct dsdb_schema return NULL; } +const struct dsdb_class *dsdb_class_by_cn(const struct dsdb_schema *schema, + const char *cn) +{ + struct dsdb_class *cur; + + if (!cn) return NULL; + + /* TODO: add binary search */ + for (cur = schema->classes; cur; cur = cur->next) { + if (strcasecmp(cur->cn, cn) != 0) continue; + + return cur; + } + + return NULL; +} + const char *dsdb_lDAPDisplayName_by_id(const struct dsdb_schema *schema, uint32_t id) { @@ -964,6 +1010,22 @@ int dsdb_set_schema(struct ldb_context *ldb, struct dsdb_schema *schema) return LDB_SUCCESS; } +static struct dsdb_schema *global_schema; + +int dsdb_set_global_schema(struct ldb_context *ldb) +{ + int ret; + if (!global_schema) { + return LDB_SUCCESS; + } + ret = ldb_set_opaque(ldb, "dsdb_schema", global_schema); + if (ret != LDB_SUCCESS) { + return ret; + } + + return LDB_SUCCESS; +} + const struct dsdb_schema *dsdb_get_schema(struct ldb_context *ldb) { const void *p; @@ -983,6 +1045,26 @@ const struct dsdb_schema *dsdb_get_schema(struct ldb_context *ldb) return schema; } +void dsdb_make_schema_global(struct ldb_context *ldb) +{ + const void *p; + const struct dsdb_schema *schema; + + /* see if we have a cached copy */ + p = ldb_get_opaque(ldb, "dsdb_schema"); + if (!p) { + return; + } + + schema = talloc_get_type(p, struct dsdb_schema); + if (!schema) { + return; + } + + talloc_steal(NULL, schema); + global_schema = schema; +} + WERROR dsdb_attach_schema_from_ldif_file(struct ldb_context *ldb, const char *pf, const char *df) { struct ldb_ldif *ldif; diff --git a/source4/lib/db_wrap.c b/source4/lib/db_wrap.c index f884140d1c..e7d3388f72 100644 --- a/source4/lib/db_wrap.c +++ b/source4/lib/db_wrap.c @@ -35,6 +35,7 @@ #include "lib/ldb/include/ldb_errors.h" #include "lib/ldb/samba/ldif_handlers.h" #include "db_wrap.h" +#include "dsdb/samdb/samdb.h" static struct tdb_wrap *tdb_list; @@ -126,6 +127,10 @@ struct ldb_context *ldb_wrap_connect(TALLOC_CTX *mem_ctx, talloc_free(ldb); return NULL; } + + if (strcmp(lp_sam_url(), url) == 0) { + dsdb_set_global_schema(ldb); + } ret = ldb_register_samba_handlers(ldb); if (ret == -1) { diff --git a/source4/lib/ldb/common/ldb_msg.c b/source4/lib/ldb/common/ldb_msg.c index 1d02fb0f3e..d0dd252e47 100644 --- a/source4/lib/ldb/common/ldb_msg.c +++ b/source4/lib/ldb/common/ldb_msg.c @@ -666,7 +666,15 @@ const char **ldb_attr_list_copy_add(TALLOC_CTX *mem_ctx, const char * const *att { const char **ret; int i; - for (i=0;attrs[i];i++) /* noop */ ; + bool found = false; + for (i=0;attrs[i];i++) { + if (ldb_attr_cmp(attrs[i], new_attr) == 0) { + found = true; + } + } + if (found) { + return ldb_attr_list_copy(mem_ctx, attrs); + } ret = talloc_array(mem_ctx, const char *, i+2); if (ret == NULL) { return NULL; @@ -686,7 +694,7 @@ const char **ldb_attr_list_copy_add(TALLOC_CTX *mem_ctx, const char * const *att int ldb_attr_in_list(const char * const *attrs, const char *attr) { int i; - for (i=0;attrs[i];i++) { + for (i=0;attrs && attrs[i];i++) { if (ldb_attr_cmp(attrs[i], attr) == 0) { return 1; } diff --git a/source4/lib/ldb/samba/ldif_handlers.c b/source4/lib/ldb/samba/ldif_handlers.c index 44b956a8b6..e1691d0cb3 100644 --- a/source4/lib/ldb/samba/ldif_handlers.c +++ b/source4/lib/ldb/samba/ldif_handlers.c @@ -299,66 +299,53 @@ static int ldif_canonicalise_objectCategory(struct ldb_context *ldb, void *mem_c const struct ldb_val *in, struct ldb_val *out) { struct ldb_dn *dn1 = NULL; - char *oc1, *oc2; + const struct dsdb_schema *schema = dsdb_get_schema(ldb); + const struct dsdb_class *class; + if (!schema) { + *out = data_blob_talloc(mem_ctx, in->data, in->length); + return LDB_SUCCESS; + } dn1 = ldb_dn_new(mem_ctx, ldb, (char *)in->data); if ( ! ldb_dn_validate(dn1)) { - oc1 = talloc_strndup(mem_ctx, (char *)in->data, in->length); - } else if (ldb_dn_get_comp_num(dn1) >= 1 && strcasecmp(ldb_dn_get_rdn_name(dn1), "cn") == 0) { + const char *lDAPDisplayName = talloc_strndup(mem_ctx, (char *)in->data, in->length); + class = dsdb_class_by_lDAPDisplayName(schema, lDAPDisplayName); + talloc_free(lDAPDisplayName); + } else if (ldb_dn_get_comp_num(dn1) >= 1 && ldb_attr_cmp(ldb_dn_get_rdn_name(dn1), "cn") == 0) { const struct ldb_val *val = ldb_dn_get_rdn_val(dn1); - oc1 = talloc_strndup(mem_ctx, (char *)val->data, val->length); + const char *cn = talloc_strndup(mem_ctx, (char *)val->data, val->length); + class = dsdb_class_by_cn(schema, cn); + talloc_free(cn); } else { + talloc_free(dn1); return -1; } - - oc2 = ldb_casefold(ldb, mem_ctx, oc1); - out->data = (void *)oc2; - out->length = strlen(oc2); - talloc_free(oc1); talloc_free(dn1); - return 0; + + if (!class) { + return -1; + } + + *out = data_blob_string_const(talloc_strdup(mem_ctx, class->lDAPDisplayName)); + + return LDB_SUCCESS; } static int ldif_comparison_objectCategory(struct ldb_context *ldb, void *mem_ctx, const struct ldb_val *v1, const struct ldb_val *v2) { - struct ldb_dn *dn1 = NULL, *dn2 = NULL; - const char *oc1, *oc2; - dn1 = ldb_dn_new(mem_ctx, ldb, (char *)v1->data); - if ( ! ldb_dn_validate(dn1)) { - oc1 = talloc_strndup(mem_ctx, (char *)v1->data, v1->length); - } else if (ldb_dn_get_comp_num(dn1) >= 1 && strcasecmp(ldb_dn_get_rdn_name(dn1), "cn") == 0) { - const struct ldb_val *val = ldb_dn_get_rdn_val(dn1); - oc1 = talloc_strndup(mem_ctx, (char *)val->data, val->length); - } else { - oc1 = NULL; - } + int ret1, ret2; + struct ldb_val v1_canon, v2_canon; + ret1 = ldif_canonicalise_objectCategory(ldb, mem_ctx, v1, &v1_canon); + ret2 = ldif_canonicalise_objectCategory(ldb, mem_ctx, v2, &v2_canon); - dn2 = ldb_dn_new(mem_ctx, ldb, (char *)v2->data); - if ( ! ldb_dn_validate(dn2)) { - oc2 = talloc_strndup(mem_ctx, (char *)v2->data, v2->length); - } else if (ldb_dn_get_comp_num(dn2) >= 2 && strcasecmp(ldb_dn_get_rdn_name(dn2), "cn") == 0) { - const struct ldb_val *val = ldb_dn_get_rdn_val(dn2); - oc2 = talloc_strndup(mem_ctx, (char *)val->data, val->length); + if (ret1 == LDB_SUCCESS && ret2 == LDB_SUCCESS) { + return ldb_attr_cmp(v1_canon.data, v2_canon.data); } else { - oc2 = NULL; + return strcasecmp(v1->data, v2->data); } - - oc1 = ldb_casefold(ldb, mem_ctx, oc1); - oc2 = ldb_casefold(ldb, mem_ctx, oc2); - if (!oc1 && oc2) { - return -1; - } - if (oc1 && !oc2) { - return 1; - } - if (!oc1 && !oc2) { - return -1; - } - - return strcmp(oc1, oc2); } #define LDB_SYNTAX_SAMBA_SID "LDB_SYNTAX_SAMBA_SID" diff --git a/source4/scripting/libjs/provision.js b/source4/scripting/libjs/provision.js index 9adcab2679..f94c34e932 100644 --- a/source4/scripting/libjs/provision.js +++ b/source4/scripting/libjs/provision.js @@ -611,7 +611,7 @@ function provision(subobj, message, blank, paths, session_info, credentials, lda var modify_ok = setup_ldb_modify("provision_schema_basedn_modify.ldif", info, samdb); if (!modify_ok) { if (!add_ok) { - message("Failed to both add and modify schema dn: + samdb.errstring() + "\n"); + message("Failed to both add and modify schema dn:" + samdb.errstring() + "\n"); message("Perhaps you need to run the provision script with the --ldap-base-dn option, and add this record to the backend manually\n"); assert(modify_ok); } @@ -744,7 +744,7 @@ function provision_schema(subobj, message, tmp_schema_path, paths) var modify_ok = setup_ldb_modify("provision_schema_basedn_modify.ldif", info, samdb); if (!modify_ok) { if (!add_ok) { - message("Failed to both add and modify schema dn: + samdb.errstring() + "\n"); + message("Failed to both add and modify schema dn: " + samdb.errstring() + "\n"); message("Perhaps you need to run the provision script with the --ldap-base-dn option, and add this record to the backend manually\n"); assert(modify_ok); } @@ -882,16 +882,18 @@ function provision_guess() "extended_dn", "asq", "samldb", - "password_hash", "operational", "objectclass", "rdn_name", "show_deleted", "partition"); subobj.MODULES_LIST = join(",", modules_list); - subobj.DOMAINDN_MOD = "objectguid"; - subobj.CONFIGDN_MOD = "objectguid"; - subobj.SCHEMADN_MOD = "objectguid"; + subobj.DOMAINDN_MOD = "pdc_fsmo,password_hash"; + subobj.CONFIGDN_MOD = "naming_fsmo"; + subobj.SCHEMADN_MOD = "schema_fsmo"; + subobj.DOMAINDN_MOD2 = ",objectguid"; + subobj.CONFIGDN_MOD2 = ",objectguid"; + subobj.SCHEMADN_MOD2 = ",objectguid"; subobj.EXTENSIBLEOBJECT = "# no objectClass: extensibleObject for local ldb"; subobj.ACI = "# no aci for local ldb"; diff --git a/source4/setup/provision b/source4/setup/provision index 3c5d31dc0f..9a67d06963 100755 --- a/source4/setup/provision +++ b/source4/setup/provision @@ -132,11 +132,11 @@ if (ldapbackend) { subobj["LDAPMODULE"] = "entryUUID"; } subobj["DOMAINDN_LDB"] = subobj["LDAPBACKEND"]; - subobj["DOMAINDN_MOD"] = subobj["LDAPMODULE"] + ",paged_searches"; + subobj["DOMAINDN_MOD2"] = subobj["LDAPMODULE"] + ",paged_searches"; subobj["CONFIGDN_LDB"] = subobj["LDAPBACKEND"]; - subobj["CONFIGDN_MOD"] = subobj["LDAPMODULE"] + ",paged_searches"; + subobj["CONFIGDN_MOD2"] = subobj["LDAPMODULE"] + ",paged_searches"; subobj["SCHEMADN_LDB"] = subobj["LDAPBACKEND"]; - subobj["SCHEMADN_MOD"] = subobj["LDAPMODULE"] + ",paged_searches"; + subobj["SCHEMADN_MOD2"] = subobj["LDAPMODULE"] + ",paged_searches"; } if (!provision_validate(subobj, message)) { diff --git a/source4/setup/provision_partitions.ldif b/source4/setup/provision_partitions.ldif index 3800918bc1..c6107c6502 100644 --- a/source4/setup/provision_partitions.ldif +++ b/source4/setup/provision_partitions.ldif @@ -5,9 +5,9 @@ partition: ${DOMAINDN}:${DOMAINDN_LDB} replicateEntries: @SUBCLASSES replicateEntries: @ATTRIBUTES replicateEntries: @INDEXLIST -modules:${SCHEMADN}:${SCHEMADN_MOD} -modules:${CONFIGDN}:${CONFIGDN_MOD} -modules:${DOMAINDN}:${DOMAINDN_MOD} +modules:${SCHEMADN}:${SCHEMADN_MOD}${SCHEMADN_MOD2} +modules:${CONFIGDN}:${CONFIGDN_MOD}${CONFIGDN_MOD2} +modules:${DOMAINDN}:${DOMAINDN_MOD}${DOMAINDN_MOD2} dn: @MODULES @LIST: ${MODULES_LIST} diff --git a/source4/setup/provision_schema_basedn_modify.ldif b/source4/setup/provision_schema_basedn_modify.ldif index 1f188d0679..a222a654f7 100644 --- a/source4/setup/provision_schema_basedn_modify.ldif +++ b/source4/setup/provision_schema_basedn_modify.ldif @@ -23,3 +23,21 @@ fSMORoleOwner: CN=NTDS Settings,CN=${NETBIOSNAME},CN=Servers,CN=${DEFAULTSITE},C - replace: objectVersion objectVersion: 30 +- +replace: prefixMap +prefixMap:: QkRTRAAAAAAiAAAAAAACACIAAAAAAAAAAgAAAAQAAgABAAAAAgAAAAgAAgACAAAACA + AAAAwAAgADAAAACAAAABAAAgAEAAAACAAAABQAAgAFAAAACAAAABgAAgAGAAAACAAAABwAAgAHAAA + ACAAAACAAAgAIAAAAAgAAACQAAgAJAAAACAAAACgAAgAKAAAACAAAACwAAgATAAAACAAAADAAAgAU + AAAACAAAADQAAgAVAAAACQAAADgAAgAWAAAACQAAADwAAgAXAAAACgAAAEAAAgAYAAAAAgAAAEQAA + gAZAAAAAgAAAEgAAgAaAAAAAgAAAEwAAgALAAAACgAAAFAAAgAMAAAACQAAAFQAAgANAAAACgAAAF + gAAgAOAAAACQAAAFwAAgAPAAAACgAAAGAAAgAQAAAACQAAAGQAAgARAAAACQAAAGgAAgASAAAACgA + AAGwAAgAbAAAACQAAAHAAAgAcAAAACQAAAHQAAgAdAAAACAAAAHgAAgAeAAAACAAAAHwAAgAfAAAA + CQAAAIAAAgAgAAAACQAAAIQAAgAhAAAACQAAAIgAAgACAAAAVQQAAAIAAABVBgAACAAAACqGSIb3F + AECCAAAACqGSIb3FAEDCAAAAGCGSAFlAgIBCAAAAGCGSAFlAgIDCAAAAGCGSAFlAgEFCAAAAGCGSA + FlAgEEAgAAAFUFAAAIAAAAKoZIhvcUAQQIAAAAKoZIhvcUAQUIAAAACZImiZPyLGQIAAAAYIZIAYb + 4QgMJAAAACZImiZPyLGQBAAAACQAAAGCGSAGG+EIDAQAAAAoAAAAqhkiG9xQBBbZYAAACAAAAVRUA + AAIAAABVEgAAAgAAAFUUAAAKAAAAKoZIhvcUAQSCBAAACQAAACqGSIb3FAEFOAAAAAoAAAAqhkiG9 + xQBBIIGAAAJAAAAKoZIhvcUAQU5AAAACgAAACqGSIb3FAEEggcAAAkAAAAqhkiG9xQBBToAAAAJAA + AAKoZIhvcUAQVJAAAACgAAACqGSIb3FAEEgjEAAAkAAAArBgEEAYs6ZXcAAAAJAAAAYIZIAYb4QgM + CAAAACAAAACsGAQQBgXoBCAAAACqGSIb3DQEJCQAAAAmSJomT8ixkBAAAAAkAAAArBgEEAbd9BAEA + AAAJAAAAKwYBBAG3fQQC diff --git a/testprogs/ejs/ldap.js b/testprogs/ejs/ldap.js index ecd50c3097..7ea66a7998 100755 --- a/testprogs/ejs/ldap.js +++ b/testprogs/ejs/ldap.js @@ -25,7 +25,7 @@ if (options.ARGV.length != 1) { var host = options.ARGV[0]; -function basic_tests(ldb, gc_ldb, base_dn, configuration_dn) +function basic_tests(ldb, gc_ldb, base_dn, configuration_dn, schema_dn) { println("Running basic tests"); @@ -473,6 +473,33 @@ objectClass: user assert(res.error == 0); assert (res.msgs.length > 0); + println("Testing objectCategory canonacolisation"); + var attrs = new Array("cn"); + var res = ldb.search("objectCategory=ntDsDSA", configuration_dn, ldb.SCOPE_SUBTREE, attrs); + assert(res.error == 0); + if (res.msgs.length == 0) { + println("Didn't find any records with objectCategory=ntDsDSA"); + } + assert(res.msgs.length != 0); + + var attrs = new Array("cn"); + var res = ldb.search("objectCategory=CN=ntDs-DSA," + schema_dn, configuration_dn, ldb.SCOPE_SUBTREE, attrs); + assert(res.error == 0); + if (res.msgs.length == 0) { + println("Didn't find any records with objectCategory=CN=ntDs-DSA," + schema_dn); + } + assert(res.msgs.length != 0); + + println("Testing objectClass attribute order on "+ base_dn); + var attrs = new Array("objectclass"); + var res = ldb.search("objectClass=domain", base_dn, ldb.SCOPE_BASE, attrs); + assert(res.error == 0); + assert(res.msgs.length == 1); + + assert(res.msgs[0].objectClass[0] == "top"); + assert(res.msgs[0].objectClass[1] == "domain"); + assert(res.msgs[0].objectClass[2] == "domainDNS"); + } function basedn_tests(ldb, gc_ldb) @@ -522,6 +549,15 @@ function find_configurationdn(ldb) return res.msgs[0].configurationNamingContext; } +function find_schemadn(ldb) +{ + var attrs = new Array("schemaNamingContext"); + var res = ldb.search("", "", ldb.SCOPE_BASE, attrs); + assert(res.error == 0); + assert(res.msgs.length == 1); + return res.msgs[0].schemaNamingContext; +} + /* use command line creds if available */ ldb.credentials = options.get_credentials(); gc_ldb.credentials = options.get_credentials(); @@ -529,6 +565,7 @@ gc_ldb.credentials = options.get_credentials(); var ok = ldb.connect("ldap://" + host); var base_dn = find_basedn(ldb); var configuration_dn = find_configurationdn(ldb); +var schema_dn = find_schemadn(ldb); printf("baseDN: %s\n", base_dn); @@ -537,7 +574,7 @@ if (!ok) { gc_ldb = undefined; } -basic_tests(ldb, gc_ldb, base_dn, configuration_dn) +basic_tests(ldb, gc_ldb, base_dn, configuration_dn, schema_dn) basedn_tests(ldb, gc_ldb) diff --git a/testprogs/ejs/samba3sam.js b/testprogs/ejs/samba3sam.js index e0fab647b5..5fa527a694 100755 --- a/testprogs/ejs/samba3sam.js +++ b/testprogs/ejs/samba3sam.js @@ -270,7 +270,7 @@ objectClass: user cn: X codePage: x revision: x -objectCategory: x +dnsHostName: x nextRid: y lastLogon: x description: x @@ -282,7 +282,7 @@ objectClass: top cn: Y codePage: x revision: x -objectCategory: y +dnsHostName: y nextRid: y lastLogon: y description: x @@ -292,7 +292,7 @@ objectClass: top cn: Z codePage: x revision: y -objectCategory: z +dnsHostName: z nextRid: y lastLogon: z description: y @@ -342,86 +342,86 @@ description: y /* Search remote record by local DN */ dn = s4.dn("cn=A"); - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("", dn, ldb.SCOPE_BASE, attrs); assert(res.error == 0); assert(res.msgs.length == 1); assert(res.msgs[0].dn == dn); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "x"); /* Search remote record by remote DN */ dn = s3.dn("cn=A"); - attrs = new Array("objectCategory", "lastLogon", "sambaLogonTime"); + attrs = new Array("dnsHostName", "lastLogon", "sambaLogonTime"); res = s3.db.search("", dn, ldb.SCOPE_BASE, attrs); assert(res.error == 0); assert(res.msgs.length == 1); assert(res.msgs[0].dn == dn); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == undefined); assert(res.msgs[0].sambaLogonTime == "x"); /* Search split record by local DN */ dn = s4.dn("cn=X"); - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("", dn, ldb.SCOPE_BASE, attrs); assert(res.error == 0); assert(res.msgs.length == 1); assert(res.msgs[0].dn == dn); - assert(res.msgs[0].objectCategory == "x"); + assert(res.msgs[0].dnsHostName == "x"); assert(res.msgs[0].lastLogon == "x"); /* Search split record by remote DN */ dn = s3.dn("cn=X"); - attrs = new Array("objectCategory", "lastLogon", "sambaLogonTime"); + attrs = new Array("dnsHostName", "lastLogon", "sambaLogonTime"); res = s3.db.search("", dn, ldb.SCOPE_BASE, attrs); assert(res.error == 0); assert(res.msgs.length == 1); assert(res.msgs[0].dn == dn); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == undefined); assert(res.msgs[0].sambaLogonTime == "x"); println("Testing search by attribute"); /* Search by ignored attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(revision=x)", NULL, ldb. SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=Y")); - assert(res.msgs[0].objectCategory == "y"); + assert(res.msgs[0].dnsHostName == "y"); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=X")); - assert(res.msgs[1].objectCategory == "x"); + assert(res.msgs[1].dnsHostName == "x"); assert(res.msgs[1].lastLogon == "x"); /* Search by kept attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(description=y)", NULL, ldb. SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=Z")); - assert(res.msgs[0].objectCategory == "z"); + assert(res.msgs[0].dnsHostName == "z"); assert(res.msgs[0].lastLogon == "z"); assert(res.msgs[1].dn == s4.dn("cn=C")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "z"); /* Search by renamed attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(badPwdCount=x)", NULL, ldb. SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); /* Search by converted attribute */ - attrs = new Array("objectCategory", "lastLogon", "objectSid"); + attrs = new Array("dnsHostName", "lastLogon", "objectSid"); /* TODO: Using the SID directly in the parse tree leads to conversion errors, letting the search fail with no results. @@ -431,23 +431,23 @@ description: y assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=X")); - assert(res.msgs[0].objectCategory == "x"); + assert(res.msgs[0].dnsHostName == "x"); assert(res.msgs[0].lastLogon == "x"); assert(res.msgs[0].objectSid == "S-1-5-21-4231626423-2410014848-2360679739-552"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[1].objectSid == "S-1-5-21-4231626423-2410014848-2360679739-552"); /* Search by generated attribute */ /* In most cases, this even works when the mapping is missing * a `convert_operator' by enumerating the remote db. */ - attrs = new Array("objectCategory", "lastLogon", "primaryGroupID"); + attrs = new Array("dnsHostName", "lastLogon", "primaryGroupID"); res = ldb.search("(primaryGroupID=512)", NULL, ldb. SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 1); assert(res.msgs[0].dn == s4.dn("cn=A")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "x"); assert(res.msgs[0].primaryGroupID == "512"); @@ -468,23 +468,23 @@ description: y */ /* Search by remote name of renamed attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(sambaBadPasswordCount=*)", "", ldb. SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 0); /* Search by objectClass */ - attrs = new Array("objectCategory", "lastLogon", "objectClass"); + attrs = new Array("dnsHostName", "lastLogon", "objectClass"); res = ldb.search("(objectClass=user)", NULL, ldb. SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=X")); - assert(res.msgs[0].objectCategory == "x"); + assert(res.msgs[0].dnsHostName == "x"); assert(res.msgs[0].lastLogon == "x"); assert(res.msgs[0].objectClass != undefined); assert(res.msgs[0].objectClass[3] == "user"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[1].objectClass != undefined); assert(res.msgs[1].objectClass[0] == "user"); @@ -494,19 +494,19 @@ description: y assert(res.error == 0); assert(res.msgs.length == 3); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[0].objectClass != undefined); for (i=0;i<res.msgs[0].objectClass.length;i++) { assert(res.msgs[0].objectClass[i] != "user"); } assert(res.msgs[1].dn == s4.dn("cn=X")); - assert(res.msgs[1].objectCategory == "x"); + assert(res.msgs[1].dnsHostName == "x"); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[1].objectClass != undefined); assert(res.msgs[1].objectClass[3] == "user"); assert(res.msgs[2].dn == s4.dn("cn=A")); - assert(res.msgs[2].objectCategory == undefined); + assert(res.msgs[2].dnsHostName == undefined); assert(res.msgs[2].lastLogon == "x"); assert(res.msgs[2].objectClass != undefined); assert(res.msgs[2].objectClass[0] == "user"); @@ -514,43 +514,43 @@ description: y println("Testing search by parse tree"); /* Search by conjunction of local attributes */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(&(codePage=x)(revision=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=Y")); - assert(res.msgs[0].objectCategory == "y"); + assert(res.msgs[0].dnsHostName == "y"); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=X")); - assert(res.msgs[1].objectCategory == "x"); + assert(res.msgs[1].dnsHostName == "x"); assert(res.msgs[1].lastLogon == "x"); /* Search by conjunction of remote attributes */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(&(lastLogon=x)(description=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=X")); - assert(res.msgs[0].objectCategory == "x"); + assert(res.msgs[0].dnsHostName == "x"); assert(res.msgs[0].lastLogon == "x"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); /* Search by conjunction of local and remote attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(&(codePage=x)(description=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=Y")); - assert(res.msgs[0].objectCategory == "y"); + assert(res.msgs[0].dnsHostName == "y"); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=X")); - assert(res.msgs[1].objectCategory == "x"); + assert(res.msgs[1].dnsHostName == "x"); assert(res.msgs[1].lastLogon == "x"); /* Search by conjunction of local and remote attribute w/o match */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(&(codePage=x)(nextRid=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 0); @@ -559,203 +559,203 @@ description: y assert(res.msgs.length == 0); /* Search by disjunction of local attributes */ - attrs = new Array("objectCategory", "lastLogon"); - res = ldb.search("(|(revision=x)(objectCategory=x))", NULL, ldb.SCOPE_DEFAULT, attrs); + attrs = new Array("dnsHostName", "lastLogon"); + res = ldb.search("(|(revision=x)(dnsHostName=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=Y")); - assert(res.msgs[0].objectCategory == "y"); + assert(res.msgs[0].dnsHostName == "y"); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=X")); - assert(res.msgs[1].objectCategory == "x"); + assert(res.msgs[1].dnsHostName == "x"); assert(res.msgs[1].lastLogon == "x"); /* Search by disjunction of remote attributes */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(|(badPwdCount=x)(lastLogon=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 3); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=X")); - assert(res.msgs[1].objectCategory == "x"); + assert(res.msgs[1].dnsHostName == "x"); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[2].dn == s4.dn("cn=A")); - assert(res.msgs[2].objectCategory == undefined); + assert(res.msgs[2].dnsHostName == undefined); assert(res.msgs[2].lastLogon == "x"); /* Search by disjunction of local and remote attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(|(revision=x)(lastLogon=y))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 3); assert(res.msgs[0].dn == s4.dn("cn=Y")); - assert(res.msgs[0].objectCategory == "y"); + assert(res.msgs[0].dnsHostName == "y"); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=B")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "y"); assert(res.msgs[2].dn == s4.dn("cn=X")); - assert(res.msgs[2].objectCategory == "x"); + assert(res.msgs[2].dnsHostName == "x"); assert(res.msgs[2].lastLogon == "x"); /* Search by disjunction of local and remote attribute w/o match */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(|(codePage=y)(nextRid=z))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 0); /* Search by negated local attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(!(revision=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 4); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[2].dn == s4.dn("cn=Z")); - assert(res.msgs[2].objectCategory == "z"); + assert(res.msgs[2].dnsHostName == "z"); assert(res.msgs[2].lastLogon == "z"); assert(res.msgs[3].dn == s4.dn("cn=C")); - assert(res.msgs[3].objectCategory == undefined); + assert(res.msgs[3].dnsHostName == undefined); assert(res.msgs[3].lastLogon == "z"); /* Search by negated remote attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(!(description=x))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 2); assert(res.msgs[0].dn == s4.dn("cn=Z")); - assert(res.msgs[0].objectCategory == "z"); + assert(res.msgs[0].dnsHostName == "z"); assert(res.msgs[0].lastLogon == "z"); assert(res.msgs[1].dn == s4.dn("cn=C")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "z"); /* Search by negated conjunction of local attributes */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(!(&(codePage=x)(revision=x)))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 4); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[2].dn == s4.dn("cn=Z")); - assert(res.msgs[2].objectCategory == "z"); + assert(res.msgs[2].dnsHostName == "z"); assert(res.msgs[2].lastLogon == "z"); assert(res.msgs[3].dn == s4.dn("cn=C")); - assert(res.msgs[3].objectCategory == undefined); + assert(res.msgs[3].dnsHostName == undefined); assert(res.msgs[3].lastLogon == "z"); /* Search by negated conjunction of remote attributes */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(!(&(lastLogon=x)(description=x)))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 4); assert(res.msgs[0].dn == s4.dn("cn=Y")); - assert(res.msgs[0].objectCategory == "y"); + assert(res.msgs[0].dnsHostName == "y"); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=B")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "y"); assert(res.msgs[2].dn == s4.dn("cn=Z")); - assert(res.msgs[2].objectCategory == "z"); + assert(res.msgs[2].dnsHostName == "z"); assert(res.msgs[2].lastLogon == "z"); assert(res.msgs[3].dn == s4.dn("cn=C")); - assert(res.msgs[3].objectCategory == undefined); + assert(res.msgs[3].dnsHostName == undefined); assert(res.msgs[3].lastLogon == "z"); /* Search by negated conjunction of local and remote attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(!(&(codePage=x)(description=x)))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 4); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[2].dn == s4.dn("cn=Z")); - assert(res.msgs[2].objectCategory == "z"); + assert(res.msgs[2].dnsHostName == "z"); assert(res.msgs[2].lastLogon == "z"); assert(res.msgs[3].dn == s4.dn("cn=C")); - assert(res.msgs[3].objectCategory == undefined); + assert(res.msgs[3].dnsHostName == undefined); assert(res.msgs[3].lastLogon == "z"); /* Search by negated disjunction of local attributes */ - attrs = new Array("objectCategory", "lastLogon"); - res = ldb.search("(!(|(revision=x)(objectCategory=x)))", NULL, ldb.SCOPE_DEFAULT, attrs); + attrs = new Array("dnsHostName", "lastLogon"); + res = ldb.search("(!(|(revision=x)(dnsHostName=x)))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=A")); - assert(res.msgs[1].objectCategory == undefined); + assert(res.msgs[1].dnsHostName == undefined); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[2].dn == s4.dn("cn=Z")); - assert(res.msgs[2].objectCategory == "z"); + assert(res.msgs[2].dnsHostName == "z"); assert(res.msgs[2].lastLogon == "z"); assert(res.msgs[3].dn == s4.dn("cn=C")); - assert(res.msgs[3].objectCategory == undefined); + assert(res.msgs[3].dnsHostName == undefined); assert(res.msgs[3].lastLogon == "z"); /* Search by negated disjunction of remote attributes */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(!(|(badPwdCount=x)(lastLogon=x)))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 3); assert(res.msgs[0].dn == s4.dn("cn=Y")); - assert(res.msgs[0].objectCategory == "y"); + assert(res.msgs[0].dnsHostName == "y"); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=Z")); - assert(res.msgs[1].objectCategory == "z"); + assert(res.msgs[1].dnsHostName == "z"); assert(res.msgs[1].lastLogon == "z"); assert(res.msgs[2].dn == s4.dn("cn=C")); - assert(res.msgs[2].objectCategory == undefined); + assert(res.msgs[2].dnsHostName == undefined); assert(res.msgs[2].lastLogon == "z"); /* Search by negated disjunction of local and remote attribute */ - attrs = new Array("objectCategory", "lastLogon"); + attrs = new Array("dnsHostName", "lastLogon"); res = ldb.search("(!(|(revision=x)(lastLogon=y)))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 3); assert(res.msgs[0].dn == s4.dn("cn=A")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "x"); assert(res.msgs[1].dn == s4.dn("cn=Z")); - assert(res.msgs[1].objectCategory == "z"); + assert(res.msgs[1].dnsHostName == "z"); assert(res.msgs[1].lastLogon == "z"); assert(res.msgs[2].dn == s4.dn("cn=C")); - assert(res.msgs[2].objectCategory == undefined); + assert(res.msgs[2].dnsHostName == undefined); assert(res.msgs[2].lastLogon == "z"); /* Search by complex parse tree */ - attrs = new Array("objectCategory", "lastLogon"); - res = ldb.search("(|(&(revision=x)(objectCategory=x))(!(&(description=x)(nextRid=y)))(badPwdCount=y))", NULL, ldb.SCOPE_DEFAULT, attrs); + attrs = new Array("dnsHostName", "lastLogon"); + res = ldb.search("(|(&(revision=x)(dnsHostName=x))(!(&(description=x)(nextRid=y)))(badPwdCount=y))", NULL, ldb.SCOPE_DEFAULT, attrs); assert(res.error == 0); assert(res.msgs.length == 5); assert(res.msgs[0].dn == s4.dn("cn=B")); - assert(res.msgs[0].objectCategory == undefined); + assert(res.msgs[0].dnsHostName == undefined); assert(res.msgs[0].lastLogon == "y"); assert(res.msgs[1].dn == s4.dn("cn=X")); - assert(res.msgs[1].objectCategory == "x"); + assert(res.msgs[1].dnsHostName == "x"); assert(res.msgs[1].lastLogon == "x"); assert(res.msgs[2].dn == s4.dn("cn=A")); - assert(res.msgs[2].objectCategory == undefined); + assert(res.msgs[2].dnsHostName == undefined); assert(res.msgs[2].lastLogon == "x"); assert(res.msgs[3].dn == s4.dn("cn=Z")); - assert(res.msgs[3].objectCategory == "z"); + assert(res.msgs[3].dnsHostName == "z"); assert(res.msgs[3].lastLogon == "z"); assert(res.msgs[4].dn == s4.dn("cn=C")); - assert(res.msgs[4].objectCategory == undefined); + assert(res.msgs[4].dnsHostName == undefined); assert(res.msgs[4].lastLogon == "z"); /* Clean up */ |