summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/providers/data_provider_fo.c1
-rw-r--r--src/providers/fail_over.c14
-rw-r--r--src/providers/fail_over.h4
3 files changed, 17 insertions, 2 deletions
diff --git a/src/providers/data_provider_fo.c b/src/providers/data_provider_fo.c
index 526ae58f1..0a443c04f 100644
--- a/src/providers/data_provider_fo.c
+++ b/src/providers/data_provider_fo.c
@@ -71,6 +71,7 @@ static int be_fo_get_options(struct be_ctx *ctx,
DP_RES_OPT_RESOLVER_TIMEOUT);
opts->retry_timeout = 30;
opts->srv_retry_timeout = 14400;
+ opts->srv_retry_neg_timeout = 15;
opts->family_order = ctx->be_res->family_order;
return EOK;
diff --git a/src/providers/fail_over.c b/src/providers/fail_over.c
index e10556c99..c45fe9c49 100644
--- a/src/providers/fail_over.c
+++ b/src/providers/fail_over.c
@@ -150,6 +150,7 @@ fo_context_init(TALLOC_CTX *mem_ctx, struct fo_options *opts)
}
ctx->opts->srv_retry_timeout = opts->srv_retry_timeout;
+ ctx->opts->srv_retry_neg_timeout = opts->srv_retry_neg_timeout;
ctx->opts->retry_timeout = opts->retry_timeout;
ctx->opts->family_order = opts->family_order;
ctx->opts->service_resolv_timeout = opts->service_resolv_timeout;
@@ -265,9 +266,15 @@ get_srv_data_status(struct srv_data *data)
struct timeval tv;
time_t timeout;
- timeout = data->meta->service->ctx->opts->srv_retry_timeout;
gettimeofday(&tv, NULL);
+ /* Determine timeout value based on state of previous lookup. */
+ if (data->srv_lookup_status == SRV_RESOLVE_ERROR) {
+ timeout = data->meta->service->ctx->opts->srv_retry_neg_timeout;
+ } else {
+ timeout = data->meta->service->ctx->opts->srv_retry_timeout;
+ }
+
if (timeout && STATUS_DIFF(data, tv) > timeout) {
switch(data->srv_lookup_status) {
case SRV_EXPIRED:
@@ -280,6 +287,9 @@ get_srv_data_status(struct srv_data *data)
case SRV_RESOLVE_ERROR:
data->srv_lookup_status = SRV_NEUTRAL;
data->last_status_change.tv_sec = 0;
+ DEBUG(SSSDBG_TRACE_FUNC,
+ "Changing state of SRV lookup from 'SRV_RESOLVE_ERROR' to "
+ "'SRV_NEUTRAL'.\n.");
break;
default:
DEBUG(SSSDBG_CRIT_FAILURE, "Unknown state for SRV server!\n");
@@ -1022,7 +1032,7 @@ fo_resolve_service_activate_timeout(struct tevent_req *req,
tv = tevent_timeval_current();
tv = tevent_timeval_add(&tv, timeout_seconds, 0);
state->timeout_handler = tevent_add_timer(ev, state, tv,
- fo_resolve_service_timeout, req);
+ fo_resolve_service_timeout, req);
if (state->timeout_handler == NULL) {
DEBUG(SSSDBG_CRIT_FAILURE, "tevent_add_timer failed.\n");
return ENOMEM;
diff --git a/src/providers/fail_over.h b/src/providers/fail_over.h
index e4cc1b1cb..b1ec6a23c 100644
--- a/src/providers/fail_over.h
+++ b/src/providers/fail_over.h
@@ -71,11 +71,15 @@ struct fo_server;
* The 'srv_retry_timeout' member specifies how long a SRV lookup
* is considered valid until we ask the server again.
*
+ * The 'srv_retry_neg_timeout' member specifies how long a SRV lookup
+ * waits before previously failed lookup is tried again.
+ *
* The family_order member specifies the order of address families to
* try when looking up the service.
*/
struct fo_options {
time_t srv_retry_timeout;
+ time_t srv_retry_neg_timeout;
time_t retry_timeout;
int service_resolv_timeout;
enum restrict_family family_order;