The branch, master has been updated
       via  404f7ac... s4-cldap: we should set the w2k8 flags even if not the 
PDC emulator
       via  e7262b5... s4-drs: validate RODC credentials via the user_sid
       via  bb1ba4f... s4-drs: added new SECURITY_RO_DOMAIN_CONTROLLER level
       via  ec0bb2f... s4-net: fixed two compiler warnings
       via  ec3d1de... s4-torture: fixed a initialiser
       via  47712ab... s4-libnet: fixed two compiler warnings
       via  1f92df9... s4-drs: removed dsdb_validate_client_flags()
       via  90230ce... s4-drs: only allow replication with the right 
invocationId
       via  0d3823b... s4-dsdb: removed an unused variable
       via  a06b537... s4-dsdb: added dsdb_validate_invocation_id()
       via  1ecefd7... s4-dsdb: added dsdb_get_extended_dn_sid()
       via  6669152... build: we don't need this makefile magic any more
       via  70cc9fd... s4-dsdb: moved rodc schema validation to samldb.c
       via  73513fb... s4-drs: Use new samdb_rodc() function in s4 code
       via  d940a44... s4-drs: Do not send RODC filtered attributes to RODCs on 
GetNCChanges reply
       via  59aa0a0... s40-drs: Do not send GetNCChanges messages to RODCs
       via  fbdbd67... s4-drs: dsdb_validate_client_flags() function
       via  57bcdf0... s4-drs: samdb_is_rodc() function and new samdb_rodc() 
function
       via  c023fc2... s4-drs: Do not allow system-critical attributes to be 
RODC filtered
      from  e11f92b... s4:provision Make OpenLDAP backend more robust

http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 404f7ac0292c91ef3101e9bc32b8aea3b2aec4be
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 17:53:25 2010 +1000

    s4-cldap: we should set the w2k8 flags even if not the PDC emulator
    
    these two tests are independent
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit e7262b51d1a8905ba3b874f5d48eab4292ebca4d
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 16:56:40 2010 +1000

    s4-drs: validate RODC credentials via the user_sid
    
    This checks whether a replication client is a RODC by inclusion of the
    the DOMAIN_RID_ENTERPRISE_READONLY_DCS sid in the users token
    
    Pair-Programmed-With: Rusty Russell <[email protected]>
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit bb1ba4ff76eb90d0d62dd3edbe288f45cf7a0a1e
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 16:48:01 2010 +1000

    s4-drs: added new SECURITY_RO_DOMAIN_CONTROLLER level
    
    This is used for allowing operations by RODCs, and denying them
    operations that should only be allowed for a full DC
    
    This required a new domain_sid argument to
    security_session_user_level()
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>
    Pair-Programmed-With: Rusty Russell <[email protected]>

commit ec0bb2f46b855d44cccb71a5511c2acb7d8eae09
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 16:44:53 2010 +1000

    s4-net: fixed two compiler warnings

commit ec3d1de61dd81f042b9ac65ff4f94db5b4ae643c
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 16:44:30 2010 +1000

    s4-torture: fixed a initialiser
    
    we were not initialising the whole array
    
    Pair-Programmed-With: Rusty Russell <[email protected]>
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit 47712ab3dd63d3da408d37f6efea08cc34407b1d
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 16:43:21 2010 +1000

    s4-libnet: fixed two compiler warnings

commit 1f92df90fdb0ade233af52df1fbc9e76bddb4fd0
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 16:41:32 2010 +1000

    s4-drs: removed dsdb_validate_client_flags()
    
    This test is in the wrong place. We end up validating our own flags.
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit 90230ce27eaa81e02273f0120b7cdc99879514ac
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 14:56:19 2010 +1000

    s4-drs: only allow replication with the right invocationId
    
    Non-administrator replication checks the invocationId matches
    the sid of the user token being used
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit 0d3823b15248ed6269bb0a513d862ef694bfde64
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 14:55:54 2010 +1000

    s4-dsdb: removed an unused variable

