be limited by the DNS TTL on the TLSA records).
-For client-side DANE there is a new smtp transport option,
-hosts_try_dane. It does the obvious thing.
-[ may add a hosts_require_dane, too? ]
-[ should it be domain-based rather than host-based? ]
+For client-side DANE there are two new smtp transport options,
+hosts_try_dane and hosts_require_dane. They do the obvious thing.
+[ should they be domain-based rather than host-based? ]
DANE will only be usable if the target host has DNSSEC-secured
MX, A and TLSA records.
#endif
#ifdef EXPERIMENTAL_DANE
-/*XXX TBD: test for transport options, and for TLSA records */
-/*dane = TRUE;*/
-
-# ifdef notyet
dane_required = verify_check_this_host(&ob->hosts_require_dane, NULL,
host->name, host->address, NULL) == OK;
-# else
-dane_required = FALSE;
-#endif
if (host->dnssec == DS_YES)
{
{
/* move this out to host.c given the similarity to dns_lookup() ? */
uschar buffer[300];
- int prefix_length; /* why do we want this? */
uschar * fullname = buffer;
/* TLSA lookup string */
- (void)sprintf(CS buffer, "_%d._tcp.%n%.256s", host->port, &prefix_length,
+ (void)sprintf(CS buffer, "_%d._tcp.%.256s", host->port,
host->name);
switch (rc = dns_lookup(&tlsa_dnsa, buffer, T_TLSA, &fullname))
case DNS_FAIL:
if (dane_required)
{
- /* log that TLSA lookup failed */
+ log_write(0, LOG_MAIN, "DANE error: TLSA lookup failed");
return FAIL;
}
break;
case DNS_SUCCEED:
if (!dns_is_secure(&tlsa_dnsa))
{
- /*log it - tlsa should never be non-dnssec */
+ log_write(0, LOG_MAIN, "DANE error: TLSA lookup not DNSSEC");
return DEFER;
}
dane = TRUE;
}
}
}
-else if (dane_required && !dane)
+else if (dane_required)
{
- /* log that dnssec pre-req failed. Hmm - what? */
+ /* Hmm - what lookup, precisely? */
+ log_write(0, LOG_MAIN, "DANE error: previous lookup not DNSSEC");
return FAIL;
}
{ "hosts_require_auth", opt_stringptr,
(void *)offsetof(smtp_transport_options_block, hosts_require_auth) },
#ifdef SUPPORT_TLS
+# ifdef EXPERIMENTAL_DANE
+ { "hosts_require_dane", opt_stringptr,
+ (void *)offsetof(smtp_transport_options_block, hosts_require_dane) },
+# endif
# ifndef DISABLE_OCSP
{ "hosts_require_ocsp", opt_stringptr,
(void *)offsetof(smtp_transport_options_block, hosts_require_ocsp) },
#endif
{ "hosts_try_auth", opt_stringptr,
(void *)offsetof(smtp_transport_options_block, hosts_try_auth) },
-#ifdef EXPERIMENTAL_DANE
+#if defined(SUPPORT_TLS) && defined(EXPERIMENTAL_DANE)
{ "hosts_try_dane", opt_stringptr,
(void *)offsetof(smtp_transport_options_block, hosts_try_dane) },
#endif
NULL, /* hosts_require_auth */
#ifdef EXPERIMENTAL_DANE
NULL, /* hosts_try_dane */
+ NULL, /* hosts_require_dane */
#endif
#ifndef DISABLE_PRDR
NULL, /* hosts_try_prdr */
/* If the host is required to use a secure channel, ensure that we
have one. */
-else if (verify_check_this_host(&(ob->hosts_require_tls), NULL, host->name,
- host->address, NULL) == OK)
+else if ( verify_check_this_host(&(ob->hosts_require_tls), NULL, host->name,
+ host->address, NULL) == OK
+#ifdef EXPERIMENTAL_DANE
+ || verify_check_this_host(&(ob->hosts_require_dane), NULL, host->name,
+ host->address, NULL) == OK
+#endif
+ )
{
save_errno = ERRNO_TLSREQUIRED;
message = string_sprintf("a TLS session is required for %s [%s], but %s",
happens inside smtp_deliver().] */
#ifdef SUPPORT_TLS
- if (rc == DEFER && first_addr->basic_errno == ERRNO_TLSFAILURE &&
- ob->tls_tempfail_tryclear &&
- verify_check_this_host(&(ob->hosts_require_tls), NULL, host->name,
- host->address, NULL) != OK)
+ if ( rc == DEFER
+ && first_addr->basic_errno == ERRNO_TLSFAILURE
+ && ob->tls_tempfail_tryclear
+ && verify_check_this_host(&(ob->hosts_require_tls), NULL, host->name,
+ host->address, NULL) != OK
+#ifdef EXPERIMENTAL_DANE
+ && verify_check_this_host(&(ob->hosts_require_dane), NULL, host->name,
+ host->address, NULL) != OK
+#endif
+ )
{
log_write(0, LOG_MAIN, "TLS session failure: delivering unencrypted "
"to %s [%s] (not in hosts_require_tls)", host->name, host->address);
uschar *hosts_require_auth;
#ifdef EXPERIMENTAL_DANE
uschar *hosts_try_dane;
+ uschar *hosts_require_dane;
#endif
#ifndef DISABLE_PRDR
uschar *hosts_try_prdr;
if the options permit it for this host. */
if (rc != OK)
{
- if (rc == DEFER && ob->tls_tempfail_tryclear && !smtps &&
- verify_check_this_host(&(ob->hosts_require_tls), NULL, host->name,
- host->address, NULL) != OK)
+ if ( rc == DEFER
+ && ob->tls_tempfail_tryclear
+ && !smtps
+ && verify_check_this_host(&(ob->hosts_require_tls), NULL,
+ host->name, host->address, NULL) != OK
+#ifdef EXPERIMENTAL_DANE
+ && verify_check_this_host(&(ob->hosts_require_dane), NULL,
+ host->name, host->address, NULL) != OK
+#endif
+ )
{
(void)close(inblock.sock);
log_write(0, LOG_MAIN, "TLS session failure: delivering unencrypted "
/* If the host is required to use a secure channel, ensure that we have one. */
if (tls_out.active < 0)
- if (verify_check_this_host(&(ob->hosts_require_tls), NULL, host->name,
- host->address, NULL) == OK)
+ if ( verify_check_this_host(&(ob->hosts_require_tls), NULL, host->name,
+ host->address, NULL) == OK
+#ifdef EXPERIMENTAL_DANE
+ || verify_check_this_host(&(ob->hosts_require_dane), NULL, host->name,
+ host->address, NULL) == OK
+#endif
+ )
{
/*save_errno = ERRNO_TLSREQUIRED;*/
log_write(0, LOG_MAIN, "a TLS session is required for %s [%s], but %s",
# tls_privatekey = DIR/aux-fixed/cert2
# tls_verify_certificates = DIR/aux-fixed/cert2
+# hosts_try_dane = *
+ hosts_require_dane = *
+
# ----- Retry -----
exim CALLER@test.ex
Testing
****
-exim -qf
+exim -d+all -qf
****
killdaemon
exim -DSERVER=server -DNOTDAEMON -qf