Blob Blame History Raw
From 7afd36a4c4b35d72742eec2d23bd6908e635c097 Mon Sep 17 00:00:00 2001
From: Sumit Bose <sbose@redhat.com>
Date: Fri, 19 Jun 2020 13:36:49 +0200
Subject: [PATCH 70/71] AD: do not override LDAP data during GC lookups
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

The Global Catalog contains user and group information of the whole
forest and hence any Global Catalog server can be used. Currently when a
Global Catalog server is looked up the data of the LDAP server is
overwritten as well. I guess the original intention was to use a single
server for both services.

However since the Global Catalog server can come from any domain in the
forest this might overwrite the LDAP data of a DC from the local domain
with the data from a AD of a remote domain and as a result lookups for
users and groups from the local domain might fail since the remote DC
does not has this information available at the LDAP port. In most cases
this overwrite is hidden by a following lookup to find a KDC for
authentication which is searched only in the local domain again where
the LDAP data is overwritten again to make sure the same DC is used for
LDAP and Kerberos communication. But depending on the connection
timeouts and lifetime of Kerberos tickets the KDC lookup might be
skipped because new credentials are not needed and as a result the wrong
LDAP data is used.

To avoid this the LDAP data is now only set if the current lookup is not
a Global Catalog lookup.

Resolves: https://github.com/SSSD/sssd/issues/5351

Reviewed-by: Pavel Březina <pbrezina@redhat.com>
(cherry picked from commit 5f3b9e1d45df77bca1b2665e67bbd73b26fafbc2)

Reviewed-by: Alexey Tikhonov <atikhono@redhat.com>
---
 src/providers/ad/ad_common.c | 12 ++++++++----
 1 file changed, 8 insertions(+), 4 deletions(-)

diff --git a/src/providers/ad/ad_common.c b/src/providers/ad/ad_common.c
index 4e51d08e6..c99c4d110 100644
--- a/src/providers/ad/ad_common.c
+++ b/src/providers/ad/ad_common.c
@@ -942,10 +942,14 @@ ad_resolve_callback(void *private_data, struct fo_server *server)
     }
 
     /* free old one and replace with new one */
-    talloc_zfree(service->sdap->uri);
-    service->sdap->uri = new_uri;
-    talloc_zfree(service->sdap->sockaddr);
-    service->sdap->sockaddr = talloc_steal(service->sdap, sockaddr);
+    if (sdata == NULL || !sdata->gc) {
+        /* do not update LDAP data during GC lookups because the selected server
+         * might be from a different domain. */
+        talloc_zfree(service->sdap->uri);
+        service->sdap->uri = new_uri;
+        talloc_zfree(service->sdap->sockaddr);
+        service->sdap->sockaddr = talloc_steal(service->sdap, sockaddr);
+    }
 
     talloc_zfree(service->gc->uri);
     talloc_zfree(service->gc->sockaddr);
-- 
2.26.3