fix dns over TLS and HTTPS

This commit is contained in:
erebe 2024-06-19 20:34:53 +00:00 committed by Σrebe - Romain GERARD
parent fb378d29d5
commit 7165f328a8
No known key found for this signature in database
GPG key ID: 7A42B4B97E0332F4
4 changed files with 48 additions and 17 deletions

View file

@ -1,6 +1,6 @@
use anyhow::anyhow;
use anyhow::{anyhow, Context};
use futures_util::FutureExt;
use hickory_resolver::config::{NameServerConfig, ResolverConfig, ResolverOpts};
use hickory_resolver::config::{NameServerConfig, Protocol, ResolverConfig, ResolverOpts};
use hickory_resolver::name_server::{GenericConnector, RuntimeProvider, TokioRuntimeProvider};
use hickory_resolver::proto::iocompat::AsyncIoTokioAsStd;
use hickory_resolver::proto::TokioTime;
@ -67,10 +67,24 @@ impl DnsResolver {
// otherwise, use the specified resolvers
let mut cfg = ResolverConfig::new();
for resolver in resolvers.iter() {
let (protocol, port) = match resolver.scheme() {
"dns" => (hickory_resolver::config::Protocol::Udp, resolver.port().unwrap_or(53)),
"dns+https" => (hickory_resolver::config::Protocol::Https, resolver.port().unwrap_or(443)),
"dns+tls" => (hickory_resolver::config::Protocol::Tls, resolver.port().unwrap_or(853)),
let (protocol, port, tls_sni) = match resolver.scheme() {
"dns" => (Protocol::Udp, resolver.port().unwrap_or(53), None),
"dns+https" => {
let tls_sni = resolver
.query_pairs()
.find(|(k, _)| k == "sni")
.with_context(|| "Missing `sni` query parameter for dns over https")?
.1;
(Protocol::Https, resolver.port().unwrap_or(443), Some(tls_sni.to_string()))
}
"dns+tls" => {
let tls_sni = resolver
.query_pairs()
.find(|(k, _)| k == "sni")
.with_context(|| "Missing `sni` query parameter for dns over tls")?
.1;
(Protocol::Tls, resolver.port().unwrap_or(853), Some(tls_sni.to_string()))
}
_ => return Err(anyhow!("invalid protocol for dns resolver")),
};
let host = resolver
@ -87,7 +101,10 @@ impl DnsResolver {
Host::Ipv4(ip) => SocketAddr::V4(SocketAddrV4::new(ip, port)),
Host::Ipv6(ip) => SocketAddr::V6(SocketAddrV6::new(ip, port, 0, 0)),
};
cfg.add_name_server(NameServerConfig::new(sock, protocol))
let mut ns = NameServerConfig::new(sock, protocol);
ns.tls_dns_name = tls_sni;
cfg.add_name_server(ns);
}
let mut opts = ResolverOpts::default();
@ -174,4 +191,4 @@ impl RuntimeProvider for TokioRuntimeProviderWithSoMark {
Box::pin(socket)
}
}
}

View file

@ -248,8 +248,8 @@ struct Client {
/// Dns resolver to use to lookup ips of domain name. Can be specified multiple time
/// Example:
/// dns://1.1.1.1 for using udp
/// dns+https://1.1.1.1 for using dns over HTTPS
/// dns+tls://8.8.8.8 for using dns over TLS
/// dns+https://1.1.1.1?sni=loudflare-dns.com for using dns over HTTPS
/// dns+tls://8.8.8.8?sni=dns.google for using dns over TLS
/// To use libc resolver, use
/// system://0.0.0.0
///
@ -286,8 +286,8 @@ struct Server {
/// Can be specified multiple time
/// Example:
/// dns://1.1.1.1 for using udp
/// dns+https://1.1.1.1 for using dns over HTTPS
/// dns+tls://8.8.8.8 for using dns over TLS
/// dns+https://1.1.1.1?sni=loudflare-dns.com for using dns over HTTPS
/// dns+tls://8.8.8.8?sni=dns.google for using dns over TLS
/// To use libc resolver, use
/// system://0.0.0.0
#[arg(long, verbatim_doc_comment)]
@ -1316,4 +1316,4 @@ async fn main() {
}
tokio::signal::ctrl_c().await.unwrap();
}
}