diff --git a/dirmngr/dirmngr.c b/dirmngr/dirmngr.c index a11832746..ef30d2c3c 100644 --- a/dirmngr/dirmngr.c +++ b/dirmngr/dirmngr.c @@ -1383,6 +1383,7 @@ cleanup (void) { crl_cache_deinit (); cert_cache_deinit (1); + reload_dns_stuff (1); #if USE_LDAP ldapserver_list_free (opt.ldapservers); @@ -1689,6 +1690,7 @@ dirmngr_sighup_action (void) crl_cache_deinit (); cert_cache_init (); crl_cache_init (); + reload_dns_stuff (0); } diff --git a/dirmngr/dns-stuff.c b/dirmngr/dns-stuff.c index 0f1f0ede9..63951e5eb 100644 --- a/dirmngr/dns-stuff.c +++ b/dirmngr/dns-stuff.c @@ -133,8 +133,13 @@ struct libdns_s struct sockaddr_storage socks_host; } libdns; + +/* If this flag is set, libdns shall be reinited for the next use. */ +static int libdns_reinit_pending; + #endif /*USE_LIBDNS*/ + /* Calling this function with YES set to True forces the use of the * standard resolver even if dirmngr has been built with support for * an alternative resolver. */ @@ -159,6 +164,7 @@ void enable_recursive_resolver (int yes) { recursive_resolver = yes; + libdns_reinit_pending = 1; } @@ -203,6 +209,7 @@ set_dns_nameserver (const char *ipaddr) strncpy (tor_nameserver, ipaddr? ipaddr : DEFAULT_NAMESERVER, sizeof tor_nameserver -1); tor_nameserver[sizeof tor_nameserver -1] = 0; + libdns_reinit_pending = 1; } @@ -315,6 +322,9 @@ libdns_init (void) const char *fname; char *cfgstr = NULL; + if (libdns.resolv_conf) + return 0; /* Already initialized. */ + memset (&ld, 0, sizeof ld); ld.resolv_conf = dns_resconf_open (&derr); @@ -409,6 +419,41 @@ libdns_init (void) #endif /*USE_LIBDNS*/ +#ifdef USE_LIBDNS +/* Deinitialize libdns. */ +static void +libdns_deinit (void) +{ + struct libdns_s ld; + + if (!libdns.resolv_conf) + return; /* Not initialized. */ + + ld = libdns; + memset (&libdns, 0, sizeof libdns); + dns_hints_close (ld.hints); + dns_hosts_close (ld.hosts); + dns_resconf_close (ld.resolv_conf); +} +#endif /*USE_LIBDNS*/ + +/* SIGHUP action handler for this module. With FORCE set objects are + * all immediately released. */ +void +reload_dns_stuff (int force) +{ + if (force) + { +#ifdef USE_LIBDNS + libdns_deinit (); +#endif + libdns_reinit_pending = 0; + } + else + libdns_reinit_pending = 1; +} + + #ifdef USE_LIBDNS /* * Initialize libdns if needed and open a dns_resolver context. @@ -424,6 +469,12 @@ libdns_res_open (struct dns_resolver **r_res) *r_res = NULL; + if (libdns_reinit_pending) + { + libdns_reinit_pending = 0; + libdns_deinit (); + } + err = libdns_init (); if (err) return err; diff --git a/dirmngr/dns-stuff.h b/dirmngr/dns-stuff.h index 20a4b41ef..2be972a53 100644 --- a/dirmngr/dns-stuff.h +++ b/dirmngr/dns-stuff.h @@ -116,6 +116,8 @@ gpg_error_t enable_dns_tormode (int new_circuit); next DNS query. Note that this is only used in Tor mode. */ void set_dns_nameserver (const char *ipaddr); +/* SIGHUP action handler for this module. */ +void reload_dns_stuff (int force); void free_dns_addrinfo (dns_addrinfo_t ai); diff --git a/dirmngr/t-dns-stuff.c b/dirmngr/t-dns-stuff.c index 224e9484d..531513800 100644 --- a/dirmngr/t-dns-stuff.c +++ b/dirmngr/t-dns-stuff.c @@ -217,7 +217,6 @@ main (int argc, char **argv) { printf ("CNAME found: '%s'\n", cname); } - xfree (cname); } else if (opt_srv) @@ -291,6 +290,7 @@ main (int argc, char **argv) free_dns_addrinfo (aibuf); } + reload_dns_stuff (1); /* Release objects. */ return 0; }