commit a06b537cc30cb21e77f58b5e9ea2a8f89c4683e0
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 14:54:52 2010 +1000

    s4-dsdb: added dsdb_validate_invocation_id()
    
    this validates that a invocationID matches an account sid
    
    This will be used to ensure that we don't allow DRS replication
    from someone a non-DC or administrator
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit 1ecefd74a2b7a6cec0c6ef765669eab0635e5568
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 14:53:53 2010 +1000

    s4-dsdb: added dsdb_get_extended_dn_sid()
    
    This will be used by the RODC code
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit 6669152a4a5919ecad633b594708d6b95577b4dc
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 14:52:19 2010 +1000

    build: we don't need this makefile magic any more
    
    The waf build now checks for all A=B variables passed via make
    and sets the same waf internal variable. This means all waf options
    are available via make.
    
    Removing this from the Makefile makes us less reliant on a modern
    version of make.
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit 70cc9fd5c62f385d6e94380597f02da80cea3649
Author: Andrew Tridgell <[email protected]>
Date:   Thu Apr 22 13:32:55 2010 +1000

    s4-dsdb: moved rodc schema validation to samldb.c
    
    This means we are only doing the checks for schema changes
    
    Pair-Programmed-With: Andrew Bartlett <[email protected]>

commit 73513fb7e7145e9abe1a155acd47c27bc09c5092
Author: Fernando J V da Silva <[email protected]>
Date:   Thu Apr 15 18:54:13 2010 -0300

    s4-drs: Use new samdb_rodc() function in s4 code
    
    This patch fits the calling to the new samdb_rodc() function and
    fix a little bug in this function.
    
    Signed-off-by: Andrew Tridgell <[email protected]>

commit d940a44496f184073fe036fc1977796c901ec96d
Author: Fernando J V da Silva <[email protected]>
Date:   Thu Apr 15 17:42:08 2010 -0300

    s4-drs: Do not send RODC filtered attributes to RODCs on GetNCChanges reply
    
    During building an object to send it on a GetNCChanges reply, it checks
    the attributes and if any of them is a RODC filtered and the recipient
    is a RODC, then such attribute is not sent.
    
    Signed-off-by: Andrew Tridgell <[email protected]>

commit 59aa0a07d24bfb9ff9795ffe90801577043058a5
Author: Fernando J V da Silva <[email protected]>
Date:   Thu Apr 15 17:39:54 2010 -0300

    s40-drs: Do not send GetNCChanges messages to RODCs
    
    Signed-off-by: Andrew Tridgell <[email protected]>

commit fbdbd67c7640757f80a2ffd70a17c6ab50491844
Author: Fernando J V da Silva <[email protected]>
Date:   Thu Apr 15 17:38:47 2010 -0300

    s4-drs: dsdb_validate_client_flags() function
    
    This function is intended to check if some client is not lying about
    his flags. At this moment, it only checks for RODC flags.
    
    Signed-off-by: Andrew Tridgell <[email protected]>

commit 57bcdf008fa44d4c550819cbceada968b11be63c
Author: Fernando J V da Silva <[email protected]>
Date:   Thu Apr 15 17:37:40 2010 -0300

    s4-drs: samdb_is_rodc() function and new samdb_rodc() function
    
    This patch creates the samdb_is_rodc() function, which looks for
    the NTDSDSA object for a DC that has a specific invocationId
    and if msDS-isRODC is present on such object and it is TRUE, then
    consider the DC as a RODC.
    The new samdb_rodc() function uses the samdb_is_rodc() function
    for the local server.
    
    Signed-off-by: Andrew Tridgell <[email protected]>

commit c023fc217ed370e5c890c1984da533e0133060d9
Author: Fernando J V da Silva <[email protected]>
Date:   Thu Mar 25 16:58:58 2010 -0300

    s4-drs: Do not allow system-critical attributes to be RODC filtered
    
    Signed-off-by: Andrew Tridgell <[email protected]>

-----------------------------------------------------------------------

