summaryrefslogtreecommitdiff
path: root/source3/nsswitch/winbindd_ads.c
diff options
context:
space:
mode:
authorGerald Carter <jerry@samba.org>2007-05-06 19:17:30 +0000
committerGerald (Jerry) Carter <jerry@samba.org>2007-10-10 12:21:47 -0500
commit7cb2a4be354c23b4228d67fe2bba68067ea619cf (patch)
tree782cd4a9fe6e8deffca6a44e8b0a64aada7f878e /source3/nsswitch/winbindd_ads.c
parent879b84362715e8796f7ef92124007f5673338b37 (diff)
downloadsamba-7cb2a4be354c23b4228d67fe2bba68067ea619cf.tar.gz
samba-7cb2a4be354c23b4228d67fe2bba68067ea619cf.tar.bz2
samba-7cb2a4be354c23b4228d67fe2bba68067ea619cf.zip
r22704: Implement three step method for enumerating domain trusts.
(a) Query our primary domain for trusts (b) Query all tree roots in our forest (c) Query all forest roots in trusted forests. This will give us a complete trust topology including domains via transitive Krb5 trusts. We also store the trust type, flags, and attributes so we can determine one-way trusted domains (outgoing only trust path). Patch for one-way trusts coming in a later check-in. "wbinfo -m" now lists all domains in the domain_list() as held by the main winbindd process. (This used to be commit 9cf6068f1e0a1063d331af17aa493140497b96ef)
Diffstat (limited to 'source3/nsswitch/winbindd_ads.c')
-rw-r--r--source3/nsswitch/winbindd_ads.c82
1 files changed, 77 insertions, 5 deletions
diff --git a/source3/nsswitch/winbindd_ads.c b/source3/nsswitch/winbindd_ads.c
index 355a093855..111736244a 100644
--- a/source3/nsswitch/winbindd_ads.c
+++ b/source3/nsswitch/winbindd_ads.c
@@ -1020,8 +1020,10 @@ static NTSTATUS trusted_domains(struct winbindd_domain *domain,
struct ds_domain_trust *domains = NULL;
int count = 0;
int i;
- uint32 flags = DS_DOMAIN_IN_FOREST | DS_DOMAIN_DIRECT_OUTBOUND;
+ uint32 flags;
struct rpc_pipe_client *cli;
+ uint32 fr_flags = (DS_DOMAIN_IN_FOREST | DS_DOMAIN_TREE_ROOT);
+ int ret_count;
DEBUG(3,("ads: trusted_domains\n"));
@@ -1030,6 +1032,20 @@ static NTSTATUS trusted_domains(struct winbindd_domain *domain,
*names = NULL;
*dom_sids = NULL;
+ /* If this is our primary domain or a root in our forest,
+ query for all trusts. If not, then just look for domain
+ trusts in the target forest */
+
+ if ( domain->primary ||
+ ((domain->domain_flags&fr_flags) == fr_flags) )
+ {
+ flags = DS_DOMAIN_DIRECT_OUTBOUND |
+ DS_DOMAIN_DIRECT_INBOUND |
+ DS_DOMAIN_IN_FOREST;
+ } else {
+ flags = DS_DOMAIN_IN_FOREST;
+ }
+
result = cm_connect_netlogon(domain, &cli);
if (!NT_STATUS_IS_OK(result)) {
@@ -1067,14 +1083,70 @@ static NTSTATUS trusted_domains(struct winbindd_domain *domain,
/* Copy across names and sids */
+
+ ret_count = 0;
for (i = 0; i < count; i++) {
- (*names)[i] = domains[i].netbios_domain;
- (*alt_names)[i] = domains[i].dns_domain;
+ struct winbindd_domain d;
+
+ /* drop external trusts if this is not our primary
+ domain. This means that the returned number of
+ domains may be less that the ones actually trusted
+ by the DC. */
+
+ if ( (domains[i].trust_attributes == DS_DOMAIN_TRUST_ATTRIB_QUARANTINED_DOMAIN) &&
+ !domain->primary )
+ {
+ DEBUG(10,("trusted_domains: Skipping external trusted domain "
+ "%s because it is outside of our primary domain\n",
+ domains[i].netbios_domain));
+ continue;
+ }
+
+ (*names)[ret_count] = domains[i].netbios_domain;
+ (*alt_names)[ret_count] = domains[i].dns_domain;
+ sid_copy(&(*dom_sids)[ret_count], &domains[i].sid);
+
+ /* add to the trusted domain cache */
+
+ fstrcpy( d.name, domains[i].netbios_domain );
+ fstrcpy( d.alt_name, domains[i].dns_domain );
+ sid_copy( &d.sid, &domains[i].sid );
+
+ /* This gets a little tricky. If we are
+ following a transitive forest trust, then
+ innerit the flags, type, and attrins from
+ the domain we queried to make sure we don't
+ record the view of the trust from the wrong
+ side. Always view it from the side of our
+ primary domain. --jerry */
+ if ( domain->primary ||
+ ((domain->domain_flags&fr_flags) == fr_flags) )
+ {
+ DEBUG(10,("trusted_domains(ads): Storing trust "
+ "flags for domain %s\n", d.alt_name));
+
+ /* Look this up in cache to make sure
+ we have the current trust flags and
+ attributes */
+
+ d.domain_flags = domains[i].flags;
+ d.domain_type = domains[i].trust_type;
+ d.domain_trust_attribs = domains[i].trust_attributes;
+ } else {
+ DEBUG(10,("trusted_domains(ads): Inheriting trust "
+ "flags for domain %s\n", d.alt_name));
+ d.domain_flags = domain->domain_flags;
+ d.domain_type = domain->domain_type;
+ d.domain_trust_attribs = domain->domain_trust_attribs;
+ }
+
+ wcache_tdc_add_domain( &d );
+
+ ret_count++;
- sid_copy(&(*dom_sids)[i], &domains[i].sid);
}
- *num_domains = count;
+ *num_domains = ret_count;
}
return result;