From 8cb85952cca11876b3ab2a7f3c45d3d9cfb6c15a Mon Sep 17 00:00:00 2001 From: Stefan Metzmacher Date: Tue, 7 Jan 2025 14:06:43 +0100 Subject: [PATCH] s4:dsdb: fix logic of dsdb_trust_routing_by_name() We need to use the longest dnsname match as possible. If we are the domain samba.example.com and have a trust to example.com, a routing request for dc.samba.example.com should return the tdo for samba.example.com instead of example.com. I reproduced the problem with the following diff: > diff --git a/selftest/target/Samba.pm b/selftest/target/Samba.pm > index 15d7692b5d64..6e9595b784c4 100644 > --- a/selftest/target/Samba.pm > +++ b/selftest/target/Samba.pm > @@ -564,7 +564,7 @@ sub realm_to_ip_mappings > 'samba2000.example.com' => 'dc5', > 'samba2003.example.com' => 'dc6', > 'samba2008r2.example.com' => 'dc7', > - 'addom.samba.example.com' => 'addc', > + 'addom.samba2008r2.example.com' => 'addc', > 'addom2.samba.example.com' => 'addcsmb1', > 'sub.samba.example.com' => 'localsubdc', > 'chgdcpassword.samba.example.com' => 'chgdcpass', > diff --git a/selftest/target/Samba4.pm b/selftest/target/Samba4.pm > index 0e4cf50235c3..6bca0cfd0c89 100755 > --- a/selftest/target/Samba4.pm > +++ b/selftest/target/Samba4.pm > @@ -2631,7 +2631,7 @@ sub setup_fl2008r2dc > return undef; > } > > - $env = $self->setup_trust($env, $ad_dc_vars, "forest", ""); > + $env = $self->setup_trust($env, $ad_dc_vars, "forest", "--skip-validation"); > if (!defined $env) { > return undef; > } > @@ -2843,7 +2843,7 @@ sub _setup_ad_dc > $server = "addc"; > } > if (!defined($dom)) { > - $dom = "addom.samba.example.com"; > + $dom = "addom.samba2008r2.example.com"; > } > my $env = $self->provision_ad_dc($path, $server, "ADDOMAIN", > $dom, and running: make -j testenv SELFTEST_TESTENV="fl2008r2dc:local" Inside the testenv: bin/smbclient //addc.addom.samba2008r2.example.com/netlogon \ -U$TRUST_USERNAME@$TRUST_REALM%$TRUST_PASSWORD \ --use-kerberos=required \ -c 'ls' It lets the KDC of ADDOM.SAMBA2008R2.EXAMPLE.COM to generate a (referral) ticket for krbtgt/SAMBA2008R2.EXAMPLE.COM@ADDOM.SAMBA2008R2.EXAMPLE.COM instead of cifs/addc.addom.samba2008r2.example.com@ADDOM.SAMBA2008R2.EXAMPLE.COM As ADDOM.SAMBA2008R2.EXAMPLE.COM has a forest trust (without msDS-TrustForestTrustInfo) to SAMBA2008R2.EXAMPLE.COM dsdb_trust_update_best_tln() overwrote the best match of addom.samba2008r2.example.com with samba2008r2.example.com. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15778 Signed-off-by: Stefan Metzmacher Reviewed-by: Douglas Bagnall Autobuild-User(master): Douglas Bagnall Autobuild-Date(master): Wed Jan 8 04:14:47 UTC 2025 on atb-devel-224 (cherry picked from commit 56947612452c32bd26f30ad6c9767830fe608d67) --- source4/dsdb/common/util_trusts.c | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/source4/dsdb/common/util_trusts.c b/source4/dsdb/common/util_trusts.c index 34a836a6a6f2..c1797e3138ed 100644 --- a/source4/dsdb/common/util_trusts.c +++ b/source4/dsdb/common/util_trusts.c @@ -3038,7 +3038,7 @@ static void dsdb_trust_update_best_tln( return; } - cmp = dns_cmp(*best_tln, tln); + cmp = dns_cmp(tln, *best_tln); if (cmp != DNS_CMP_FIRST_IS_CHILD) { return; } @@ -3127,10 +3127,6 @@ const struct lsa_TrustDomainInfoInfoEx *dsdb_trust_routing_by_name( continue; } - if (!transitive) { - continue; - } - dsdb_trust_update_best_tln(&best_d, &best_tln, d, d->tdo->domain_name.string); continue; @@ -3212,15 +3208,19 @@ const struct lsa_TrustDomainInfoInfoEx *dsdb_trust_routing_by_name( } cmp = dns_cmp(name, fti_tln); - switch (cmp) { - case DNS_CMP_MATCH: - case DNS_CMP_FIRST_IS_CHILD: - dsdb_trust_update_best_tln(&best_d, &best_tln, - d, fti_tln); - break; - default: - break; + if (cmp == DNS_CMP_MATCH) { + /* + * exact match + */ + return d->tdo; } + if (cmp != DNS_CMP_FIRST_IS_CHILD) { + continue; + } + + dsdb_trust_update_best_tln(&best_d, &best_tln, + d, fti_tln); + continue; } } -- 2.34.1