Summary of changes:
 buildtools/scripts/Makefile.waf                 |    4 +-
 libds/common/flags.h                            |    3 +
 source4/cldap_server/netlogon.c                 |    7 +-
 source4/dsdb/common/util.c                      |  189 +++++++++++++++++++----
 source4/dsdb/kcc/kcc_topology.c                 |   18 ++-
 source4/dsdb/repl/drepl_out_helpers.c           |    9 +-
 source4/dsdb/repl/drepl_service.c               |    5 +-
 source4/dsdb/samdb/ldb_modules/descriptor.c     |    1 -
 source4/dsdb/samdb/ldb_modules/kludge_acl.c     |    2 +-
 source4/dsdb/samdb/ldb_modules/repl_meta_data.c |    2 +-
 source4/dsdb/samdb/ldb_modules/rootdse.c        |    2 +-
 source4/dsdb/samdb/ldb_modules/samldb.c         |   37 +++++
 source4/dsdb/samdb/ldb_modules/util.c           |    2 +-
 source4/dsdb/schema/schema_syntax.c             |   17 +--
 source4/libcli/security/security.h              |   11 +-
 source4/libcli/security/security_token.c        |   13 ++-
 source4/libnet/libnet_become_dc.c               |    5 +-
 source4/rpc_server/drsuapi/addentry.c           |    4 +-
 source4/rpc_server/drsuapi/dcesrv_drsuapi.c     |   10 +-
 source4/rpc_server/drsuapi/dcesrv_drsuapi.h     |    3 +-
 source4/rpc_server/drsuapi/drsutil.c            |    8 +-
 source4/rpc_server/drsuapi/getncchanges.c       |   42 +++++-
 source4/rpc_server/drsuapi/updaterefs.c         |   23 +++-
 source4/rpc_server/lsa/dcesrv_lsa.c             |   18 ++-
 source4/rpc_server/winreg/rpc_winreg.c          |   16 +-
 source4/torture/smb2/acls.c                     |    2 +-
 source4/utils/net/drs/net_drs_replicate.c       |   10 +-
 27 files changed, 352 insertions(+), 111 deletions(-)


Changeset truncated at 500 lines:

diff --git a/buildtools/scripts/Makefile.waf b/buildtools/scripts/Makefile.waf
index ac5c013..f9c3fbb 100644
--- a/buildtools/scripts/Makefile.waf
+++ b/buildtools/scripts/Makefile.waf
@@ -12,10 +12,10 @@ uninstall:
        $(WAF) uninstall
 
 test:
-       $(WAF) test $(if $(TESTS),--tests="$(TESTS)")
+       $(WAF) test
 
 quicktest:
-       $(WAF) test --quick $(if $(TESTS),--tests="$(TESTS)")
+       $(WAF) test --quick
 
 dist:
        $(WAF) dist
diff --git a/libds/common/flags.h b/libds/common/flags.h
index aa88487..de3e71c 100644
--- a/libds/common/flags.h
+++ b/libds/common/flags.h
@@ -155,6 +155,9 @@
 #define SYSTEM_FLAG_CONFIG_ALLOW_RENAME                0x40000000
 #define SYSTEM_FLAG_DISALLOW_DELETE            0x80000000
 
+/* schemaFlags_Ex */
+#define SCHEMA_FLAG_ATTR_IS_CRITICAL   0x0000001
+
 /* "searchFlags" */
 #define SEARCH_FLAG_ATTINDEX           0x0000001
 #define SEARCH_FLAG_PDNTATTINDEX       0x0000002
