From 0eb08b9fb339c5913c29e112933d13607e644fb4 Mon Sep 17 00:00:00 2001 From: Maurus Decimus <11444311+mdecimus@users.noreply.github.com> Date: Thu, 25 Jun 2026 19:24:10 +0200 Subject: [PATCH] Fix DANE: Treat DNSSEC `bogus` as a temporary failures to prevent downgrade attacks --- CHANGELOG.md | 11 + Cargo.lock | 66 ++-- crates/common/Cargo.toml | 4 +- crates/common/src/config/inner.rs | 14 +- crates/common/src/expr/functions/asynch.rs | 4 + crates/common/src/lib.rs | 11 +- crates/common/src/network/dns/resolve.rs | 8 +- crates/common/src/scripts/plugins/dns.rs | 4 + crates/coordinator/Cargo.toml | 2 +- crates/dav-proto/Cargo.toml | 2 +- crates/dav/Cargo.toml | 2 +- crates/directory/Cargo.toml | 2 +- crates/email/Cargo.toml | 2 +- crates/groupware/Cargo.toml | 2 +- crates/http-proto/Cargo.toml | 2 +- crates/http/Cargo.toml | 4 +- crates/http/src/api/diagnose.rs | 23 +- crates/imap-proto/Cargo.toml | 2 +- crates/imap/Cargo.toml | 2 +- crates/jmap-proto/Cargo.toml | 2 +- crates/jmap/Cargo.toml | 4 +- crates/main/Cargo.toml | 2 +- crates/managesieve/Cargo.toml | 2 +- crates/migration/Cargo.toml | 2 +- crates/nlp/Cargo.toml | 2 +- crates/pop3/Cargo.toml | 2 +- crates/registry/Cargo.toml | 4 +- crates/services/Cargo.toml | 2 +- crates/smtp/Cargo.toml | 4 +- crates/smtp/src/outbound/dane/dnssec.rs | 326 ++++++++++++++---- crates/smtp/src/outbound/delivery.rs | 378 ++++++++++++--------- crates/smtp/src/outbound/lookup.rs | 225 ++---------- crates/smtp/src/outbound/mod.rs | 10 +- crates/spam-filter/Cargo.toml | 4 +- crates/store/Cargo.toml | 2 +- crates/store/src/backend/postgres/main.rs | 4 +- crates/trc/Cargo.toml | 4 +- crates/trc/event-macro/Cargo.toml | 2 +- crates/trc/src/event/enums.rs | 6 +- crates/trc/src/event/enums_impl.rs | 15 + crates/types/Cargo.toml | 2 +- crates/utils/Cargo.toml | 4 +- crates/utils/proc-macros/Cargo.toml | 2 +- crates/utils/src/cache.rs | 8 +- resources/schema/schema.json.gz | Bin 146243 -> 146296 bytes resources/schema/schema.json.sha256 | 2 +- tests/Cargo.toml | 4 +- tests/resources/tls_cert.pem | 54 +-- tests/src/smtp/inbound/antispam.rs | 5 +- tests/src/smtp/lookup/expressions.rs | 3 +- tests/src/smtp/lookup/utils.rs | 54 +-- tests/src/smtp/management/queue.rs | 3 +- tests/src/smtp/outbound/dane.rs | 155 ++++++++- tests/src/smtp/outbound/extensions.rs | 3 +- tests/src/smtp/outbound/fallback_relay.rs | 3 +- tests/src/smtp/outbound/ip_lookup.rs | 3 +- tests/src/smtp/outbound/mta_sts.rs | 3 +- tests/src/smtp/outbound/smtp.rs | 3 +- tests/src/smtp/outbound/throttle.rs | 4 +- tests/src/smtp/outbound/tls.rs | 3 +- tests/src/smtp/queue/concurrent.rs | 4 +- tests/src/smtp/queue/virtualq.rs | 4 +- tests/src/utils/dns.rs | 67 ++-- 63 files changed, 948 insertions(+), 614 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 3d9babb9..61c6c49d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,17 @@ All notable changes to this project will be documented in this file. This project adheres to [Semantic Versioning](http://semver.org/). +## [0.16.12] - 2026-06-XX + +If you are upgrading from v0.16.x, replace the binary (or run `docker pull`). If you are upgrading from v0.15.x and below, please read the [upgrading documentation](https://github.com/stalwartlabs/stalwart/blob/main/UPGRADING/v0_16.md) for more information on how to upgrade from previous versions. + +## Added + +## Changed + +## Fixed +- DANE: Treat DNSSEC `bogus` as a temporary failures to prevent downgrade attacks. + ## [0.16.11] - 2026-06-25 If you are upgrading from v0.16.x, replace the binary (or run `docker pull`). If you are upgrading from v0.15.x and below, please read the [upgrading documentation](https://github.com/stalwartlabs/stalwart/blob/main/UPGRADING/v0_16.md) for more information on how to upgrade from previous versions. diff --git a/Cargo.lock b/Cargo.lock index 436d6481..75955e32 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1259,7 +1259,7 @@ dependencies = [ [[package]] name = "common" -version = "0.16.11" +version = "0.16.12" dependencies = [ "aes-gcm-siv", "ahash", @@ -1455,7 +1455,7 @@ checksum = "3d52eff69cd5e647efe296129160853a42795992097e8af39800e1060caeea9b" [[package]] name = "coordinator" -version = "0.16.11" +version = "0.16.12" dependencies = [ "async-nats", "futures", @@ -1808,7 +1808,7 @@ checksum = "a4ae5f15dda3c708c0ade84bfee31ccab44a3da4f88015ed22f63732abe300c8" [[package]] name = "dav" -version = "0.16.11" +version = "0.16.12" dependencies = [ "calcard", "chrono", @@ -1831,7 +1831,7 @@ dependencies = [ [[package]] name = "dav-proto" -version = "0.16.11" +version = "0.16.12" dependencies = [ "calcard", "chrono", @@ -2037,7 +2037,7 @@ dependencies = [ [[package]] name = "directory" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "argon2", @@ -2288,7 +2288,7 @@ dependencies = [ [[package]] name = "email" -version = "0.16.11" +version = "0.16.12" dependencies = [ "aes 0.9.1", "aes-gcm", @@ -2396,7 +2396,7 @@ dependencies = [ [[package]] name = "event_macro" -version = "0.16.11" +version = "0.16.12" dependencies = [ "proc-macro2", "quote", @@ -2912,7 +2912,7 @@ dependencies = [ [[package]] name = "groupware" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "calcard", @@ -3195,7 +3195,7 @@ dependencies = [ [[package]] name = "http" -version = "0.16.11" +version = "0.16.12" dependencies = [ "async-stream", "base64 0.22.1", @@ -3295,7 +3295,7 @@ dependencies = [ [[package]] name = "http_proto" -version = "0.16.11" +version = "0.16.12" dependencies = [ "common", "compact_str", @@ -3592,7 +3592,7 @@ checksum = "09e54e57b4c48b40f7aec75635392b12b3421fa26fe8b4332e63138ed278459c" [[package]] name = "imap" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "common", @@ -3619,7 +3619,7 @@ dependencies = [ [[package]] name = "imap_proto" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "chrono", @@ -3832,7 +3832,7 @@ dependencies = [ [[package]] name = "jmap" -version = "0.16.11" +version = "0.16.12" dependencies = [ "aes-gcm", "aes-gcm-siv", @@ -3920,7 +3920,7 @@ dependencies = [ [[package]] name = "jmap_proto" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "calcard", @@ -4379,9 +4379,9 @@ dependencies = [ [[package]] name = "mail-auth" -version = "0.9.2" +version = "0.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d3c5a279d798bf41bfcf94ee593a34b545fb2010ebf5cfce3416d6b4019f697" +checksum = "9e533fed1dd496906478a2ebf4700525da7579ef116f3e90812ca5832aedd158" dependencies = [ "aws-lc-rs", "flate2", @@ -4422,7 +4422,7 @@ dependencies = [ [[package]] name = "managesieve" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "common", @@ -4564,7 +4564,7 @@ checksum = "c797b9d6bb23aab2fc369c65f871be49214f5c759af65bde26ffaaa2b646b492" [[package]] name = "migration" -version = "0.16.11" +version = "0.16.12" dependencies = [ "base64 0.22.1", "common", @@ -4781,7 +4781,7 @@ dependencies = [ [[package]] name = "nlp" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "bincode 1.3.3", @@ -5585,7 +5585,7 @@ dependencies = [ [[package]] name = "pop3" -version = "0.16.11" +version = "0.16.12" dependencies = [ "common", "directory", @@ -5768,7 +5768,7 @@ dependencies = [ [[package]] name = "proc_macros" -version = "0.16.11" +version = "0.16.12" dependencies = [ "proc-macro2", "quote", @@ -6391,7 +6391,7 @@ checksum = "d6f6ff9a378485b298a5286656da665ba74413d36db0979633275d2e708145d4" [[package]] name = "registry" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "hashify", @@ -7276,7 +7276,7 @@ dependencies = [ [[package]] name = "services" -version = "0.16.11" +version = "0.16.12" dependencies = [ "aes-gcm", "aes-gcm-siv", @@ -7534,7 +7534,7 @@ checksum = "8ed6a63f02c8539c91a8685a86f4099661ba3da017932f6ebbea6de3f0fa7c90" [[package]] name = "smtp" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "base64 0.22.1", @@ -7636,7 +7636,7 @@ dependencies = [ [[package]] name = "spam-filter" -version = "0.16.11" +version = "0.16.12" dependencies = [ "common", "compact_str", @@ -7745,7 +7745,7 @@ checksum = "6ce2be8dc25455e1f91df71bfa12ad37d7af1092ae736f3a6cd0e37bc7810596" [[package]] name = "stalwart" -version = "0.16.11" +version = "0.16.12" dependencies = [ "common", "coordinator", @@ -7753,7 +7753,7 @@ dependencies = [ "directory", "email", "groupware", - "http 0.16.11", + "http 0.16.12", "http_proto", "imap", "jemallocator", @@ -7782,7 +7782,7 @@ checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f" [[package]] name = "store" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "arc-swap", @@ -8022,7 +8022,7 @@ dependencies = [ [[package]] name = "tests" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "async-trait", @@ -8046,7 +8046,7 @@ dependencies = [ "form_urlencoded", "futures", "groupware", - "http 0.16.11", + "http 0.16.12", "http-body-util", "http_proto", "hyper", @@ -8589,7 +8589,7 @@ dependencies = [ [[package]] name = "trc" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "base64 0.22.1", @@ -8682,7 +8682,7 @@ checksum = "b6f5e870be6c3b371b77fe0ee0bafb859fa4964b4404c27de1d380043c4dda20" [[package]] name = "types" -version = "0.16.11" +version = "0.16.12" dependencies = [ "blake3", "compact_str", @@ -8880,7 +8880,7 @@ checksum = "b6c140620e7ffbb22c2dee59cafe6084a59b5ffc27a8859a5f0d494b5d52b6be" [[package]] name = "utils" -version = "0.16.11" +version = "0.16.12" dependencies = [ "ahash", "arcstr", diff --git a/crates/common/Cargo.toml b/crates/common/Cargo.toml index 8e115eeb..66f8c99d 100644 --- a/crates/common/Cargo.toml +++ b/crates/common/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "common" -version = "0.16.11" +version = "0.16.12" edition = "2024" build = "build.rs" @@ -18,7 +18,7 @@ imap_proto = { path = "../imap-proto" } sieve-rs = { version = "0.7", features = ["rkyv", "serde"] } mail-parser = { version = "0.11", features = ["full_encoding"] } mail-builder = { version = "0.4" } -mail-auth = { version = "0.9", features = ["generate"] } +mail-auth = { version = "0.10", features = ["generate"] } smtp-proto = { version = "0.2", features = ["rkyv"] } dns-update = { version = "0.5" } calcard = { version = "0.3", features = ["rkyv"] } diff --git a/crates/common/src/config/inner.rs b/crates/common/src/config/inner.rs index cb2e7b20..86f71391 100644 --- a/crates/common/src/config/inner.rs +++ b/crates/common/src/config/inner.rs @@ -22,7 +22,7 @@ use crate::{ }; use ahash::{AHashMap, AHashSet}; use arc_swap::ArcSwap; -use mail_auth::{MX, Parameters, Txt}; +use mail_auth::{MX, Parameters, RecordSet, Txt}; use parking_lot::RwLock; use registry::schema::{prelude::ObjectType, structs}; use std::{ @@ -178,10 +178,6 @@ impl Caches { ((std::mem::size_of::() + 255) * 2) as u64, ), dns_tlsa: CacheWithTtl::new(cache.dns_tlsa, (std::mem::size_of::() + 255) as u64), - dns_dnssec: CacheWithTtl::new( - cache.dns_tlsa, - (std::mem::size_of::() + 255) as u64, - ), dns_mta_sts: CacheWithTtl::new( cache.dns_mta_sts, (std::mem::size_of::() + 255) as u64, @@ -203,10 +199,10 @@ impl Caches { '_, T, CacheWithTtl, Txt>, - CacheWithTtl, Arc<[MX]>>, - CacheWithTtl, Arc<[Ipv4Addr]>>, - CacheWithTtl, Arc<[Ipv6Addr]>>, - CacheWithTtl]>>, + CacheWithTtl, RecordSet>, + CacheWithTtl, RecordSet>, + CacheWithTtl, RecordSet>, + CacheWithTtl>>, > { Parameters { params, diff --git a/crates/common/src/expr/functions/asynch.rs b/crates/common/src/expr/functions/asynch.rs index aead9848..b66b99e0 100644 --- a/crates/common/src/expr/functions/asynch.rs +++ b/crates/common/src/expr/functions/asynch.rs @@ -218,6 +218,7 @@ impl Server { .map_err(|err| trc::Error::from(err).caused_by(trc::location!())) .map(|result| { result + .rrset .iter() .flat_map(|mx| { mx.exchanges.iter().map(|host| { @@ -256,6 +257,7 @@ impl Server { .map_err(|err| trc::Error::from(err).caused_by(trc::location!())) .map(|result| { result + .rrset .iter() .map(|host| Variable::from(host.to_compact_string())) .collect::>() @@ -271,6 +273,7 @@ impl Server { .map_err(|err| trc::Error::from(err).caused_by(trc::location!())) .map(|result| { result + .rrset .iter() .map(|ip| Variable::from(ip.to_compact_string())) .collect::>() @@ -286,6 +289,7 @@ impl Server { .map_err(|err| trc::Error::from(err).caused_by(trc::location!())) .map(|result| { result + .rrset .iter() .map(|ip| Variable::from(ip.to_compact_string())) .collect::>() diff --git a/crates/common/src/lib.rs b/crates/common/src/lib.rs index a4205619..f200e83a 100644 --- a/crates/common/src/lib.rs +++ b/crates/common/src/lib.rs @@ -39,7 +39,7 @@ use config::{ telemetry::Metrics, }; use ipc::{BroadcastEvent, PushEvent, QueueEvent, ReportingEvent}; -use mail_auth::{MX, Txt}; +use mail_auth::{MX, RecordSet, Txt}; use manager::application::Resource; use parking_lot::{Mutex, RwLock}; use rustls::sign::CertifiedKey; @@ -196,12 +196,11 @@ pub struct Caches { pub dkim_signers: Cache>, pub dns_txt: CacheWithTtl, Txt>, - pub dns_mx: CacheWithTtl, Arc<[MX]>>, - pub dns_ptr: CacheWithTtl]>>, - pub dns_ipv4: CacheWithTtl, Arc<[Ipv4Addr]>>, - pub dns_ipv6: CacheWithTtl, Arc<[Ipv6Addr]>>, + pub dns_mx: CacheWithTtl, RecordSet>, + pub dns_ptr: CacheWithTtl>>, + pub dns_ipv4: CacheWithTtl, RecordSet>, + pub dns_ipv6: CacheWithTtl, RecordSet>, pub dns_tlsa: CacheWithTtl, Arc>, - pub dns_dnssec: CacheWithTtl, bool>, pub dns_mta_sts: CacheWithTtl, Arc>, pub dns_rbl: CacheWithTtl, Option>>, diff --git a/crates/common/src/network/dns/resolve.rs b/crates/common/src/network/dns/resolve.rs index 1e81ace0..94c56c28 100644 --- a/crates/common/src/network/dns/resolve.rs +++ b/crates/common/src/network/dns/resolve.rs @@ -18,7 +18,7 @@ impl Server { .mx_lookup(entry, Some(&self.inner.cache.dns_mx)) .await { - Ok(result) => Ok(result.iter().any(|mx| !mx.exchanges.is_empty())), + Ok(result) => Ok(result.rrset.iter().any(|mx| !mx.exchanges.is_empty())), Err(Error::DnsRecordNotFound(_)) => Ok(false), Err(err) => Err(err.into()), } @@ -55,7 +55,7 @@ impl Server { .ptr_lookup(addr, Some(&self.inner.cache.dns_ptr)) .await { - Ok(result) => Ok(!result.is_empty()), + Ok(result) => Ok(!result.rrset.is_empty()), Err(Error::DnsRecordNotFound(_)) => Ok(false), Err(err) => Err(err.into()), } @@ -73,7 +73,7 @@ impl Server { .ipv4_lookup(entry, Some(&self.inner.cache.dns_ipv4)) .await { - Ok(result) => Ok(!result.is_empty()), + Ok(result) => Ok(!result.rrset.is_empty()), Err(Error::DnsRecordNotFound(_)) => Ok(false), Err(err) => Err(err.into()), } @@ -88,7 +88,7 @@ impl Server { .ipv6_lookup(entry, Some(&self.inner.cache.dns_ipv6)) .await { - Ok(result) => Ok(!result.is_empty()), + Ok(result) => Ok(!result.rrset.is_empty()), Err(Error::DnsRecordNotFound(_)) => Ok(false), Err(err) => Err(err.into()), } diff --git a/crates/common/src/scripts/plugins/dns.rs b/crates/common/src/scripts/plugins/dns.rs index 18d5816e..9301b553 100644 --- a/crates/common/src/scripts/plugins/dns.rs +++ b/crates/common/src/scripts/plugins/dns.rs @@ -57,6 +57,7 @@ pub async fn exec(ctx: PluginContext<'_>) -> trc::Result { .await { Ok(result) => result + .rrset .iter() .flat_map(|mx| { mx.exchanges @@ -99,6 +100,7 @@ pub async fn exec(ctx: PluginContext<'_>) -> trc::Result { .await { Ok(result) => result + .rrset .iter() .map(|host| Variable::from(host.to_string())) .collect::>() @@ -127,6 +129,7 @@ pub async fn exec(ctx: PluginContext<'_>) -> trc::Result { .await { Ok(result) => result + .rrset .iter() .map(|ip| Variable::from(ip.to_string())) .collect::>() @@ -144,6 +147,7 @@ pub async fn exec(ctx: PluginContext<'_>) -> trc::Result { .await { Ok(result) => result + .rrset .iter() .map(|ip| Variable::from(ip.to_string())) .collect::>() diff --git a/crates/coordinator/Cargo.toml b/crates/coordinator/Cargo.toml index e84503ae..bf7b149f 100644 --- a/crates/coordinator/Cargo.toml +++ b/crates/coordinator/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "coordinator" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/dav-proto/Cargo.toml b/crates/dav-proto/Cargo.toml index 3adddcf1..2fdb038d 100644 --- a/crates/dav-proto/Cargo.toml +++ b/crates/dav-proto/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "dav-proto" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/dav/Cargo.toml b/crates/dav/Cargo.toml index 6ebf6f6f..218a877c 100644 --- a/crates/dav/Cargo.toml +++ b/crates/dav/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "dav" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/directory/Cargo.toml b/crates/directory/Cargo.toml index 269a2893..693e390e 100644 --- a/crates/directory/Cargo.toml +++ b/crates/directory/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "directory" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/email/Cargo.toml b/crates/email/Cargo.toml index 956c3b2d..4f33e6f5 100644 --- a/crates/email/Cargo.toml +++ b/crates/email/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "email" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/groupware/Cargo.toml b/crates/groupware/Cargo.toml index 92b59c50..6db3480c 100644 --- a/crates/groupware/Cargo.toml +++ b/crates/groupware/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "groupware" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/http-proto/Cargo.toml b/crates/http-proto/Cargo.toml index ba9c02cf..a0bf8a06 100644 --- a/crates/http-proto/Cargo.toml +++ b/crates/http-proto/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "http_proto" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/http/Cargo.toml b/crates/http/Cargo.toml index c1294709..b37d9099 100644 --- a/crates/http/Cargo.toml +++ b/crates/http/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "http" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] @@ -23,7 +23,7 @@ registry = { path = "../registry" } smtp-proto = { version = "0.2" } mail-parser = { version = "0.11", features = ["full_encoding", "rkyv"] } mail-builder = { version = "0.4" } -mail-auth = { version = "0.9", features = ["generate"] } +mail-auth = { version = "0.10", features = ["generate"] } tokio = { version = "1.47", features = ["rt"] } hyper = { version = "1.0.1", features = ["server", "http1", "http2"] } hyper-util = { version = "0.1.1", features = ["tokio"] } diff --git a/crates/http/src/api/diagnose.rs b/crates/http/src/api/diagnose.rs index 55443b20..6e64a364 100644 --- a/crates/http/src/api/diagnose.rs +++ b/crates/http/src/api/diagnose.rs @@ -16,7 +16,10 @@ use mail_auth::{IpLookupStrategy, mta_sts::TlsRpt}; use serde::{Deserialize, Serialize}; use smtp::outbound::{ client::{SmtpClient, StartTlsResult}, - dane::{dnssec::TlsaLookup, verify::TlsaVerify}, + dane::{ + dnssec::{TlsaLookup, TlsaResult}, + verify::TlsaVerify, + }, error::ClientError, lookup::{DnsLookup, SourceIp, ToNextHop}, mta_sts::{lookup::MtaStsLookup, verify::VerifyPolicy}, @@ -249,13 +252,14 @@ async fn delivery_diagnose( // Obtain remote host list let mx_config = MxConfig { - max_mx: mxs.len(), + max_mx: mxs.rrset.len(), max_multi_homed: 10, ip_lookup_strategy: IpLookupStrategy::Ipv4thenIpv6, }; let hosts = if let Some(hosts) = mxs.to_remote_hosts(&domain, &mx_config) { tx.send(DeliveryStage::MxLookupSuccess { mxs: mxs + .rrset .iter() .map(|mx| MX { exchanges: mx.exchanges.iter().map(|e| e.to_string()).collect(), @@ -385,7 +389,7 @@ async fn delivery_diagnose( let now = Instant::now(); let dane_policy = match server.tlsa_lookup(format!("_25._tcp.{hostname}.")).await { - Ok(Some(tlsa)) if tlsa.has_end_entities => { + Ok(TlsaResult::Secure(tlsa)) if tlsa.has_end_entities => { tx.send(DeliveryStage::TlsaLookupSuccess { record: tlsa.as_ref().clone(), elapsed: now.elapsed_ms(), @@ -394,7 +398,7 @@ async fn delivery_diagnose( Some(tlsa) } - Ok(Some(_)) => { + Ok(TlsaResult::Secure(_)) => { tx.send(DeliveryStage::TlsaLookupError { elapsed: now.elapsed_ms(), reason: "TLSA record does not have end entities".to_string(), @@ -403,7 +407,16 @@ async fn delivery_diagnose( None } - Ok(None) => { + Ok(TlsaResult::Bogus) => { + tx.send(DeliveryStage::TlsaLookupError { + elapsed: now.elapsed_ms(), + reason: "Bogus TLSA record".to_string(), + }) + .await?; + + None + } + Ok(TlsaResult::Missing) => { tx.send(DeliveryStage::TlsaNotFound { elapsed: now.elapsed_ms(), reason: "No TLSA DNSSEC records found".to_string(), diff --git a/crates/imap-proto/Cargo.toml b/crates/imap-proto/Cargo.toml index b41e6085..93da1681 100644 --- a/crates/imap-proto/Cargo.toml +++ b/crates/imap-proto/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "imap_proto" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/imap/Cargo.toml b/crates/imap/Cargo.toml index 8bae44ec..c21aa064 100644 --- a/crates/imap/Cargo.toml +++ b/crates/imap/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "imap" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/jmap-proto/Cargo.toml b/crates/jmap-proto/Cargo.toml index 1ffbf219..e0ea9383 100644 --- a/crates/jmap-proto/Cargo.toml +++ b/crates/jmap-proto/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "jmap_proto" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/jmap/Cargo.toml b/crates/jmap/Cargo.toml index e7de8197..e674567b 100644 --- a/crates/jmap/Cargo.toml +++ b/crates/jmap/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "jmap" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] @@ -23,7 +23,7 @@ calcard = { version = "0.3" } smtp-proto = { version = "0.2" } mail-parser = { version = "0.11", features = ["full_encoding", "rkyv"] } mail-builder = { version = "0.4" } -mail-auth = { version = "0.9", features = ["generate"] } +mail-auth = { version = "0.10", features = ["generate"] } sieve-rs = { version = "0.7", features = ["rkyv"] } jmap-tools = { version = "0.1", features = ["rkyv"] } serde = { version = "1.0", features = ["derive"]} diff --git a/crates/main/Cargo.toml b/crates/main/Cargo.toml index 50b5322a..65b4ad89 100644 --- a/crates/main/Cargo.toml +++ b/crates/main/Cargo.toml @@ -7,7 +7,7 @@ homepage = "https://stalw.art" keywords = ["imap", "jmap", "smtp", "email", "mail", "webdav", "server"] categories = ["email"] license = "AGPL-3.0-only OR LicenseRef-SEL" -version = "0.16.11" +version = "0.16.12" edition = "2024" [[bin]] diff --git a/crates/managesieve/Cargo.toml b/crates/managesieve/Cargo.toml index a427dd0d..43d62b89 100644 --- a/crates/managesieve/Cargo.toml +++ b/crates/managesieve/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "managesieve" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/migration/Cargo.toml b/crates/migration/Cargo.toml index 9f6bfb6d..cc6f16a8 100644 --- a/crates/migration/Cargo.toml +++ b/crates/migration/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "migration" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/nlp/Cargo.toml b/crates/nlp/Cargo.toml index f493d89f..c6d96d98 100644 --- a/crates/nlp/Cargo.toml +++ b/crates/nlp/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "nlp" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/pop3/Cargo.toml b/crates/pop3/Cargo.toml index 73fb931b..e8ac5998 100644 --- a/crates/pop3/Cargo.toml +++ b/crates/pop3/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "pop3" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/registry/Cargo.toml b/crates/registry/Cargo.toml index 6ddfe434..243fdefa 100644 --- a/crates/registry/Cargo.toml +++ b/crates/registry/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "registry" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] @@ -13,7 +13,7 @@ hashify = "0.2.7" ahash = { version = "0.8" } jmap-tools = { version = "0.1" } xxhash-rust = { version = "0.8.5", features = ["xxh3"] } -mail-auth = { version = "0.9" } +mail-auth = { version = "0.10" } tokio = { version = "1.47", features = ["fs"] } lz4_flex = { version = "0.13", default-features = false } diff --git a/crates/services/Cargo.toml b/crates/services/Cargo.toml index 3eb2b63d..93b32749 100644 --- a/crates/services/Cargo.toml +++ b/crates/services/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "services" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/smtp/Cargo.toml b/crates/smtp/Cargo.toml index 5366b855..8bd988b5 100644 --- a/crates/smtp/Cargo.toml +++ b/crates/smtp/Cargo.toml @@ -7,7 +7,7 @@ homepage = "https://stalw.art/smtp" keywords = ["smtp", "email", "mail", "server"] categories = ["email"] license = "AGPL-3.0-only OR LicenseRef-SEL" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] @@ -21,7 +21,7 @@ email = { path = "../email" } registry = { path = "../registry" } spam-filter = { path = "../spam-filter" } trc = { path = "../trc" } -mail-auth = { version = "0.9", features = ["rkyv"] } +mail-auth = { version = "0.10", features = ["rkyv"] } mail-parser = { version = "0.11", features = ["full_encoding"] } mail-builder = { version = "0.4" } smtp-proto = { version = "0.2", features = ["rkyv", "serde"] } diff --git a/crates/smtp/src/outbound/dane/dnssec.rs b/crates/smtp/src/outbound/dane/dnssec.rs index d1ce4e12..db396a0d 100644 --- a/crates/smtp/src/outbound/dane/dnssec.rs +++ b/crates/smtp/src/outbound/dane/dnssec.rs @@ -8,30 +8,63 @@ use common::{ Server, config::smtp::resolver::{Tlsa, TlsaEntry, TlsaMatching}, }; +pub use mail_auth::DnssecStatus; use mail_auth::{ + MX, RecordSet, common::resolver::ToFqdn, - hickory_resolver::proto::rr::{ - Name, RData, - rdata::tlsa::{CertUsage, Matching, Selector}, + hickory_resolver::{ + net::{DnsError, NetError}, + proto::{ + dnssec::Proof, + op::ResponseCode, + rr::{ + Name, RData, Record, RecordType, + rdata::tlsa::{CertUsage, Matching, Selector}, + }, + }, }, }; -use std::{future::Future, sync::Arc}; +use std::{ + future::Future, + sync::Arc, + time::{Duration, Instant}, +}; pub trait TlsaLookup: Sync + Send { + fn mx_lookup( + &self, + key: impl ToFqdn + Sync + Send, + ) -> impl Future>> + Send; + fn tlsa_lookup( &self, key: impl ToFqdn + Sync + Send, - ) -> impl Future>>> + Send; + ) -> impl Future> + Send; +} + +pub enum TlsaResult { + Secure(Arc), + Bogus, + Missing, } impl TlsaLookup for Server { - async fn tlsa_lookup( - &self, - key: impl ToFqdn + Sync + Send, - ) -> mail_auth::Result>> { + async fn mx_lookup(&self, key: impl ToFqdn + Sync + Send) -> mail_auth::Result> { + if !self.core.smtp.resolvers.dnssec_available { + return self + .core + .smtp + .resolvers + .dns + .mx_lookup(key, Some(&self.inner.cache.dns_mx)) + .await; + } + let key = key.to_fqdn(); - if let Some(value) = self.inner.cache.dns_tlsa.get(key.as_ref()) { - return Ok(Some(value)); + if let Some(value) = self.inner.cache.dns_mx.get::(key.as_ref()) + && value.dnssec_status != DnssecStatus::Indeterminate + { + return Ok(value); } #[cfg(any(test, feature = "test_mode"))] @@ -39,78 +72,245 @@ impl TlsaLookup for Server { return mail_auth::common::resolver::mock_resolve(key.as_ref()); } - let mut entries = Vec::new(); - let tlsa_lookup = self + let mx_lookup = match self + .core + .smtp + .resolvers + .dnssec + .resolver + .mx_lookup(Name::from_str_relaxed::<&str>(key.as_ref())?) + .await + { + Ok(mx_lookup) => mx_lookup, + Err(err) => { + if let Some(denial) = NegativeAnswer::from_error(&err) + && denial.response_code == ResponseCode::NoError + { + let records = RecordSet { + rrset: Arc::new([]), + dnssec_status: denial.dnssec_status, + }; + if let Some(valid_until) = denial.valid_until { + self.inner.cache.dns_mx.insert_with_expiry( + key, + records.clone(), + valid_until, + ); + } + return Ok(records); + } + return Err(err.into()); + } + }; + let mx_records = mx_lookup.answers(); + let mut dnssec_status: Option = None; + let mut records: Vec<(u16, Vec>)> = Vec::with_capacity(mx_records.len()); + for mx_record in mx_records { + if let RData::MX(mx) = &mx_record.data { + dnssec_status = Some(match dnssec_status { + Some(status) => least_secure(status, proof_to_dnssec_status(mx_record.proof)), + None => proof_to_dnssec_status(mx_record.proof), + }); + + let preference = mx.preference; + let exchange = mx.exchange.to_lowercase().to_string().into_boxed_str(); + + if let Some(record) = records.iter_mut().find(|r| r.0 == preference) { + record.1.push(exchange); + } else { + records.push((preference, vec![exchange])); + } + } + } + + records.sort_unstable_by_key(|a| a.0); + let rrset: Arc<[MX]> = records + .into_iter() + .map(|(preference, exchanges)| MX { + preference, + exchanges: exchanges.into_boxed_slice(), + }) + .collect::>(); + let records = RecordSet { + rrset, + dnssec_status: dnssec_status.unwrap_or(DnssecStatus::Indeterminate), + }; + + self.inner + .cache + .dns_mx + .insert_with_expiry(key, records.clone(), mx_lookup.valid_until()); + + Ok(records) + } + + async fn tlsa_lookup(&self, key: impl ToFqdn + Sync + Send) -> mail_auth::Result { + let key = key.to_fqdn(); + if let Some(value) = self.inner.cache.dns_tlsa.get(key.as_ref()) { + return Ok(TlsaResult::Secure(value)); + } + + #[cfg(any(test, feature = "test_mode"))] + if true { + if key.as_ref().contains("_dnssec_bogus.") { + return Ok(TlsaResult::Bogus); + } + return mail_auth::common::resolver::mock_resolve(key.as_ref()); + } + + let tlsa_lookup = match self .core .smtp .resolvers .dnssec .resolver .tlsa_lookup(Name::from_str_relaxed(key.as_ref())?) - .await?; + .await + { + Ok(tlsa_lookup) => tlsa_lookup, + Err(err) => { + if let Some(denial) = NegativeAnswer::from_error(&err) { + return Ok(if denial.dnssec_status == DnssecStatus::Bogus { + TlsaResult::Bogus + } else { + TlsaResult::Missing + }); + } + return Err(err.into()); + } + }; + let mut entries = Vec::new(); let mut has_end_entities = false; let mut has_intermediates = false; - let mut found_insecure = false; + let mut dnssec_status: Option = None; for record in tlsa_lookup.answers() { if let RData::TLSA(tlsa) = &record.data { - if record.proof.is_secure() { - let is_end_entity = match tlsa.cert_usage { - CertUsage::DaneEe => true, - CertUsage::DaneTa => false, - _ => continue, - }; - let matching = match tlsa.matching { - Matching::Raw => TlsaMatching::Full, - Matching::Sha256 => TlsaMatching::Sha256, - Matching::Sha512 => TlsaMatching::Sha512, - _ => continue, - }; - let is_spki = match tlsa.selector { - Selector::Spki => true, - Selector::Full => false, - _ => continue, - }; - if is_end_entity { - has_end_entities = true; - } else { - has_intermediates = true; - } - entries.push(TlsaEntry { - is_end_entity, - is_spki, - matching, - data: tlsa.cert_data.clone(), - }); - } else { - found_insecure = true; + dnssec_status = Some(match dnssec_status { + Some(status) => least_secure(status, proof_to_dnssec_status(record.proof)), + None => proof_to_dnssec_status(record.proof), + }); + + if !record.proof.is_secure() { + continue; } + + let is_end_entity = match tlsa.cert_usage { + CertUsage::DaneEe => true, + CertUsage::DaneTa => false, + _ => continue, + }; + let matching = match tlsa.matching { + Matching::Raw => TlsaMatching::Full, + Matching::Sha256 => TlsaMatching::Sha256, + Matching::Sha512 => TlsaMatching::Sha512, + _ => continue, + }; + let is_spki = match tlsa.selector { + Selector::Spki => true, + Selector::Full => false, + _ => continue, + }; + if is_end_entity { + has_end_entities = true; + } else { + has_intermediates = true; + } + entries.push(TlsaEntry { + is_end_entity, + is_spki, + matching, + data: tlsa.cert_data.clone(), + }); } } - if !entries.is_empty() || !found_insecure { - let tlsa = Arc::new(Tlsa { - entries, - has_end_entities, - has_intermediates, - }); + match dnssec_status { + Some(DnssecStatus::Bogus) => Ok(TlsaResult::Bogus), + Some(DnssecStatus::Secure) => { + let tlsa = Arc::new(Tlsa { + entries, + has_end_entities, + has_intermediates, + }); - self.inner.cache.dns_tlsa.insert_with_expiry( - key, - tlsa.clone(), - tlsa_lookup.valid_until(), - ); + self.inner.cache.dns_tlsa.insert_with_expiry( + key, + tlsa.clone(), + tlsa_lookup.valid_until(), + ); - Ok(Some(tlsa)) - } else { - Ok(None) + Ok(TlsaResult::Secure(tlsa)) + } + _ => Ok(TlsaResult::Missing), } } } -#[derive(Debug, Clone, Copy, PartialEq, Eq)] -pub enum DnssecStatus { - Secure, - Insecure, +struct NegativeAnswer { + response_code: ResponseCode, + dnssec_status: DnssecStatus, + valid_until: Option, +} + +impl NegativeAnswer { + fn from_error(err: &NetError) -> Option { + let NetError::Dns(dns_error) = err else { + return None; + }; + + match dns_error { + DnsError::NoRecordsFound(no_records) => Some(NegativeAnswer { + response_code: no_records.response_code, + dnssec_status: no_records + .authorities + .as_deref() + .map(denial_dnssec_status) + .unwrap_or(DnssecStatus::Indeterminate), + valid_until: no_records + .negative_ttl + .map(|ttl| Instant::now() + Duration::from_secs(ttl as u64)), + }), + DnsError::Nsec { + response, proof, .. + } => Some(NegativeAnswer { + response_code: response.response_code, + dnssec_status: proof_to_dnssec_status(*proof), + valid_until: None, + }), + _ => None, + } + } +} + +fn denial_dnssec_status(authorities: &[Record]) -> DnssecStatus { + authorities + .iter() + .filter(|record| matches!(record.record_type(), RecordType::NSEC | RecordType::NSEC3)) + .map(|record| proof_to_dnssec_status(record.proof)) + .reduce(least_secure) + .unwrap_or(DnssecStatus::Indeterminate) +} + +fn proof_to_dnssec_status(proof: Proof) -> DnssecStatus { + match proof { + Proof::Secure => DnssecStatus::Secure, + Proof::Insecure => DnssecStatus::Insecure, + Proof::Bogus => DnssecStatus::Bogus, + Proof::Indeterminate => DnssecStatus::Indeterminate, + } +} + +fn least_secure(a: DnssecStatus, b: DnssecStatus) -> DnssecStatus { + fn rank(status: DnssecStatus) -> u8 { + match status { + DnssecStatus::Bogus => 0, + DnssecStatus::Indeterminate => 1, + DnssecStatus::Insecure => 2, + DnssecStatus::Secure => 3, + } + } + + if rank(a) <= rank(b) { a } else { b } } diff --git a/crates/smtp/src/outbound/delivery.rs b/crates/smtp/src/outbound/delivery.rs index ffbb4628..8e0ebfb5 100644 --- a/crates/smtp/src/outbound/delivery.rs +++ b/crates/smtp/src/outbound/delivery.rs @@ -9,7 +9,7 @@ use crate::outbound::DeliveryResult; use crate::outbound::client::{ SmtpClient, from_error_details, from_error_status, from_mail_send_error, }; -use crate::outbound::dane::dnssec::{DnssecStatus, TlsaLookup}; +use crate::outbound::dane::dnssec::{DnssecStatus, TlsaLookup, TlsaResult}; use crate::outbound::error::ClientError; use crate::outbound::lookup::{DnsLookup, SourceIp}; use crate::outbound::mta_sts::lookup::MtaStsLookup; @@ -29,6 +29,7 @@ use common::config::smtp::queue::RoutingStrategy; use common::config::{server::ServerProtocol, smtp::report::AggregateFrequency}; use common::ipc::{PolicyType, QueueEvent, QueueEventStatus, TlsEvent}; use compact_str::ToCompactString; +use mail_auth::RecordSet; use mail_auth::{ mta_sts::TlsRpt, report::tlsrpt::{FailureDetails, ResultType}, @@ -496,14 +497,7 @@ impl QueuedMessage { if let Some(mx_config) = mx_config { // Lookup MX let time = Instant::now(); - mx_list = match server - .core - .smtp - .resolvers - .dns - .mx_lookup(domain, Some(&server.inner.cache.dns_mx)) - .await - { + mx_list = match server.mx_lookup(domain).await { Ok(mx) => mx, Err(mail_auth::Error::DnsRecordNotFound(_)) => { trc::event!( @@ -514,7 +508,10 @@ impl QueuedMessage { Elapsed = time.elapsed(), ); - Arc::new([]) + RecordSet { + rrset: Arc::new([]), + dnssec_status: DnssecStatus::Indeterminate, + } } Err(err) => { trc::event!( @@ -640,22 +637,15 @@ impl QueuedMessage { ); // Obtain source and remote IPs - let dane_enabled = tls_strategy.try_dane() - && is_smtp - && server.core.smtp.resolvers.dnssec_available; let time = Instant::now(); - let resolve_result = match server - .resolve_host(remote_host, &envelope, dane_enabled) - .await - { - Ok(result) => { + let remote_ips = match server.resolve_host(remote_host, &envelope).await { + Ok(remote_ips) => { trc::event!( Delivery(DeliveryEvent::IpLookup), SpanId = message.span_id, Domain = domain.to_string(), Hostname = envelope.mx.to_string(), - Details = result - .remote_ips + Details = remote_ips .iter() .map(|ip| trc::Value::from(*ip)) .collect::>(), @@ -663,7 +653,7 @@ impl QueuedMessage { Elapsed = time.elapsed(), ); - result + remote_ips } Err(status) => { trc::event!( @@ -681,130 +671,96 @@ impl QueuedMessage { }; // Lookup DANE policy - let dane_policy = if dane_enabled { + let dane_policy = if tls_strategy.try_dane() && is_smtp { let time = Instant::now(); let strict = tls_strategy.is_dane_required(); - if resolve_result.dnssec_status == DnssecStatus::Insecure { - trc::event!( - Dane(DaneEvent::TlsaRecordNotDnssecSigned), - SpanId = message.span_id, - Domain = domain.to_string(), - Hostname = envelope.mx.to_string(), - Strict = strict, - Elapsed = time.elapsed(), - ); + match remote_host.dnssec_status() { + DnssecStatus::Secure => { + match server + .tlsa_lookup(format!("_25._tcp.{}.", envelope.mx)) + .await + { + Ok(TlsaResult::Secure(tlsa)) => { + if tlsa.has_end_entities || tlsa.has_intermediates { + trc::event!( + Dane(DaneEvent::TlsaRecordFetch), + SpanId = message.span_id, + Domain = domain.to_string(), + Hostname = envelope.mx.to_string(), + Details = format!("{tlsa:?}"), + Strict = strict, + Elapsed = time.elapsed(), + ); - if strict { - // Report DANE required - if let Some(tls_report) = &tls_report { - server - .schedule_report(TlsEvent { - policy: PolicyType::Tlsa(None), - domain: domain.to_string(), - failure: FailureDetails::new(ResultType::DaneRequired) - .with_receiving_mx_hostname(envelope.mx) - .with_failure_reason_code( - "MX host is not in a DNSSEC signed zone.", - ) - .into(), - tls_record: tls_report.record.clone(), - interval: tls_report.interval, - span_id: message.span_id, - }) - .await; - } + tlsa.into() + } else { + trc::event!( + Dane(DaneEvent::TlsaRecordInvalid), + SpanId = message.span_id, + Domain = domain.to_string(), + Hostname = envelope.mx.to_string(), + Details = format!("{tlsa:?}"), + Strict = strict, + Elapsed = time.elapsed(), + ); - last_status = Status::PermanentFailure(ErrorDetails { - entity: envelope.mx.into(), - details: Error::DaneError("No TLSA DNSSEC records found".into()), - }); - continue 'next_host; - } - None - } else { - match server - .tlsa_lookup(format!("_25._tcp.{}.", envelope.mx)) - .await - { - Ok(Some(tlsa)) => { - if tlsa.has_end_entities || tlsa.has_intermediates { - trc::event!( - Dane(DaneEvent::TlsaRecordFetch), - SpanId = message.span_id, - Domain = domain.to_string(), - Hostname = envelope.mx.to_string(), - Details = format!("{tlsa:?}"), - Strict = strict, - Elapsed = time.elapsed(), - ); + // Report invalid TLSA record + if let Some(tls_report) = &tls_report { + server + .schedule_report(TlsEvent { + policy: tlsa.into(), + domain: domain.to_string(), + failure: FailureDetails::new( + ResultType::TlsaInvalid, + ) + .with_receiving_mx_hostname(envelope.mx) + .with_failure_reason_code( + "Invalid TLSA record.", + ) + .into(), + tls_record: tls_report.record.clone(), + interval: tls_report.interval, + span_id: message.span_id, + }) + .await; + } - tlsa.into() - } else { - trc::event!( - Dane(DaneEvent::TlsaRecordInvalid), - SpanId = message.span_id, - Domain = domain.to_string(), - Hostname = envelope.mx.to_string(), - Details = format!("{tlsa:?}"), - Strict = strict, - Elapsed = time.elapsed(), - ); - - // Report invalid TLSA record - if let Some(tls_report) = &tls_report { - server - .schedule_report(TlsEvent { - policy: tlsa.into(), - domain: domain.to_string(), - failure: FailureDetails::new( - ResultType::TlsaInvalid, - ) - .with_receiving_mx_hostname(envelope.mx) - .with_failure_reason_code("Invalid TLSA record.") - .into(), - tls_record: tls_report.record.clone(), - interval: tls_report.interval, - span_id: message.span_id, - }) - .await; + if strict { + last_status = Status::PermanentFailure(ErrorDetails { + entity: envelope.mx.into(), + details: Error::DaneError( + "No valid TLSA records were found".into(), + ), + }); + continue 'next_host; + } + None } - - if strict { - last_status = Status::PermanentFailure(ErrorDetails { - entity: envelope.mx.into(), - details: Error::DaneError( - "No valid TLSA records were found".into(), - ), - }); - continue 'next_host; - } - None } - } - Ok(None) => { - trc::event!( - Dane(DaneEvent::TlsaRecordNotDnssecSigned), - SpanId = message.span_id, - Domain = domain.to_string(), - Hostname = envelope.mx.to_string(), - Strict = strict, - Elapsed = time.elapsed(), - ); + Ok(TlsaResult::Bogus) => { + trc::event!( + Dane(DaneEvent::BogusDnssecRecord), + SpanId = message.span_id, + Domain = domain.to_string(), + Hostname = envelope.mx.to_string(), + Details = "TLSA", + Strict = strict, + Elapsed = time.elapsed(), + ); - if strict { - // Report DANE required + // Report bogus TLSA record if let Some(tls_report) = &tls_report { server .schedule_report(TlsEvent { policy: PolicyType::Tlsa(None), domain: domain.to_string(), failure: FailureDetails::new( - ResultType::DaneRequired, + ResultType::DnssecInvalid, ) .with_receiving_mx_hostname(envelope.mx) .with_failure_reason_code( - "No TLSA DNSSEC records found.", + "Bogus TLSA records were found.", ) .into(), tls_record: tls_report.record.clone(), @@ -814,23 +770,17 @@ impl QueuedMessage { .await; } - last_status = Status::PermanentFailure(ErrorDetails { + last_status = Status::TemporaryFailure(ErrorDetails { entity: envelope.mx.into(), details: Error::DaneError( - "No TLSA DNSSEC records found".into(), + "Bogus TLSA records were found".into(), ), }); continue 'next_host; } - None - } - Err(err) => { - let not_found = - matches!(&err, mail_auth::Error::DnsRecordNotFound(_)); - - if not_found { + Ok(TlsaResult::Missing) => { trc::event!( - Dane(DaneEvent::TlsaRecordNotFound), + Dane(DaneEvent::TlsaRecordNotDnssecSigned), SpanId = message.span_id, Domain = domain.to_string(), Hostname = envelope.mx.to_string(), @@ -850,7 +800,7 @@ impl QueuedMessage { ) .with_receiving_mx_hostname(envelope.mx) .with_failure_reason_code( - "No TLSA records found for MX.", + "No TLSA DNSSEC records found.", ) .into(), tls_record: tls_report.record.clone(), @@ -863,35 +813,159 @@ impl QueuedMessage { last_status = Status::PermanentFailure(ErrorDetails { entity: envelope.mx.into(), details: Error::DaneError( - "No TLSA records found".into(), + "No TLSA DNSSEC records found".into(), ), }); continue 'next_host; } None - } else { - trc::event!( - Dane(DaneEvent::TlsaRecordFetchError), - SpanId = message.span_id, - Domain = domain.to_string(), - Hostname = envelope.mx.to_string(), - CausedBy = trc::Error::from(err.clone()), - Strict = strict, - Elapsed = time.elapsed(), - ); + } + Err(err) => { + let not_found = + matches!(&err, mail_auth::Error::DnsRecordNotFound(_)); - last_status = Status::from_mail_auth_error(envelope.mx, err); - continue 'next_host; + if not_found { + trc::event!( + Dane(DaneEvent::TlsaRecordNotFound), + SpanId = message.span_id, + Domain = domain.to_string(), + Hostname = envelope.mx.to_string(), + Strict = strict, + Elapsed = time.elapsed(), + ); + + if strict { + // Report DANE required + if let Some(tls_report) = &tls_report { + server + .schedule_report(TlsEvent { + policy: PolicyType::Tlsa(None), + domain: domain.to_string(), + failure: FailureDetails::new( + ResultType::DaneRequired, + ) + .with_receiving_mx_hostname(envelope.mx) + .with_failure_reason_code( + "No TLSA records found for MX.", + ) + .into(), + tls_record: tls_report.record.clone(), + interval: tls_report.interval, + span_id: message.span_id, + }) + .await; + } + + last_status = Status::PermanentFailure(ErrorDetails { + entity: envelope.mx.into(), + details: Error::DaneError( + "No TLSA records found".into(), + ), + }); + continue 'next_host; + } + None + } else { + trc::event!( + Dane(DaneEvent::TlsaRecordFetchError), + SpanId = message.span_id, + Domain = domain.to_string(), + Hostname = envelope.mx.to_string(), + CausedBy = trc::Error::from(err.clone()), + Strict = strict, + Elapsed = time.elapsed(), + ); + + last_status = + Status::from_mail_auth_error(envelope.mx, err); + continue 'next_host; + } } } } + DnssecStatus::Bogus => { + trc::event!( + Dane(DaneEvent::BogusDnssecRecord), + SpanId = message.span_id, + Domain = domain.to_string(), + Hostname = envelope.mx.to_string(), + Details = "MX", + Strict = strict, + Elapsed = time.elapsed(), + ); + + // Report bogus MX record + if let Some(tls_report) = &tls_report { + server + .schedule_report(TlsEvent { + policy: PolicyType::Tlsa(None), + domain: domain.to_string(), + failure: FailureDetails::new(ResultType::DnssecInvalid) + .with_receiving_mx_hostname(envelope.mx) + .with_failure_reason_code( + "Bogus MX records were found.", + ) + .into(), + tls_record: tls_report.record.clone(), + interval: tls_report.interval, + span_id: message.span_id, + }) + .await; + } + + last_status = Status::TemporaryFailure(ErrorDetails { + entity: envelope.mx.into(), + details: Error::DaneError("Bogus MX records were found".into()), + }); + continue 'next_host; + } + _ => { + trc::event!( + Dane(DaneEvent::TlsaRecordNotDnssecSigned), + SpanId = message.span_id, + Domain = domain.to_string(), + Hostname = envelope.mx.to_string(), + Strict = strict, + Elapsed = time.elapsed(), + ); + + if strict { + // Report DANE required + if let Some(tls_report) = &tls_report { + server + .schedule_report(TlsEvent { + policy: PolicyType::Tlsa(None), + domain: domain.to_string(), + failure: FailureDetails::new(ResultType::DaneRequired) + .with_receiving_mx_hostname(envelope.mx) + .with_failure_reason_code( + "MX host is not in a DNSSEC signed zone.", + ) + .into(), + tls_record: tls_report.record.clone(), + interval: tls_report.interval, + span_id: message.span_id, + }) + .await; + } + + last_status = Status::PermanentFailure(ErrorDetails { + entity: envelope.mx.into(), + details: Error::DaneError( + "No TLSA DNSSEC records found".into(), + ), + }); + continue 'next_host; + } + None + } } } else { None }; // Try each IP address - 'next_ip: for remote_ip in resolve_result.remote_ips { + 'next_ip: for remote_ip in remote_ips { // Throttle remote host envelope.remote_ip = remote_ip; for throttle in &queue_config.outbound_limiters.remote { diff --git a/crates/smtp/src/outbound/lookup.rs b/crates/smtp/src/outbound/lookup.rs index df7c62e7..f9fb9328 100644 --- a/crates/smtp/src/outbound/lookup.rs +++ b/crates/smtp/src/outbound/lookup.rs @@ -5,31 +5,16 @@ */ use super::NextHop; -use crate::outbound::dane::dnssec::DnssecStatus; use crate::queue::{Error, ErrorDetails, HostResponse, Status}; use common::{ Server, config::smtp::queue::{ConnectionStrategy, HostOrIp, IpAndHost, MxConfig}, expr::functions::ResolveVariable, }; -use mail_auth::{ - IpLookupStrategy, MX, - common::resolver::ToFqdn, - hickory_resolver::proto::rr::{Name, RData, RecordType}, -}; +use mail_auth::{IpLookupStrategy, MX, RecordSet}; use rand::{Rng, seq::SliceRandom}; use registry::schema::enums::ExpressionVariable; -use std::{ - future::Future, - net::{IpAddr, Ipv4Addr, Ipv6Addr}, - sync::Arc, - time::Instant, -}; - -pub struct IpLookupResult { - pub remote_ips: Vec, - pub dnssec_status: DnssecStatus, -} +use std::{future::Future, net::IpAddr, sync::Arc}; pub trait DnsLookup: Sync + Send { fn ip_lookup( @@ -39,19 +24,11 @@ pub trait DnsLookup: Sync + Send { max_results: usize, ) -> impl Future>> + Send; - fn dnssec_ip_lookup( - &self, - key: &str, - strategy: IpLookupStrategy, - max_results: usize, - ) -> impl Future, DnssecStatus)>> + Send; - fn resolve_host( &self, remote_host: &NextHop<'_>, envelope: &impl ResolveVariable, - use_dnssec: bool, - ) -> impl Future>, ErrorDetails>>> + Send; + ) -> impl Future, Status>, ErrorDetails>>> + Send; } impl DnsLookup for Server { @@ -76,7 +53,7 @@ impl DnsLookup for Server { .ipv4_lookup(key, Some(&self.inner.cache.dns_ipv4)) .await { - Ok(addrs) => addrs, + Ok(addrs) => addrs.rrset, Err(_) if has_ipv6 => Arc::new([]), Err(err) => return Err(err), } @@ -93,7 +70,7 @@ impl DnsLookup for Server { .ipv6_lookup(key, Some(&self.inner.cache.dns_ipv6)) .await { - Ok(addrs) => addrs, + Ok(addrs) => addrs.rrset, Err(_) if !ipv4_addrs.is_empty() => Arc::new([]), Err(err) => return Err(err), }; @@ -124,174 +101,21 @@ impl DnsLookup for Server { } } - async fn dnssec_ip_lookup( - &self, - key: &str, - strategy: IpLookupStrategy, - max_results: usize, - ) -> mail_auth::Result<(Vec, DnssecStatus)> { - let fqdn = key.to_fqdn(); - if let Some(secure) = self.inner.cache.dns_dnssec.get(fqdn.as_ref()) { - return Ok(( - self.ip_lookup(key, strategy, max_results).await?, - if secure { - DnssecStatus::Secure - } else { - DnssecStatus::Insecure - }, - )); - } - - #[cfg(any(test, feature = "test_mode"))] - if true { - return Ok(( - self.ip_lookup(key, strategy, max_results).await?, - DnssecStatus::Secure, - )); - } - - let (query_v4, query_v6, v4_first) = match strategy { - IpLookupStrategy::Ipv4Only => (true, false, true), - IpLookupStrategy::Ipv6Only => (false, true, false), - IpLookupStrategy::Ipv4thenIpv6 => (true, true, true), - IpLookupStrategy::Ipv6thenIpv4 => (true, true, false), - }; - let resolver = &self.core.smtp.resolvers.dnssec.resolver; - let name = Name::from_str_relaxed(fqdn.as_ref())?; - - let mut ipv4: Vec = Vec::new(); - let mut ipv6: Vec = Vec::new(); - let mut all_secure = true; - let mut v4_valid_until: Option = None; - let mut v6_valid_until: Option = None; - let mut not_found: Option = None; - - let mut record_types = Vec::with_capacity(2); - if query_v4 { - record_types.push(RecordType::A); - } - if query_v6 { - record_types.push(RecordType::AAAA); - } - - for record_type in record_types { - match resolver.lookup(name.clone(), record_type).await { - Ok(lookup) => { - let valid_until = lookup.valid_until(); - let mut found = false; - for record in lookup.answers() { - if !record.proof.is_secure() { - all_secure = false; - } - match &record.data { - RData::A(a) => { - ipv4.push(a.0); - found = true; - } - RData::AAAA(aaaa) => { - ipv6.push(aaaa.0); - found = true; - } - _ => {} - } - } - if found { - if record_type == RecordType::A { - v4_valid_until = Some(valid_until); - } else { - v6_valid_until = Some(valid_until); - } - } - } - Err(err) => { - let err: mail_auth::Error = err.into(); - if matches!(err, mail_auth::Error::DnsRecordNotFound(_)) { - not_found = Some(err); - } else { - return Err(err); - } - } - } - } - - if ipv4.is_empty() && ipv6.is_empty() { - return Err(not_found.unwrap_or(mail_auth::Error::DnsRecordNotFound( - mail_auth::hickory_resolver::proto::op::ResponseCode::NXDomain, - ))); - } - - if let Some(valid_until) = v4_valid_until { - self.inner.cache.dns_ipv4.insert_with_expiry( - fqdn.clone(), - Arc::from(ipv4.as_slice()), - valid_until, - ); - } - if let Some(valid_until) = v6_valid_until { - self.inner.cache.dns_ipv6.insert_with_expiry( - fqdn.clone(), - Arc::from(ipv6.as_slice()), - valid_until, - ); - } - if let Some(valid_until) = v4_valid_until.into_iter().chain(v6_valid_until).min() { - self.inner - .cache - .dns_dnssec - .insert_with_expiry(fqdn, all_secure, valid_until); - } - - let remote_ips: Vec = if v4_first { - ipv4.into_iter() - .map(IpAddr::from) - .chain(ipv6.into_iter().map(IpAddr::from)) - .take(max_results) - .collect() - } else { - ipv6.into_iter() - .map(IpAddr::from) - .chain(ipv4.into_iter().map(IpAddr::from)) - .take(max_results) - .collect() - }; - - Ok(( - remote_ips, - if all_secure { - DnssecStatus::Secure - } else { - DnssecStatus::Insecure - }, - )) - } - #[allow(unused_mut)] async fn resolve_host( &self, remote_host: &NextHop<'_>, envelope: &impl ResolveVariable, - use_dnssec: bool, - ) -> Result>, ErrorDetails>> { - let (mut remote_ips, dnssec_status) = match remote_host.fqdn_hostname() { - HostOrIp::Host(hostname) => { - let lookup = if use_dnssec { - self.dnssec_ip_lookup( - hostname.as_ref(), - remote_host.ip_lookup_strategy(), - remote_host.max_multi_homed(), - ) - .await - } else { - self.ip_lookup( - hostname.as_ref(), - remote_host.ip_lookup_strategy(), - remote_host.max_multi_homed(), - ) - .await - .map(|ips| (ips, DnssecStatus::Insecure)) - }; - - lookup.map_err(|err| { + ) -> Result, Status>, ErrorDetails>> { + let mut remote_ips = match remote_host.fqdn_hostname() { + HostOrIp::Host(hostname) => self + .ip_lookup( + hostname.as_ref(), + remote_host.ip_lookup_strategy(), + remote_host.max_multi_homed(), + ) + .await + .map_err(|err| { if let mail_auth::Error::DnsRecordNotFound(_) = &err { if matches!( remote_host, @@ -318,9 +142,8 @@ impl DnsLookup for Server { ), }) } - })? - } - HostOrIp::Ip(ip) => (vec![ip], DnssecStatus::Insecure), + })?, + HostOrIp::Ip(ip) => vec![ip], }; if !remote_ips.is_empty() { @@ -335,10 +158,7 @@ impl DnsLookup for Server { } } - Ok(IpLookupResult { - remote_ips, - dnssec_status, - }) + Ok(remote_ips) } else { Err(Status::TemporaryFailure(ErrorDetails { entity: remote_host.hostname().into(), @@ -383,17 +203,17 @@ pub trait ToNextHop { ) -> Option>>; } -impl ToNextHop for Arc<[MX]> { +impl ToNextHop for RecordSet { fn to_remote_hosts<'x, 'y: 'x>( &'x self, domain: &'y str, config: &'x MxConfig, ) -> Option>> { - if !self.is_empty() { + if !self.rrset.is_empty() { // Obtain max number of MX hosts to process let mut remote_hosts = Vec::with_capacity(config.max_mx); - 'outer: for mx in self.iter() { + 'outer: for mx in self.rrset.iter() { if mx.exchanges.len() > 1 { let mut slice = mx.exchanges.iter().collect::>(); slice.shuffle(&mut rand::rng()); @@ -401,6 +221,7 @@ impl ToNextHop for Arc<[MX]> { remote_hosts.push(NextHop::MX { host: remote_host.as_ref(), is_implicit: false, + dnssec_status: self.dnssec_status, config, }); if remote_hosts.len() == config.max_mx { @@ -415,6 +236,7 @@ impl ToNextHop for Arc<[MX]> { remote_hosts.push(NextHop::MX { host: remote_host.as_ref(), is_implicit: false, + dnssec_status: self.dnssec_status, config, }); if remote_hosts.len() == config.max_mx { @@ -429,6 +251,7 @@ impl ToNextHop for Arc<[MX]> { vec![NextHop::MX { host: domain, is_implicit: true, + dnssec_status: self.dnssec_status, config, }] .into() diff --git a/crates/smtp/src/outbound/mod.rs b/crates/smtp/src/outbound/mod.rs index 7587f844..22064995 100644 --- a/crates/smtp/src/outbound/mod.rs +++ b/crates/smtp/src/outbound/mod.rs @@ -13,7 +13,7 @@ use common::config::{ smtp::queue::{HostOrIp, MxConfig, RelayConfig}, }; use directory::Credentials; -use mail_auth::IpLookupStrategy; +use mail_auth::{DnssecStatus, IpLookupStrategy}; use smtp_proto::{Response, Severity}; use std::{borrow::Cow, net::IpAddr}; @@ -233,6 +233,7 @@ pub enum NextHop<'x> { is_implicit: bool, host: &'x str, config: &'x MxConfig, + dnssec_status: DnssecStatus, }, } @@ -334,6 +335,13 @@ impl NextHop<'_> { NextHop::Relay(host) => host.protocol == ServerProtocol::Smtp, } } + + fn dnssec_status(&self) -> DnssecStatus { + match self { + NextHop::MX { dnssec_status, .. } => *dnssec_status, + NextHop::Relay(_) => DnssecStatus::Indeterminate, + } + } } impl DeliveryResult { diff --git a/crates/spam-filter/Cargo.toml b/crates/spam-filter/Cargo.toml index 7191fadb..b545c182 100644 --- a/crates/spam-filter/Cargo.toml +++ b/crates/spam-filter/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "spam-filter" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] @@ -14,7 +14,7 @@ registry = { path = "../registry" } smtp-proto = { version = "0.2", features = ["rkyv"] } mail-parser = { version = "0.11", features = ["full_encoding"] } mail-builder = { version = "0.4" } -mail-auth = { version = "0.9" } +mail-auth = { version = "0.10" } tokio = { version = "1.47", features = ["net", "macros"] } psl = "2" hyper = { version = "1.0.1", features = ["server", "http1", "http2"] } diff --git a/crates/store/Cargo.toml b/crates/store/Cargo.toml index 56ee9520..031146fc 100644 --- a/crates/store/Cargo.toml +++ b/crates/store/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "store" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/store/src/backend/postgres/main.rs b/crates/store/src/backend/postgres/main.rs index 722988a4..0e6dad6e 100644 --- a/crates/store/src/backend/postgres/main.rs +++ b/crates/store/src/backend/postgres/main.rs @@ -14,9 +14,7 @@ use crate::{ *, }; use ::registry::schema::{enums::PostgreSqlRecyclingMethod, structs}; -use deadpool_postgres::{ - Config, ManagerConfig, Object, PoolConfig, RecyclingMethod, Runtime, -}; +use deadpool_postgres::{Config, ManagerConfig, Object, PoolConfig, RecyclingMethod, Runtime}; use tokio_postgres::NoTls; use utils::tls::rustls_client_config; diff --git a/crates/trc/Cargo.toml b/crates/trc/Cargo.toml index 0f3759c9..2bbe2282 100644 --- a/crates/trc/Cargo.toml +++ b/crates/trc/Cargo.toml @@ -1,11 +1,11 @@ [package] name = "trc" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] event_macro = { path = "./event-macro" } -mail-auth = { version = "0.9" } +mail-auth = { version = "0.10" } mail-parser = { version = "0.11", features = ["full_encoding"] } base64 = "0.22.1" serde = "1.0" diff --git a/crates/trc/event-macro/Cargo.toml b/crates/trc/event-macro/Cargo.toml index 66ab146c..da44d1c6 100644 --- a/crates/trc/event-macro/Cargo.toml +++ b/crates/trc/event-macro/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "event_macro" -version = "0.16.11" +version = "0.16.12" edition = "2024" [lib] diff --git a/crates/trc/src/event/enums.rs b/crates/trc/src/event/enums.rs index 4120aa9a..53d883df 100644 --- a/crates/trc/src/event/enums.rs +++ b/crates/trc/src/event/enums.rs @@ -6,8 +6,8 @@ // This file is auto-generated. Do not edit directly. -pub const TOTAL_EVENT_COUNT: usize = 605; -pub const TOTAL_METRIC_COUNT: usize = 339; +pub const TOTAL_EVENT_COUNT: usize = 606; +pub const TOTAL_METRIC_COUNT: usize = 340; #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub enum EventType { @@ -156,6 +156,7 @@ pub enum DaneEvent { TlsaRecordNotFound = 75, TlsaRecordNotDnssecSigned = 74, TlsaRecordInvalid = 72, + BogusDnssecRecord = 605, } #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] @@ -912,6 +913,7 @@ pub enum MetricType { DaneTlsaRecordNotFound = 61, DaneTlsaRecordNotDnssecSigned = 62, DaneTlsaRecordInvalid = 63, + DaneBogusDnssecRecord = 339, DeliveryTotalTime = 2, DeliveryAttemptTime = 3, DeliveryActiveConnections = 22, diff --git a/crates/trc/src/event/enums_impl.rs b/crates/trc/src/event/enums_impl.rs index 619ca607..56e1c715 100644 --- a/crates/trc/src/event/enums_impl.rs +++ b/crates/trc/src/event/enums_impl.rs @@ -81,6 +81,7 @@ impl EventType { b"dane.tlsa-record-not-found" => EventType::Dane(DaneEvent::TlsaRecordNotFound), b"dane.tlsa-record-not-dnssec-signed" => EventType::Dane(DaneEvent::TlsaRecordNotDnssecSigned), b"dane.tlsa-record-invalid" => EventType::Dane(DaneEvent::TlsaRecordInvalid), + b"dane.bogus-dnssec-record" => EventType::Dane(DaneEvent::BogusDnssecRecord), b"delivery.attempt-start" => EventType::Delivery(DeliveryEvent::AttemptStart), b"delivery.attempt-end" => EventType::Delivery(DeliveryEvent::AttemptEnd), b"delivery.completed" => EventType::Delivery(DeliveryEvent::Completed), @@ -702,6 +703,7 @@ impl EventType { "dane.tlsa-record-not-dnssec-signed" } EventType::Dane(DaneEvent::TlsaRecordInvalid) => "dane.tlsa-record-invalid", + EventType::Dane(DaneEvent::BogusDnssecRecord) => "dane.bogus-dnssec-record", EventType::Delivery(DeliveryEvent::AttemptStart) => "delivery.attempt-start", EventType::Delivery(DeliveryEvent::AttemptEnd) => "delivery.attempt-end", EventType::Delivery(DeliveryEvent::Completed) => "delivery.completed", @@ -1436,6 +1438,7 @@ impl EventType { EventType::Dane(DaneEvent::TlsaRecordNotFound) => 75, EventType::Dane(DaneEvent::TlsaRecordNotDnssecSigned) => 74, EventType::Dane(DaneEvent::TlsaRecordInvalid) => 72, + EventType::Dane(DaneEvent::BogusDnssecRecord) => 605, EventType::Delivery(DeliveryEvent::AttemptStart) => 77, EventType::Delivery(DeliveryEvent::AttemptEnd) => 76, EventType::Delivery(DeliveryEvent::Completed) => 80, @@ -2046,6 +2049,7 @@ impl EventType { 75 => Some(EventType::Dane(DaneEvent::TlsaRecordNotFound)), 74 => Some(EventType::Dane(DaneEvent::TlsaRecordNotDnssecSigned)), 72 => Some(EventType::Dane(DaneEvent::TlsaRecordInvalid)), + 605 => Some(EventType::Dane(DaneEvent::BogusDnssecRecord)), 77 => Some(EventType::Delivery(DeliveryEvent::AttemptStart)), 76 => Some(EventType::Delivery(DeliveryEvent::AttemptEnd)), 80 => Some(EventType::Delivery(DeliveryEvent::Completed)), @@ -2710,6 +2714,7 @@ impl EventType { EventType::Dane(DaneEvent::TlsaRecordNotFound) => Level::Info, EventType::Dane(DaneEvent::TlsaRecordNotDnssecSigned) => Level::Info, EventType::Dane(DaneEvent::TlsaRecordInvalid) => Level::Info, + EventType::Dane(DaneEvent::BogusDnssecRecord) => Level::Info, EventType::Delivery(DeliveryEvent::AttemptStart) => Level::Info, EventType::Delivery(DeliveryEvent::AttemptEnd) => Level::Info, EventType::Delivery(DeliveryEvent::Completed) => Level::Info, @@ -3059,6 +3064,7 @@ impl EventType { "TLSA record not DNSSEC signed" } EventType::Dane(DaneEvent::TlsaRecordInvalid) => "Invalid TLSA record", + EventType::Dane(DaneEvent::BogusDnssecRecord) => "Bogus DNSSEC record", EventType::Delivery(DeliveryEvent::AttemptStart) => "Delivery attempt started", EventType::Delivery(DeliveryEvent::AttemptEnd) => "Delivery attempt ended", EventType::Delivery(DeliveryEvent::Completed) => "Delivery completed", @@ -4072,6 +4078,7 @@ impl EventType { EventType::Dane(DaneEvent::TlsaRecordNotFound), EventType::Dane(DaneEvent::TlsaRecordNotDnssecSigned), EventType::Dane(DaneEvent::TlsaRecordInvalid), + EventType::Dane(DaneEvent::BogusDnssecRecord), EventType::Delivery(DeliveryEvent::AttemptStart), EventType::Delivery(DeliveryEvent::AttemptEnd), EventType::Delivery(DeliveryEvent::Completed), @@ -4652,6 +4659,7 @@ impl MetricType { b"dane.tlsa-record-not-found" => MetricType::DaneTlsaRecordNotFound, b"dane.tlsa-record-not-dnssec-signed" => MetricType::DaneTlsaRecordNotDnssecSigned, b"dane.tlsa-record-invalid" => MetricType::DaneTlsaRecordInvalid, + b"dane.bogus-dnssec-record" => MetricType::DaneBogusDnssecRecord, b"delivery.total-time" => MetricType::DeliveryTotalTime, b"delivery.attempt-time" => MetricType::DeliveryAttemptTime, b"delivery.active-connections" => MetricType::DeliveryActiveConnections, @@ -4997,6 +5005,7 @@ impl MetricType { MetricType::DaneTlsaRecordNotFound => "dane.tlsa-record-not-found", MetricType::DaneTlsaRecordNotDnssecSigned => "dane.tlsa-record-not-dnssec-signed", MetricType::DaneTlsaRecordInvalid => "dane.tlsa-record-invalid", + MetricType::DaneBogusDnssecRecord => "dane.bogus-dnssec-record", MetricType::DeliveryTotalTime => "delivery.total-time", MetricType::DeliveryAttemptTime => "delivery.attempt-time", MetricType::DeliveryActiveConnections => "delivery.active-connections", @@ -5353,6 +5362,7 @@ impl MetricType { MetricType::DaneTlsaRecordNotFound => 61, MetricType::DaneTlsaRecordNotDnssecSigned => 62, MetricType::DaneTlsaRecordInvalid => 63, + MetricType::DaneBogusDnssecRecord => 339, MetricType::DeliveryTotalTime => 2, MetricType::DeliveryAttemptTime => 3, MetricType::DeliveryActiveConnections => 22, @@ -5697,6 +5707,7 @@ impl MetricType { 61 => Some(MetricType::DaneTlsaRecordNotFound), 62 => Some(MetricType::DaneTlsaRecordNotDnssecSigned), 63 => Some(MetricType::DaneTlsaRecordInvalid), + 339 => Some(MetricType::DaneBogusDnssecRecord), 2 => Some(MetricType::DeliveryTotalTime), 3 => Some(MetricType::DeliveryAttemptTime), 22 => Some(MetricType::DeliveryActiveConnections), @@ -6042,6 +6053,7 @@ impl MetricType { MetricType::DaneTlsaRecordNotFound => 75, MetricType::DaneTlsaRecordNotDnssecSigned => 74, MetricType::DaneTlsaRecordInvalid => 72, + MetricType::DaneBogusDnssecRecord => 605, MetricType::DeliveryAttemptStart => 77, MetricType::DeliveryAttemptEnd => 76, MetricType::DeliveryCompleted => 80, @@ -6360,6 +6372,7 @@ impl MetricType { MetricType::DaneTlsaRecordNotFound => "TLSA record not found", MetricType::DaneTlsaRecordNotDnssecSigned => "TLSA record not DNSSEC signed", MetricType::DaneTlsaRecordInvalid => "Invalid TLSA record", + MetricType::DaneBogusDnssecRecord => "Bogus DNSSEC record", MetricType::DeliveryTotalTime => { "Total message delivery time from submission to delivery" } @@ -6726,6 +6739,7 @@ impl MetricType { | MetricType::DaneTlsaRecordNotFound | MetricType::DaneTlsaRecordNotDnssecSigned | MetricType::DaneTlsaRecordInvalid + | MetricType::DaneBogusDnssecRecord | MetricType::DeliveryAttemptStart | MetricType::DeliveryAttemptEnd | MetricType::DeliveryCompleted @@ -7060,6 +7074,7 @@ impl MetricType { MetricType::DaneTlsaRecordNotFound, MetricType::DaneTlsaRecordNotDnssecSigned, MetricType::DaneTlsaRecordInvalid, + MetricType::DaneBogusDnssecRecord, MetricType::DeliveryTotalTime, MetricType::DeliveryAttemptTime, MetricType::DeliveryActiveConnections, diff --git a/crates/types/Cargo.toml b/crates/types/Cargo.toml index 2922a279..b5a5ba6b 100644 --- a/crates/types/Cargo.toml +++ b/crates/types/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "types" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] diff --git a/crates/utils/Cargo.toml b/crates/utils/Cargo.toml index 3f9d2f83..b4863371 100644 --- a/crates/utils/Cargo.toml +++ b/crates/utils/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "utils" -version = "0.16.11" +version = "0.16.12" edition = "2024" [dependencies] @@ -12,7 +12,7 @@ rustls-platform-verifier = "0.7" tokio = { version = "1.47", features = ["net", "macros", "signal"] } tokio-rustls = { version = "0.26", default-features = false, features = ["aws_lc_rs", "tls12"] } serde = { version = "1.0", features = ["derive"]} -mail-auth = { version = "0.9" } +mail-auth = { version = "0.10" } smtp-proto = { version = "0.2" } ahash = { version = "0.8", features = ["serde"] } chrono = "0.4" diff --git a/crates/utils/proc-macros/Cargo.toml b/crates/utils/proc-macros/Cargo.toml index f2ffb76d..3077e42a 100644 --- a/crates/utils/proc-macros/Cargo.toml +++ b/crates/utils/proc-macros/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "proc_macros" -version = "0.16.11" +version = "0.16.12" edition = "2024" [lib] diff --git a/crates/utils/src/cache.rs b/crates/utils/src/cache.rs index 3c3f540f..d747afcf 100644 --- a/crates/utils/src/cache.rs +++ b/crates/utils/src/cache.rs @@ -5,7 +5,7 @@ */ use arcstr::ArcStr; -use mail_auth::{MX, ResolverCache, Txt}; +use mail_auth::{DnssecStatus, MX, RecordSet, ResolverCache, Txt}; use quick_cache::{ Equivalent, Weighter, sync::{DefaultLifecycle, PlaceholderGuard}, @@ -258,6 +258,12 @@ impl CacheItemWeight for Arc<[T]> { } } +impl CacheItemWeight for RecordSet { + fn weight(&self) -> u64 { + self.rrset.weight() + std::mem::size_of::() as u64 + } +} + impl CacheItemWeight for u32 { fn weight(&self) -> u64 { std::mem::size_of::() as u64 diff --git a/resources/schema/schema.json.gz b/resources/schema/schema.json.gz index a8181418fc77d17eb816f402a8c6b3bc5f5fd299..634bb244e86423d78bc0e09689a765620376e429 100644 GIT binary patch delta 96123 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�Sz`y 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 ?Oz!G$dqOQ<*&E5L`PO=9 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 AH~;_u delta 96057 zcmV(tKw3!b4rz`lv0t-FAMx!H_+e1cfz;k*-mrf186|NVT%HrB?SQ zUp(a77y05IA3gc?LF3I%{+h+3jt^tb7@|F@mS=)YJ)(t*S4}$fd~v%X2awDb)b>C} zN5=+n;Ni5o8Rl{4E4uy{MLjPzb=DNjs^X@oK2x8EEQSvgkuY`-g_*En@33b>##MY_ zA1=bXd$$}k8HV*{ zyfFH8-YSUS4V~TA#0&$yAiCMQO;CVSVB5`;vJg$8kKYd?!4WXYEHaw?1Xy27r*QS2+N&k6VEXwuL)QRr% zSILd_I!(9V3aWsa@mA#3iy!R$c6Rq`lR|siN@YP(JZ#et#=kR z&wx-B0~SAqf3Hb`?g$Ly(K=17ef~~wBRSArvm4}vN?r>NalL)Lo2&L2E)bWz@2T;m_a0Tjviy z{P5imshb3MV7z;jrRU_HyGM^{E6UvRc*Nk+%c5B)e`Z-_n&aA?-WS>7rGpr6f%8@P z0(z;@$bee0p&h>d@g?i=?HtW-yYP3Tz4iBWG%tB#{IDbBGMdJ}TA_*m{KX1K`l4x( zSeXjH{r>y!Uzb4^r`^*B(DQl49rf5-o)_B{Q)t$fn$=np>u0+DJ=1lp@1D-lRQ6{T(g`gnM?>r#Bb^Wn!KGhnKZ#!x2SoJ2l^zN74Jc=EtGHk!d7ARMK z?4Sy{QG21kh5;i+)z%X82}u55I7nSdu{nM7yog7_;Pj`{Po&(Kty%jK0r#c?aPPP5 ze=A#!!Jfdoqf?iM?DYHdBO*|sMEJ(S-AHs?FtLs~s@82emMkfhAHt^QQ9SdLf~;*d zu7#OO4Q5!H3$Nz}!L; zBCr>K>zew-)vsR#biqBBGcRp^XZh9cypP&LMs2GNY$7s0TLxj?VCe>3na<-ui{sc1 z)E9vmvK6L-xSRjooCo@6ij2R^tZV|7m?=a^#ukj&Pt512Rg77&9TEr?0bVMue?}FK z8?}1alUrG~al3!d5 zJI4BlkV>HCUcg~N%oMj4c4OVofA`_z*kT%Jnm|`?nz}^zYMr!>A0sj$r_v_2N>S8grH!fe7icmJSk;y*C6h)307rjQECYR@A zi8J8&@pq)n+9=KJ+#iZYF7DM z|6&fzzgPPd!6RYPkqoU|HZ>YX&dpjc*V0W~0Jh zPvFd}8sJ4>?Y4Pv@P|i{9*VOmqG{RLQbaFAi@Q~ckMD2)ch_tXG{gVR&UT8Noz; zuGu@+BBFcGpb;{8vq;gwkPseWI_Z@g*~yTMuY`+y{;@!_W?*PcA3L(G*R$H{r}7rj zEdE~MJvgOrkMdw~Z@jP6RTjB>zLNKdIQYL(LKAt6!i7$Me?&LtSJQ)|gT0xVcfw&N z&ZoWdGmSU&%eAYhwOR#^2a+PsSa(kQK7Cp4LR0mfCf*OuYXMrvNoT zOYz^Fm~6$N$4BX1wtKR#B1yq-+znqD=B4b5X&;rdt@2pVz_T1*pe%Qp{`m;1XFw78 zV_q98ct9WLf46%E1$tDBP74~{3AxZC_{;p;>wo`tps&B6TT43_?ua~JT2fNvi_Z5l zqkit_*p{aI?%3LgIr?jFk?-#lO(nJ-ueJ0MyM6>JfOW(?guoqEdCc?jJ)?t^J_k^$ zSn(_$&<~x8KF~dehIil;72bczPo_>vo`j);k|%6^f1#c~(9Jy%#k2g(dp1xystPvS zAizqMHSif+2SY$ia`OSLb5exHPpLgg;J<+YlTlZp{PODe;aR1&Z zpSR%%f4asqPW2M{OR)2xa4%>fce3Nzt`Ub|j~fz}tSZ>io#r!aJFqG>iB__Ubx)pF z-3l%;L~MTq?gy{(gWLIaUSADHYbEZhFa^o87+t2iYaAh>>Ky+C*)@1$rKkRgz1h6U zKX$t?5Y~C{;=(0Z#xAeOmf$X;=Z=PVHfR*~Fyd+%8e> z1v=dI3^zb^Nc^_A!R^Fkgi-q>xDyScoJZf*NnHF83I5FOWeOdCYk&tB$L-w=wW7u1 zgq>7lLSZ(Jp~Cpzz5(u(wzj)qq&bJlfr+SfQ}+g@C|9aG$*${ZO>YNXB3LBc3Am>R ze-`UOYc=IY&eTk8AIyO3Cx_0g)ETfQ@nF)PhqYq7^fMC_fqA7;Gvse*CHKzWXK1Sh zdk4)*^6n!@mG+Zd85Vy8&TM;zEIbQe@vWyS$&tt>Xv<~-A~0us;i1gnZar*4K$qN zHOZOgkEJRH(zw859omKepMGBtsm0S;>2(ncnM?1kg7z@_`8rk)-N#{N?hwfdZRyfZ z)J!$!Z8Cg%@};W_W(`3*sA#_MH|~I}5t5TJQ9t7AMco+S?Lo&F6SS+VmGey)f6eGb zrOqSl&y?FAV1=>NUS5G5CU1AEyj>=ooF362V_+2bBDWm7J+5POHPVdgY}3E(fPDl} zE}HpzS&W@KU3#0&ZU3nJ?Y1Z!q;-E#FJcVK!u!0xYE<{0b|3n?vtQ#jC8D#9ukI z^~#^iSBbO#r0Gp~u;(k_`3m@)SHKfK^xA?&8}lM=%&Bu@M-NdI2SZ)0D%eXG+j`uL zoW!Sm2GQT)8FSc|t35V#jR;-uZJ1fk4$sn24DW4tse29dornE0*{n>8e?{oqwqL{6 zj%W&sCUB?iRbGPtp&e}#%9B;HaIVqS$6nPj<4{S6>*X?!foe`UWAs*j{2A+;4Fpvf zk}~@6ZX{VfILvHd$?9*FV;cqbcXJUxUvxqoq1=1Y(oUDiy6x8}F7{8Jxli*lF~q-L zz*07Mn#fXgKcLNGEmpZff9$p3@1RNThI{(HdaVb@B(g;LW{fCq*ZEeOC;!ckg(tGx;Bua`ZE!>b{+mq>t8Ygd zU+y38p6_M(6{vu(uw%-A{88>Ynjd^Cv~^yod3x$gT6f2!uUHnbfAe#ZJUC-lGaaRm zGn3(2`9v=0rk<`rL)~@fMO}Py4J?LW2T%iv%4OhaE3~A9s?MDKOBYy#tjV%vcklQ> zdDeCORWwt-%cyHu05zOS(Z98O@^49iI_+HbJ>g*G49{^nVp@{r>JWcmWr;`|4Hk{BU~c!%2N*m}eX4OKPFR4JsCH zSZDf7<1kgTHjmi?{BzC?LPX?oVQsi|sOaNtYF>l{q1pxGizEWDxXf>NdkihnkFpof zRasiTw&>eCWE%2&%fB~R*um+5aWrCrJ(c5{i<1Oj$0b@$m+YyNQ-BBHHn`u9j+igj_`9J0-@g9Ct5*i=o~Wg0 zuZkI4e?9dZ?1{XmmHg~5#(F9t>f~_W96s!EZG>*h6bh#uP4|`299!BwZj7#{bYRl( zHj9Il!J#`xe~$&+z+0ZY8&qVz1;$@{JOelO!KXykK5Y78seLmaSH9+qV6%uz_9wM ziSv0hSevSlaXy>5=hb{&v1o;u07hXPW&A84w$ibF%DU`Jyw9QCm_C+r75Jm#I~;bz zVU-@vckF!ix3ceJYGGG$1-g#Aj0aA#_$$W2p1pRU)aHO78I)dl(wz*m-Ai=}}5 zNlcFBe{c2V^q&gYTHG1U={`C)rm5#!giDi)M|_x_M24QT-GBXW9-k)2^=)}uEMk6S z(VBfHCI{>W0Ksqn- zE(U+X>Abh}_t)(xE17h3+~9PKOwcQzkj{#FfnRt!l=SH5(x?qZ7eM5-azFYapEktB z>x+R--kZAq!PjQ1?E{~I=X?KIwve~_uU(>n^W&f9dX3{)BraBOW;WcZ*Lk}j8FQOEcW(?Mgf5QQ2+}_mpABxOYZ1PEPALb-_$ z#F@=hv3(ddn+Y`0gA`>rjio{JK&2H$8pL$kM2qs00MPr4o2QGllkuz*9oquHf$3AB z%hA`97!D)&=v0Vu5O+ledydHupKfX#9 zf>vgo#vU^L%D%q1>x=H2F)U7pm=(kNoT@vx6=zu((kBfA|BHTisN=QtFyF1p;eOA9 z@y2o+G`B#3`DHQ2_h7OI$I~E*!F0UNW zrO4@Iit);~fkYIFP1yV4a2MrYg>eW_&-4=~cPfe>EWW+jZ>t z_8pvvVdvf*9G$*Acz1NF=jx$dyywJ0|B}ddI_Hb`tpi!r@LO8L@gpC-#`_?4ibwb_ zJYY@h1Mw4ZX8L>_RjKlynWmzGaCvOJGAE+h8W8v0-T&gm5O@DGfcLne zL*51cxP2ROsUuh!e#CN{-4H9<2?+>QrMPu?J6;tv3fYjB>_Xqa^DJP0I^3Yy?8!~e zLF(f0lPZE;Ryr`0Ch)7F2IY#Mf1bb;!c2P;_70y#(y!`!f>rObhT=@ z=ZBu|n;>DS`Tb2-f3ofeE53@jBw>5>du(z_Wn!YS{FDAFw?k1;(clR|H5Z?GN`^UI zd+(}vRnRlFBS-VRXZAZoJ_~PMp0eBe8Hznc8&m>@UPiCFdp|^}e^cX z_xjQL>G9~%Nqsdim{;DxlZJoa`fg`-x~%8bdSL^dJ$?|tf6o-iFs9%79mFn-s^y+? zxWX^f;bnfS2s{cit?h16pg-6#7ze2b9PzQ_>Q zyIC>XItDblZq{vew*xBC694&B6d&LLih|+T)t`n{enJ5pzXTZvF`B#+S;svj z#O&13_^_yse|^soDCc3uGg~q+HXW#hVs5)7>EyX|5e@WZ!HOpn}b|`ArHYDPFx$j4P*0o#v z>yG62;f1Q6L-1_{9ArgSMi#OjDQG zl!-nJYf>s`vWiFZs+y}S+-g+Bs!>u)6Ok@MNoe4RK9Tx<({*=)PTvb4BkT*^d?@rU zf9V;~QUF8@!VG!a@-&i+HEFWbv|N_26m@)Mrs}JbqTx9tf7C>duN?N%;J8qhxqC7_ z1XWAbv>k_Cz1ki+@p)rCZ>*=Xu|Qk|o2rb1TRETp)M6ZK_uHVk$}_|ntqNtR3Up%H z+O`+*P}(^6D<_;bejiA(cmy3{TU?g6e~B+rp7q^)w2!u+D(VxF7%z>$7skp3H+(&$ zGC0=Gsiu|Jjq)L-gHN5M_c&SYY@*Xp^(iMwxgM;R5<184XV)i-alyOU?930N&1}nf!PYzdrGcKjBPC-uXmihs zNU?~(E>REZZ0h=Lg69q$w2u?w_@DIh@2}yQ?yJO|v@B~<-R8#Ai=NA*s9UaKv#wy) z4U`g@kg3Jh7q&RC%n|b#;8WO>e`ejM_06$PPu2CrYQ|4_$){b8rf@6JmloDS_H*@o z_$3qGOm2p}H@3T??MlBU+$l4EuN`P6b35ZP@O(S}W8KcrxAF6B{Cpcf-^S0k@$cz2 zp7skhvA>bD@?uR`3X8#yaUroG6o4HHj>zs4@y6<|sfuTL>9f4_Szh`ee|f2QY}qY( ze<2>9Iq$ooO@~9Q%Dfx0Xj1NmT+Bu&R_$%2lO`+eU2N$d2!l}+pky~j8L+|E$U!Nu z2F7m-DcqS(f&qElAY5kG&EkO*wP(JW_Stp%8hSOEUmGXt!5)HRf>?QBx#--`82c8E z1g)GQ1O7*b!noIq9-)Kkf5Hj5;JJ3IW_FZ4bxAY7asmQ%RMZtz6V z1E=VdrmJInc;Begpd@JTs6)Fw21kh9vbw}1??2QW$6M z0XcrYk+T^@JHsc~Uz>XHu%Wl>uT6cg^Jb<$Fmiu9BK(>OZTv|1Ym)uchcpcKzu!+4 zC;3Zpv7g_>LKNhSe=|0BsO~&=(Fo-smKNUF7;4lQpTdVVq6x7qXvWU!H@;7^$O^gP8nD} zcuAI*6sY0s{PgVY;mN*{*qL}5P18HoUS#LG02v}LVC2`?e`|6DlYwOC*9f4XxF;<1 zt!9muIppRjK|qXfsBi(V6qsT-u-58$$+`yi!n`W^S&Xv|@^CtW$fb^h)WAh@o!^vA z`(o>N7DB~57NKBUpMy}+9+ALYe4M3(V)0&UNfn(fybd{DZy#YPYV?V_E-Df-kbtaN zxAWpLM0cvQf8E$_+W3IjH?{ORpUT)#ewS_E&yl|4 zd*~Wxf5dWFMI2H38oOu~Waa(=e3Sn=5uach33_=)?OF({BfoXbZ$NkTa$#%zOOF60pw{Qmv^3#@~&2`Z!+D&od|NI{;t9u5#PHUS3_(U8Wm2zROe^bOgHMuAjqJ-0- z-ikGKEqvc)l=jqim!6@=+FEbhqIk3J?z}CQVfstTkedWEF?4q4SK!3R&fKjke{*J- z7AboAsSb)_nk@RBE)bZ(n_O&HPR~?Ec4qH1ZwS*5XKwHD=cAt%$3SZr&24gle{}vm z&I(W!6*a4`bdfVk%5MiN~`;upz+mp?)2s%E0^j-3$cwDA2&}#%G=bAtbm&mY2Hot5ckb z#h3fOys{DUQy$q~fm!37f49!OMh@Jy7PL5fi&ETgz?k3gP|fv8lQF}|pd6?4b-%2< z(ll9IjtRn;wgiM5cJV*G{i$j)>XYBz8OUw${BkKwS1@^!z(^yCu8f1Ur-FRueN+B$+1 zX3*`o-0fY_?PzZrCFr%y!vuI0GlOvKuY?PI?5#vqBLo4RcHS(-x_^WgR%Z7wMxTs}O%RgnCWyOidO&IZuIf1OnY9fR!X zIVPd{!6jyG_q_GZ!WuDou}I-+OrF}&DWhnyOPy}lpb69#j2EVsqG^V0rjX`~9X5tm z0-l>a3^7ioe*skqT(4qAiguz;%D-FNz;yem(@yt#<9dF;eoWa^%3V?J-;_-Zob!=- z{|@%giR3f2;0m*{keQ}TC16X`RJp3Ml+39jY%ZA^inFBNTg)!0e1hCMi|d~~IDYr~ zE000poPLY!9%cvHq@Wv`^9}qtDq!5hT{Ve^?9Nv(e?Rl$x~b?mCzWjXyUj+r$ zK^0OH%PL~*)aIE`#YLxrzg@cx#b&}luFLmUrqU$!@%TH9!|uP^Y-~XBbn{!uv6cTU zZgbp&xGjZ{G5I?4oB1VgG1SJ7=wQ^s`fJPU?uX+L&A0a@WnGoLFrp#!#eGI>y&HC3+`)}!oxH7_E@c4amn*?J^AIT z^ud-qRGc!g&S~T9_kwvmSE>FBy%-~-f80tE0!-@};|4m)qVuE7BuWx^nJ<>XtDBXU ziSrT!#GG&85Ce6miyUL6#owHIYZ@b1)Bfxj4E0rVDw|`nnxYTM18&*8N zYUgiNfVKpysIu%)$f3+Vb~xF<7IOW^IKF*3#ywB=B>P@;@|oLSzAcIcx>anLXI(5h zNjD(RlbrJhmEum1YQYnl>V`94da4}0?%1JDTGvoUrgB^xj(SevxI1YHf2z_1&7!qn zo*D z*?Oi6xbz1lR19^mUZ#?R{lIbN`@7w$ysDRSsSj0NW-~pN5(YTd(b}U*?~mnDK>|5D zjcRG2AW?Q&RP>PaOPh4ByzZf2-lTiwcNg7iUo7+P{`4%{KbgXGf6hH2irXPsNv94} z+{^2xMqmM8e;2HraBpHa*Xk|?n((ZKWCPlK$URxk-VUxzx4QJkgcY3O#P{}|VJaf( zpg=QYszpY)48+XA0b(zdt`_>`=?Up?e=Zs{AJGOYF~u@zi}OCuloUt%;Z^8=wO&y^ z?2o2ymdzRzy`-+le^i`x))B8UULE|qDA;Fy+4O}Yn=S(N@n)XV2$ej(va9#&v=ARx z2W?*B3yStWhpP|Y3wij>_sU9U$1nE>S?&)pYns_#W{MoLx9oQnH_Te)Z7w(M)TD`P zbWz;mQaZa2R`L*&W92+;6P6`3q)3tU%R{;re`)oxTJ8+MKE7kd~>$SdIKPtO4XdP@}A;eH;6VNsiP~ zwlr$@g=RQh|^ zl{8R>F?Ng^MJ(?KJ*vJ7>^93-h*=E8ec&0gC%*a!&9g7dQ~+!;>%!Y zvU@OuG$4-~e1mvWgJu#`;vr@dV@)J3@Izn5e?;O<)AXQ4&eNlwGR~9p^o#MNSms^R z^}bYg0hQ$3#|}c>=|xYj zB}dcDEiM?&8qN8NeRw~5=i<*QOZ9UKYzB&a^fBqa9eMY}uPAs->FsAv+>(^{d8TW6 ze?nou!mim)+5aY$N33F3pa|Hn`gUDa6Y{N@Qhw|;a13v>_Rg=l2cIn9duZ|qAA`M* zU5*=$XCry1s4f3YZDXg|BSyiA>$5c!j`e`Jf~R}eBcMjeJ{yXl*ZOf@!?Z0^Px3|G zF~z$bg=%UW%*2616Xc$?hxLS~GNY_+fAGXr_-ti8S#q5@)v?GoD-g-zlbfF7d}-~_ z81OB=UcnE`T_Xk^AH2x&0#6D|;;($LK%?`IX`UAw=YhoK?(6{Pn_hN-xuvjXRz?Y3 z#Ni@h^(>0%3&B;~#bkqafa%`zq|tTVg_pfb_snIzml@g0itqV*f0ZwBOCma0f4V0? zSLYYPOyH}{F)0PlNuIe8Ossx$wZ}- z;wtx?THVSzJJyN|!yfKK16;GQe`cf$vW1~eD1BxZsxvzu?Lct1{*#EI!oydP_ejBz z7FUSRC!Z;loN>A@cGk#ZT_6d!IUY0uU2n75QCzvKW@FY@!i7@Jk*(}r!0e^V_m)*l zn?&d0uvj)ed<}cr7|4~R_s?9ES0I3{-%n{w!xXeP-8fjdE!gFAuDpP{e?d2(*oTr1 zK>CxL9DojW$%yC;J08g2==G$#4Qw-pFOp`Krs`o0uRe73^k2R`kl&&xqLplBTn3@{ zeo_YUG`*ATO}ycDhO!5#Yg|*KEPe*h>JlYwsFA0qg?!pN`I%E7@=ez#qZ{bZ8+=t3*rz=$_H znDAY~U6+*VE}$y7y~B)W;Bnw#Ur<5Sw&%lDc@IRIote%E=*c;+e`7>7b)&ZE(cd><%FUC()Oy zDkEZ;zwouF%Xs8T2^Wls~i~s)v^N!>l`Ge-;U1i z6Gx7ck~oD())8-ysQ4x!rCBkkn3UOSq%mJ;%jR6W6&+;At@(VrGWg1zBIgUPKZsh6<3UKTHD(&f91IY%pjFm2*zL_8@%^z za>UKb&amv z1>Mkw%4QijIXhvjaOaZvP=bPT!A2%o4(As}5vUu+M?}72&Q)D@1MYxqU6&x>QS1iB zUfO{t0MFeHe@N%MKC3|XTx6|+Q$T%0hk(d*c^EU#xBzIt<^{VZ2nC1a8Jk^)GGikw z_NAn%ACW1CF(@nucgk^OI(ZwrRkZ^6{7i2awMysBI0N!~Ky^vmki7et@Z?rGo?leP zH9Wbfp~4}`jkT7hU;NJ4Erew^Y#$sB%1Om5AFFYqfBm||K=#+g%^nb=GPi^qMX0VW z?ktuyQgO%eV^xzB-~d?li#2Lfkem>t3!wqk`Ww%#hIRo?*S=LX|aUG=SjY&+p$8b#4A8+b?I1%m!VBiM8$gZ1pD~^J-FlmAZ z%vxOdf5)64K97~|`~6WL_@yX5-uDBGTqrSe30L;e(E}|t%X1yhEZV!YHAEZO7#QOM zZXSjGpm9dpYU-El7yyK9l7x+q&SgcFEi)jK!kB-!(LNT%3L}LSxV=gQm}I?#5*g~- zPI)ZoNY9XTM-nWg*1YC0WU7_a?Pa<(WLTrVf5UK)jGFmYSlg!RguX;#6g^nuxJfD@$<8*u*UcO`;Jan0;+&4sm_ViQhMlH<&yPLY4! z3t@0!JMNUTd!Ww|$H;J5i(`L z5|$3pO8Ly*;RktHUo^LTVg2!V_e|Ymu3#&>=Gh50nhfVw@EDSNO^uP9g4?9OIu@bP z_zx#ae2K&JtRk?+)DA0naIyB?7Kl|he`10|oDIJTo1Ia9tOcAkl2qLVwP`{FG33t3 z%_F;5$fqO`O@iKLaOfZ+$X)b&Ho5mbpS7GxJNR&j89u2Qh@?vrPUM8%L3Zd`?qnLZEv-OpX{w!Z3Dq>k$Ho(YZ^6T7PFwvb%Vf50Nk z7=8>|WP!+Ii8dF`N&boA?`VUoKF6#btDo61_-s2KW@STBeGs>j9s#`${l=CBMrZUm zW?0%U?4WI%H2$OU9^+!sje|L!n;Ml4d~&E{2*bmLjdO%oey>>q4GU1>V~}>~WFIG! zCTtM?R*Poe4ZVnWg5rBDCU9IGe;9t4(j(;$>TA?)Nk1@7O4dn36xn4nCOX@@{8~M` zM+!PUZKU>q#zF1-+GuyvgeH{03FEiGi7M(prNhtrO8l(=C`SXlh2B9^Hgu2p2FEqTgdime?pZidylYsN=e9e-{(f7~W+< zl^+o=U{NaRS>dauILp-mnF?q?KVVNUI>(~s$V++)N%U%c0T-B8l+t2Qs7*g)M=f`+ zE{sBst9!b;*TroQ*CpuD8R1u$Io$S{&69g>E0HvsDJwh5q!*`N0iV?I9^bW@!qSm< zXGGOuJPn<^h-~@h|0-wcfB%{MU(*5j8?A6B|Led0*YbZY{wJh}Y;ciU%q)EFk*X9K zCyPzh!`=%@Q)*b6nJm9FKTCCKcaeB!#$dDQJk-vudIJyeA*5Ngif$#~-=V;KxI%m? zvRw%dl+>0igd<@Ys>(@CNchC2p z(KYUku0eBsSU=KSf3HIzh=e%-IWyiJ8l|1f1yEMz-C+5v97WP9*}WI$VU*e;Y977TyFjL}jx`$%Kn@ z6tTW3u4I@4s*@3bpdch&;XpjPRq=!1$vxyLOIg9Ks&-XK?Ogstuz0FMWDU8-E?(fi zL9v7F5tQ#%mmWgIKxs7YY`WmKa8iRRaG3Juj@LEW*{L-WAW5a-!;y=8Ct4-L$@Umm%!}EXSL-3*YRWDaTM?nH71}R=5gWb^s^**pDq1r+-RFEU#dG<e|LguGt)ghQ)XGl&XuSzezr`tQS)U=Z#QG6+UXz<8LblM3^mMfti~}~NYj=L zZM_w57+8CoSx79ZgNH57hN(W6(ifz?7Vaxjm^V_&LBBtrFk#j3g`UPT!-|Y~OWV(WApNNXNHdf&SNVuZb0uI1lN|)QZ7mVx0je z*$_JL@%RKRjSw+@QA+c86}r09AEuk%8@R0#J=_P!v5Yn7))V6(v4b}dD$67BOX^3Z ze^-{1gJ=(zh~ic!*!H5zSDnePrz$@5eQe_y<)*&y{FX(1z1&UxpFH?VI%4b$T;u!Ij# z=>vM5R+S0urB#d{2{mDP?Bl=eWV64_b~1!8Ko*(&_0`LrTU)F#C_6cDSo0!sG3G~H z;XY2cH3xuRnZA443p*ny{u>ZI4!S4jJ-Q7BK4ZH&Sz=l!pJa)ns8UffOq%j;e`~ZT zc8EJz)Lq2c5-%Ycag+>tNXES^7NrVl;shS0{7e>byEI>&*4h%s+EU$Rv%Rwny*4Q; zI?;5}Y&c=M0nDK;x)lQpyXOUaqy?J|Ts(ub3_E*PdH8y`_r-Payb_yNLR~iZu!Mr` zp)B`;gO3{pY4c(L5O)lw_8>T(f9LzfQL~bTbqp<0fx=A(sCqNp_?)NV^~C;H;jCki zsH@ULVY~7pW|txq_Tls_J1Rr$UXb~u0H?-KT`zz_JY*2K_t-c&upT|*oT$4#@L;R_ ziq>itbm7cqW|8hVbwOJvd{z!o84a2uw*@ZaBTNjjp<4v%8etRX)A71*e;!E42rcVr z>)-372tcU-t_b79QEZUgAU4Qt|4cbpK&w)Th4Z9fk7>_5Y&W9wkM~P5p3# zs%$jsAcz;;X^J{sn*yQ-ZcVQrI(Q#Be#Vg2IYVkh%C_-C9_&@k8nw4J?|DN!*$wd~ zFBfZCvCqdMY~l}?#3KfzL%FB0h5`QS}ieDca7#)H@cAIsH#v8o!e2_P|3sn5IM>F$DuxUFn_tl>fY zK<)%J<3TtA|B<%7*!7D6V=##njqD#PmDohjwEBc-^}*MA5CR)xe*(nb;?K+e)Rz6S z$_G5)p4a{#b?srL`vPX>_Ca?D1qAWd{+W^gN1>5bUKiElaq({u=;L$p@VzG*em;qQ z2UJF?`bBY&cXwarDDuigfJ`R-cEtBeM=Wujub%1V z$&LS;0YT0J`Df7pxV`E>c6Qwd%?4^{MdmEoP_%!!co|4@2BuPTgwDDwVqgmvOf5r17{h2!A)X`j31*sGs z$W5c>vz+U|&wrGGa;KbWfL_f(@x@AK6e^d_yD=`rv;vJleeBrX@R(+;{Crbl|7t049H6t}_&wTsukUZ+k=AvqD zA4#Ca!mN#cxKGtc^AnJ8i01VR(s2aKYf*P(lqqfV*iQ4A;-4XdPdQbo&xHA83G@e{^44tuP24 zAH$Xy&s6eMspR;szb@x*iX0&s9-mgilP~6sq6$815}rD>pi|s_)9(#H!#tuu9+gON#7UQvqN=a;*L^(xv`TMCN|WX#_>e>tH!1e7={mhrfG+1FMP#&2 z&26;@Bjg$LX1U7S9`S6v3E8tbYF?f<(UaXoH`fniELWAv_YPZ|;h(rpoj_UORts&p z=g`A7@C5Qxdn(ocPIGg8P%l=E+=8bc-eo5FnJ}L$VV+e*_wgzC=*G&9})V1j5)0SBSCCQBsM-7H{)u%a+@!#=YJ;5 zCrg-ZUUv^WwjxT8qvpzspE_QC^GqvGf0kCd^6C-IhZW7-H^|SG{Tdl61u$BgrtY+SerPkH@KV$uIzXRRaBpn6)a!#USZ8V&Ec( zA-LFTP>zpG*}`y|Rw`5Wb*eY*e+L*mHEvay_wxWXK+3=C-Kq*h*Y9D@1hQiB>oE)j zr!s+yP!Kjl%v05TI!BU_HFhyQGZ|r+>STCo8_w4cJMH9n8}cX~Z+nixfG_blDWa|J z+5B|lsbJm6ORTMAAJv+Rm}p3PS^SB;eLHNyC$Eq`F5 z7Q12wIW5}_w&qLzhtAv7E+uW*+p;QB6O08^zB|3Pp8aT7^CX$@q;9xl9bS0a=l#0N zP8zlB)T4p;#~2GfD+wB-=itO3I;!yyW@k2zWc&#(t?a6(3yl2(c|)JezTTgne3MujZVPd3l4jm2!H-PFd+U!{E~z5c!De%qJR2fx$x+qqLEVrckLAB zW#4!3!$jy`>#Wm31sc_IJ}vTgem#XVtr!wFIsuiUf)`=oLdGq&SM_>{p4TEsHk(ps z&1I&tWO<+!hDr2i>)F>8$j@`o=xPWqjr+-)%9K9+t zbI!PKdr|3i->-JJa7BJspO~8USP#Z3pWxTShS@}*m=0AajWYZ-Kv-a%QJzUoiR^HG1>X>qlW6@6Yl$= z-N{Y;dENARd@h#x?XlYXE`RT^q=Q@_irpSV+C_6)$au**O_pW2avYaSj5bl0hFg7E zk`AzwcfCpVd(wS`^Pdj@uRoZRMf*?D?B~Fei;&5bm{F>KoAKl^^PRfYsEjRQFE+n2 z$mEaoz<6cRO(#li2lc$Y<4e({HGE)h^M6&elkqu$cLUrN zKy59OlqzX2f&M!0vm9Dl=JgtOINUg^6LreYCxUZ^1hDMAA^NY_mn)=P84{}iM}$5YaABwxPAMM%aOwYAz$z|z*TGS->aTguvFBL@ z5<5B~<1;7w5IqZa`#zsvBfmI>Pq~M!$;c?j+mK8-UY&ypeUZzHy`_$g4V_V?_HmS6 zjCM|oo=?a^9O;QLw3Z40}^v#=0V;xYvbL zc6HDZ+kXWVPeiUaOx|?6AxXoEi#$~nF3`eOM| z$-ycYe9Boa*_wsN`)U|8T2ttaf-<5XI{z>ex=(a&FA znm#NpUS2LPUZ{rT1kbNa&tCnQ(=tkw?Jn;o9FurbiW2~z2Wa8yX-W1W8KexDo@mWh zq!y*<7L610`R1##w*_ZO35oyl9|WN}O`I2fd*^FAkme{O(>b2u+F)zMREq-vTdGv5 z*MHJ0hl={P0(K4>?UC41B;*u{>cy(nbuKP<{Oxr2qUhcHH~3RZzup!ks}s+3`%(8Q zczuo(=UxV{Gfr|#eH)beR+rLa|G90}D~-sW8aWk;-&@382XacqQHO%c4ZP;#Gtnc| zS*~)R!887UXJ>}6+c9Mw z2@R!XGmepdgID^I-I{nEdf%hBPysWB`#(#nb}K68zoBG6QE0#e;U(oSI!jYQ>yubc3F&RuWn*&P+>w1qpCsrj!(d22_?} z^>&;uu-5dvY2^9K$ytl(LAZz8yOb^GU(5u!Uegyn>U-K^*}&`b@GL_WNibD%&0gYv zrp0^>qJq1~0;-JRCFDXzZmoqF&VO3c8;?ZVZ2t*QrgziXbSK+8J)dT)2HrAv_7#P4 zZQv*Uo|Bw#fk*uk*#ZV7!g1zW-1{Q6{LVmP2MBde+olG33b)^(_~BhAYA7ipPha1b zu(-rOkaE;?L+&zt>fIE3O&dE7Zwhy!{397<4fwYWFymEqJK3t>!!Y2 zHfu36CQZ;2Hufg(%6amtq}=TBOqK&%E7xGz>lkSC2IN4TooUO}h{rk=@GVgZ4JXTmEEJ!Hg-Io$v(GlqVr#AmJqB$r2?&il<`qIC4FT!V@q54({%| zvqt)))QAPsm?~mig9n+}uA)Pmr&$Z1$o}h?w6jn@P?~>G8GlN^y@)~MI_l4~ zb}XvHS8JilNXC|uV(XDEon8}D$KA9?P4jU8E{zWMBM{;ZKLzohZk5mdesY>i20+Jo zFD&{f!M!1dObE*E=U+>Zsk$e+P8qR{5Wz3h{cjKiwD@fFpOKQ?xr8;n7DYJ4<7X2_ z1d@Xu)C75C91-w0bG&ucJ z;FEQT$;6#|kDp8f% z7Jpx(@|nb&tbv7k3)nPdWTiBAii(vE0Ogr;V>^?z=I~8ko01V4zBN$`3&r2U>F5bT zNEE4)ecj4g1*h|@xb1x_8B(sSFgNQV+nb8OERd&Tcsr_6-WJkzBl=#o=er?0qpdkt zU2m9g4ay%b#D5VGlxIB2!neuC^9{M}LMuHQW+6x{NQZ@zQYbqN{J`9-qWWx?mQIY>Tb3#e zEyYP@XY-DXT59yy&0-IZ3~{nhYR1XFsm5(~O4AVU@>S6v*Vz%r<22 ztUmHV+kae4fLFA4(NF#vbA-+w1V&dy7cIQUd7_Usa#Zo*OgYb=o%c*>!%NDAMzG>y z`QICAa;qdMfQ#>Wfk$T`)T=^G7gMS)^5epOr?~7)xQc*U6GU2Be%Uhzu_M$2wBZJ( z1otFAVS)!*V7KR#^>o8PtnggU+eC5o440b+Q-8Y1k#n~0u7d-I5);P_6<9%mOqqGC z*y0&a1Qv)+rg$V!r_KBP&OKv@zqT^b9XOAGzv(M;2D{qV+F1X}?*S{47>qzzdqS=rT_BNF8T(khS3v(9s;~3RQ;RjSodzUfzYp zIo(&7kb#6T`%YL?aQ@)x23rDj`CT*rSoFcZXz=1kH%rbQxR9y1DVg;7R4HA>wQDMJ`OSk_wG;m<;Q%lfwZ!w z*KVp)RB%{=bJ5~Z-E-oNN^yF1g?eA1H6=}O)E{%>Ge?=q3g(MlZDJ0ZoHRAoN`C=l zmKCP(d!%bSvHA>#nJ`?ZgMyMGdlelh=#;x=Eds$vKJY+B*ncmd7J zRv;nP%Dny$70n*E+)lIpkM3p;9Df3wts6fOU_jGHLhxrS8>n{NxR6wD&^-q@(xe5+ zCFL=!mk0BealK&FU;po~`Kh*7!Ex~)pg8PL+bdA4bxr-v*T_`<$N%q}Z=_%z8&W3Y zp+k%QP*{TuDNZlN{w3b*^wLz4&P_eYATQQ^k+7G6Z0dC+jtd$fWTw8LS${~}-?UBB zReiqutSy&0@Kj1DKU_~+huVi!rKvf?e!S?{k0ANTxt z%{bHJ1e+!<30*<)t6B5jb52fZoV6pGQit4L!WKPcefHg}F3}RG5_lweWH zJ=*fPbo@ECmC@eza0(`Rs@`-l9Dj4>aDK^Z>Tw9d80QgRVBQ{F4=xlyY61_v4Zd4l$^^M>8DG#jQz$VTr zy*H|y2mLI5Q$z{&VdNt^J^R+rF+KZZrv0&eaduqLC%nCU6mF7Hcz>@~6eFcIkOfJZ zI$^|St7Q9mUu*{pFmhQzL>wr?cRP5emDE;9c9O$&ih62X)x$S;ksiJYK&~(Y$9Xy+ zwV`D`15Ips8!Wa;c9)NQnf;+DM`okmS5#QQ{_Z}%cRa$(L@;I&(j652NHwob@opHw zyTJ%gBj(zuP0Qpn>VMfkeyo2y>!VmbJ|v6a5=n8yXd{XM)zq_)sG5s2U;sg?;IeLz zn(5?J*I%OV*_#RlF^dg&KB`nUfa@dsDPVnuzCUXRB1>XsW-rrCAJr_mg=rc3F8XOK zM&TG~bJ#~4^!v8b=CK2U97Nu8iapNv+0bG$(N45Q#^)m4n}3+a$3tiv4N`-FZC1*1 zMNccsiF<>75nAaK^Hg4YD({d9Q2mYS&UBXSqAwE~VC&^Drt5To-*>>rHdk%F+-4xI zx9?Keo-Kd7Q3}<$PD)7W`P(2huPP-+Lt#5GUY?X5#qX!9qMj91u_W~iDZjX2LCUKF z?Q@oh{ICYS)PK6Fj5Vu9g(&CO`h!Sh>?*I2YZeG0QQY$1X#?*eyBRZ5Igj2$lakKZ z#M)s5NOF@MH;aJwyO(=BJ577qvyZFpkDL)xEH&A(xavxL?xT<$ILF39m`rzlzF_-V zYur8w0=I*aj8$qBE*F@dLQ5m=L^_nSaTcAjktvM1C4W48mR7dcW2Pw5MZ0bRS0-i( zN$lr#mA0&x(|>h-wwGDT9|h6vgyNIkM!v5D0esKi+Aox}_{F?gzPx$;vgxH9q>La# z;-OGRSoc9Q&|m_zpV5d3AWPlf`vg2yR{wquQQm^u&4A#Y_{b>+oJ;M_$;UyEzaOVr z#G-*P*?)rdiXI2XcPf3@^zPGj(H8nBA_pl_bm;>C?>ZQL$HCOm9Pb)A4m7z%XAL~` z$?^j-7G+0zDqXc>H+X^yYYU3p^$7NM$9--exQ8o(zfLU+8xWuu*3cWIqf#P(ys0R} z5Z6`nE)-WDygNG0tjsdn&nd!c6jyg6LW5+c?0-GbUbd5pjTukijt&nr_kh_(m8^^$ zW+{EBRA>|hQdU^_XO-g*B`k>}k%E}ALa&an9LT?&R6{`((L)(*=#a9 z^c7n<@mZcRj8l$8EB#|Kj=5mC&(_jbC>h7N3X5p#t zMt?kOKwy7UL_dqz_KS6ueiQ2g*^uz`!5hopDCVn+`0o4rx>!p{i4SGlui;evGv)+x zUje00~yWMK*S3sfcj32iDeX6^6dQgd@E4v~P7zNSdQ zk=RDmB32k|7C3wvq`#WpZ)R$T*R6DNeSd+n+;RuEJ%TSawRnz9kAbOlvXVDGzG$hi z4hsd(H(iTv{Ct5PoMp$JnaU(>C+pTw5wzuJhi3;zhbM<8KksCF@7|yMiT*l2`1AY2 z^Ml#ZbSK-Np6p}?e>ppO`QiNSf9+&%-_PEkADkZ?9qdjIARDTGI5>avU;M^Co_|fw z&JRz|4`=_CeCGsXi#&JA6-=~;(sgDNg^BgL{wNFX=_H|;`}-P>BWaFv&WXM~PTfq& zJ*St=o-`9D-91t|L21(yaiQI=gsuZ-Qpny~vHft4h2CI|KqTkz+Qk zGBAfp_!{0{_u-#)LuxOOdr83B^L34S9F^_{dWk=9@YU!jGd&=RnPUR<$#nLUTJ%8woYn_m0 z8E`RGO5Yqih?lv<6U{Xbw%&K9JVHK^S@9+8FAZ^&KKHcQ2k+=22= z!8Az4<^IS!QO&fmEKXm*JjvEqEdgt})k`MOQ*=I5#0aNziJnKub|@YUf$I`S$U;oW zF`qoivyTP0-F;1C?i~{{sDJqSyYIf;@__s-2CARu934LS%%K^Hl=%UL9)kF^A8)3! z?t2_M7j>0ib-Qzq$~hr>i`vved+U1MwGZvFm_Stv(thCM#yBz7;Qgk|@03D1N- z-F^!`%Zsbw`e}B zfs(V1zeO1Ls}-=oDo}-DmB`;xgC`T15w_mwF4OZab*P(xP0cqFKxJ!rbaCJPaBuYb zb>swQV1naytwJ^|v)J6Ut0OD6@vJwa{D(j6>BY`&iK)rZPK%#)@XIhH0v>ZFQi4l2 zW869)cb3kHnzvW*Q-8fs3QWm(@C-oaa@Ef&_X)ame4D=Y|AJReQ>~MnZ>exQoP*9t z0?ypZo_q8yat31E|B`W%S8!eRvF^>G=i-7l%2`t9gwihsNyJtBPx+3x$v-?IlOI%z6s@^xG6HGc&y#R!-t7XLr$tj2BLJx5sZ3w zD(}bZh-XH(>{mu5=hSe=FBw+syZ3gRa$>Ly^jz@Q0DskL!wZ1nO+;W5IH56mGt4-M zYRs-RjnTW&-P8oDM2p5I0$L12c!MldFP3BWimZ`>s72(u~!QR z>3`C}8nr5xuwIuqPLFj(B#<6;MeW%1*g_V>NokmKURYktYk1A3k;S}$CD5-&L`U}T zk8R?P?=*@u7-LF8qaf&1}V9B1sAg1{IlJ zw2c=*;Bip9D+)#%5vA;2`EoJcZBZ~La8W)jUG}ve&o^R4;B~*z5D+ELpVtD=mu0wL zl*UR?aOdpYxsT%l&0N5!?(d!)NCN^QP1ksU7Ex@mK5so?$aJ=QK6_L_$gpOl>VG0g zNb>VMl87~-9+0#4%D9VdyHblUEx^9W>eHuEHfsHK3rt^kRohr5_+IoQa z(mfpV#Y0j#F6%_SvX=EU^`GQ@HwFvsWEXDtK_90)5>DINRtKD+m5zCwq0YFs_B^Fo z9RNtvP>LZKb==G5ECuY0VKE|T1X$hyoRla5`6{2Mf;G%l<{rJdL_odLLw}9YMUm>> ztWogolcGwE)Nyew!*H`PE@a3mq;3x8*Nrf}%qV57>B?_+>Ike22a!;h{NpdP%*86S z`>5!lg^!44Q`7_YM!LYT#gQK>Syz%Wr$Kd>gj@4L+49839C_;ahqHP>bPqYCfzi`? zwh^i~D80{aPI}0l3_eC`?|;l@M(ggCE0A1G*JWQst8;$G`LczO+k6L)sqQ-e7)N4+ z(OuQRWbnp4ZKVj0^R#HCX%`_bGDiB!Y9_OUFRps*P*DZTaAGT%2w?h+w~|fz4l;zf zI<&BiJo*N>h^n~~2!)*Dz9SgYRDeLkBO+3y={|h#7D5O+c#KXNlz%X+fHEIG*nGh@ zWMmh?k;k=^=r~$Y2h zO^`JH!7`b-KVkt}F-thW?5Ut>``f@HZGlvEPd~Z22H*}bxw8=XI|ve@1{K0l>act7 z+p>#=-Ftt2D5HipSAUHJmTW!)E|pp1axwqXfUIzU+?1&}_hr|ui&n8R|$f$16w^dufc>*8&?{$PR(P;s^mT5J_4Wo|4;#|c$;D3LTsuMP409M(lChmhj zhZJil=tut~LWv`~;2-X1*4i~G0_8g2zIYX>hxZqKL|B1ffITBA1nD|*Y+ZR(lRSKJ z2ZKSp5UrA#{j4wi#ubws-oLvME?u^P*NVs{T_TT+0XoG2;B!6 z);$pVq@nL~$A1^pWy@$LHXKDrb=dlW@9~FJ2b#Y{5$j7(nnoLxo};Rtx)D@RaS(%G zVDZu_E*Q^ws@6Gh$e+ZkOH_l!hJ2w%TExEw6lTISy6%~ZcGNv`?$FMV(vgdMrF}JI zgdW9A>TpDZjj<%dl=WKkUT@w8j4*ewXDE#JZgqwJWPjHJpGaqdqD|)tn^u)ADcjZ( zXz{1Y$0*6cpsCpAM_|*h_M~w1lzsb%m|tg>QSO--aWinlWpU;FZU`Ih(-S zD&0Hjaz-&^(YZ2KnsF7$b&Sy7bv}`$zMW@i0u_XZ$ ze*>K^u)t!Hub5eC6nZ5tF$WSk_uy7eFkER6b{I>Z1h^?!)Wuub0`7Yd65n;rx;d1{ z=Ql+Kf(K8`M!uykR7Av;^t3In%G9faZDJ8#Ng!z%(_PH*0JU_b4`m)m9aSyJ%KSSu zb}X3+Ng8~q{zcIpQAW~9OM%s>g7N4$e^qlKMVGo&@8gCNH)6x29G!as-ZrQn7i7xth)2y#fBOii z_??8s|GN8TYg3UCUiLTI%l?UQw7gZO8)9I`0zcwitdcyF7pVs=>uBw=j@SO-)vIOq zkU#^T;F-u{c!0<@<3XNcoyiaWi}KGSLkn#m`scoZhvcTiXsTshRFAytbhBBw{ZtsW zlhA<+QZs)8{G)DGGeIM|(5bQ`f4iZJkL}7oC*6O}*eheDAOCzakJ2btq-gIh1=Ks_ zF{w@a_m6ka_jWSE@!LIr%NnYNe61MpS0muVbulkiC=FnH{=B;T6}_IdMr%=A=Ig50 z9zZ1tvU{c4BCpjeG%w1@Mb;pvsBffHTn0gkieV6A5mKK^hT*y~YPY!bUfq(;hqUw<8cMqjH)H!+@ z&a2q8ue(W+cm3qGq%+T0{UnC47Blex(NYk^427RMgqin#sLK4JtWpBXLGFE9mhFb3 zuJ5ArDP$=vQj#2ue^?1FO0(lppuAUb zieUv6WZEweeC%Z@uF^A=GER4K52b`4@I68cP^5W(VrS5SgD^mZAGXi^T(C84=O|d7 z%PqWJSJecC-n1vqqM5%pq{J z3IfBFe%*+iz{6IIe+IOQd_|SlS8Ei_Es9?0#uSU8Ko>3;js(v5?q2ayRBK1-JCTdn zWQiC`D+(vH(3#?;rZY2}E0_!z+ZzH{k@wu8o=VEhB64Zgh3Ik#{s%Jspvg+%#?^U& zeNSgo?JYOyD_}Sot&`~UfoB0P_=vvgqG9(;Bk3OMB0(ojf87oJ)YLelpP>n;?x${K zpr2eM?4~jz9q#2!ZIjKNjKxFJ+Evv^x|6Cz&`Di0(n$KOFmPgM~eGO;fgfy1;bB1Lfnxlx(LBH??zbUI7Old_-MWA_Kaom;_5|q zOb*Uj%+{wHe}&bxiBnufxjc`#dlIHXQ_X*X-m7ez8r_yZ#es`{4F{7H!NRnhhsdeE^c6~-`MM?-4%~f2xC2Xn8cU7% zwkkIEf8$4H7E>SQdEWeGQ*P|1&)fw{ejW>K{)*SS!kl)EVlo-YSG< z<0B-ptS)#1Mt2LnGBugO^=!aFlnPyvz02h9|LO2}C!3yubWw>L=|7D3gvx{>+dl#M z;|jD=#3x_{ZBTFUn1LHHV#AGKYS_RBr^E3Vf569b$q!_~4(Ql3JEGu}?zGUIuB_=T z>vWpTkAuKFm^$RE`+r68NKmQOb=xro}DVgEimWUbnhL{IH-+ zA2$oip*k`sXW^lIK7?rtPU?+)P;_{>3R<_VxVs4v5)Ghy`fej2#ldJDt;&2ifd4P- ze>%9hXN9gm5tyRu@(1;GUe60@8^lS;I@+EqfTfcYfgY1XGk}`N>3u^V2u~v5^zp3_ z2x9h3j_uer$m)y581 zi_c-?D?2Cy()l9mpf#Y2i=zKjfZhiEe|M5mQ7o7k)hap#h{gXb2w-6aY^d}*<4lEv z=9U?F4fpIlopo;A($;mSJfU6N5mzMww{a{%gJH_ZvPz~p&sWT<@)sv?b%C54e391V|V@0CPWfFWv;DIWSPQ;mq>rmA!vGZW>+%vU}o?^AOV>w7wY)IVH| zJdNuHfi+mnzjs~CKL$hv%t|q@Xgkey(K28ThS68GlW@#&*f$9RePjfz6;iJnHZG5% zwr&H)Dxn-!>pfIY3rW}6d#}_306%Y}*15JWjTxM}2$dK)=BDsM$=vuOM5~s>p+)|e zTOC>JS|3_#TQ_lJDX~pfI|icU=f0!eTni1k3`tt0D7MK?c9W}$TJ~?le`_&vsCVL} zH33RgkW}>)3${)5JoHce-ut#vG>&lNoS7j;c8(hCo_it$`qOMLePDdh(_(@o4js+Y z^~K+0#2>BU&^h5zt8xO3r>?2BolFMoE-lGoOaPZ36W*8 z>hRGSIo02wOe}JytMpivSs}qRRSiy#Re0O92g+*Rs{=VjKKI8#F$|#VT@cSkkH`Pc zQ3LF;SA)`$HF#Hh)1_j}MPZ3I=?C5auk;` z2(%~oT&5y?bs{{pt~7@Q1)+d7>!aWZ3aHnVf=d@3_D$I)uiIc`ajaffReemq1AStt`Tvt#n zs4u-0VFKSlhW-vd$U+4gPj5!GQ{y+Q;Gp|it++}GtbNq-#|7n>Lop`M?Ej*ASIU#( z%~5t;$_*f@z;p;D-4SN0I2!n}qrZA8caPyTV<%4b2{q zmBVcul_p)p5JZTj)xkib_%H(r0ctYdC2V<$8^2dbO!V z$G@qdH}BE6Cr!J|D|vYxeVctLWC$s@lz~zyLc27w07`r&Y2&1GBbe$g-0uH>bST+C>GsaHabL{5TGuGVwkyr zYbshncrYi$VBNfFB~y>TrC1#*OQAg`xc7{7Kb-MTf5)d8QsVT28A+7+{OW!^hG*)k z=}Mnra#BTK_UrDVVx7l50zZNV5U!VwRVJP_j%<9l9>A!hRyeF;9L6`lk~8cM_}4~& z+5Z)Pdhb+ff3pzZV@1!`mG6VS9Y#Vt$C)%+ouBVl=4?ezu5)AO@8Tv z33V$hU9SA1Fu1VTx(%9yF`0ty@}S|X)fNoef71>t6$&R;xYl(Z8I|3eT)^Dti>!zj z+(pxSDHl{JqS(o=uE6rIZz3W{L?;)|nZx6Qj1$Fl992t~Mvsn;vn>RSCOX$q-U9Jy z|CNlSa;~&dL)9t|;H+DBt8!i<7^t?&^KC_T4;>jL=*-Ya)VKiXrmgYecJBrpr!z!< ze@Z|Px55CtMH&OhYauDC6z-WyTIsyqiscI3o7dt^HFHv>;&3T|WX?Dtcy6*)*IN`n zq>Q9dbh(v~d-XOz-b9lN#2Z zbDyMgbk8QrtuoXzNfl>zzcxY+PYEOUe+ieJHx+!P!3zw7SmHLbZfXp)>u&-$=zCCB zE!9l}GItei#>(2szWgO=qcg$*axK(HZWuYHjdphr1H2sNotnCP)l7=5E3wh#Fr&a+ z^N&8l6e%9F05*wc)i0~e2mP|dmq=6XvXL}|49Pu&9K^?j!VOFwl4{V`;%HGIe^>VL zp4WkoD}DCKFkLNmaAzF0oj*;3f{f>RGV`=ScJVw@W~PS470(l8CTfF(;(4abObrMn zo@dF-(vTeDd75aNV!{V{)WNHEz*O_9YA&>)$R(AGTZ3SMm!RdDgVy~eho#R*E95Yq zJK0rR+*N3Nf)?h=1zS09fu@}mf9fWvv%}8fyIsE)FAD-|V8;U0B??VGXhFiG9Oh!F zzgXIR0Fj-69)k3kgVOsvVyV-@lz}?ug=a#^3Go^!I&c<*-14Qblrv%-J}nW75@$Su zQn25kv8`sQ?-VEpn>|=Gj*hw^&0CaZcbZHu;5AAPuTXvV1BkVe-j;orYUI` zlW?;{SxiePtBPV`K4c^hf^t+whToth3LGUiS4?NRnT3a15e^*Q~He@K|C1c0t9ugzL)u*e=G}a$FSiV&*-{%%fFD1Po z{~GH&q$YC5_}VH7Gac?|j7>)M4ul`NAJG!SXX9?}1~m||KJerxBSKYep)E?{M?N&_ zd9%x*r4EzJk*-IVTlpM~qOvhwy8=yg5i=vCFp{kZN-+I<^`#^7e~Hk>3BN?oEfFQe zZy3}iXslW<6MJS(c>z?B(i~8x6z*Y45`i^YgCt1dK|`|hWTpL0lV)m);aaD{DD-%H zchp=7`k>$BX(&uasjLMPk3>00)Hx;`!P84|;E}rN^fFO}7GSq3b1&=$uY<}6>yD1m z2P9nf#b?Htygv%$f6hGtV$JYyU`kV(^c*8>p#gO&>GD?j+_zijH23I;>^}FnSYN0k z3=T<#o=bOXeKE0xv-DGoA?4PBljXLl5_;IQ48P}egdOVCRrOMZ23CIH;_6aanaNAs zTPk*Nrm(Jo<6PXJMh7n?ysOZpdG3-CU0snEnh40y%KQMbM?a5b#OoIi@u`luA!{!>Crh4e zNNFz;Si!1UW>&=6?O_jxb@uEWL@PS^Te;kAjmq8A(T*p(=X|vR^4AY@o+9s|sOBms zJ8{C9GwIIq?&G~4lif$}HHk@zQ-QMqEdUUuBYBu>f2PJQ`+%3%(l#@bU3ES{9F%`j z>EJc@ifgkFab@<`-h60`$K5J#m&5XU0|!ZEGtFeioPHr+P6wul7ut;W!*8ds^a9e1FcR$ph-J~t*Gqqj z_Eq9EXJ{d2{V?MX{{cBs z--u|?Qu2d^Pur`!h8v^x#Q`=$2n3ePTv*LaRf^lN9^yWOk?Nu*T?I=_&B~@AdZrng z9ShNv^atuf5m@(+PG!iahsW9@zHRmx6yT-*iQe4JGT!tIC-&QCb>*pH=29g6_@>jqhPWX z7N+#h)9C{seHtYFswJ4y9;tX@oHbfYv_#mWeDL8ioE}z94CJcwB2Sw@vp3vx> zoLv-`D51P6Z?J*&%4+W^f+!TM^1H0lf9Re&DfOcmUi6{AF>JBRw?QBGRTl*dhkZ90 z(TI(;AdBYmy3_+UA~O#P zlGKi9??6JzyJ2w%%bB+7;j)=7oKfjfF?SKkQ?NzO_q-z$lhkp!^ZBBn>khmJe{E$I zx_K-z&iJA$(IfgOlQL@Mn#;?fsNWzMps)p*E*pJf<#Xv=pbCR(cJ6r?fQB2J+s7kA z;2cqM#_19&$S;d0LQw8+en7L`71|yB(TiyoOu^gowpa}K1wn46I}laui>|3|xnG+a zqmwa`I@i8uleF$>is87zTe^MHfAh-O4-19CH=HQQ?Iz069dbffo=Yc@yG5BPoELc~ zG`!Z*fHETEK4T+>7Tqb2 zxuqPL4`MsBXOgpVFfkgx=d*4<)~}D55iYrLO8PNT2cPCqG^@G|QV3Mse?4g#1kd#F z65a>qZu}-kyRQAR`}pT|BV?7Bmc93l<*MeYkp?WymVt!YMq;k1u$4RajxnNouEmLGIG}FiYjB=K%>a-c^V-VgZvKwe%i-@6*VMjS2L~j)iB2*wr-$hWd9V$1?N(2EJFfjx)e}Xm}+d8ql*L}Z| zbto2(suMs#H&r>mJ0#Ou^kx+Y80BSdrkIci9tev7;XY6zY!ig8DiLE#qD51hzfU(T ziPE8^b*hb1z>|Bpbpz>#a%J#LkaU1W-Zwj&FM4wHiOew)p^2yznQavIqp_B+_2)XF z+TT==s()4dAh4Vze`-nDlCEr~pe})AY1W1bFa2WS?BsXuyaQCxv44JY+5OE_$ORd^ zIhRb}?$t0v)d>D0GAoGzpQ7KO@*OfWS-D^*0Mh|*w;H`U0bVE0U=$N{668dX- z(}h=+&Iy+`W)+8r;O^B`TU?>WXoNe!^cW5_dvp>iCHy=;f17=i<)$HJ(eF!|gHR;W ziC`yl_cy{LaD-rPjd6v^y+8*7(>=I!4CIq%y+6#~y=wqW*1#D!`uGblyopw%p&Sa? z)Dh?-m8TpOY?`ISK{ZWUK|^LToo^)*1U-kx)pF$lOK{qF{&s+M?K}j25gCL!&&E50 z}1&a2_PG}WVB|0u$@dvV)uRJAH@!Asw# zv^Nbr?(%vd>T2ryqd#H11wZ3AhN(b7@;`tK{EiH-Eakkdn!Nvf@957e(ZKEl1uURgK z9BsK~H{>*)#se%Vg2G&iuPfNcm6Uy5A*;gaLPpkg0(%~R6Zo0`lqbVq>k6K}DGihE z#CulpZkL{PA$hgR`Gel4vCx_;iUo+FR#QOZF^{Yu^z=>Mz66P(L_P3g37OzRvMvUt z`vi}ue-~c;7T9oUB}EDG*b6yOwTmIxf!6tCdWgtfjTf;59uB2vX>hF5GMK-|sNHW=Que7WdoRrKGt2YaEjQxh ze`urwcghGYMfvVW<*=WwVL1)xw^F~{@ocewI(3 z+jUh%ENeG{TWoivgXV3)W|p1Qy_r-We>kf_NcjJqoi{10EAAr|lor5TS3a2@+2Ufz zpEdvzadAX`3(F1H2_1uZ7BH=NH)nt4I0caac#Rjui|hH<{a%V=?K>Z~kB{dDJ3o>dt=#L91s0gyfcekm^Y^Bebg!<5|*nSqoTP&BEce;WGQ zDw62w-t`(89--Rr9NiG;ixAG)3uj5_H5uD@h)DMcR7Vn7#58Q^9BnQ&>L6lvTcm;L z38uO^h&QNu3}hBntMG6l5n!!`QdZ#9fLGmBL)q6Oad|>LOq&@19PmsIU@zc3qsxVZ zIYL}>oh{GOe37oUPpCVln!g1Fa!a= zYnqSA>kIO)A%B>|Sqor6{r(|r!PFb*^|$}};uZYg>zAMS3sMiIbb)^oS{I`t%sl-I z!I&S`aN?BD-IhqV}i4a)piesj;fu5;FI~qDxMe?x4xq`U+OcAKdPGReW zXgeN;<@y2}xDf9|Cy`cBf8z$Ylc>|;6F7Hr$4#ED;ZK~~((h{0&`9v2xpn7EB^B{G zV`$u^Q)b-EsT%&oxeaYUamf68ynkTTL_B)u`&bGdu|^lfpxk>(=4m>EV`W~h@=63% z(TUzneJG1h!0PEtI6HyEo#%Dde5&y^OWYbVcO091^c0#V{YhN8e;wI=7Ja>>XZ%+9 zD3Ug^Pg;V>xQAH|h!FEWU2B@)pS-bsl$gnfrULZ*E zS~dPHfq=!#2D;Ofq(S^o^&O@WAR7>UE_Yo9g!6CUY;kQ7@TmD&(SrAV*Y{V|re|e< zpV}qszNGhs8uCe0HZ#yVxq~uPcH|Qg+->(A_bqZ5I@e^eqPRENmaYBJ?6q#^wn zKupB9;Ti>g>0P+y=@FX{(?07Sj7s(XiFcqQCQMMV-XKDX_*?95ey(q|xvjK$`|bTX zHlY8Fv-Jf$!|)Lw`2=V3!~b!&wi&(N+{;2Ew2IBWcYKg(MA!Hhry?E(s;J`g6$=NF zJmAn&7Xk*&e>N967v|R>^eE~p-~Dt?rz=%OU?ClG4pH3MW9;`w-4$w?v^A?eeT}%% zuFS!0F<LFWtT#a;(q<9XYw< zSWz7`)bF)UPxM>YNyh1<0<#!XuZC6?tzf|^At7U^e_RoqGbA@kk-rwyzP}W@q1e3` z7dm+a9|T3BZf7>f3=f2a#o}-!he(Mc+;C#R(SrW)b90Nw#VZNPO6r}P2TTEcUvUIq z7u`3~-OGa*P@b6hBBI`J8HMAKnTT*GhO<%YvnugMa2Mz7P+uUCeFd4I7ULHm9Hdum zzC^Fme>w7H&WGF+TJTN&uH*KCO{YE+U!Uz_WNmT;j!xr(EkE@%CL3XAqkWA+O%uA( zks`#bu2z{&PtZD)Sm_dvHos1z!6dsM{C&=J<>2l*dX>z{icdDEMsUL2LR-zNQ#UwV zWU~*QRnP#P`G(9G=}aZMx|((0yeDwTm`fGse`Lb5ie}LR(lP|=VrC^MRu@4Iy36t# zV0K79fyCPq_Ew&lKDTBtfuh;O5j_$nRW&8Z$&BoN09!ko0XgE79^v5JVI*D@k@4w; zy9^N`%<7%LjXPwjrE3jp0u;O~iUoyFYHba# zO(Z`NS)=qpK!2%=PkEIYKT{5MqfbbGRaEC{Mlq4g z;^d`t0FWh)ejKD1NcB2|7>S{Z;1JHa@2)}|2d0xpo%rrjkmf706xzftqWg5loCzbk zjqg^ab(06PYT>geKS$AZ^fNq3BFvm0S*}b>&_d*I#j3dyA~8#{%@HyQ^=uz|xj#@m zvwyGr`Pp^fovS|`9%m*eK3`PE82fZ4E-ogiAXKnfn{|KHkcoze-S3{XMO7$BPG5Ov zI_K-}+`f&G^;B0Fi}-rEwWY1oIg3A}lH|6%3LN?HIWg_o=5XwiJ{_$UlL(^Yr>w8nusD8C9O0PbDFI=W`G0DYQn{u(QrhjXSvEFxFPxYypU##A{JfMH zVrLnvy>&m96dPGIMvB4lZ^FDjm`1-Ww$;N)Rn30gO-VX0u8EVWlG!J&2$8?lm1?W{ zlPen?arWB^fm)^SU6yP%I~wZ+_oXgqUYQ^LI1)pqTD+Q_M!hdvT!tOGuGysA*MEIE z_MzkWK|?Q+*D*cY%oF-&p|PxCMZh9Z4TxxBPUl5D4YO68!8rxoZ6hM3NK$cYJP9rO zLp0M{D4x;V1HrtD6zB1h|1n-6kU?g($|vlIOn}`t3CC4sUoSEcPP|M+IoF^#Mv@wT z#-mA{EJ)Ir0mpPuF&vxha4~4@%zswSJa+U%wy|=J|0Y;431crfP)zqfb z0d&1lVoiULmHJp>*NqCrD}4aa^gr<4h-mA09u)S53%7Bg+$}>ZNp%jxDjT27aF8l9 zcumP#k@1d3ph_(4&UlogMF4PTf$i>nXz+xhJudDi1^45c>Eg~v6W3Ce(0>#WY#nKi z6fxMuA9vpTDM0x5QRYn&(+O9vfWq<8h0qw0^L=!8W)<};&%OhZSqvdG>ABaxVOP8QY0Th4WgV|0w7xGyX zG263KK;e3@PZQn#|0Kr`{EuJ($O^BA#0^TJV&a_yu)|2KRiN8vHa*)tre+>ZA0%hv zU?O+=rU`+6mlN*K&|FYB>5vw5oav3U&?gH1mb9SyG=di1w;-C(QeSucs84TAPPQ0$ z#v1tU!l__M`7BDSt{x(*57~<#)HJF@%8y$ zQ`b!GCX(Hc0%%6%>OglXt`Y1GxqN(*@g7As=AP6^xIKS)l6o?8y`A*`on=omi_qllLrdqwba*sDBFGweA%Bd=gZIYJI}ipV^zFMdiJ`x z{xtI2+?&Pgh%@hX+KG3-$KQ5Y>2i!edqmB1jv_UKzz{pMxg2f;1!J+T;Mei67o*eZ zk77m`muM`U$vA(e^%pD1{)n0|qRZ$P@kj1h4EU!lf6qT{O-qp>k2F82cYT6UvQ`Tegu9TyB9^P`9D!$(Pc1{mQ7Lt5*D@$b6uR@C7+V z2&28KRIwb)m5s?6r>E?2u5hvtK8y>`sqiLO1ujJ#wznp3EB?B;c`08=+py8!a*yQ6 z{nYUZHjd-7DI~1Zt&3G6+;l@SSaH5_v|_D9;lh9WZN<3Q_5xp6`=!TV;T$znkyJFv z{dhmGp+{CQ(1o;6e3|4eF~f3farTnRC@daTGFz!Qh|aAQ$Z+^`fe^=hE3zJK(XZS3 zOol|5QfMpzWeW7K<1(8Q3eqx8+^`$9LEYvEMvuQ$V?mVS_HOZ*(eYMkjl6(YR`?LF zGdO?MFmlk}brJK8z)5}&BNihtX(b)(d$WDrnMXKsEV}cR!ly)54@J9XMSuM2+gGn% zO#`jP(kSCH?fO-hD7cG7&h&&M`E1;mV4jt#+k`%`Scm+D{ip*NAb5_kuO z@p{K-#gXF~QSx5u$MU}2j4lF#7Eo=Cf1rPs)-%qR+O%As=AFxRvN;pV3>nNc5%ny2DuqD+ih2H6j&I@FMw*r zqw)-%zQ9X@rUY?O!f7S6?ah;VRW%pze3Nr)FxM_X3b~|!2sFO|=MV-R0z|L3gM9s3yM?$McCres3x(&vxdYp=u<<)7zQNujBQ0t#%`Tlus_R8Z|`_0xT*b=8*W zf+Vn%bkY|i>REmjn5sZe+oaA9vj~J7k z$%E7s|4cqlWru@ug;iZfDNpScO@TZ@t80$$ab!%YBgR(Bg^hxV6!)~g=I;hp$-1fS z4N6q7mAn(WV*H&jl*{KI5%d#XJFt*Z$}d=mLkwnIy@uZiwqf^itY0b=4ZLUKujBh6 zR}}Sn>ClM&J|?T)Vi#sZy^4RgWcuMX#od|tabmcS+Xw{g8otE;uz#MroXTS_va0lC zz2t0vX~QK{1!F7eWIbd-zwnyH%*#|4^sFh9GW9ld_XwpVOb9s-VFxHI)Pxg2x(TYE zre3<(@EaM0UcVFN)-j*oUfuA>!Au_LZ2-E+w0keA8%H_yV!_|FORs;PixCc{nz_i)CXVEF+}vSNDhMWA{u<{{6W{@ZLQ-IEn%J zy3ntYOqZTvv73ZlxL|)s%YOC3nt@K>vuFY35J(`pjk=YOAQ7|kBQyf+nbP7o+82*T zg8Dv@_ywM+=+=gt#=hWQXM=hhQ5$1;={4 zA5+`+irX_P9#9Z{$_qFZp9Lp#l#Q#7E#=L`C)>={mahN9+$n#D;o+Ahv8PT03IX4Z z&}d>#IP(;R7`Fw1)DWV2PXIkTUja^Iw_4S&Ub~y&Xgb+FIy(V1nENG=>Yj0MOi>zS zwv)4i^XcJq7FGyK$`a_hEQ+9I4wX^;CS0mF#U(}mw7oum{jF2!^~-M&;tMqyEo!Do zvVmJRTO*8NRv3RwP50a9-+t$`@$Jj+?$gG1-#cx5_wxJuwDJ89P8;99{9$w(G)MTS zzo_R$)#Qt*2d7{%epE7e3%KBRhl&7M>_t%NoF)R`x}Xh~f{;Wc)`0T9={P^AZEy}_ zbuHdu$8N$-bq4?3U5SbgNUDRY@METsLWRwd)7A_&6C8g!9qjX-U|(EnM$8tN2d9XK zf4s*6w>wXyMPfS+8TMnQ%VfE}j@=eiz&YsRUJe2l5#|&Ve#~qMRF{C_iHb#=I6?Lw z?v@cv)v9Quy|Wx1gW5jXJ?dw>KW3E4>;<|IBcP8rCm57*nXJ#bkp_^|85iBBbvW62 ziCo`jdkuezDgBK$3$Og_XEfGxwi5z-lL3$anSBlfypWII01@P1(0iDhC#Z_g(!2w2 zs{|%42&c+*g{!3X?JT%0Y2A|0w&Ed6!8p$;S12S@luk6xkd?g-`ZI9gxqlld+5^|t z$n68_#XRFwQ;Fb1+^wj>q#by03Z{ZCkOcq>D!zZgUfwRE6;=2H%6F={L8l_s+~8Ac zZZ6SA5v5J*Hn^tqMJISqguL6`pPpqaibY7WJ4B~*twfu}-MhTI_N!rfb`2RB^6i)U zRJ>GTE_aP@nvaqsvHr(`s)K&Js54zA7IxFGXfif^xLaMi$K~1EEEi!iBUKi$!+CSH zb=`lhiaF{;#M*|{)+%auRyTcS>!^j(Pcn`;D~(VnM>MZ&ezH$_mzjLjXn}O7T$LXA zb@K8^R%Q((2S^o8H(sntw}ETe?-}C-ISD_m{e0-BEA737xn9^2K4}JxD zKCoH{w<~NW9RykulH2RD&IQwjzlFYFa)rUOYY*1!{WSa8rejZllfR%R!kfGcZoR4d zLYsa!nFC)3Tg;2lLW6OSZ~TpBL>GVbxQK8KY&Q3m2;f_=5u7NB5-!@(`xkCuoBT#_ z#!c6QjD7ld;lH60|16NKj_+itc_%S8GT@!{9*nDj$aDQBY zy%=_)PxQy}uLsDH%P6=a@No?VlyQkR7IbYXkrow(x%MX`iCXYnp?4P>uX_?oe23TU zrsjB-xkodf?6R^-++3T#GHrjB5#eYDsiVH_Ro5R+)wh#^53b1DG7*QCB%_Ew^VR?7 z^$-8{>br%f&S)-+pJws zW8-?IzA>~$s*W6>KQ_7-j&n5YuF-g3%rzPxxq0sS#lquwO(m^P)m4A6EbyG3g9P1k zAW&(U28jvlovp=#6@SJ`uOR)T>CGdu^Xte=fufGWj>CFU+{#07N*S5S@t$CN#&}K} z-1!ncTf*4ni33q-%#MWth0*Gq50hFG}<(xhJn1XLu|c6Wh;yjVM=$ zcTnAlFfxD2FF(2y&A*)jC%MqqpX|=2ZuVb`x^XG-U|y9g_&%o#mK?q>1Yr2vFQ9g* zUoO+>e)%af2DQ+XaRrk>lMHWv{GC^4#-!Lcj!sQz6~U zb}?CjuJtad4p0FEomMz@UowIn4>45G?89cilhz_Y(TiM&U4AKwkC9TJAX(_p;OQ4B zb`8n&eb7_q(HDQkIq+|t;J7(OFx$XCm*Nx$2D+5$``?0n*P@|=wha%MMcq-l_x^?B z4b-$rNg!y}NRS1O=@qQIq+rLSCSzYol9p$-8UYO8H@LElAgY*izgNm26KEH$3*eOv zH6RKKY1`cQ*LD8w4}Wm$z1y8&iu;Z0{Iyr&wP`Rd7>SBDbQ&*5Tqcr|s03A1 z7j%F4D2^UA^yD|nLEutJhTL6aT+^DII#H%hak(xPd3eXULXb!_C!I^MJr+_c!5OrT z8|tp$Fzq+qy7y(9XxgYTyEPCxbdOzibJ$FusKCV<#AAJljH@@I;1e4arOO8OzGR}S zXQUL+8HLf4i*RTG?+BT%4;J74@WbnWpZb3kh97>NO){0AMJSHypLcn(?)h}r*2CVQ zZj}v<-~q5|y3*gl;qja+4hA@pdf-sj8YoOgSP=xQ4bGsyuk$viS5HC%W(zDHq_#|G zA?=tWx*VRIn8GVOHcs2CyjBNbuH)mtrt3lOfK_!}5{ha^0<9CK{=U4A%3U5`q>U zWl7KIHa>-Wu`L&3|GjP6PriD^rL0Sn@3KhbIJr1or|7Y`#Ym)l{wOw@oGo!+U$5r< zH_|MPV8C@x+L%rk-}rRcC#qn*?UDyk}!XZbAz1bKF||9Ur_KQ;7?CNCiEmBAl!E&UyarK;KjLxuE&2eL|#4q z{u$rtp*o|x1F5z=Gb_d3qOn|Ixq)FGMty+d3)d_l^3-IC%A!?b6!@`jKGlI=q+x#+ zh~2W}i;%~7PQ4B!BoT877amOt8geOQ*ws@pY_1V0w7hkf^e?d@aYL@~ZPc|l?)T0= zM88MUinO4Dt9YY57Y2JMRAGM$9bA&I!aNs-5WCUI0a;}O58cc1%A?LXB@S0PDz0*Q zvQk2}xjtNT^X5ig59PdVIyfDu`a%`34QQePNg1RY@JZL9r}FJes0G53bSQP&0c23l)F8P4tWZd7Ur* zUHJ0AZ@-rlmYl%Fc!X?tpOhL6oqIZdLiG5Xb%M6e-|l_;`nx}5U(cq8KYt^& zDj+IBrT5}>tUMHd1y6v5DfP`3lO~l1S0(6kPv=E0yg=P#(XHvho{-?-Zx&;&T7S5gP4(p+T-!bAVy zTG#CUGR<^qKsq#)(r`*Hw>NoBIl>;`?VK}YCFIq3lb4IN-xo@Z_x(+^Msob%di`M99z1^_6w;=0>u7y?mHna= z?<4?ueP2{n>0VAwqFZ#8OP$>Oj1pW5f_W1MBz$f9V&R+S9p{VUAn)#ike|RKQ@UFm zv~4xAkSpmxl4I7}JvJFa+Z5%AF zJkr?xn8QmVqYQtq>}}J{rA>%Qa@pawD30$A-PyQ=q~%?S?zO_Q>}Qa&lpkFGDoV+Y zKuCo1ee;7T?IHT`Z?^zhuel|vV)|d+9k9q3i#xG{_bJ6y*%ke-wYZmciqPwI$aCzw zJ-X&JkDgRX*`P^t3$F7|Md|N5PK|H8ccAlt7m;A$OeuKE?=@+rWSz@hgb8w~j_*K) zJ%0mlX32l@QgWu!g#pB}0J*Br@z^x4;C|EZ39bqg{oRIX)3R#3Vw5DFjs0A>tf~ZA zq$)2Zpf9Jmh04phM`E!Mf5&dF3bpq{q*T;01uP=~1@&7Q&jcd3tm3o*}S;a$ma z%3!LuSW`UIKIL};KTIWwH#)!95O14|}OgevA&p_DL3GRea4h0wfz5)(Z5)~)O zo_;9Wxw!LGf?K4ipgUJmx`&CN^vMo5!z~UH5O?$NZ(;awF?U1?etfJ>1ij zf46_=UVr;^Mox}gWeFa+T zyVu{n`auGQP}W4}`K{nIASQ&;a66+fYtq@f8vv?gDw!iIXq9lL5CR2`v0we*cBrQA zNZ{!{ha&~e;T2Sv=j`UW8B!TqvEp`B0q=juCLUkSu1&yiP%#!QvgEEM?_48DDVwIN zb^Q}}l=Tvy&`L^q5Ry4#+uX2gdD~PP(nx(k8S7K`upB7%+ZWOUNe?Mhs>TLoONE1? z@~V^9NQ{M=-Y|a> zU1oS3r1xu=Gyq`b``FsqVSOT#8f)gN$5<>99o3`V)LFNj?C|~oCE+4mmNi?`5fU9b zZa~XTtBj*~<`L-px)2NGSY0Y;T{2+`&Kzxoc~O6`i3WP4 zR%GI-PAGB|CLQ~lVT{6&G-yy2KY1xDdEiq2MYp-UW0ZQaEc>1vM1sEmG(fc-pT?IB z22e?Lc@^_1bowpwH_;Lvg?8<*v)o92i4idfnap;MO|kr=^ixhw9_A=@X9gw!!|BjU zr^b^!w74hfvnm`7E`cH|zbAi0F}=G;&bewRDAh-dn0goQpU(1#q^btj+3rMhrkf*` z+oiJxnpSgoiAQPqYr2ckONyJ?a5tH8ptUyj;Q#%Ks{FrS@!7qTEkS_(8<)vT+1 z$sI?6SitBJ`Y+Y%vL5KS%^d8xhGl?ntCRhruw?TS@Pp)4wM4hm!M%T1w1qufRfw%L zn?twB1i^Hg%S(R%l$qJgVYa|HgCLA%_Wig24(C9B4Tmwsx0~$JW`t)d9UuA@!>yZ> zZ9a~i4vq`#KL{u=jq0%5(t;Li!CqD2KsfN|q+7Fn=cKDke>f_{t1gmFPYy%Yfjv?j z5K`wlwzts^6Or=hG8caae?ZMPx#+<+G996w?WHvZszv0}e}E@a10%=P`f6ZYs>H*G z!q1A0LE?{+o z4E8w6=$Y=OS-eg2ZW%oU?_#!^&{4ks{yTLPK{Wz-s1?@@k92~L5LFV`6o*D_Z4`uvg8j!R=2Mt%*8a7}Wn z_o<5637Da95YYvRufs0-%c7|voK-ZH(z8#PJ#YZeg$7aYFCwk(&1klT0=^$c3gK-YYy6&Gs; zzurBZAa(?;mxgdt{5+JqG8m=)VDeQNZivGSz0wmaVEBB^QXX2Oz-oFITo&YegoEXG z40Hv@#oa{EkL>H>#np?fTjmHMzNZGNI>t z8D-KdL}iAwzm)KG9pB8bHS6q$R~a_KR~^C}cRT1|0k1T@FPHgkxm+(f#vo2ReGjR< zzy66T3pdNe27pm0=3+v;pM*+LfV$M0lO1dd*;N)&)TTyOuQ7lqpE(G10YVB8r*ycG zn2kFKkD-50CBb9RCwH<7IIupNL+F~HWj!oK+219{FuzIke(yt^_b?0P9Hd{*Z~o&O z49sR1hDO7!H7(18a$qLVj~HvN?Rf)D*&9sxtpweL37YVHO=S2qnn=X8y7Y2SaR$mWD@UbJ++)2LkiD<#{x3%Ypf z@R{@#?FrcFlbR<=@vAPK{$#z6tV5MLrijl2ZgBJbb}%_Gx6z9U`$O3qE+(g7TU-|C zsL#HW;yEoZqMvNs3O#P5V9k{?sQEB0ALv&#XWytlW!fhN}StrO+qf_7_cva(hV|kfRjI*U{xWTOd@!MV1BOj!u33s|J?09fSDw1GYZx#KviA?Yanc+6# zLNSGSd1`rxrDTH9;25)f8VRE7SQOYQA^9hGLN=e^j9RzEH=9z5Q&5P4;hd`nSX+Nw zmFPC%g)e5p*yGN6Wnv;XF0TgXK>dVra&C+emgymF1y=vkZQQp3V>U(_y<1y&5RW^C zJE(F&@gw_AF?W2M@=8buF5y zcW|b!v)sRR&E5efA9uMuDmlC*6bFC)zq*SMi8;a|hm6IU8a!ic8`;+y9cqXBv_q_m zeRF(c@eI5{;(k#M?Pae{9|U*uloxY_IR65p{bHAMia#7M^ahz8%Vnlqf`A-IAuNfI z&M<*!d4e#Zx+zjA{!6E_h>fJyN$`!(Iv51raG-D{nEO_dBc{@}B_tELmh*pBGbea+ zLepk=(J|*$-YzGdL=sES=T0_!_d%7or&?aPL6-lwy(?9(e31y=7qWF`m$g58f$|O)QNMc7;kYn#;^J1 z!=$BfW*yzQW{3q%3=K2jro5ren{~zVHsm;C6llPu;1QPl%PQzlKc?l9=v{MBsM0uM zR*$b&Ahg4cIxq}SlB_0*>rHN;a)vybdLJkDQD*=kP06p}l~$sheocR2adz&tRR47JWlg$ zeKB2MkSYYmm3>Wso;w-hb`oV0Jmxpra)5Dw;sb+D&D-)KqP11uuq6hpW#~f-R$VC} zuf1Np&LVk{#SE70)=Snlo3TgVu+i=cQ|4H2o9OLhdJB{*Yps6_$3m+Ej8;v$wjB)Y zfOuVadn#5gyFvjb+^C@2U-wvQQ-^)h4||-Xe~5YOS4Wzb(ucZZ5&K& zU$|o#y)A4dtKkP?r#j$3r^@EvA?Kigesx zp5$B$?gA(U?s9WsGb5o*0We+=Mg)az4zCo(BD*O1Pq=M1Z(z)sfYw2Y;si+00t4k{ zHYdGt7bt)3DKF?fQ5AV7tiMP?hz}!WFi970uOe%93Ne}j9bQx9EM&y-Af}Zv@q_du zL-pH7(S0G`|C3PgOt`xFXzBBegMV7!Ut~CiK9q?+&m1%!g-iI8YqzG)V3;kk<3@n$ z)wR0TjgT6dE$rdOfn5eMO=1H}$fGw6N}D+_6`_Bq(iz-Oo-SQq-&UYqXdp$DGLfZr zIGnnfxDiVO<;F=PBAP1gI6+RrI8$Z?4(75kxgddU?KMZLfj~|z=7c^*)_Xq)X(Yt_zKF%a3$FeJm*-k3nua68hc!KYQk$gp&`ei zrWAiwq}5GZZx?YS2)VA=_UV1$_WH7ry?$FL3nS-ak?BUeU?tJC56_}S!KV%ehz3|U zg`Rse71q>T4w_e2}7A+2r;ds`}wq5 z61KNnu(*YrquVf@v0)%or=yD8y7%bmTFieZ9fy=lj{-el4_FPFI8WUg3_Xbl7M?w& z(G~T^43XQTOFYm4o0CBdb$BdkUStymx&4OMSfAf&y8tD#)Ybyh7SjmagWVk*luAbT zLOqm%_l^6g^7mA27K6UhI?%D^zb19DysvzyP4w?zTbux`hg~E4>t)PT1zvP% z62fy5+t)_@xy1^$(r|su!sajvzJ;(NO?WbxF)eQ=Tr-9(nVBrv@iV@FSgu6~0$vT= zj|NRs+5b5Eu~YE*7DHV9y9#u=+ob6ZY%RHM{50yJsX_85wWczsfrYtW%^LW6z{&!`Cy zBRWNvu*SwA6vC>v2WJTf6v!-mrJ{4Pb6gJr z4Wdo;gTOWs>+-!b?*+>|vMX^kS0**(>`sP^_7A4Pj)rP?`|$y*a@os)4k_x%YZk?6 za@RD(&K4z5T~t?V&kp5-pa(b6^cgWlG815E*f+n6vB;*@!MmeVr)q!aC}Ut8BFC66 zk>4-99ktMeT2Vn#gLUuXgS={s0_h~&&cuG{?9q}2>q0@IL^f7sR_@zxU)lE9*Tt^q zPrg|gwh^@qGhHvP1&jlI!<~X?XT==3s?|_Ffcn|lgf%x+Je|l+)Uk`9*{FZp4RXB@$TVK_V)brc#uwm zQi50)#hj3n$xfxdDXL~gS`c#cQFm~RrZ;poNu#zm_a)R|JbHh_i#{9fcgRf9a@hK% z5ecT?=56Yzi4Ns*{vki7-V5LU@XGk8$U9p9aMzPQII+Co*3s^IWdtcOpMNJw z!FGCkYEb=5(t_^HeJLU68{TmH(-U()D<2&7(h8or-Eg<#=Y{U{z(L_pa$udLExBDL zS-%+#8F)UOi4A{e^n1Y+9~;e)J(Py|w++*+>6xO}D;M#(>ouo|CbXJYbQ3BWch|@*mQ2kqOrV;qevg!Mv1EznYKHx<+)m$-*r{%ds@Bmaz z5_4Hm)ahF?4F-D1FQCPy9-{yX2eAmji%f@{JUJ9o!e|+FQKKdl4lYJErB)5OpZL0< zSX>V;@y=cH+by~ThblAMW*HQ9mu_A1dS&N6c7XlE58tE~NXllD4=f$2b3*O{6YWeO zUt7A6@+p6C3Jo$)+L2Fr$)RT){H}U9pPO}OpEI`Conb|tHF34Z1YjVq(FOW2wW%TE zk(3_Wxrt#qdQhgHH$7)a8(Gk{7uBW83I(yQ$YH_XHP1{o|F(Yv4U8x3NV=$29xfJ@D*6=Zx%oz{ zeD*c8#5S>(O~BilgvM53r))wh#bBnpilVQHAAb}&Yo)?ky1t>?VFf!76F5lP&6^Pj zUYJxeS~rP)s4jJ}U}liHz)|5+#zqzD3^t4^tngT)a*59#ZH8@6ZT?T73R{WDZs++Y z<`jP@BW)3dQJ^9jp+Z*L z`63p{S7>BaY`3VgS_a46*LK4*|e^iZf)fvz-pER)3V}keEG8;RN z9n_*VRPb7`InwniJr_;{P(RBXr46roCg^|If<@m)=QPOyNE;~go!(9eGe zAq75Nqu*WOz~k6}a1rX>5RiKqupw{Tl3p!dt)D`N#tI9
    siHzLP_%PaVP*sFEj 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 diff --git a/resources/schema/schema.json.sha256 b/resources/schema/schema.json.sha256 index 0c7a0eb8..d8237afb 100644 --- a/resources/schema/schema.json.sha256 +++ b/resources/schema/schema.json.sha256 @@ -1 +1 @@ -nvdIm9lmWr6eYd0LhUUTOCKQrZ6EP2w7aPmfNXw7qzI \ No newline at end of file +zeYWlKx8i_-qA0NG_5jMhgD9U2mcTmGFevxlNBSDDoI \ No newline at end of file diff --git a/tests/Cargo.toml b/tests/Cargo.toml index c94575fe..f594adc5 100644 --- a/tests/Cargo.toml +++ b/tests/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tests" -version = "0.16.11" +version = "0.16.12" edition = "2024" [features] @@ -45,7 +45,7 @@ migration = { path = "../crates/migration", features = ["test_mode", "enterprise trc = { path = "../crates/trc", features = ["enterprise"] } managesieve = { path = "../crates/managesieve", features = ["test_mode", "enterprise"] } smtp-proto = { version = "0.2" } -mail-auth = { version = "0.9", features = ["test"] } +mail-auth = { version = "0.10", features = ["test"] } mail-parser = { version = "0.11", features = ["full_encoding", "rkyv"] } mail-builder = "0.4.4" sieve-rs = { version = "0.7", features = ["rkyv"] } diff --git a/tests/resources/tls_cert.pem b/tests/resources/tls_cert.pem index 02b9b963..5c8104bd 100644 --- a/tests/resources/tls_cert.pem +++ b/tests/resources/tls_cert.pem @@ -1,29 +1,29 @@ -----BEGIN CERTIFICATE----- -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 -----END CERTIFICATE----- diff --git a/tests/src/smtp/inbound/antispam.rs b/tests/src/smtp/inbound/antispam.rs index b5300f2f..a099eb75 100644 --- a/tests/src/smtp/inbound/antispam.rs +++ b/tests/src/smtp/inbound/antispam.rs @@ -21,8 +21,8 @@ use common::{ use http_proto::{JsonResponse, ToHttpResponse}; use hyper::Method; use mail_auth::{ - ArcOutput, DkimOutput, DkimResult, DmarcResult, IprevOutput, IprevResult, MX, SpfOutput, - SpfResult, dkim::Signature, dmarc::Policy, + ArcOutput, DkimOutput, DkimResult, DmarcResult, DnssecStatus, IprevOutput, IprevResult, MX, + SpfOutput, SpfResult, dkim::Signature, dmarc::Policy, }; use mail_parser::MessageParser; use registry::{ @@ -214,6 +214,7 @@ async fn antispam() { exchanges: vec!["127.0.0.1".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(100), ); } diff --git a/tests/src/smtp/lookup/expressions.rs b/tests/src/smtp/lookup/expressions.rs index 691b238b..ad0f4c79 100644 --- a/tests/src/smtp/lookup/expressions.rs +++ b/tests/src/smtp/lookup/expressions.rs @@ -6,7 +6,7 @@ use crate::utils::{dns::DnsCache, server::TestServerBuilder}; use common::expr::{tokenizer::TokenMap, *}; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::schema::{ enums::ExpressionVariable, prelude::{ObjectType, Property}, @@ -75,6 +75,7 @@ async fn expressions() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); diff --git a/tests/src/smtp/lookup/utils.rs b/tests/src/smtp/lookup/utils.rs index b415fa70..f7b05a55 100644 --- a/tests/src/smtp/lookup/utils.rs +++ b/tests/src/smtp/lookup/utils.rs @@ -11,7 +11,7 @@ use common::config::smtp::{ report::AggregateFrequency, resolver::{Mode, MxPattern, Policy}, }; -use mail_auth::{IpLookupStrategy, MX}; +use mail_auth::{DnssecStatus, IpLookupStrategy, MX, RecordSet}; use mail_parser::DateTime; use registry::{ schema::{ @@ -225,25 +225,28 @@ async fn strategies() { #[test] fn to_remote_hosts() { - let mx: Arc<[MX]> = Arc::from(vec![ - MX { - exchanges: vec!["mx1".into(), "mx2".into()].into_boxed_slice(), - preference: 10, - }, - MX { - exchanges: vec!["mx3".into(), "mx4".into(), "mx5".into(), "mx6".into()] - .into_boxed_slice(), - preference: 20, - }, - MX { - exchanges: vec!["mx7".into(), "mx8".into()].into_boxed_slice(), - preference: 10, - }, - MX { - exchanges: vec!["mx9".into(), "mxA".into()].into_boxed_slice(), - preference: 10, - }, - ]); + let mx: RecordSet = RecordSet { + rrset: Arc::from(vec![ + MX { + exchanges: vec!["mx1".into(), "mx2".into()].into_boxed_slice(), + preference: 10, + }, + MX { + exchanges: vec!["mx3".into(), "mx4".into(), "mx5".into(), "mx6".into()] + .into_boxed_slice(), + preference: 20, + }, + MX { + exchanges: vec!["mx7".into(), "mx8".into()].into_boxed_slice(), + preference: 10, + }, + MX { + exchanges: vec!["mx9".into(), "mxA".into()].into_boxed_slice(), + preference: 10, + }, + ]), + dnssec_status: DnssecStatus::Indeterminate, + }; let mx_config = MxConfig { max_mx: 7, max_multi_homed: 2, @@ -256,10 +259,13 @@ fn to_remote_hosts() { assert!((*host.as_bytes().last().unwrap() - b'0') <= 8); } } - let mx: Arc<[MX]> = Arc::from(vec![MX { - exchanges: vec![".".into()].into_boxed_slice(), - preference: 0, - }]); + let mx: RecordSet = RecordSet { + rrset: Arc::from(vec![MX { + exchanges: vec![".".into()].into_boxed_slice(), + preference: 0, + }]), + dnssec_status: DnssecStatus::Indeterminate, + }; assert!(mx.to_remote_hosts("domain", &mx_config).is_none()); } diff --git a/tests/src/smtp/management/queue.rs b/tests/src/smtp/management/queue.rs index cda46abd..f2e4ee9b 100644 --- a/tests/src/smtp/management/queue.rs +++ b/tests/src/smtp/management/queue.rs @@ -9,7 +9,7 @@ use crate::{ utils::{dns::DnsCache, server::TestServerBuilder}, }; use ahash::{AHashMap, HashMap, HashSet}; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::NetworkListenerProtocol, @@ -134,6 +134,7 @@ async fn manage_queue() { exchanges: vec!["mx1.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); diff --git a/tests/src/smtp/outbound/dane.rs b/tests/src/smtp/outbound/dane.rs index 953fbaf4..1d2d3b1c 100644 --- a/tests/src/smtp/outbound/dane.rs +++ b/tests/src/smtp/outbound/dane.rs @@ -16,7 +16,7 @@ use common::{ ipc::PolicyType, }; use mail_auth::{ - MX, + DnssecStatus, MX, common::parse::TxtRecordParser, mta_sts::{ReportUri, TlsRpt}, report::tlsrpt::ResultType, @@ -32,7 +32,10 @@ use registry::schema::{ }; use rustls_pki_types::CertificateDer; use sha2::{Digest, Sha256}; -use smtp::outbound::dane::{dnssec::TlsaLookup, verify::TlsaVerify}; +use smtp::outbound::dane::{ + dnssec::{TlsaLookup, TlsaResult}, + verify::TlsaVerify, +}; use smtp::queue::{Error, ErrorDetails, Status}; use std::{ collections::BTreeSet, @@ -118,6 +121,7 @@ async fn dane_verify() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( @@ -255,9 +259,13 @@ async fn dane_verify() { // An insecure (non-DNSSEC) MX zone must not honor TLSA records, // even when valid records are cached. - local.server.dnssec_add( - "mx.foobar.org", - false, + local.server.mx_add( + "foobar.org", + vec![MX { + exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), + preference: 10, + }], + DnssecStatus::Insecure, Instant::now() + Duration::from_secs(10), ); session @@ -347,6 +355,7 @@ async fn dane_downgrade_on_tlsa_servfail() { exchanges: vec!["mx._dns_error.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( @@ -372,6 +381,135 @@ async fn dane_downgrade_on_tlsa_servfail() { remote.assert_no_events(); } +#[tokio::test] +#[serial_test::serial] +async fn dane_bogus_dnssec_temp_fails() { + let mut local = TestServerBuilder::new("smtp_dane_bogus_local") + .await + .with_http_listener(19022) + .await + .disable_services() + .capture_queue() + .capture_reporting() + .build() + .await; + + let local_admin = local.account("admin"); + local_admin.mta_allow_relaying().await; + local_admin.mta_no_auth().await; + local_admin + .registry_create_object(TlsReportSettings { + send_frequency: Expression { + else_: "weekly".into(), + ..Default::default() + }, + ..Default::default() + }) + .await; + let (tls_strategy_id, mut tls_strategy) = local_admin + .registry_get_all::() + .await + .into_iter() + .find(|(_, s)| s.name == "default") + .unwrap(); + tls_strategy.dane = MtaRequiredOrOptional::Require; + tls_strategy.start_tls = MtaRequiredOrOptional::Require; + let mut tls_strategy = serde_json::to_value(tls_strategy).unwrap(); + tls_strategy + .as_object_mut() + .unwrap() + .retain(|k, _| k != "name"); + local_admin + .registry_update_object(ObjectType::MtaTlsStrategy, tls_strategy_id, tls_strategy) + .await; + local_admin.reload_settings().await; + local.reload_core(); + local.expect_reload_settings().await; + + local.server.txt_add( + "_smtp._tls.foobar.org", + TlsRpt::parse(b"v=TLSRPTv1; rua=mailto:reports@foobar.org").unwrap(), + Instant::now() + Duration::from_secs(30), + ); + local.server.ipv4_add( + "mx.foobar.org", + vec!["127.0.0.1".parse().unwrap()], + Instant::now() + Duration::from_secs(30), + ); + local.server.ipv4_add( + "mx._dnssec_bogus.foobar.org", + vec!["127.0.0.1".parse().unwrap()], + Instant::now() + Duration::from_secs(30), + ); + + let mut session = local.new_mta_session(); + session.data.remote_ip_str = "10.0.0.1".into(); + session.eval_session_params().await; + session.ehlo("mx.test.org").await; + + local.server.mx_add( + "foobar.org", + vec![MX { + exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), + preference: 10, + }], + DnssecStatus::Bogus, + Instant::now() + Duration::from_secs(30), + ); + session + .send_message("john@test.org", &["bill@foobar.org"], "test:no_dkim", "250") + .await; + local + .expect_message_then_deliver() + .await + .try_deliver(local.server.clone()); + let retry = local.expect_message().await; + assert!(retry.message.recipients[0].retry.due > now()); + + let report = local.read_report().await.unwrap_tls(); + assert_eq!(report.domain, "foobar.org"); + assert_eq!(report.policy, PolicyType::Tlsa(None)); + assert_eq!( + report.failure.as_ref().unwrap().result_type, + ResultType::DnssecInvalid + ); + assert_eq!( + report.failure.as_ref().unwrap().receiving_mx_hostname, + Some("mx.foobar.org".to_string()) + ); + + local.server.mx_add( + "foobar.org", + vec![MX { + exchanges: vec!["mx._dnssec_bogus.foobar.org".into()].into_boxed_slice(), + preference: 10, + }], + DnssecStatus::Secure, + Instant::now() + Duration::from_secs(30), + ); + session + .send_message("john@test.org", &["bill@foobar.org"], "test:no_dkim", "250") + .await; + local + .expect_message_then_deliver() + .await + .try_deliver(local.server.clone()); + let retry = local.expect_message().await; + assert!(retry.message.recipients[0].retry.due > now()); + + let report = local.read_report().await.unwrap_tls(); + assert_eq!(report.domain, "foobar.org"); + assert_eq!(report.policy, PolicyType::Tlsa(None)); + assert_eq!( + report.failure.as_ref().unwrap().result_type, + ResultType::DnssecInvalid + ); + assert_eq!( + report.failure.as_ref().unwrap().receiving_mx_hostname, + Some("mx._dnssec_bogus.foobar.org".to_string()) + ); +} + #[tokio::test] #[serial_test::serial] async fn dane_test() { @@ -462,12 +600,15 @@ async fn dane_test() { } // Successful DANE verification (end-entity match, RFC 7671 Section 5.1) - let tlsa = test + let tlsa = match test .server .tlsa_lookup(format!("_25._tcp.{host}.")) .await .unwrap() - .unwrap(); + { + TlsaResult::Secure(tlsa) => tlsa, + _ => panic!("expected secure TLSA records"), + }; assert_eq!( tlsa.verify(0, &host, &[host.as_str()], Some(&certs)), diff --git a/tests/src/smtp/outbound/extensions.rs b/tests/src/smtp/outbound/extensions.rs index f14be93e..07037d1f 100644 --- a/tests/src/smtp/outbound/extensions.rs +++ b/tests/src/smtp/outbound/extensions.rs @@ -11,7 +11,7 @@ use crate::{ }, utils::{dns::DnsCache, server::TestServerBuilder}, }; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::schema::structs::{Expression, MtaStageData}; use smtp_proto::{MAIL_REQUIRETLS, MAIL_RET_HDRS, MAIL_SMTPUTF8, RCPT_NOTIFY_NEVER}; use std::time::{Duration, Instant}; @@ -98,6 +98,7 @@ async fn extensions() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( diff --git a/tests/src/smtp/outbound/fallback_relay.rs b/tests/src/smtp/outbound/fallback_relay.rs index 4854f093..a6363990 100644 --- a/tests/src/smtp/outbound/fallback_relay.rs +++ b/tests/src/smtp/outbound/fallback_relay.rs @@ -8,7 +8,7 @@ use crate::{ smtp::session::TestSession, utils::{dns::DnsCache, server::TestServerBuilder}, }; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::MtaProtocol, @@ -102,6 +102,7 @@ async fn fallback_relay() { exchanges: vec!["_dns_error.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( diff --git a/tests/src/smtp/outbound/ip_lookup.rs b/tests/src/smtp/outbound/ip_lookup.rs index 4beaf26f..4dd4a5d5 100644 --- a/tests/src/smtp/outbound/ip_lookup.rs +++ b/tests/src/smtp/outbound/ip_lookup.rs @@ -8,7 +8,7 @@ use crate::{ smtp::{inbound::TestQueueEvent, session::TestSession}, utils::{dns::DnsCache, server::TestServerBuilder}, }; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::MtaIpStrategy, @@ -84,6 +84,7 @@ async fn ip_lookup_strategy() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); if matches!(strategy, MtaIpStrategy::V6ThenV4) { diff --git a/tests/src/smtp/outbound/mta_sts.rs b/tests/src/smtp/outbound/mta_sts.rs index a3c6bfab..0248fec2 100644 --- a/tests/src/smtp/outbound/mta_sts.rs +++ b/tests/src/smtp/outbound/mta_sts.rs @@ -13,7 +13,7 @@ use crate::{ }; use common::{config::smtp::resolver::Policy, ipc::PolicyType}; use mail_auth::{ - MX, + DnssecStatus, MX, common::parse::TxtRecordParser, mta_sts::{MtaSts, ReportUri, TlsRpt}, report::tlsrpt::ResultType, @@ -102,6 +102,7 @@ async fn mta_sts_verify() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( diff --git a/tests/src/smtp/outbound/smtp.rs b/tests/src/smtp/outbound/smtp.rs index 4d384577..334fbbdb 100644 --- a/tests/src/smtp/outbound/smtp.rs +++ b/tests/src/smtp/outbound/smtp.rs @@ -12,7 +12,7 @@ use crate::{ utils::{dns::DnsCache, server::TestServerBuilder}, }; use common::{config::smtp::queue::QueueName, ipc::QueueEvent}; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::NetworkListenerProtocol, @@ -224,6 +224,7 @@ async fn smtp_delivery() { .into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( diff --git a/tests/src/smtp/outbound/throttle.rs b/tests/src/smtp/outbound/throttle.rs index 4e250117..c601135b 100644 --- a/tests/src/smtp/outbound/throttle.rs +++ b/tests/src/smtp/outbound/throttle.rs @@ -12,7 +12,7 @@ use crate::{ }, utils::{dns::DnsCache, server::TestServerBuilder}, }; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::MtaOutboundThrottleKey, @@ -239,6 +239,7 @@ async fn throttle_outbound() { exchanges: vec!["mx.test.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( @@ -269,6 +270,7 @@ async fn throttle_outbound() { exchanges: vec!["mx.test.net".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( diff --git a/tests/src/smtp/outbound/tls.rs b/tests/src/smtp/outbound/tls.rs index da402c03..fdf08e6f 100644 --- a/tests/src/smtp/outbound/tls.rs +++ b/tests/src/smtp/outbound/tls.rs @@ -11,7 +11,7 @@ use crate::{ }, utils::{dns::DnsCache, server::TestServerBuilder}, }; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::MtaRequiredOrOptional, @@ -119,6 +119,7 @@ async fn starttls_optional() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(10), ); local.server.ipv4_add( diff --git a/tests/src/smtp/queue/concurrent.rs b/tests/src/smtp/queue/concurrent.rs index 98e2b7b9..35a8de08 100644 --- a/tests/src/smtp/queue/concurrent.rs +++ b/tests/src/smtp/queue/concurrent.rs @@ -9,7 +9,7 @@ use crate::{ utils::{dns::DnsCache, server::TestServerBuilder}, }; use common::{BuildServer, ipc::QueueEvent}; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::NetworkListenerProtocol, @@ -125,6 +125,7 @@ async fn concurrent_queue() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(100), ); local.server.ipv4_add( @@ -149,6 +150,7 @@ async fn concurrent_queue() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(100), ); server.ipv4_add( diff --git a/tests/src/smtp/queue/virtualq.rs b/tests/src/smtp/queue/virtualq.rs index 4b06a7ba..4cf110aa 100644 --- a/tests/src/smtp/queue/virtualq.rs +++ b/tests/src/smtp/queue/virtualq.rs @@ -9,7 +9,7 @@ use crate::{ utils::{dns::DnsCache, server::TestServerBuilder}, }; use common::{BuildServer, config::smtp::queue::QueueName, ipc::QueueEvent}; -use mail_auth::MX; +use mail_auth::{DnssecStatus, MX}; use registry::{ schema::{ enums::NetworkListenerProtocol, @@ -185,6 +185,7 @@ async fn virtual_queue() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(100), ); local.server.ipv4_add( @@ -209,6 +210,7 @@ async fn virtual_queue() { exchanges: vec!["mx.foobar.org".into()].into_boxed_slice(), preference: 10, }], + DnssecStatus::Secure, Instant::now() + Duration::from_secs(100), ); server.ipv4_add( diff --git a/tests/src/utils/dns.rs b/tests/src/utils/dns.rs index 31757622..5e01f631 100644 --- a/tests/src/utils/dns.rs +++ b/tests/src/utils/dns.rs @@ -8,7 +8,7 @@ use common::{ Server, config::{mailstore::spamfilter::IpResolver, smtp::resolver::Tlsa}, }; -use mail_auth::{MX, Txt, common::resolver::ToFqdn}; +use mail_auth::{DnssecStatus, MX, RecordSet, Txt, common::resolver::ToFqdn}; use std::{ net::{IpAddr, Ipv4Addr, Ipv6Addr}, sync::Arc, @@ -20,9 +20,14 @@ pub trait DnsCache { fn ipv6_add(&self, name: impl ToFqdn, value: Vec, valid_until: std::time::Instant); fn dnsbl_add(&self, name: &str, value: Vec, valid_until: std::time::Instant); fn ptr_add(&self, name: IpAddr, value: Vec, valid_until: std::time::Instant); - fn mx_add(&self, name: impl ToFqdn, value: Vec, valid_until: std::time::Instant); + fn mx_add( + &self, + name: impl ToFqdn, + value: Vec, + dnssec_status: DnssecStatus, + valid_until: std::time::Instant, + ); fn tlsa_add(&self, name: impl ToFqdn, value: Arc, valid_until: std::time::Instant); - fn dnssec_add(&self, name: impl ToFqdn, secure: bool, valid_until: std::time::Instant); } impl DnsCache for Server { @@ -34,10 +39,14 @@ impl DnsCache for Server { } fn ipv4_add(&self, name: impl ToFqdn, value: Vec, valid_until: std::time::Instant) { - self.inner - .cache - .dns_ipv4 - .insert_with_expiry(name.to_fqdn(), Arc::from(value), valid_until); + self.inner.cache.dns_ipv4.insert_with_expiry( + name.to_fqdn(), + RecordSet { + rrset: Arc::from(value), + dnssec_status: DnssecStatus::Indeterminate, + }, + valid_until, + ); } fn dnsbl_add(&self, name: &str, value: Vec, valid_until: std::time::Instant) { @@ -56,25 +65,42 @@ impl DnsCache for Server { } fn ipv6_add(&self, name: impl ToFqdn, value: Vec, valid_until: std::time::Instant) { - self.inner - .cache - .dns_ipv6 - .insert_with_expiry(name.to_fqdn(), Arc::from(value), valid_until); + self.inner.cache.dns_ipv6.insert_with_expiry( + name.to_fqdn(), + RecordSet { + rrset: Arc::from(value), + dnssec_status: DnssecStatus::Indeterminate, + }, + valid_until, + ); } fn ptr_add(&self, name: IpAddr, value: Vec, valid_until: std::time::Instant) { self.inner.cache.dns_ptr.insert_with_expiry( name, - Arc::from(value.into_iter().map(Into::into).collect::>()), + RecordSet { + rrset: Arc::from(value.into_iter().map(Into::into).collect::>()), + dnssec_status: DnssecStatus::Indeterminate, + }, valid_until, ); } - fn mx_add(&self, name: impl ToFqdn, value: Vec, valid_until: std::time::Instant) { - self.inner - .cache - .dns_mx - .insert_with_expiry(name.to_fqdn(), Arc::from(value), valid_until); + fn mx_add( + &self, + name: impl ToFqdn, + value: Vec, + dnssec_status: DnssecStatus, + valid_until: std::time::Instant, + ) { + self.inner.cache.dns_mx.insert_with_expiry( + name.to_fqdn(), + RecordSet { + rrset: Arc::from(value), + dnssec_status, + }, + valid_until, + ); } fn tlsa_add(&self, name: impl ToFqdn, value: Arc, valid_until: std::time::Instant) { @@ -83,11 +109,4 @@ impl DnsCache for Server { .dns_tlsa .insert_with_expiry(name.to_fqdn(), value, valid_until); } - - fn dnssec_add(&self, name: impl ToFqdn, secure: bool, valid_until: std::time::Instant) { - self.inner - .cache - .dns_dnssec - .insert_with_expiry(name.to_fqdn(), secure, valid_until); - } }