Blame SOURCES/0013-AD-Remember-last-site-discovered.patch

9f2ebf
From 020d7f12f7c57e3a5c8f844de2b2d0cad020e662 Mon Sep 17 00:00:00 2001
9f2ebf
From: =?UTF-8?q?Pavel=20B=C5=99ezina?= <pbrezina@redhat.com>
9f2ebf
Date: Wed, 18 Oct 2017 15:20:34 +0200
9f2ebf
Subject: [PATCH 13/21] AD: Remember last site discovered
9f2ebf
9f2ebf
To discover Active Directory site for a client we must first contact any
9f2ebf
directory controller for an LDAP ping. This is done by searching
9f2ebf
domain-wide DNS tree which may however contain servers that are not
9f2ebf
reachable from current site and than we face long timeouts or failure.
9f2ebf
9f2ebf
This patch makes sssd remember the last successfuly discovered site
9f2ebf
and use this for DNS search to lookup a site and forest again similar
9f2ebf
to what we do when ad_site option is set.
9f2ebf
9f2ebf
Resolves:
9f2ebf
https://pagure.io/SSSD/sssd/issue/3265
9f2ebf
9f2ebf
Reviewed-by: Jakub Hrozek <jhrozek@redhat.com>
9f2ebf
(cherry picked from commit f54d202db528207d7794870aabef0656b20369f1)
9f2ebf
---
9f2ebf
 src/providers/ad/ad_srv.c | 44 +++++++++++++++++++++++++++++++++++++++++++-
9f2ebf
 1 file changed, 43 insertions(+), 1 deletion(-)
9f2ebf
9f2ebf
diff --git a/src/providers/ad/ad_srv.c b/src/providers/ad/ad_srv.c
9f2ebf
index ff01ee95c4d2c6875a989394489f1a0495cc3003..be1ba0f237add894566ae713ce5e29fd202d414c 100644
9f2ebf
--- a/src/providers/ad/ad_srv.c
9f2ebf
+++ b/src/providers/ad/ad_srv.c
9f2ebf
@@ -481,6 +481,7 @@ struct ad_srv_plugin_ctx {
9f2ebf
     const char *hostname;
9f2ebf
     const char *ad_domain;
9f2ebf
     const char *ad_site_override;
9f2ebf
+    const char *current_site;
9f2ebf
 };
9f2ebf
 
9f2ebf
 struct ad_srv_plugin_ctx *
9f2ebf
@@ -518,6 +519,11 @@ ad_srv_plugin_ctx_init(TALLOC_CTX *mem_ctx,
9f2ebf
         if (ctx->ad_site_override == NULL) {
9f2ebf
             goto fail;
9f2ebf
         }
9f2ebf
+
9f2ebf
+        ctx->current_site = talloc_strdup(ctx, ad_site_override);
9f2ebf
+        if (ctx->current_site == NULL) {
9f2ebf
+            goto fail;
9f2ebf
+        }
9f2ebf
     }
9f2ebf
 
9f2ebf
     return ctx;
9f2ebf
@@ -527,6 +533,32 @@ fail:
9f2ebf
     return NULL;
9f2ebf
 }
9f2ebf
 
9f2ebf
+static errno_t
9f2ebf
+ad_srv_plugin_ctx_switch_site(struct ad_srv_plugin_ctx *ctx,
9f2ebf
+                              const char *new_site)
9f2ebf
+{
9f2ebf
+    const char *site;
9f2ebf
+    errno_t ret;
9f2ebf
+
9f2ebf
+    if (new_site == NULL) {
9f2ebf
+        return EOK;
9f2ebf
+    }
9f2ebf
+
9f2ebf
+    if (ctx->current_site != NULL && strcmp(ctx->current_site, new_site) == 0) {
9f2ebf
+        return EOK;
9f2ebf
+    }
9f2ebf
+
9f2ebf
+    site = talloc_strdup(ctx, new_site);
9f2ebf
+    if (site == NULL) {
9f2ebf
+        return ENOMEM;
9f2ebf
+    }
9f2ebf
+
9f2ebf
+    talloc_zfree(ctx->current_site);
9f2ebf
+    ctx->current_site = site;
9f2ebf
+
9f2ebf
+    return EOK;
9f2ebf
+}
9f2ebf
+
9f2ebf
 struct ad_srv_plugin_state {
9f2ebf
     struct tevent_context *ev;
9f2ebf
     struct ad_srv_plugin_ctx *ctx;
9f2ebf
@@ -613,7 +645,7 @@ struct tevent_req *ad_srv_plugin_send(TALLOC_CTX *mem_ctx,
9f2ebf
 
9f2ebf
     subreq = ad_get_dc_servers_send(state, ev, ctx->be_res->resolv,
9f2ebf
                                     state->discovery_domain,
9f2ebf
-                                    state->ctx->ad_site_override);
9f2ebf
+                                    state->ctx->current_site);
9f2ebf
     if (subreq == NULL) {
9f2ebf
         ret = ENOMEM;
9f2ebf
         goto immediately;
9f2ebf
@@ -709,6 +741,16 @@ static void ad_srv_plugin_site_done(struct tevent_req *subreq)
9f2ebf
     backup_domain = NULL;
9f2ebf
 
9f2ebf
     if (ret == EOK) {
9f2ebf
+        /* Remember current site so it can be used during next lookup so
9f2ebf
+         * we can contact directory controllers within a known reachable
9f2ebf
+         * site first. */
9f2ebf
+        ret = ad_srv_plugin_ctx_switch_site(state->ctx, state->site);
9f2ebf
+        if (ret != EOK) {
9f2ebf
+            DEBUG(SSSDBG_CRIT_FAILURE, "Unable to set site [%d]: %s\n",
9f2ebf
+                  ret, sss_strerror(ret));
9f2ebf
+            goto done;
9f2ebf
+        }
9f2ebf
+
9f2ebf
         if (strcmp(state->service, "gc") == 0) {
9f2ebf
             if (state->forest != NULL) {
9f2ebf
                 if (state->site != NULL) {
9f2ebf
-- 
9f2ebf
2.13.5
9f2ebf