diff --git a/source4/cldap_server/netlogon.c b/source4/cldap_server/netlogon.c
index 139c1ca..8f445d0 100644
--- a/source4/cldap_server/netlogon.c
+++ b/source4/cldap_server/netlogon.c
@@ -226,9 +226,10 @@ NTSTATUS fill_netlogon_samlogon_response(struct 
ldb_context *sam_ctx,
 
        if (samdb_is_pdc(sam_ctx)) {
                server_type |= DS_SERVER_PDC;
-               if (dsdb_functional_level(sam_ctx) >= DS_DOMAIN_FUNCTION_2008) {
-                       server_type |= DS_SERVER_FULL_SECRET_DOMAIN_6;
-               }
+       }
+
+       if (dsdb_functional_level(sam_ctx) >= DS_DOMAIN_FUNCTION_2008) {
+               server_type |= DS_SERVER_FULL_SECRET_DOMAIN_6;
        }
 
        if (samdb_is_gc(sam_ctx)) {
diff --git a/source4/dsdb/common/util.c b/source4/dsdb/common/util.c
index 30cb5c5..3a04797 100644
--- a/source4/dsdb/common/util.c
+++ b/source4/dsdb/common/util.c
@@ -2413,7 +2413,6 @@ int dsdb_find_sid_by_dn(struct ldb_context *ldb,
 }
 
 
-
 /*
   load a repsFromTo blob list for a given partition GUID
   attr must be "repsFrom" or "repsTo"
@@ -2618,50 +2617,59 @@ int drsuapi_DsReplicaCursor_compare(const struct 
drsuapi_DsReplicaCursor *c1,
        return GUID_compare(&c1->source_dsa_invocation_id, 
&c2->source_dsa_invocation_id);
 }
 
+
 /*
-  see if we are a RODC
+  see if a computer identified by its invocationId is a RODC
 */
-bool samdb_rodc(struct ldb_context *sam_ctx)
-{
-       TALLOC_CTX *tmp_ctx;
-       const char *obj_category;
-       struct ldb_dn *obj_category_dn;
-       const struct ldb_val *obj_category_dn_rdn_val;
+int samdb_is_rodc(struct ldb_context *sam_ctx, const struct GUID 
*invocationId, bool *is_rodc)
+{
+       /* 1) find the DN for this servers NTDSDSA object
+          2) search for the msDS-isRODC attribute
+          3) if not present then not a RODC
+          4) if present and TRUE then is a RODC
+       */
+       struct ldb_dn *config_dn;
+       const char *attrs[] = { "msDS-isRODC", NULL };
+       int ret;
+       struct ldb_result *res;
+       TALLOC_CTX *tmp_ctx = talloc_new(sam_ctx);
 
-       tmp_ctx = talloc_new(sam_ctx);
-       if (tmp_ctx == NULL) {
-               DEBUG(1,("samdb_rodc: Failed to talloc new context.\n"));
-               goto failed;
+       config_dn = ldb_get_config_basedn(sam_ctx);
+       if (!config_dn) {
+               talloc_free(tmp_ctx);
+               return LDB_ERR_OPERATIONS_ERROR;
        }
 
-       obj_category = samdb_ntds_object_category(tmp_ctx, sam_ctx);
-       if (!obj_category) {
-               DEBUG(1,("samdb_rodc: Failed to get object category.\n"));
-               goto failed;
+       ret = dsdb_search(sam_ctx, tmp_ctx, &res, config_dn, LDB_SCOPE_SUBTREE, 
attrs,
+                         DSDB_SEARCH_ONE_ONLY, "invocationID=%s", 
GUID_string(tmp_ctx, invocationId));
+       if (ret != LDB_SUCCESS) {
+               talloc_free(tmp_ctx);
+               return ret;
        }
 
-       obj_category_dn = ldb_dn_new(tmp_ctx, sam_ctx, obj_category);
-       if (!obj_category_dn) {
-               DEBUG(1,("samdb_rodc: Failed to create object category dn.\n"));
-               goto failed;
-       }
+       ret = ldb_msg_find_attr_as_bool(res->msgs[0], "msDS-isRODC", 0);
+       *is_rodc = (ret == 1);
 
-       obj_category_dn_rdn_val = ldb_dn_get_rdn_val(obj_category_dn);
-       if (!obj_category_dn_rdn_val) {
-               DEBUG(1, ("samdb_rodc: Failed to get object category dn rdn 
value.\n"));
-               goto failed;
-       }
+       talloc_free(tmp_ctx);
+       return LDB_SUCCESS;
+}
 
-       if (strequal((const char*)obj_category_dn_rdn_val->data, 
"NTDS-DSA-RO")) {
-               talloc_free(tmp_ctx);
-               return true;
-       }
 
-failed:
-       talloc_free(tmp_ctx);
-       return false;
+/*
+  see if we are a RODC
+*/
+int samdb_rodc(struct ldb_context *sam_ctx, bool *am_rodc)
+{
+       const struct GUID *invocationId;
+       invocationId = samdb_ntds_invocation_id(sam_ctx);
+       if (!invocationId) {
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+       return samdb_is_rodc(sam_ctx, invocationId, am_rodc);
 }
 
+
+
 /*
   return NTDS options flags. See MS-ADTS 7.1.1.2.2.1.2.1.1 
 
@@ -2850,6 +2858,35 @@ NTSTATUS dsdb_get_extended_dn_uint32(struct ldb_dn *dn, 
uint32_t *val, const cha
 }
 
 /*
+  return a dom_sid from a extended DN structure
+ */
+NTSTATUS dsdb_get_extended_dn_sid(struct ldb_dn *dn, struct dom_sid *sid, 
const char *component_name)
+{
+       const struct ldb_val *sid_blob;
+       struct TALLOC_CTX *tmp_ctx;
+       enum ndr_err_code ndr_err;
+
+       sid_blob = ldb_dn_get_extended_component(dn, "SID");
+       if (!sid_blob) {
+               return NT_STATUS_OBJECT_NAME_NOT_FOUND;
+       }
+
+       tmp_ctx = talloc_new(NULL);
+
+       ndr_err = ndr_pull_struct_blob_all(sid_blob, tmp_ctx, NULL, sid,
+                                          
(ndr_pull_flags_fn_t)ndr_pull_dom_sid);
+       if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
+               NTSTATUS status = ndr_map_error2ntstatus(ndr_err);
+               talloc_free(tmp_ctx);
+               return status;
+       }
+
+       talloc_free(tmp_ctx);
+       return NT_STATUS_OK;
+}
+
+
+/*
   return RMD_FLAGS directly from a ldb_dn
   returns 0 if not found
  */
@@ -3531,3 +3568,89 @@ const char *samdb_forest_name(struct ldb_context *ldb, 
TALLOC_CTX *mem_ctx)
 
        return forest_name;
 }
+
+/*
+   validate that an invocationID belongs to the specified user sid.
+   The user SID must be a domain controller account (either RODC or
+   RWDC)
+ */
+int dsdb_validate_invocation_id(struct ldb_context *ldb,
+                               const struct GUID *invocation_id,
+                               const struct dom_sid *sid)
+{
+       /* strategy:
+           - find DN of record with the invocationID in the
+             configuration partition
+            - remote "NTDS Settings" component from DN
+           - do a base search on that DN for serverReference with
+             extended-dn enabled
+            - extract objectSID from resulting serverReference
+              attribute
+           - check this sid matches the sid argument
+       */
+       struct ldb_dn *config_dn;
+       TALLOC_CTX *tmp_ctx = talloc_new(ldb);
+       struct ldb_message *msg;
+       const char *attrs1[] = { NULL };
+       const char *attrs2[] = { "serverReference", NULL };
+       int ret;
+       struct ldb_dn *dn, *account_dn;
+       struct dom_sid sid2;
+       NTSTATUS status;
+
+       config_dn = ldb_get_config_basedn(ldb);
+
+       ret = dsdb_search_one(ldb, tmp_ctx, &msg, config_dn, LDB_SCOPE_SUBTREE,
+                             attrs1, 0, 
"(&(invocationID=%s)(objectClass=nTDSDSA))", GUID_string(tmp_ctx, 
invocation_id));
+       if (ret != LDB_SUCCESS) {
+               DEBUG(1,(__location__ ": Failed to find invocationID %s for sid 
%s\n",
+                        GUID_string(tmp_ctx, invocation_id), 
dom_sid_string(tmp_ctx, sid)));
+               talloc_free(tmp_ctx);
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+       dn = msg->dn;
+
+       if (!ldb_dn_remove_child_components(dn, 1)) {
+               talloc_free(tmp_ctx);
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+
+       ret = dsdb_search_one(ldb, tmp_ctx, &msg, dn, LDB_SCOPE_BASE,
+                             attrs2, DSDB_SEARCH_SHOW_EXTENDED_DN,
+                             "(objectClass=server)");
+       if (ret != LDB_SUCCESS) {
+               DEBUG(1,(__location__ ": Failed to find server record for 
invocationID %s, sid %s\n",
+                        GUID_string(tmp_ctx, invocation_id), 
dom_sid_string(tmp_ctx, sid)));
+               talloc_free(tmp_ctx);
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+
+       account_dn = ldb_msg_find_attr_as_dn(ldb, tmp_ctx, msg, 
"serverReference");
+       if (account_dn == NULL) {
+               DEBUG(1,(__location__ ": Failed to find account_dn for 
invocationID %s, sid %s\n",
+                        GUID_string(tmp_ctx, invocation_id), 
dom_sid_string(tmp_ctx, sid)));
+               talloc_free(tmp_ctx);
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+
+       status = dsdb_get_extended_dn_sid(account_dn, &sid2, "SID");
+       if (!NT_STATUS_IS_OK(status)) {
+               DEBUG(1,(__location__ ": Failed to find SID for invocationID 
%s, sid %s\n",
+                        GUID_string(tmp_ctx, invocation_id), 
dom_sid_string(tmp_ctx, sid)));
+               talloc_free(tmp_ctx);
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+
+       if (!dom_sid_equal(sid, &sid2)) {
+               /* someone is trying to spoof another account */
+               DEBUG(0,(__location__ ": Bad invocationID invocationID %s for 
sid %s - expected sid %s\n",
+                        GUID_string(tmp_ctx, invocation_id),
+                        dom_sid_string(tmp_ctx, sid),
+                        dom_sid_string(tmp_ctx, &sid2)));
+               talloc_free(tmp_ctx);
+               return LDB_ERR_OPERATIONS_ERROR;
+       }
+
+       talloc_free(tmp_ctx);
+       return LDB_SUCCESS;
+}
diff --git a/source4/dsdb/kcc/kcc_topology.c b/source4/dsdb/kcc/kcc_topology.c
index 72eb5e1..215cc4d 100644
--- a/source4/dsdb/kcc/kcc_topology.c
+++ b/source4/dsdb/kcc/kcc_topology.c
@@ -1155,7 +1155,13 @@ static NTSTATUS kcctpl_get_all_bridgehead_dcs(struct 
ldb_context *ldb,
 
        el = ldb_msg_find_element(transport, "bridgeheadServerListBL");
 
-       rodc = samdb_rodc(ldb);
+       ret = samdb_rodc(ldb, &rodc);
+       if (ret != LDB_SUCCESS) {
+               DEBUG(1, (__location__ ": unable to tell if we are an RODC: 
%s\n",
+                         ldb_strerror(ret)));
+               talloc_free(tmp_ctx);
+               return NT_STATUS_INTERNAL_DB_CORRUPTION;
+       }
 
        transport_name = samdb_result_string(transport, "name", NULL);
        if (!transport_name) {
@@ -3155,6 +3161,7 @@ static NTSTATUS kcctpl_create_connections(struct 
ldb_context *ldb,
        struct ldb_dn *transports_dn;
        const char * const attrs[] = { "bridgeheadServerListBL", "name",
                                       "transportAddressAttribute", NULL };
+       int ret;
 
        connected = true;
 
@@ -3223,14 +3230,19 @@ static NTSTATUS kcctpl_create_connections(struct 
ldb_context *ldb,
                return NT_STATUS_INTERNAL_DB_CORRUPTION;
        }
 
-       rodc = samdb_rodc(ldb);
+       ret = samdb_rodc(ldb, &rodc);
+       if (ret != LDB_SUCCESS) {
+               DEBUG(1, (__location__ ": Unable to tell if we are an RODC: 
%s\n",
+                         ldb_strerror(ret)));
+               talloc_free(tmp_ctx);
+               return NT_STATUS_INTERNAL_DB_CORRUPTION;
+       }
 
        for (i = 0; i < st_edge_list.count; i++) {
                struct kcctpl_multi_edge *edge;
                struct GUID other_site_id;
                struct kcctpl_vertex *other_site_vertex;
                struct ldb_result *res;
-               int ret;
                struct ldb_message *transport, *r_bridgehead, *l_bridgehead;
                uint8_t schedule[84];
                uint32_t first_available, j, interval;
diff --git a/source4/dsdb/repl/drepl_out_helpers.c 
b/source4/dsdb/repl/drepl_out_helpers.c
index a12481b..60dccff 100644
--- a/source4/dsdb/repl/drepl_out_helpers.c
+++ b/source4/dsdb/repl/drepl_out_helpers.c
@@ -272,6 +272,10 @@ static void 
dreplsrv_op_pull_source_get_changes_trigger(struct tevent_req *req)
        struct drsuapi_DsReplicaCursorCtrEx *uptodateness_vector;
        struct tevent_req *subreq;
 
+       if ((rf1->replica_flags & DRSUAPI_DRS_WRIT_REP) == 0) {
+               return;
+       }
+
        r = talloc(state, struct drsuapi_DsGetNCChanges);
        if (tevent_req_nomem(r, req)) {
                return;
@@ -542,6 +546,8 @@ static void dreplsrv_update_refs_trigger(struct tevent_req 
*req)
        char *ntds_guid_str;
        char *ntds_dns_name;
        struct tevent_req *subreq;
+       bool am_rodc;
+       int ret;
 
        r = talloc(state, struct drsuapi_DsReplicaUpdateRefs);
        if (tevent_req_nomem(r, req)) {
@@ -566,7 +572,8 @@ static void dreplsrv_update_refs_trigger(struct tevent_req 
*req)
        r->in.req.req1.dest_dsa_dns_name  = ntds_dns_name;
        r->in.req.req1.dest_dsa_guid      = service->ntds_guid;
        r->in.req.req1.options            = DRSUAPI_DRS_ADD_REF | 
DRSUAPI_DRS_DEL_REF;
-       if (!samdb_rodc(service->samdb)) {
+       ret = samdb_rodc(service->samdb, &am_rodc);
+       if (ret == LDB_SUCCESS && !am_rodc) {
                r->in.req.req1.options |= DRSUAPI_DRS_WRIT_REP;
        }
 
diff --git a/source4/dsdb/repl/drepl_service.c 
b/source4/dsdb/repl/drepl_service.c
index 4196f94..59436d6 100644
--- a/source4/dsdb/repl/drepl_service.c
+++ b/source4/dsdb/repl/drepl_service.c
@@ -132,6 +132,8 @@ static void dreplsrv_task_init(struct task_server *task)
        WERROR status;
        struct dreplsrv_service *service;
        uint32_t periodic_startup_interval;
+       bool am_rodc;
+       int ret;
 
        switch (lp_server_role(task->lp_ctx)) {
        case ROLE_STANDALONE:
@@ -194,7 +196,8 @@ static void dreplsrv_task_init(struct task_server *task)
        }
 
        /* if we are a RODC then we do not send DSReplicaSync*/
-       if (!samdb_rodc(service->samdb)) {
+       ret = samdb_rodc(service->samdb, &am_rodc);
+       if (ret == LDB_SUCCESS && !am_rodc) {
                service->notify.interval = lp_parm_int(task->lp_ctx, NULL, 
"dreplsrv",
                                                           "notify_interval", 
5); /* in seconds */
                status = dreplsrv_notify_schedule(service, 
service->notify.interval);
diff --git a/source4/dsdb/samdb/ldb_modules/descriptor.c 
b/source4/dsdb/samdb/ldb_modules/descriptor.c
index cdfab3c..70b02e8 100644
--- a/source4/dsdb/samdb/ldb_modules/descriptor.c
+++ b/source4/dsdb/samdb/ldb_modules/descriptor.c
@@ -64,7 +64,6 @@ struct dom_sid *get_default_ag(TALLOC_CTX *mem_ctx,
 {
        TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
        struct ldb_dn *root_base_dn = ldb_get_root_basedn(ldb);
-       struct ldb_dn *default_base_dn = ldb_get_default_basedn(ldb);
        struct ldb_dn *schema_base_dn = ldb_get_schema_basedn(ldb);
        struct ldb_dn *config_base_dn = ldb_get_config_basedn(ldb);
        const struct dom_sid *domain_sid = samdb_domain_sid(ldb);
diff --git a/source4/dsdb/samdb/ldb_modules/kludge_acl.c 
b/source4/dsdb/samdb/ldb_modules/kludge_acl.c
index 72863ad..42f0a30 100644
--- a/source4/dsdb/samdb/ldb_modules/kludge_acl.c
+++ b/source4/dsdb/samdb/ldb_modules/kludge_acl.c
@@ -56,7 +56,7 @@ static enum security_user_level what_is_user(struct 
ldb_module *module)
        struct ldb_context *ldb = ldb_module_get_ctx(module);
        struct auth_session_info *session_info
                = (struct auth_session_info *)ldb_get_opaque(ldb, 
"sessionInfo");
-       return security_session_user_level(session_info);
+       return security_session_user_level(session_info, NULL);
 }
 
 static const char *user_name(TALLOC_CTX *mem_ctx, struct ldb_module *module) 
diff --git a/source4/dsdb/samdb/ldb_modules/repl_meta_data.c 
b/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
index 75aed6a..efb44bf 100644
--- a/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
+++ b/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
@@ -2402,7 +2402,7 @@ static int replmd_delete(struct ldb_module *module, 
struct ldb_request *req)
        if (next_deletion_state == OBJECT_REMOVED) {
                struct auth_session_info *session_info =
                                (struct auth_session_info *)ldb_get_opaque(ldb, 
"sessionInfo");
-               if (security_session_user_level(session_info) != 
SECURITY_SYSTEM) {
+               if (security_session_user_level(session_info, NULL) != 
SECURITY_SYSTEM) {
                        ldb_asprintf_errstring(ldb, "Refusing to delete deleted 
object %s",
                                        ldb_dn_get_linearized(old_msg->dn));
                        return LDB_ERR_UNWILLING_TO_PERFORM;
diff --git a/source4/dsdb/samdb/ldb_modules/rootdse.c 
b/source4/dsdb/samdb/ldb_modules/rootdse.c
index f10a125..5fffef7 100644
--- a/source4/dsdb/samdb/ldb_modules/rootdse.c
+++ b/source4/dsdb/samdb/ldb_modules/rootdse.c
@@ -884,7 +884,7 @@ static int rootdse_enableoptionalfeature(struct ldb_module 
*module, struct ldb_r
        int ret;
        const char *guid_string;
 
-       if (security_session_user_level(session_info) != SECURITY_SYSTEM) {
+       if (security_session_user_level(session_info, NULL) != SECURITY_SYSTEM) 
{
                ldb_asprintf_errstring(ldb, "rootdse: Insufficient rights for 
enableoptionalfeature");
                return LDB_ERR_UNWILLING_TO_PERFORM;
        }
diff --git a/source4/dsdb/samdb/ldb_modules/samldb.c 
b/source4/dsdb/samdb/ldb_modules/samldb.c
index c3a95f1..375b624 100644
--- a/source4/dsdb/samdb/ldb_modules/samldb.c
+++ b/source4/dsdb/samdb/ldb_modules/samldb.c
@@ -826,6 +826,26 @@ static int samldb_add_entry(struct samldb_ctx *ac)
        return ldb_next_request(ac->module, req);
 }
 
+/*
+ * return true if msg carries an attributeSchema that is intended to be RODC
+ * filtered but is also a system-critical attribute.
+ */
+static bool check_rodc_critical_attribute(struct ldb_message *msg)
+{
+       uint32_t schemaFlagsEx, searchFlags, rodc_filtered_flags;
+
+       schemaFlagsEx = ldb_msg_find_attr_as_uint(msg, "schemaFlagsEx", 0);
+       searchFlags = ldb_msg_find_attr_as_uint(msg, "searchFlags", 0);
+       rodc_filtered_flags = (SEARCH_FLAG_RODC_ATTRIBUTE | 
SEARCH_FLAG_CONFIDENTIAL);
+
+       if ((schemaFlagsEx & SCHEMA_FLAG_ATTR_IS_CRITICAL) &&
+               ((searchFlags & rodc_filtered_flags) == rodc_filtered_flags)) {
+               return true;
+       } else {
+               return false;
+       }
+}
+
 
 static int samldb_fill_object(struct samldb_ctx *ac, const char *type)
 {
@@ -885,6 +905,15 @@ static int samldb_fill_object(struct samldb_ctx *ac, const 
char *type)
                                                  "rdnAttId", "cn");
                if (ret != LDB_SUCCESS) return ret;
 
+               /* do not allow to mark an attributeSchema as RODC filtered if 
it
+                * is system-critical */
+               if (check_rodc_critical_attribute(ac->msg)) {
+                       ldb_asprintf_errstring(ldb, "Refusing schema add of %s 
- cannot combine critical class with RODC filtering",
+                                              
ldb_dn_get_linearized(ac->msg->dn));
+                       return LDB_ERR_UNWILLING_TO_PERFORM;
+               }
+
+
                rdn_value = ldb_dn_get_rdn_val(ac->msg->dn);
                if (!ldb_msg_find_element(ac->msg, "lDAPDisplayName")) {
                        /* the RDN has prefix "CN" */
@@ -932,6 +961,14 @@ static int samldb_fill_object(struct samldb_ctx *ac, const 
char *type)
                        }
                }
 
+               /* do not allow to mark an attributeSchema as RODC filtered if 
it
+                * is system-critical */
+               if (check_rodc_critical_attribute(ac->msg)) {
+                       ldb_asprintf_errstring(ldb, "Refusing schema add of %s 
- cannot combine critical attribute with RODC filtering",
+                                              
ldb_dn_get_linearized(ac->msg->dn));
+                       return LDB_ERR_UNWILLING_TO_PERFORM;
+               }
+
                ret = samdb_find_or_add_attribute(ldb, ac->msg,
                                                  "isSingleValued", "FALSE");
                if (ret != LDB_SUCCESS) return ret;
diff --git a/source4/dsdb/samdb/ldb_modules/util.c 
b/source4/dsdb/samdb/ldb_modules/util.c
index fe0ff75..7913ac8 100644


-- 
Samba Shared Repository

Reply via email to