s4:dsdb - proof against empty RDN values where expected
authorMatthias Dieter Wallnöfer <mdw@samba.org>
Wed, 10 Nov 2010 15:05:16 +0000 (16:05 +0100)
committerMatthias Dieter Wallnöfer <mdw@samba.org>
Thu, 11 Nov 2010 09:03:40 +0000 (10:03 +0100)
This should prevent crashes as pointed out on the mailing list.

source4/dsdb/common/util.c
source4/dsdb/samdb/ldb_modules/objectclass.c
source4/dsdb/samdb/ldb_modules/repl_meta_data.c
source4/dsdb/samdb/ldb_modules/samldb.c
source4/lib/ldb/modules/rdn_name.c

index 04d97043b2ed74a0d7c730cb0983f67ba948b3fd..7f6ce64180d19f59e9f31836df5047304b65fee1 100644 (file)
@@ -1595,7 +1595,12 @@ int samdb_find_site_for_computer(struct ldb_context *ldb,
                talloc_free(dn);
                return LDB_ERR_INVALID_DN_SYNTAX;
        }
+
        rdn_val = ldb_dn_get_rdn_val(dn);
+       if (rdn_val == NULL) {
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+
        (*site_name) = talloc_strndup(mem_ctx, (const char *)rdn_val->data, rdn_val->length);
        talloc_free(dn);
        if (!*site_name) {
index 811bc96f025bfe5bb756f846187c840d7ccf5f00..2e95eb5e91a1c8af51d6b28abd672f905ca46132 100644 (file)
@@ -334,8 +334,10 @@ static int fix_dn(struct ldb_context *ldb,
                return ldb_operr(ldb);
        }
 
-
        rdn_val = ldb_dn_get_rdn_val(newdn);
+       if (rdn_val == NULL) {
+               return ldb_operr(ldb);
+       }
 
 #if 0
        /* the rules for rDN length constraints are more complex than
index 7838b65fdfccebce45621c309917b58f18c5de59..b2d5292a14f05347290559c4d2e4dd03681908e1 100644 (file)
@@ -2561,6 +2561,10 @@ static int replmd_delete(struct ldb_module *module, struct ldb_request *req)
 
        rdn_name = ldb_dn_get_rdn_name(old_dn);
        rdn_value = ldb_dn_get_rdn_val(old_dn);
+       if ((rdn_name == NULL) || (rdn_value == NULL)) {
+               talloc_free(tmp_ctx);
+               return ldb_operr(ldb);
+       }
 
        msg = ldb_msg_new(tmp_ctx);
        if (msg == NULL) {
@@ -2753,6 +2757,10 @@ static int replmd_delete(struct ldb_module *module, struct ldb_request *req)
                /* work out what the new rdn value is, for updating the
                   rDN and name fields */
                new_rdn_value = ldb_dn_get_rdn_val(new_dn);
+               if (new_rdn_value == NULL) {
+                       talloc_free(tmp_ctx);
+                       return ldb_operr(ldb);
+               }
 
                sa = dsdb_attribute_by_lDAPDisplayName(schema, rdn_name);
                if (!sa) {
index 04b8dff0e0e1699d0981163e8e22784d2637679a..1ac86148e6e6b2f53dc9cd55403962a0eaf2acbb 100644 (file)
@@ -575,6 +575,9 @@ static int samldb_fill_object(struct samldb_ctx *ac)
                }
 
                rdn_value = ldb_dn_get_rdn_val(ac->msg->dn);
+               if (rdn_value == NULL) {
+                       return ldb_operr(ldb);
+               }
                if (!ldb_msg_find_element(ac->msg, "lDAPDisplayName")) {
                        /* the RDN has prefix "CN" */
                        ret = ldb_msg_add_string(ac->msg, "lDAPDisplayName",
@@ -638,6 +641,9 @@ static int samldb_fill_object(struct samldb_ctx *ac)
        } else if (strcmp(ac->type, "attributeSchema") == 0) {
                const struct ldb_val *rdn_value;
                rdn_value = ldb_dn_get_rdn_val(ac->msg->dn);
+               if (rdn_value == NULL) {
+                       return ldb_operr(ldb);
+               }
                if (!ldb_msg_find_element(ac->msg, "lDAPDisplayName")) {
                        /* the RDN has prefix "CN" */
                        ret = ldb_msg_add_string(ac->msg, "lDAPDisplayName",
@@ -692,6 +698,7 @@ static int samldb_fill_object(struct samldb_ctx *ac)
 static int samldb_fill_foreignSecurityPrincipal_object(struct samldb_ctx *ac)
 {
        struct ldb_context *ldb;
+       const struct ldb_val *rdn_value;
        struct dom_sid *sid;
        int ret;
 
@@ -699,8 +706,12 @@ static int samldb_fill_foreignSecurityPrincipal_object(struct samldb_ctx *ac)
 
        sid = samdb_result_dom_sid(ac->msg, ac->msg, "objectSid");
        if (sid == NULL) {
+               rdn_value = ldb_dn_get_rdn_val(ac->msg->dn);
+               if (rdn_value == NULL) {
+                       return ldb_operr(ldb);
+               }
                sid = dom_sid_parse_talloc(ac->msg,
-                                          (const char *)ldb_dn_get_rdn_val(ac->msg->dn)->data);
+                                          (const char *)rdn_value->data);
                if (sid == NULL) {
                        ldb_set_errstring(ldb,
                                          "samldb: No valid SID found in ForeignSecurityPrincipal CN!");
index 623471a397af277a20b98eb60fc6ad016ce9b12f..38d87b0712e9a17e7162d5e8924e76b154e94a1c 100644 (file)
@@ -87,6 +87,7 @@ static int rdn_name_add(struct ldb_module *module, struct ldb_request *req)
        struct ldb_message_element *attribute;
        const struct ldb_schema_attribute *a;
        const char *rdn_name;
+       const struct ldb_val *rdn_val_p;
        struct ldb_val rdn_val;
        unsigned int i;
        int ret;
@@ -116,7 +117,11 @@ static int rdn_name_add(struct ldb_module *module, struct ldb_request *req)
                return LDB_ERR_OPERATIONS_ERROR;
        }
        
-       rdn_val = ldb_val_dup(msg, ldb_dn_get_rdn_val(msg->dn));
+       rdn_val_p = ldb_dn_get_rdn_val(msg->dn);
+       if (rdn_val_p == NULL) {
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+       rdn_val = ldb_val_dup(msg, rdn_val_p);
        
        /* Perhaps someone above us tried to set this? Then ignore it */
        ldb_msg_remove_attr(msg, "name");
@@ -233,6 +238,7 @@ static int rdn_rename_callback(struct ldb_request *req, struct ldb_reply *ares)
        struct rename_context *ac;
        struct ldb_request *mod_req;
        const char *rdn_name;
+       const struct ldb_val *rdn_val_p;
        struct ldb_val rdn_val;
        struct ldb_message *msg;
        int ret;
@@ -273,8 +279,11 @@ static int rdn_rename_callback(struct ldb_request *req, struct ldb_reply *ares)
        if (rdn_name == NULL) {
                goto error;
        }
-       
-       rdn_val = ldb_val_dup(msg, ldb_dn_get_rdn_val(ac->req->op.rename.newdn));
+       rdn_val_p = ldb_dn_get_rdn_val(msg->dn);
+       if (rdn_val_p == NULL) {
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+       rdn_val = ldb_val_dup(msg, rdn_val_p);
        
        if (ldb_msg_add_empty(msg, rdn_name, LDB_FLAG_MOD_REPLACE, NULL) != 0) {
                goto error;