From: sergey.kitov Date: Tue, 6 May 2025 15:20:19 +0000 (+0300) Subject: lib-dns src: Change dns_client_settings to config setting. X-Git-Tag: 2.4.2~767 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=dd6f9b3a3fab7d1c4b93d4f65086e8f019338b83;p=thirdparty%2Fdovecot%2Fcore.git lib-dns src: Change dns_client_settings to config setting. --- diff --git a/src/auth/auth.c b/src/auth/auth.c index b962320f07..4981cf8534 100644 --- a/src/auth/auth.c +++ b/src/auth/auth.c @@ -9,8 +9,6 @@ #include "auth.h" #include "dns-lookup.h" -#define AUTH_DNS_SOCKET_PATH "dns-client" -#define AUTH_DNS_DEFAULT_TIMEOUT_MSECS (1000*10) #define AUTH_DNS_IDLE_TIMEOUT_MSECS (1000*60) #define AUTH_DNS_CACHE_TTL_SECS 10 @@ -376,8 +374,11 @@ static void auth_init(struct auth *auth) { struct auth_passdb *passdb; struct auth_userdb *userdb; - struct dns_client_settings dns_set; - struct dns_client_parameters dns_params; + const char *error; + const struct dns_client_parameters params = { + .idle_timeout_msecs = AUTH_DNS_IDLE_TIMEOUT_MSECS, + .cache_ttl_secs = AUTH_DNS_CACHE_TTL_SECS + }; for (passdb = auth->masterdbs; passdb != NULL; passdb = passdb->next) auth_passdb_init(passdb); @@ -386,13 +387,8 @@ static void auth_init(struct auth *auth) for (userdb = auth->userdbs; userdb != NULL; userdb = userdb->next) userdb_init(userdb->userdb); - i_zero(&dns_set); - dns_set.dns_client_socket_path = AUTH_DNS_SOCKET_PATH; - dns_set.timeout_msecs = AUTH_DNS_DEFAULT_TIMEOUT_MSECS; - dns_params.idle_timeout_msecs = AUTH_DNS_IDLE_TIMEOUT_MSECS; - dns_params.cache_ttl_secs = AUTH_DNS_CACHE_TTL_SECS; - - auth->dns_client = dns_client_init(&dns_set, &dns_params, NULL); + if (dns_client_init(¶ms, auth_event, &auth->dns_client, &error) < 0) + i_fatal("%s", error); } static void auth_deinit(struct auth *auth) diff --git a/src/lib-dns-client/Makefile.am b/src/lib-dns-client/Makefile.am index 9719dc1747..ee27398d15 100644 --- a/src/lib-dns-client/Makefile.am +++ b/src/lib-dns-client/Makefile.am @@ -2,10 +2,14 @@ noinst_LTLIBRARIES = libdns-client.la AM_CPPFLAGS = \ -I$(top_srcdir)/src/lib \ - -I$(top_srcdir)/src/lib-test + -I$(top_srcdir)/src/lib-settings \ + -I$(top_srcdir)/src/lib-var-expand \ + -I$(top_srcdir)/src/lib-test \ + -DPKG_RUNDIR=\""$(rundir)"\" libdns_client_la_SOURCES = \ dns-client-cache.c \ + dns-client-settings.c \ dns-lookup.c headers = \ @@ -19,8 +23,10 @@ noinst_PROGRAMS = $(test_programs) test_libs = \ libdns-client.la \ + ../lib-settings/libsettings.la \ ../lib-dns/libdns.la \ ../lib-test/libtest.la \ + ../lib-var-expand/libvar_expand.la \ ../lib/liblib.la test_dns_lookup_SOURCES = test-dns-lookup.c diff --git a/src/lib-dns-client/dns-client-settings.c b/src/lib-dns-client/dns-client-settings.c new file mode 100644 index 0000000000..71fe940d08 --- /dev/null +++ b/src/lib-dns-client/dns-client-settings.c @@ -0,0 +1,61 @@ +/* Copyright (c) 2005-2024 Dovecot authors, see the included COPYING file */ + +#include "lib.h" +#include "settings-parser.h" +#include "dns-lookup.h" +#include "strfuncs.h" + +static bool dns_client_settings_check(void *_set, pool_t pool, + const char **error_r); + +#undef DEF +#define DEF(type, name) \ + SETTING_DEFINE_STRUCT_##type(#name, name, struct dns_client_settings) + +#undef DEF_MSECS +#define DEF_MSECS(type, name) \ + SETTING_DEFINE_STRUCT_##type("dns_client_"#name, name##_msecs, struct dns_client_settings) + +static const struct setting_define dns_client_setting_defines[] = { + DEF(STR_HIDDEN, dns_client_socket_path), + DEF(STR_HIDDEN, base_dir), + DEF_MSECS(TIME_MSECS, timeout), + + SETTING_DEFINE_LIST_END +}; + +static const struct dns_client_settings dns_client_default_settings = { + .dns_client_socket_path = "dns-client", + .base_dir = PKG_RUNDIR, + .timeout_msecs = 10 * 1000, +}; + +const struct setting_parser_info dns_client_setting_parser_info = { + .name = "dns_client", + + .defines = dns_client_setting_defines, + .defaults = &dns_client_default_settings, + + .pool_offset1 = 1 + offsetof(struct dns_client_settings, pool), + .struct_size = sizeof(struct dns_client_settings), + .check_func = dns_client_settings_check, +}; + +/* */ +static bool +dns_client_settings_check(void *_set, pool_t pool, const char **error_r ATTR_UNUSED) +{ + struct dns_client_settings *set = _set; + size_t len; + len = strlen(set->base_dir); + if (len > 0 && + set->dns_client_socket_path[0] != '\0' && + !str_begins_with(set->dns_client_socket_path, "./")) { + if (set->base_dir[len - 1] == '/') + set->base_dir = p_strndup(pool, set->base_dir, len); + set->dns_client_socket_path = p_strconcat(pool, set->base_dir, "/", + set->dns_client_socket_path, NULL); + } + return TRUE; +} +/* */ diff --git a/src/lib-dns-client/dns-lookup.c b/src/lib-dns-client/dns-lookup.c index a4b1772708..907a7a0476 100644 --- a/src/lib-dns-client/dns-lookup.c +++ b/src/lib-dns-client/dns-lookup.c @@ -9,6 +9,7 @@ #include "time-util.h" #include "dns-client-cache.h" #include "dns-lookup.h" +#include "settings.h" static struct event_category event_category_dns = { .name = "dns" @@ -128,7 +129,7 @@ static void dns_lookup_callback(struct dns_lookup *lookup) event_create_passthrough(lookup->event)-> set_name("dns_request_finished"); - if (!lookup->cached) { + if (!lookup->cached && lookup->client != NULL) { dns_client_cache_entry(lookup->client->cache, lookup->cache_key, &lookup->result); } @@ -290,7 +291,7 @@ dns_lookup_create(pool_t pool, lookup->context = context; lookup->ptr_lookup = ptr_lookup; lookup->result.ret = EAI_FAIL; - if (event == NULL) + if (event == NULL && client != NULL) lookup->event = event_create(client->conn.event); else { lookup->event = event_create(event); @@ -303,22 +304,49 @@ dns_lookup_create(pool_t pool, return lookup; } -int dns_lookup(const char *host, const struct dns_client_settings *set, - const struct dns_client_parameters *params, +static int +dns_client_init_handle_failure(const struct dns_client_parameters *params, + struct event *event_parent, + const char *cmd_param, + bool ptr_lookup, + dns_lookup_callback_t *callback, + void *context, + struct dns_client **client_r) +{ + const char *error; + int ret = dns_client_init(params, event_parent, client_r, &error); + if (ret < 0) { + pool_t pool = pool_alloconly_create("dns lookup", 512); + struct dns_lookup *tmp_lookup = dns_lookup_create(pool, NULL, + ptr_lookup, + cmd_param, + event_parent, + callback, context); + tmp_lookup->result.error = error; + dns_lookup_callback(tmp_lookup); + dns_lookup_free(&tmp_lookup); + } + return ret; +} + +int dns_lookup(const char *host, const struct dns_client_parameters *params, struct event *event_parent, dns_lookup_callback_t *callback, void *context, struct dns_lookup **lookup_r) { struct dns_client *client; + int ret = dns_client_init_handle_failure(params, event_parent, + host, FALSE, callback, + context, &client); i_assert(params == NULL || params->cache_ttl_secs == 0); - client = dns_client_init(set, params, event_parent); + if (ret < 0) + return -1; client->deinit_client_at_free = TRUE; return dns_client_lookup(client, host, client->conn.event, callback, context, lookup_r); } int dns_lookup_ptr(const struct ip_addr *ip, - const struct dns_client_settings *set, const struct dns_client_parameters *params, struct event *event_parent, dns_lookup_callback_t *callback, void *context, @@ -327,7 +355,10 @@ int dns_lookup_ptr(const struct ip_addr *ip, struct dns_client *client; i_assert(params == NULL || params->cache_ttl_secs == 0); - client = dns_client_init(set, params, event_parent); + if (dns_client_init_handle_failure(params, event_parent, + net_ip2addr(ip), TRUE, + callback, context, &client) < 0) + return -1; client->deinit_client_at_free = TRUE; return dns_client_lookup_ptr(client, ip, client->conn.event, callback, context, lookup_r); @@ -350,13 +381,15 @@ static void dns_lookup_free(struct dns_lookup **_lookup) *_lookup = NULL; timeout_remove(&lookup->to); - if (client->deinit_client_at_free) - dns_client_deinit(&client); - else if (client->head == NULL && client->connected && - client->to_idle == NULL) { - client->to_idle = timeout_add_to(client->ioloop, - client->idle_timeout_msecs, - dns_client_idle_timeout, client); + if (client != NULL) { + if (client->deinit_client_at_free) + dns_client_deinit(&client); + else if (client->head == NULL && client->connected && + client->to_idle == NULL) { + client->to_idle = timeout_add_to(client->ioloop, + client->idle_timeout_msecs, + dns_client_idle_timeout, client); + } } event_unref(&lookup->event); pool_unref(&lookup->pool); @@ -421,13 +454,16 @@ static const struct connection_settings dns_client_set = { .client = TRUE, }; -struct dns_client *dns_client_init(const struct dns_client_settings *set, - const struct dns_client_parameters *params, - struct event *event_parent) +int dns_client_init(const struct dns_client_parameters *params, + struct event *event_parent, + struct dns_client **client_r, + const char **error_r) { struct dns_client *client; - - i_assert(set->dns_client_socket_path[0] != '\0'); + struct dns_client_settings *set; + i_assert(event_parent != NULL); + if (settings_get(event_parent, &dns_client_setting_parser_info, 0, &set, error_r) < 0) + return -1; client = i_new(struct dns_client, 1); client->timeout_msecs = set->timeout_msecs; @@ -442,7 +478,9 @@ struct dns_client *dns_client_init(const struct dns_client_settings *set, client->cache = dns_client_cache_init(params->cache_ttl_secs, dns_client_cache_refresh, client); } - return client; + settings_free(set); + *client_r = client; + return 0; } void dns_client_deinit(struct dns_client **_client) @@ -557,6 +595,31 @@ int dns_client_lookup(struct dns_client *client, const char *host, struct dns_lookup **lookup_r) { int ret; + if (client->path[0] == '\0') { + /* Fallback to gethostbyname() */ + pool_t pool = pool_alloconly_create("dns_lookup", 512); + struct dns_lookup *lookup = dns_lookup_create(pool, NULL, + FALSE, NULL, + client->conn.event_parent, + callback, context); + *lookup_r = lookup; + unsigned int ips_count; + struct ip_addr *ips; + ret = lookup->result.ret = net_gethostbyname(host, &ips, &ips_count); + if (lookup->result.ret != 0) { + lookup->result.error = + t_strdup_printf("net_gethostbyname() failed: %s", + net_gethosterror(lookup->result.ret)); + } + lookup->result.ips_count = ips_count; + if (ips_count > 0) + lookup->result.ips = + p_memdup(pool, ips, + sizeof(struct ip_addr) * ips_count); + dns_lookup_callback(lookup); + dns_lookup_free(&lookup); + return ret; + } T_BEGIN { ret = dns_client_lookup_common(client, "IP", host, FALSE, event, callback, context, lookup_r); diff --git a/src/lib-dns-client/dns-lookup.h b/src/lib-dns-client/dns-lookup.h index 247a51f875..6b1b631d17 100644 --- a/src/lib-dns-client/dns-lookup.h +++ b/src/lib-dns-client/dns-lookup.h @@ -10,9 +10,12 @@ #endif struct dns_lookup; +struct dns_client; struct dns_client_settings { + pool_t pool; const char *dns_client_socket_path; + const char *base_dir; unsigned int timeout_msecs; }; @@ -48,27 +51,24 @@ typedef void dns_lookup_callback_t(const struct dns_lookup_result *result, started, -1 if there was an error communicating with the UNIX socket. When failing with -1, the callback is called before returning from the function. */ -int dns_lookup(const char *host, const struct dns_client_settings *set, - const struct dns_client_parameters *params, - struct event *event_parent, - dns_lookup_callback_t *callback, void *context, - struct dns_lookup **lookup_r) ATTR_NULL(4); -#define dns_lookup(host, set, params, event_parent, callback, context, lookup_r) \ +int dns_lookup(const char *host, const struct dns_client_parameters *params, + struct event *event_parent, dns_lookup_callback_t *callback, + void *context, struct dns_lookup **lookup_r) ATTR_NULL(4); +#define dns_lookup(host, params, event_parent, callback, context, lookup_r) \ dns_lookup(host - \ CALLBACK_TYPECHECK(callback, void (*)( \ const struct dns_lookup_result *, typeof(context))), \ - set, params, event_parent, (dns_lookup_callback_t *)callback, context, lookup_r) + params, event_parent, (dns_lookup_callback_t *)callback, context, lookup_r) int dns_lookup_ptr(const struct ip_addr *ip, - const struct dns_client_settings *set, const struct dns_client_parameters *params, struct event *event_parent, dns_lookup_callback_t *callback, void *context, struct dns_lookup **lookup_r) ATTR_NULL(4); -#define dns_lookup_ptr(host, set, params, event_parent, callback, context, lookup_r) \ +#define dns_lookup_ptr(host, params, event_parent, callback, context, lookup_r) \ dns_lookup_ptr(host - \ CALLBACK_TYPECHECK(callback, void (*)( \ const struct dns_lookup_result *, typeof(context))), \ - set, params, event_parent, \ + params, event_parent, \ (dns_lookup_callback_t *)callback, context, lookup_r) /* Abort the DNS lookup without calling the callback. */ void dns_lookup_abort(struct dns_lookup **lookup); @@ -76,9 +76,10 @@ void dns_lookup_abort(struct dns_lookup **lookup); void dns_lookup_switch_ioloop(struct dns_lookup *lookup); /* Alternative API for clients that need to do multiple DNS lookups. */ -struct dns_client *dns_client_init(const struct dns_client_settings *set, - const struct dns_client_parameters *params, - struct event *event_parent); +int dns_client_init(const struct dns_client_parameters *params, + struct event *event_parent, + struct dns_client **client_r, + const char **error_r); void dns_client_deinit(struct dns_client **client); /* Connect immediately to the dns-lookup socket. */ @@ -107,4 +108,6 @@ bool dns_client_has_pending_queries(struct dns_client *client); void dns_client_switch_ioloop(struct dns_client *client); +extern const struct setting_parser_info dns_client_setting_parser_info; + #endif diff --git a/src/lib-dns-client/test-dns-lookup.c b/src/lib-dns-client/test-dns-lookup.c index 67e298ecd9..c4d0a96a16 100644 --- a/src/lib-dns-client/test-dns-lookup.c +++ b/src/lib-dns-client/test-dns-lookup.c @@ -11,10 +11,20 @@ #include "ostream.h" #include "connection.h" #include "dns-lookup.h" +#include "settings.h" #include #define TEST_SOCKET_NAME ".test-dns-server" +static struct settings_simple test_set; + +static const char *const set_dns_test[] = { + "dns_client_socket_path", TEST_SOCKET_NAME, + "base_dir", "", + "dns_client_timeout", "1s", + NULL +}; + static const struct { const char *name; const char *reply; @@ -167,26 +177,17 @@ static void test_callback_ips(const struct dns_lookup_result *result, static void test_dns_expect_result_ips(const char *name, const char *result) { - const struct dns_client_settings set = { - .dns_client_socket_path = TEST_SOCKET_NAME, - .timeout_msecs = 1000, - }; struct dns_lookup *lookup; struct test_expect_result ctx = { .ret = result == NULL ? -1 : 0, .result = result }; - test_assert(dns_lookup(name, &set, NULL, NULL, test_callback_ips, - &ctx, &lookup) == 0); + test_assert(dns_lookup(name, NULL, test_set.event, test_callback_ips, &ctx, &lookup) == 0); io_loop_run(test_server.loop); } static void test_dns_expect_result_name(const char *name, const char *result) { - const struct dns_client_settings set = { - .dns_client_socket_path = TEST_SOCKET_NAME, - .timeout_msecs = 1000, - }; struct dns_lookup *lookup; struct test_expect_result ctx = { .ret = result == NULL ? -1 : 0, @@ -194,14 +195,14 @@ static void test_dns_expect_result_name(const char *name, const char *result) }; struct ip_addr addr; i_assert(net_addr2ip(name, &addr) == 0); - test_assert(dns_lookup_ptr(&addr, &set, NULL, NULL, test_callback_name, - &ctx, &lookup) == 0); + test_assert(dns_lookup_ptr(&addr, NULL, test_set.event, test_callback_name, &ctx, &lookup) == 0); io_loop_run(test_server.loop); } static void test_dns_lookup(void) { test_begin("dns lookup"); + settings_simple_update(&test_set, set_dns_test); create_dns_server(&test_server); test_dns_expect_result_ips("localhost", "127.0.0.1\t::1"); @@ -218,18 +219,14 @@ static void test_dns_lookup_timeout(void) test_begin("dns lookup (timeout)"); create_dns_server(&test_server); - const struct dns_client_settings set = { - .dns_client_socket_path = TEST_SOCKET_NAME, - .timeout_msecs = 1000, - }; struct dns_lookup *lookup; struct test_expect_result ctx = { .ret = EAI_FAIL, .result = NULL, }; - test_assert(dns_lookup("waitfor1500", &set, NULL, NULL, test_callback_ips, - &ctx, &lookup) == 0); + test_assert(dns_lookup("waitfor1500", NULL, test_set.event, + test_callback_ips, &ctx, &lookup) == 0); io_loop_run(current_ioloop); destroy_dns_server(&test_server); @@ -241,18 +238,14 @@ static void test_dns_lookup_abort(void) test_begin("dns lookup (abort)"); create_dns_server(&test_server); - const struct dns_client_settings set = { - .dns_client_socket_path = TEST_SOCKET_NAME, - .timeout_msecs = 1000, - }; struct dns_lookup *lookup; struct test_expect_result ctx = { .ret = -4, .result = NULL, }; - test_assert(dns_lookup("waitfor1500", &set, NULL, NULL, test_callback_ips, - &ctx, &lookup) == 0); + test_assert(dns_lookup("waitfor1500", NULL, test_set.event, + test_callback_ips, &ctx, &lookup) == 0); struct timeout *to = timeout_add_short(100, io_loop_stop, current_ioloop); io_loop_run(current_ioloop); timeout_remove(&to); @@ -268,20 +261,18 @@ static void test_dns_lookup_cached(void) struct dns_lookup *lookup; struct timeout *to; struct event *event = event_create(NULL); + struct dns_client *client; + int init_res; + const char *err; test_begin("dns lookup (cached)"); create_dns_server(&test_server); - const struct dns_client_settings set = { - .dns_client_socket_path = TEST_SOCKET_NAME, - .timeout_msecs = 1000, - }; - const struct dns_client_parameters params = { .cache_ttl_secs = 4, }; - - struct dns_client *client = dns_client_init(&set, ¶ms, event); + init_res = dns_client_init(¶ms, test_set.event, &client, &err); + test_assert(init_res == 0); /* lookup localhost */ ctx.result = "127.0.0.1\t::1"; @@ -394,5 +385,10 @@ int main(void) NULL }; - return test_run(test_functions); + lib_init(); + settings_simple_init(&test_set, set_dns_test); + int ret = test_run(test_functions); + settings_simple_deinit(&test_set); + lib_deinit(); + return ret; } diff --git a/src/lib-doveadm/doveadm-client.c b/src/lib-doveadm/doveadm-client.c index 771337ef2c..37b7ec2f9b 100644 --- a/src/lib-doveadm/doveadm-client.c +++ b/src/lib-doveadm/doveadm-client.c @@ -677,6 +677,7 @@ doveadm_client_create_failed(struct doveadm_client_dns_lookup_context *ctx) .error = ctx->error, }; doveadm_client_callback(conn, &reply); + event_unref(&conn->conn.event); pool_unref(&conn->pool); } @@ -714,15 +715,10 @@ static int doveadm_client_dns_lookup(struct doveadm_client *conn, { struct doveadm_client_dns_lookup_context *ctx = p_new(conn->pool, struct doveadm_client_dns_lookup_context, 1); - struct dns_client_settings dns_set; - - i_zero(&dns_set); - dns_set.dns_client_socket_path = conn->set.dns_client_socket_path; - dns_set.timeout_msecs = DOVEADM_CLIENT_DNS_TIMEOUT_MSECS; ctx->conn = conn; - if (dns_lookup(conn->set.hostname, &dns_set, NULL, conn->conn.event, + if (dns_lookup(conn->set.hostname, NULL, conn->conn.event, doveadm_client_dns_lookup_callback, ctx, &conn->dns_lookup) != 0) { *error_r = t_strdup(ctx->error); @@ -783,6 +779,8 @@ int doveadm_client_create(const struct doveadm_client_settings *set, conn = p_new(pool, struct doveadm_client, 1); conn->pool = pool; conn->refcount = 1; + /* DNS lookup needs the event before connection is initialized. */ + conn->conn.event = event_create(NULL); doveadm_client_settings_dup(set, &conn->set, pool); if (set->socket_path != NULL) { @@ -794,6 +792,7 @@ int doveadm_client_create(const struct doveadm_client_settings *set, } else if (doveadm_client_resolve_hostname(conn, &error) != 0) { *error_r = t_strdup(error); + event_unref(&conn->conn.event); pool_unref(&pool); return -1; } diff --git a/src/lib-http/http-client-host.c b/src/lib-http/http-client-host.c index c7b848ec45..8429b63c65 100644 --- a/src/lib-http/http-client-host.c +++ b/src/lib-http/http-client-host.c @@ -12,6 +12,7 @@ #include "time-util.h" #include "dns-lookup.h" #include "http-response-parser.h" +#include "settings.h" #include "http-client-private.h" @@ -144,32 +145,28 @@ http_client_host_shared_lookup(struct http_client_host *host) { struct http_client_host_shared *hshared = host->shared; struct http_client_context *cctx = hshared->cctx; - struct dns_client_settings dns_set; i_assert(!hshared->explicit_ip); i_assert(hshared->dns_lookup == NULL); if (cctx->dns_client != NULL) { - e_debug(hshared->event, "Performing asynchronous DNS lookup"); + e_debug(host->client->event, "Performing asynchronous DNS lookup"); + /* Note: dns_client_lookup() takes DNS settings from cctx->dns_client + and may differ from host->client DNS settings */ (void)dns_client_lookup(cctx->dns_client, hshared->name, - hshared->event, + host->client->event, http_client_host_shared_dns_callback, hshared, &hshared->dns_lookup); - } else if (cctx->dns_client_socket_path != NULL) { + } else { struct ioloop *prev_ioloop = current_ioloop; - i_assert(cctx->dns_lookup_timeout_msecs > 0); - e_debug(hshared->event, "Performing asynchronous DNS lookup"); - i_zero(&dns_set); - dns_set.dns_client_socket_path = cctx->dns_client_socket_path; - dns_set.timeout_msecs = cctx->dns_lookup_timeout_msecs; + /* host->client->event is used in order to + get client-specific DNS settings. */ + e_debug(host->client->event, "Performing asynchronous DNS lookup"); io_loop_set_current(cctx->ioloop); - (void)dns_lookup(hshared->name, &dns_set, NULL, hshared->event, + (void)dns_lookup(hshared->name, NULL, host->client->event, http_client_host_shared_dns_callback, hshared, &hshared->dns_lookup); io_loop_set_current(prev_ioloop); - } else { - /* FIXME: fully removed in the following commits */ - i_unreached(); } } diff --git a/src/lib-http/http-client-private.h b/src/lib-http/http-client-private.h index 18c13787ee..e6cacdf174 100644 --- a/src/lib-http/http-client-private.h +++ b/src/lib-http/http-client-private.h @@ -402,9 +402,7 @@ struct http_client_context { struct ioloop *ioloop; struct dns_client *dns_client; - char *dns_client_socket_path; unsigned int dns_ttl_msecs; - unsigned int dns_lookup_timeout_msecs; struct http_client *clients_list; struct connection_list *conn_list; diff --git a/src/lib-http/http-client-settings.c b/src/lib-http/http-client-settings.c index 448cf257c9..7b34e09508 100644 --- a/src/lib-http/http-client-settings.c +++ b/src/lib-http/http-client-settings.c @@ -23,7 +23,6 @@ http_client_settings_check(void *_set, pool_t pool, const char **error_r); static const struct setting_define http_client_setting_defines[] = { SETTING_DEFINE_STRUCT_STR_HIDDEN("base_dir", base_dir, struct http_client_settings), - DEF(STR_HIDDEN, dns_client_socket_path), DEF_MSECS(TIME_MSECS_HIDDEN, dns_ttl), DEF(STR_HIDDEN, user_agent), @@ -74,7 +73,6 @@ static const struct setting_define http_client_setting_defines[] = { static const struct http_client_settings http_client_default_settings = { .base_dir = PKG_RUNDIR, - .dns_client_socket_path = "dns-client", .dns_ttl_msecs = HTTP_CLIENT_DEFAULT_DNS_TTL_MSECS, .user_agent = "", diff --git a/src/lib-http/http-client.c b/src/lib-http/http-client.c index eb10042876..85c34df793 100644 --- a/src/lib-http/http-client.c +++ b/src/lib-http/http-client.c @@ -492,7 +492,6 @@ void http_client_context_unref(struct http_client_context **_cctx) connection_list_deinit(&cctx->conn_list); event_unref(&cctx->event); - i_free(cctx->dns_client_socket_path); pool_unref(&cctx->pool); } @@ -504,32 +503,13 @@ http_client_context_update_settings(struct http_client_context *cctx) /* Revert back to default settings */ cctx->dns_client = NULL; - i_free(cctx->dns_client_socket_path); cctx->dns_ttl_msecs = UINT_MAX; - cctx->dns_lookup_timeout_msecs = HTTP_CLIENT_DEFAULT_DNS_LOOKUP_TIMEOUT_MSECS; /* Override with available client settings */ for (client = cctx->clients_list; client != NULL; client = client->next) { if (cctx->dns_client == NULL) cctx->dns_client = client->dns_client; - if (cctx->dns_client_socket_path == NULL && - client->set->dns_client_socket_path != NULL && - client->set->dns_client_socket_path[0] != '\0') { - /* FIXME: This base_dir expansion shouldn't be here. - Maybe support %{set:base_dir}/dns-client? - The "./" check is to avoid breaking unit tests. */ - if (client->set->dns_client_socket_path[0] == '/' || - str_begins_with(client->set->dns_client_socket_path, "./")) { - cctx->dns_client_socket_path = - i_strdup(client->set->dns_client_socket_path); - } else { - cctx->dns_client_socket_path = - i_strdup_printf("%s/%s", - client->set->base_dir, - client->set->dns_client_socket_path); - } - } if (client->set->dns_ttl_msecs != 0 && cctx->dns_ttl_msecs > client->set->dns_ttl_msecs) cctx->dns_ttl_msecs = client->set->dns_ttl_msecs; diff --git a/src/lib-http/http-client.h b/src/lib-http/http-client.h index 0ce065e760..006f676759 100644 --- a/src/lib-http/http-client.h +++ b/src/lib-http/http-client.h @@ -22,12 +22,6 @@ struct ssl_iostream_settings; struct http_client_settings { pool_t pool; - /* a) If http_client_set_dns_client() is used, all lookups are done - via it. - b) If dns_client_socket_path is set, each DNS lookup does its own - dns-lookup UNIX socket connection. - c) Otherwise, blocking gethostbyname() lookups are used. */ - const char *dns_client_socket_path; /* A copy of base_dir setting. FIXME: this should not be here. */ const char *base_dir; /* How long to cache DNS records internally diff --git a/src/lib-http/test-http-client-errors.c b/src/lib-http/test-http-client-errors.c index 1f66b362ab..2307f557a1 100644 --- a/src/lib-http/test-http-client-errors.c +++ b/src/lib-http/test-http-client-errors.c @@ -16,6 +16,8 @@ #include "http-url.h" #include "http-request.h" #include "http-client.h" +#include "http-client-private.h" +#include "settings.h" #include #include @@ -23,6 +25,8 @@ #define CLIENT_PROGRESS_TIMEOUT 10 #define SERVER_KILL_TIMEOUT_SECS 20 +static struct settings_root *set_root; + static void main_deinit(void); /* @@ -2257,7 +2261,8 @@ static void test_dns_service_failure(void) struct http_client_settings http_client_set; test_client_defaults(&http_client_set); - http_client_set.dns_client_socket_path = "./frop"; + settings_root_override(set_root, "dns_client_socket_path", + "./frop", SETTINGS_OVERRIDE_TYPE_CODE); test_begin("dns service failure"); test_run_client_server(&http_client_set, @@ -2341,7 +2346,8 @@ static void test_dns_timeout(void) test_client_defaults(&http_client_set); http_client_set.request_timeout_msecs = 2000; http_client_set.connect_timeout_msecs = 2000; - http_client_set.dns_client_socket_path = "./dns-test"; + settings_root_override(set_root, "dns_client_socket_path", + "./dns-test", SETTINGS_OVERRIDE_TYPE_CODE); test_begin("dns timeout"); test_run_client_server(&http_client_set, @@ -2428,7 +2434,8 @@ static void test_dns_lookup_failure(void) struct http_client_settings http_client_set; test_client_defaults(&http_client_set); - http_client_set.dns_client_socket_path = "./dns-test"; + settings_root_override(set_root, "dns_client_socket_path", + "./dns-test", SETTINGS_OVERRIDE_TYPE_CODE); test_begin("dns lookup failure"); test_run_client_server(&http_client_set, @@ -2596,8 +2603,9 @@ static void test_dns_lookup_ttl(void) struct http_client_settings http_client_set; test_client_defaults(&http_client_set); - http_client_set.dns_client_socket_path = "./dns-test"; http_client_set.dns_ttl_msecs = 1000; + settings_root_override(set_root, "dns_client_socket_path", + "./dns-test", SETTINGS_OVERRIDE_TYPE_CODE); test_begin("dns lookup ttl"); test_run_client_server(&http_client_set, @@ -2870,11 +2878,12 @@ static void test_reconnect_failure(void) struct http_client_settings http_client_set; test_client_defaults(&http_client_set); - http_client_set.dns_client_socket_path = "./dns-test"; http_client_set.dns_ttl_msecs = 10000; http_client_set.max_idle_time_msecs = 1000; http_client_set.request_max_attempts = 1; http_client_set.request_timeout_msecs = 1000; + settings_root_override(set_root, "dns_client_socket_path", + "./dns-test", SETTINGS_OVERRIDE_TYPE_CODE); test_begin("reconnect failure"); test_run_client_server(&http_client_set, @@ -3025,7 +3034,8 @@ static void test_multi_ip_attempts(void) test_client_defaults(&http_client_set); http_client_set.connect_timeout_msecs = 1000; http_client_set.request_timeout_msecs = 1000; - http_client_set.dns_client_socket_path = "./dns-test"; + settings_root_override(set_root, "dns_client_socket_path", + "./dns-test", SETTINGS_OVERRIDE_TYPE_CODE); http_client_set.max_connect_attempts = 4; test_begin("multi IP attempts (connection refused)"); @@ -3420,11 +3430,12 @@ static void test_idle_hosts(void) struct http_client_settings http_client_set; test_client_defaults(&http_client_set); - http_client_set.dns_client_socket_path = "./dns-test"; http_client_set.dns_ttl_msecs = 400; http_client_set.max_parallel_connections = 1; http_client_set.max_idle_time_msecs = 100; http_client_set.request_max_attempts = 2; + settings_root_override(set_root, "dns_client_socket_path", + "./dns-test", SETTINGS_OVERRIDE_TYPE_CODE); test_begin("idle hosts"); test_run_client_server(&http_client_set, @@ -3792,6 +3803,9 @@ int main(int argc, char *argv[]) lib_init(); main_init(); + struct http_client_context *cctx = http_client_get_global_context(); + set_root = settings_root_init(); + event_set_ptr(cctx->event, SETTINGS_EVENT_ROOT, set_root); while ((c = getopt(argc, argv, "D")) > 0) { switch (c) { @@ -3813,6 +3827,9 @@ int main(int argc, char *argv[]) ret = test_run(test_functions); test_subprocesses_deinit(); + event_set_ptr(cctx->event, SETTINGS_EVENT_ROOT, NULL); + settings_root_deinit(&set_root); + main_deinit(); lib_deinit(); diff --git a/src/lib-http/test-http-client.c b/src/lib-http/test-http-client.c index 6950268d90..87577c21ec 100644 --- a/src/lib-http/test-http-client.c +++ b/src/lib-http/test-http-client.c @@ -10,10 +10,14 @@ #include "dns-lookup.h" #include "iostream-ssl.h" #include "iostream-openssl.h" +#include "settings.h" +#include "lib-event-private.h" #include #include +static struct settings_root *set_root; + struct http_test_request { struct io *io; struct istream *payload; @@ -346,19 +350,34 @@ static void run_http_post(struct http_client *http_client, const char *url_str, http_client_request_submit(http_req); } +static bool +test_event_callback(struct event *event, + enum event_callback_type type, + struct failure_context *ctx ATTR_UNUSED, + const char *fmt ATTR_UNUSED, + va_list args ATTR_UNUSED) +{ + if (type == EVENT_CALLBACK_TYPE_CREATE && event->parent == NULL) + event_set_ptr(event, SETTINGS_EVENT_ROOT, set_root); + return TRUE; +} + int main(int argc, char *argv[]) { struct dns_client *dns_client; - struct dns_client_settings dns_set; - struct dns_client_parameters dns_params; struct http_client_settings http_set; struct http_client_context *http_cctx; struct http_client *http_client1, *http_client2, *http_client3, *http_client4; struct ssl_iostream_settings ssl_set; struct stat st; const char *error; + const char *dns_client_socket_path = PKG_RUNDIR"/dns-client"; lib_init(); + set_root = settings_root_init(); + settings_root_override(set_root, "dns_client_timeout", "30s", SETTINGS_OVERRIDE_TYPE_CODE); + event_register_callback(test_event_callback); + ssl_iostream_openssl_init(); ioloop = io_loop_create(); io_loop_set_running(ioloop); @@ -367,19 +386,21 @@ int main(int argc, char *argv[]) the binary in all systems (but is in others! so linking safe-memset.lo directly causes them to fail.) If safe_memset() isn't included, libssl-iostream plugin loading fails. */ - i_zero_safe(&dns_set); - dns_set.dns_client_socket_path = PKG_RUNDIR"/dns-client"; - dns_set.timeout_msecs = 30*1000; - dns_params.idle_timeout_msecs = UINT_MAX; + struct dns_client_parameters params = { + .idle_timeout_msecs = UINT_MAX, + }; + struct event *event = event_create(NULL); /* check if there is a DNS client */ - if (access(dns_set.dns_client_socket_path, R_OK|W_OK) == 0) { - dns_client = dns_client_init(&dns_set, &dns_params, NULL); + if (access(dns_client_socket_path, R_OK|W_OK) == 0) { + if (dns_client_init(¶ms, event, &dns_client, &error) < 0) + i_fatal("%s", error); if (dns_client_connect(dns_client, &error) < 0) i_fatal("Couldn't initialize DNS client: %s", error); } else { dns_client = NULL; + settings_root_override(set_root, "dns_client_socket_path", "", SETTINGS_OVERRIDE_TYPE_CODE); } i_zero(&ssl_set); ssl_set.pool = null_pool; @@ -409,13 +430,11 @@ int main(int argc, char *argv[]) http_cctx = http_client_context_create(); - struct event *event = event_create(NULL); event_set_forced_debug(event, TRUE); http_client1 = http_client_init_shared(http_cctx, &http_set, event); http_client2 = http_client_init_shared(http_cctx, &http_set, event); http_client3 = http_client_init_shared(http_cctx, &http_set, event); http_client4 = http_client_init_shared(http_cctx, &http_set, event); - event_unref(&event); http_client_set_ssl_settings(http_client1, &ssl_set); http_client_set_ssl_settings(http_client2, &ssl_set); @@ -473,6 +492,8 @@ int main(int argc, char *argv[]) http_client_deinit(&http_client2); http_client_deinit(&http_client3); http_client_deinit(&http_client4); + settings_root_deinit(&set_root); + event_unref(&event); http_client_context_unref(&http_cctx); @@ -482,5 +503,6 @@ int main(int argc, char *argv[]) io_loop_destroy(&ioloop); ssl_iostream_context_cache_free(); ssl_iostream_openssl_deinit(); + event_unregister_callback(test_event_callback); lib_deinit(); } diff --git a/src/lib-imap-client/imapc-client-private.h b/src/lib-imap-client/imapc-client-private.h index 3275f2c011..98bbb5b630 100644 --- a/src/lib-imap-client/imapc-client-private.h +++ b/src/lib-imap-client/imapc-client-private.h @@ -42,9 +42,6 @@ struct imapc_client { struct ioloop *ioloop; bool stop_on_state_finish; - /* Set to imapc_settings attributes with possible override by the - imapc_parameters. */ - const char *dns_client_socket_path; const char *imapc_rawlog_dir; const char *password; }; diff --git a/src/lib-imap-client/imapc-client.c b/src/lib-imap-client/imapc-client.c index 0f39961d4e..cb047e10ad 100644 --- a/src/lib-imap-client/imapc-client.c +++ b/src/lib-imap-client/imapc-client.c @@ -70,11 +70,6 @@ imapc_client_init(const struct imapc_parameters *params, p_strdup(pool, params->temp_path_prefix); client->params.flags = params->flags; - /* Set the overridden parameter only if it is set. */ - client->dns_client_socket_path = - (params->override_dns_client_socket_path != NULL) ? - p_strdup(pool, params->override_dns_client_socket_path) : - p_strdup(pool, client->set->dns_client_socket_path); client->imapc_rawlog_dir = (params->override_rawlog_dir != NULL) ? p_strdup(pool, params->override_rawlog_dir) : diff --git a/src/lib-imap-client/imapc-connection.c b/src/lib-imap-client/imapc-connection.c index d6438efcda..a9a49a52a0 100644 --- a/src/lib-imap-client/imapc-connection.c +++ b/src/lib-imap-client/imapc-connection.c @@ -18,6 +18,7 @@ #include "imap-parser.h" #include "imapc-client-private.h" #include "imapc-connection.h" +#include "settings.h" #include #include @@ -1922,10 +1923,7 @@ imapc_connection_dns_callback(const struct dns_lookup_result *result, void imapc_connection_connect(struct imapc_connection *conn) { - struct dns_client_settings dns_set; - struct ip_addr ip, *ips; - unsigned int ips_count; - int ret; + struct ip_addr ip; if (conn->fd != -1 || conn->dns_lookup != NULL) return; @@ -1952,10 +1950,6 @@ void imapc_connection_connect(struct imapc_connection *conn) (conn->reconnect_ok ? "true" : "false"), (long)conn->last_connect.tv_sec); - i_zero(&dns_set); - dns_set.dns_client_socket_path = conn->client->dns_client_socket_path; - dns_set.timeout_msecs = conn->client->set->imapc_connection_timeout_interval_msecs; - imapc_connection_set_state(conn, IMAPC_CONNECTION_STATE_CONNECTING); if (conn->ips_count > 0) { /* do nothing */ @@ -1967,21 +1961,8 @@ void imapc_connection_connect(struct imapc_connection *conn) conn->ips_count = 1; conn->ips = i_new(struct ip_addr, conn->ips_count); conn->ips[0] = ip; - } else if (*dns_set.dns_client_socket_path == '\0') { - ret = net_gethostbyname(conn->client->set->imapc_host, - &ips, &ips_count); - if (ret != 0) { - e_error(conn->event, "net_gethostbyname(%s) failed: %s", - conn->client->set->imapc_host, - net_gethosterror(ret)); - imapc_connection_set_disconnected(conn); - return; - } - conn->ips_count = ips_count; - conn->ips = i_new(struct ip_addr, ips_count); - memcpy(conn->ips, ips, ips_count * sizeof(*ips)); } else { - (void)dns_lookup(conn->client->set->imapc_host, &dns_set, NULL, + (void)dns_lookup(conn->client->set->imapc_host, NULL, conn->event, imapc_connection_dns_callback, conn, &conn->dns_lookup); return; diff --git a/src/lib-imap-client/imapc-settings.c b/src/lib-imap-client/imapc-settings.c index 74db173453..31880b9c8b 100644 --- a/src/lib-imap-client/imapc-settings.c +++ b/src/lib-imap-client/imapc-settings.c @@ -43,8 +43,6 @@ static const struct setting_define imapc_setting_defines[] = { DEF(STR, pop3_deleted_flag), - DEF(STR_HIDDEN, dns_client_socket_path), - SETTING_DEFINE_LIST_END }; @@ -70,8 +68,6 @@ static const struct imapc_settings imapc_default_settings = { .imapc_max_line_length = SET_SIZE_UNLIMITED, .pop3_deleted_flag = "", - - .dns_client_socket_path = "dns-client", }; static const struct setting_keyvalue imapc_default_settings_keyvalue[] = { diff --git a/src/lib-imap-client/imapc-settings.h b/src/lib-imap-client/imapc-settings.h index 352217d0c5..2d102ef403 100644 --- a/src/lib-imap-client/imapc-settings.h +++ b/src/lib-imap-client/imapc-settings.h @@ -59,8 +59,6 @@ struct imapc_settings { const char *pop3_deleted_flag; - const char *dns_client_socket_path; - enum imapc_features parsed_features; unsigned int throttle_init_msecs; unsigned int throttle_max_msecs; diff --git a/src/lib-lua/dlua-dovecot-http.c b/src/lib-lua/dlua-dovecot-http.c index 3b7b01bf9e..fe793f7ef1 100644 --- a/src/lib-lua/dlua-dovecot-http.c +++ b/src/lib-lua/dlua-dovecot-http.c @@ -13,6 +13,7 @@ #include "settings-parser.h" #include "master-service.h" #include "master-service-settings.h" +#include "dns-lookup.h" #define DLUA_DOVECOT_HTTP "http" #define DLUA_HTTP_CLIENT "struct http_client" @@ -447,6 +448,8 @@ static int parse_client_settings(lua_State *L, struct settings_instance *instanc settings_override(instance, real_key, value, SETTINGS_OVERRIDE_TYPE_CODE); } else if (setting_parser_info_find_key(&ssl_setting_parser_info, key, &idx)) { settings_override(instance, key, value, SETTINGS_OVERRIDE_TYPE_CODE); + } else if (setting_parser_info_find_key(&dns_client_setting_parser_info, key, &idx)) { + settings_override(instance, key, value, SETTINGS_OVERRIDE_TYPE_CODE); } else { *error_r = t_strdup_printf("%s is unknown setting", key); } diff --git a/src/lib-lua/test-dns-lua.c b/src/lib-lua/test-dns-lua.c index 9cfc1c0e47..7125bab6b9 100644 --- a/src/lib-lua/test-dns-lua.c +++ b/src/lib-lua/test-dns-lua.c @@ -38,18 +38,22 @@ static void test_dns_lua_deinit(void) static void test_dns_lua_common(const char *luascript) { - const struct dns_client_settings set = { - .dns_client_socket_path = TEST_DNS_SERVER_SOCKET_PATH, - .timeout_msecs = 1000, + static const char *const set_dns_test[] = { + "dns_client_socket_path", TEST_DNS_SERVER_SOCKET_PATH, + "dns_client_timeout", "1s", + "base_dir", "", + NULL }; + const char *error; struct settings_simple test_set; - settings_simple_init(&test_set, NULL); + settings_simple_init(&test_set, set_dns_test); - struct dns_client *client = dns_client_init(&set, NULL, NULL); + struct dns_client *client; + if (dns_client_init(NULL, test_set.event, &client, &error) < 0) + i_fatal("%s", error); struct dlua_script *script; - const char *error; if (dlua_script_create_string(luascript, &script, test_set.event, &error) < 0) i_fatal("dlua_script_create_string() failed: %s", error); if (dlua_script_init(script, &error) < 0) diff --git a/src/lib-program-client/program-client-remote.c b/src/lib-program-client/program-client-remote.c index c2629c65f3..b32d7339ce 100644 --- a/src/lib-program-client/program-client-remote.c +++ b/src/lib-program-client/program-client-remote.c @@ -251,7 +251,6 @@ struct program_client_remote { struct program_client client; const char *address; - struct dns_client_settings dns_set; struct dns_lookup *lookup; unsigned int ips_count; unsigned int ips_left; @@ -528,12 +527,8 @@ static int program_client_net_connect_init(struct program_client *pclient) if (pclient->params.dns_client_socket_path != NULL) { e_debug(pclient->event, "Performing asynchronous DNS lookup"); - prclient->dns_set.dns_client_socket_path = - pclient->params.dns_client_socket_path; - prclient->dns_set.timeout_msecs = - pclient->params.client_connect_timeout_msecs; - (void)dns_lookup(prclient->address, &prclient->dns_set, - NULL, pclient->event, + (void)dns_lookup(prclient->address, NULL, + pclient->event, program_client_net_connect_resolved, prclient, &prclient->lookup); return 0; diff --git a/src/lib-smtp/smtp-client-connection.c b/src/lib-smtp/smtp-client-connection.c index 48e1aea924..5d0abe24e4 100644 --- a/src/lib-smtp/smtp-client-connection.c +++ b/src/lib-smtp/smtp-client-connection.c @@ -1875,8 +1875,6 @@ smtp_client_connection_dns_callback(const struct dns_lookup_result *result, static void smtp_client_connection_lookup_ip(struct smtp_client_connection *conn) { - struct dns_client_settings dns_set; - if (conn->ips_count != 0) return; @@ -1889,18 +1887,12 @@ smtp_client_connection_lookup_ip(struct smtp_client_connection *conn) conn->event, smtp_client_connection_dns_callback, conn, &conn->dns_lookup); - } else if (conn->set.dns_client_socket_path != NULL) { - i_zero(&dns_set); - dns_set.dns_client_socket_path = - conn->set.dns_client_socket_path; - dns_set.timeout_msecs = conn->set.connect_timeout_msecs; + } else { e_debug(conn->event, "Performing asynchronous DNS lookup"); - (void)dns_lookup(conn->host, &dns_set, NULL, conn->event, + + (void)dns_lookup(conn->host, NULL, conn->event, smtp_client_connection_dns_callback, conn, &conn->dns_lookup); - } else { - /* FIXME: fully removed in the following commits */ - i_unreached(); } } diff --git a/src/lib-smtp/smtp-client.c b/src/lib-smtp/smtp-client.c index a068ec580a..8ddf51047c 100644 --- a/src/lib-smtp/smtp-client.c +++ b/src/lib-smtp/smtp-client.c @@ -43,8 +43,6 @@ struct smtp_client *smtp_client_init(const struct smtp_client_settings *set) } client->set.dns_client = set->dns_client; - client->set.dns_client_socket_path = - p_strdup(pool, set->dns_client_socket_path); client->set.rawlog_dir = p_strdup_empty(pool, set->rawlog_dir); if (set->ssl != NULL) { diff --git a/src/lib-smtp/smtp-client.h b/src/lib-smtp/smtp-client.h index 9f3c48ca06..32148fbc7b 100644 --- a/src/lib-smtp/smtp-client.h +++ b/src/lib-smtp/smtp-client.h @@ -58,7 +58,6 @@ struct smtp_client_settings { const char *const *extra_capabilities; struct dns_client *dns_client; - const char *dns_client_socket_path; /* SSL settings; if NULL, settings_get() is used automatically */ const struct ssl_iostream_settings *ssl; diff --git a/src/lib-smtp/test-smtp-client-errors.c b/src/lib-smtp/test-smtp-client-errors.c index 8e99872d84..260ba8d82e 100644 --- a/src/lib-smtp/test-smtp-client-errors.c +++ b/src/lib-smtp/test-smtp-client-errors.c @@ -20,6 +20,8 @@ #include "smtp-client.h" #include "smtp-client-connection.h" #include "smtp-client-transaction.h" +#include "settings.h" +#include "smtp-client-private.h" #include #include @@ -57,6 +59,11 @@ struct server_connection { bool version_sent:1; }; +struct test_smtp_client_settings { + const char *dns_client_socket_path; + const char *dns_client_timeout; +}; + typedef void (*test_server_init_t)(unsigned int index); typedef bool (*test_client_init_t)(const struct smtp_client_settings *client_set); @@ -101,7 +108,8 @@ static void test_server_run(unsigned int index); static void server_connection_deinit(struct server_connection **_conn); /* client */ -static void test_client_defaults(struct smtp_client_settings *smtp_set); +static void test_client_defaults(struct smtp_client_settings *smtp_set, + struct test_smtp_client_settings *test_set); static void test_client_deinit(void); /* test*/ @@ -112,6 +120,14 @@ test_run_client_server(const struct smtp_client_settings *client_set, unsigned int server_tests_count, test_dns_init_t dns_test) ATTR_NULL(3); +static void test_root_event_free(struct event *event) +{ + struct settings_root *set_root = + event_get_ptr(event, SETTINGS_EVENT_ROOT); + settings_root_deinit(&set_root); + event_unref(&event); +} + /* * Host lookup failed */ @@ -179,7 +195,7 @@ static void test_host_lookup_failed(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("host lookup failed"); test_run_client_server(&smtp_client_set, @@ -262,7 +278,7 @@ static void test_connection_refused(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("connection refused"); test_run_client_server(&smtp_client_set, @@ -371,7 +387,7 @@ static void test_connection_lost_prematurely(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("connection lost prematurely"); test_run_client_server(&smtp_client_set, @@ -456,7 +472,7 @@ static void test_connection_timed_out(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); smtp_client_set.connect_timeout_msecs = 1000; test_begin("connection timed out"); @@ -648,7 +664,7 @@ static void test_broken_payload(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); smtp_client_set.connect_timeout_msecs = 1000; test_begin("broken payload"); @@ -657,12 +673,18 @@ static void test_broken_payload(void) test_server_broken_payload, 1, NULL); test_end(); + test_client_defaults(&smtp_client_set, NULL); + smtp_client_set.connect_timeout_msecs = 1000; + test_begin("broken payload (later)"); test_run_client_server(&smtp_client_set, test_client_broken_payload_later, test_server_broken_payload, 1, NULL); test_end(); + test_client_defaults(&smtp_client_set, NULL); + smtp_client_set.connect_timeout_msecs = 1000; + test_begin("broken payload (later, chunking)"); test_run_client_server(&smtp_client_set, test_client_broken_payload_later, @@ -894,7 +916,7 @@ static void test_connection_lost(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("connection lost"); test_run_client_server(&smtp_client_set, @@ -1248,7 +1270,7 @@ static void test_unexpected_reply(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("unexpected reply"); test_run_client_server(&smtp_client_set, @@ -1343,7 +1365,7 @@ static void test_partial_reply(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("partial reply"); test_run_client_server(&smtp_client_set, @@ -1733,7 +1755,7 @@ static void test_premature_reply(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("premature reply"); test_run_client_server(&smtp_client_set, @@ -2072,7 +2094,7 @@ static void test_early_data_reply(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("early data reply"); test_run_client_server(&smtp_client_set, @@ -2170,7 +2192,7 @@ static void test_bad_reply(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("bad reply"); test_run_client_server(&smtp_client_set, @@ -2296,7 +2318,7 @@ static void test_bad_greeting(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("bad greeting"); test_run_client_server(&smtp_client_set, @@ -2382,7 +2404,7 @@ static void test_command_timed_out(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); smtp_client_set.command_timeout_msecs = 1000; test_begin("command timed out"); @@ -2493,7 +2515,7 @@ static void test_command_aborted_early(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("command aborted early"); test_run_client_server(&smtp_client_set, @@ -2591,7 +2613,7 @@ static void test_client_deinit_early(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("client deinit early"); @@ -2667,9 +2689,11 @@ test_client_dns_service_failure(const struct smtp_client_settings *client_set) static void test_dns_service_failure(void) { struct smtp_client_settings smtp_client_set; + struct test_smtp_client_settings test_set = { + .dns_client_socket_path = "./frop", + }; - test_client_defaults(&smtp_client_set); - smtp_client_set.dns_client_socket_path = "./frop"; + test_client_defaults(&smtp_client_set, &test_set); test_begin("dns service failure"); test_run_client_server(&smtp_client_set, @@ -2762,10 +2786,11 @@ test_client_dns_timeout(const struct smtp_client_settings *client_set) static void test_dns_timeout(void) { struct smtp_client_settings smtp_client_set; + struct test_smtp_client_settings test_set = { + .dns_client_timeout = "2s", + }; - test_client_defaults(&smtp_client_set); - smtp_client_set.connect_timeout_msecs = 2000; - smtp_client_set.dns_client_socket_path = "./dns-test"; + test_client_defaults(&smtp_client_set, &test_set); test_begin("dns timeout"); test_run_client_server(&smtp_client_set, @@ -2858,8 +2883,7 @@ static void test_dns_lookup_failure(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); - smtp_client_set.dns_client_socket_path = "./dns-test"; + test_client_defaults(&smtp_client_set, NULL); test_begin("dns lookup failure"); test_run_client_server(&smtp_client_set, @@ -3223,7 +3247,7 @@ static void test_authentication(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("authentication"); test_run_client_server(&smtp_client_set, @@ -3500,7 +3524,7 @@ static void test_transaction_timeout(void) { struct smtp_client_settings smtp_client_set; - test_client_defaults(&smtp_client_set); + test_client_defaults(&smtp_client_set, NULL); test_begin("transaction timeout"); test_run_client_server(&smtp_client_set, @@ -3642,8 +3666,7 @@ static void test_invalid_ssl_certificate(void) /* ssl settings */ ssl_iostream_test_settings_client(&ssl_set); - test_client_defaults(&smtp_client_set); - smtp_client_set.dns_client_socket_path = "./dns-test"; + test_client_defaults(&smtp_client_set, NULL); smtp_client_set.ssl = &ssl_set; test_begin("invalid ssl certificate"); @@ -3688,12 +3711,29 @@ static void (*const test_functions[])(void) = { * Test client */ -static void test_client_defaults(struct smtp_client_settings *smtp_set) +static void test_client_defaults(struct smtp_client_settings *smtp_set, + struct test_smtp_client_settings *test_set) { /* client settings */ i_zero(smtp_set); smtp_set->my_hostname = "frop.example.com"; smtp_set->debug = debug; + + struct event *event = event_create(NULL); + struct settings_root *set_root = settings_root_init(); + + const char *path = test_set != NULL && + test_set->dns_client_socket_path != NULL ? + test_set->dns_client_socket_path : "./dns-test"; + settings_root_override(set_root, "dns_client_socket_path", + path, SETTINGS_OVERRIDE_TYPE_CODE); + if (test_set != NULL && test_set->dns_client_timeout != NULL) { + settings_root_override(set_root, "dns_client_timeout", + test_set->dns_client_timeout, + SETTINGS_OVERRIDE_TYPE_CODE); + } + event_set_ptr(event, SETTINGS_EVENT_ROOT, set_root); + smtp_set->event_parent = event; } static void test_client_progress_timeout(void *context ATTR_UNUSED) @@ -4000,6 +4040,8 @@ static void test_server_run(unsigned int index) struct test_server_data { unsigned int index; test_server_init_t server_test; + test_dns_init_t dns_test; + struct event *root_event; }; static int test_open_server_fd(in_port_t *bind_port) @@ -4031,13 +4073,14 @@ static int test_run_server(struct test_server_data *data) if (debug) i_debug("Terminated"); + test_root_event_free(data->root_event); i_close_fd(&fd_listen); i_free(bind_ports); main_deinit(); return 0; } -static int test_run_dns(test_dns_init_t dns_test) +static int test_run_dns(struct test_server_data *data) { i_set_failure_prefix("DNS: "); @@ -4046,7 +4089,7 @@ static int test_run_dns(test_dns_init_t dns_test) test_subprocess_notify_signal_send_parent(SIGUSR1); ioloop = io_loop_create(); - dns_test(); + data->dns_test(); io_loop_destroy(&ioloop); if (debug) @@ -4055,6 +4098,7 @@ static int test_run_dns(test_dns_init_t dns_test) i_close_fd(&fd_listen); i_free(bind_ports); main_deinit(); + test_root_event_free(data->root_event); return 0; } @@ -4084,6 +4128,7 @@ test_run_client_server(const struct smtp_client_settings *client_set, unsigned int server_tests_count, test_dns_init_t dns_test) { + struct event *root_event = client_set->event_parent; unsigned int i; if (server_tests_count > 0) { @@ -4099,6 +4144,7 @@ test_run_client_server(const struct smtp_client_settings *client_set, i_zero(&data); data.index = i; data.server_test = server_test; + data.root_event = root_event; /* Fork server */ fd_listen = fds[i]; @@ -4111,6 +4157,10 @@ test_run_client_server(const struct smtp_client_settings *client_set, } if (dns_test != NULL) { + struct test_server_data data = { + .dns_test = dns_test, + .root_event = root_event, + }; int fd; i_unlink_if_exists("./dns-test"); @@ -4122,7 +4172,7 @@ test_run_client_server(const struct smtp_client_settings *client_set, /* Fork DNS service */ fd_listen = fd; test_subprocess_notify_signal_reset(SIGUSR1); - test_subprocess_fork(test_run_dns, dns_test, FALSE); + test_subprocess_fork(test_run_dns, &data, FALSE); test_subprocess_notify_signal_wait(SIGUSR1, TEST_SIGNALS_DEFAULT_TIMEOUT_MS); i_close_fd(&fd_listen); @@ -4136,6 +4186,7 @@ test_run_client_server(const struct smtp_client_settings *client_set, i_free(bind_ports); i_unlink_if_exists("./dns-test"); + test_root_event_free(root_event); } /* diff --git a/src/lib-storage/index/pop3c/pop3c-client.c b/src/lib-storage/index/pop3c/pop3c-client.c index 46696b9360..be75dea303 100644 --- a/src/lib-storage/index/pop3c/pop3c-client.c +++ b/src/lib-storage/index/pop3c/pop3c-client.c @@ -21,7 +21,6 @@ #include #define POP3C_MAX_INBUF_SIZE (1024*32) -#define POP3C_DNS_LOOKUP_TIMEOUT_MSECS (1000*30) #define POP3C_CONNECT_TIMEOUT_MSECS (1000*30) #define POP3C_COMMAND_TIMEOUT_MSECS (1000*60*5) @@ -241,8 +240,6 @@ static void pop3c_client_timeout(struct pop3c_client *client) static int pop3c_client_dns_lookup(struct pop3c_client *client) { - struct dns_client_settings dns_set; - i_assert(client->state == POP3C_CLIENT_STATE_CONNECTING); if (client->set.dns_client_socket_path[0] == '\0') { @@ -261,11 +258,7 @@ static int pop3c_client_dns_lookup(struct pop3c_client *client) client->ip = ips[0]; pop3c_client_connect_ip(client); } else { - i_zero(&dns_set); - dns_set.dns_client_socket_path = - client->set.dns_client_socket_path; - dns_set.timeout_msecs = POP3C_DNS_LOOKUP_TIMEOUT_MSECS; - if (dns_lookup(client->set.host, &dns_set, NULL, client->event, + if (dns_lookup(client->set.host, NULL, client->event, pop3c_dns_callback, client, &client->dns_lookup) < 0) return -1; diff --git a/src/lmtp/lmtp-proxy.c b/src/lmtp/lmtp-proxy.c index 9a8367c640..04c66af963 100644 --- a/src/lmtp/lmtp-proxy.c +++ b/src/lmtp/lmtp-proxy.c @@ -117,7 +117,6 @@ lmtp_proxy_init(struct client *client, i_zero(&lmtp_set); lmtp_set.my_hostname = client->my_domain; lmtp_set.extra_capabilities = extra_capabilities; - lmtp_set.dns_client_socket_path = dns_client_socket_path; lmtp_set.max_reply_size = LMTP_MAX_REPLY_SIZE; lmtp_set.rawlog_dir = client->lmtp_set->lmtp_proxy_rawlog_dir; diff --git a/src/submission/main.c b/src/submission/main.c index 632b83f11a..f9d7584da5 100644 --- a/src/submission/main.c +++ b/src/submission/main.c @@ -31,8 +31,6 @@ #include #include -#define DNS_CLIENT_SOCKET_PATH "dns-client" - #define LMTP_MASTER_FIRST_LISTEN_FD 3 #define IS_STANDALONE() \ @@ -358,7 +356,6 @@ int main(int argc, char *argv[]) struct smtp_server_settings smtp_server_set; struct smtp_client_settings smtp_client_set; const char *username = NULL, *auth_socket_path = "auth-master"; - const char *tmp_socket_path; const char *error; int c; @@ -443,14 +440,10 @@ int main(int argc, char *argv[]) smtp_server = smtp_server_init(&smtp_server_set); smtp_server_command_register(smtp_server, "BURL", cmd_burl, 0); - if (t_abspath(DNS_CLIENT_SOCKET_PATH, &tmp_socket_path, &error) < 0) - i_fatal("t_abspath(%s) failed: %s", DNS_CLIENT_SOCKET_PATH, error); - /* initialize SMTP client */ i_zero(&smtp_client_set); smtp_client_set.my_hostname = my_hostdomain(); smtp_client_set.debug = submission_debug; - smtp_client_set.dns_client_socket_path = tmp_socket_path; smtp_client = smtp_client_init(&smtp_client_set); if (!IS_STANDALONE())