of names or suffixes of the special nameservers.
// Used in the Syncres to not throttle certain servers
GlobalStateHolder<SuffixMatchNode> g_dontThrottleNames;
GlobalStateHolder<NetmaskGroup> g_dontThrottleNetmasks;
+GlobalStateHolder<SuffixMatchNode> g_DoTToAuthNames;
#define LOCAL_NETS "127.0.0.0/8, 10.0.0.0/8, 100.64.0.0/10, 169.254.0.0/16, 192.168.0.0/16, 172.16.0.0/12, ::1/128, fc00::/7, fe80::/10"
#define LOCAL_NETS_INVERSE "!127.0.0.0/8, !10.0.0.0/8, !100.64.0.0/10, !169.254.0.0/16, !192.168.0.0/16, !172.16.0.0/12, !::1/128, !fc00::/7, !fe80::/10"
g_xdnssec.setState(std::move(xdnssecNames));
}
+ {
+ SuffixMatchNode dotauthNames;
+ vector<string> parts;
+ stringtok(parts, ::arg()["dot-to-auth-names"], " ,");
+ for (const auto &p : parts) {
+ dotauthNames.add(DNSName(p));
+ }
+ g_DoTToAuthNames.setState(std::move(dotauthNames));
+ }
+
s_balancingFactor = ::arg().asDouble("distribution-load-factor");
if (s_balancingFactor != 0.0 && s_balancingFactor < 1.0) {
s_balancingFactor = 0.0;
::arg().set("edns-padding-tag", "Packetcache tag associated to responses sent with EDNS padding, to prevent sending these to clients for which padding is not enabled.")="7830";
::arg().set("dot-to-port-853", "Force DoT connection to target port 853 if DoT compiled in")="yes";
+ ::arg().set("dot-to-auth-names", "Use DoT to authoritative servers with these names or suffixes")="";
::arg().setCmd("help","Provide a helpful message");
::arg().setCmd("version","Print version string");
handle incoming queries and distribute them to other threads based on a hash of the query, to maximize the cache hit
ratio.
+.. _settings-dot-to-auth-names:
+
+``dot-to-auth-names``
+-------------------
+.. versionadded:: 4.6.0
+
+- Comma separated list of domain-names or suffixes
+- Default: (empty).
+
+Force DoT to the listed authoritative nameservers. For this to work, DoT support has to be compiled in.
+Currently, the certificate is checked for validity, but the name in the certificate is not checked against
+the name of the host.
+
.. _settings-dot-to-port-853:
``dot-to-port-853``
GlobalStateHolder<SuffixMatchNode> g_xdnssec;
GlobalStateHolder<SuffixMatchNode> g_dontThrottleNames;
GlobalStateHolder<NetmaskGroup> g_dontThrottleNetmasks;
+GlobalStateHolder<SuffixMatchNode> g_DoTToAuthNames;
std::unique_ptr<MemRecursorCache> g_recCache{nullptr};
std::unique_ptr<NegCache> g_negCache{nullptr};
unsigned int g_numThreads = 1;
return done;
}
-bool SyncRes::doResolveAtThisIP(const std::string& prefix, const DNSName& qname, const QType qtype, LWResult& lwr, boost::optional<Netmask>& ednsmask, const DNSName& auth, bool const sendRDQuery, const bool wasForwarded, const DNSName& nsName, const ComboAddress& remoteIP, bool doTCP, bool& truncated, bool& spoofed)
+bool SyncRes::doResolveAtThisIP(const std::string& prefix, const DNSName& qname, const QType qtype, LWResult& lwr, boost::optional<Netmask>& ednsmask, const DNSName& auth, bool const sendRDQuery, const bool wasForwarded, const DNSName& nsName, const ComboAddress& remoteIP, bool doTCP, bool doDoT, bool& truncated, bool& spoofed)
{
bool chained = false;
LWResult::Result resolveret = LWResult::Result::Success;
}
if(doTCP) {
- if (SyncRes::s_dot_to_port_853 && remoteIP.getPort() == 853) {
+ if (doDoT) {
LOG(prefix<<qname<<": using DoT with "<< remoteIP.toStringWithPort() <<endl);
s_dotoutqueries++;
d_dotoutqueries++;
return false;
}
+bool SyncRes::doDoTtoAuth(const DNSName& ns) const
+{
+ return g_DoTToAuthNames.getLocal()->check(ns);
+}
+
/** returns:
* -1 in case of no results
* rcode otherwise
typedef vector<ComboAddress> remoteIPs_t;
remoteIPs_t remoteIPs;
- remoteIPs_t::const_iterator remoteIP;
+ remoteIPs_t::iterator remoteIP;
bool pierceDontQuery=false;
bool sendRDQuery=false;
boost::optional<Netmask> ednsmask;
else {
bool hitPolicy{false};
LOG(prefix<<qname<<": Resolved '"<<auth<<"' NS "<<tns->first<<" to: ");
- for(remoteIP = remoteIPs.cbegin(); remoteIP != remoteIPs.cend(); ++remoteIP) {
- if(remoteIP != remoteIPs.cbegin()) {
+ for(remoteIP = remoteIPs.begin(); remoteIP != remoteIPs.end(); ++remoteIP) {
+ if(remoteIP != remoteIPs.begin()) {
LOG(", ");
}
LOG(remoteIP->toString());
}
}
- for(remoteIP = remoteIPs.cbegin(); remoteIP != remoteIPs.cend(); ++remoteIP) {
+ for(remoteIP = remoteIPs.begin(); remoteIP != remoteIPs.end(); ++remoteIP) {
LOG(prefix<<qname<<": Trying IP "<< remoteIP->toStringWithPort() <<", asking '"<<qname<<"|"<<qtype.toString()<<"'"<<endl);
if (throttledOrBlocked(prefix, *remoteIP, qname, qtype, pierceDontQuery)) {
bool truncated = false;
bool spoofed = false;
bool gotAnswer = false;
- bool forceTCP = SyncRes::s_dot_to_port_853 && remoteIP->getPort() == 853;
+ bool doDoT = false;
+
+ if (doDoTtoAuth(tns->first)) {
+ remoteIP->setPort(853);
+ doDoT = true;
+ }
+ if (SyncRes::s_dot_to_port_853 && remoteIP->getPort() == 853) {
+ doDoT = true;
+ }
+ bool forceTCP = doDoT;
if (!forceTCP) {
gotAnswer = doResolveAtThisIP(prefix, qname, qtype, lwr, ednsmask, auth, sendRDQuery, wasForwarded,
- tns->first, *remoteIP, false, truncated, spoofed);
+ tns->first, *remoteIP, false, false, truncated, spoofed);
}
if (forceTCP || (spoofed || (gotAnswer && truncated))) {
/* retry, over TCP this time */
gotAnswer = doResolveAtThisIP(prefix, qname, qtype, lwr, ednsmask, auth, sendRDQuery, wasForwarded,
- tns->first, *remoteIP, true, truncated, spoofed);
+ tns->first, *remoteIP, true, doDoT, truncated, spoofed);
}
if (!gotAnswer) {
extern GlobalStateHolder<SuffixMatchNode> g_xdnssec;
extern GlobalStateHolder<SuffixMatchNode> g_dontThrottleNames;
extern GlobalStateHolder<NetmaskGroup> g_dontThrottleNetmasks;
+extern GlobalStateHolder<SuffixMatchNode> g_DoTToAuthNames;
class RecursorLua4;
typedef std::map<DNSName,vState> zonesStates_t;
enum StopAtDelegation { DontStop, Stop, Stopped };
+ bool doDoTtoAuth(const DNSName& ns) const;
int doResolveAt(NsSet &nameservers, DNSName auth, bool flawedNSSet, const DNSName &qname, QType qtype, vector<DNSRecord>&ret,
unsigned int depth, set<GetBestNSAnswer>&beenthere, vState& state, StopAtDelegation* stopAtDelegation);
- bool doResolveAtThisIP(const std::string& prefix, const DNSName& qname, const QType qtype, LWResult& lwr, boost::optional<Netmask>& ednsmask, const DNSName& auth, bool const sendRDQuery, const bool wasForwarded, const DNSName& nsName, const ComboAddress& remoteIP, bool doTCP, bool& truncated, bool& spoofed);
+ bool doResolveAtThisIP(const std::string& prefix, const DNSName& qname, const QType qtype, LWResult& lwr, boost::optional<Netmask>& ednsmask, const DNSName& auth, bool const sendRDQuery, const bool wasForwarded, const DNSName& nsName, const ComboAddress& remoteIP, bool doTCP, bool doDoT, bool& truncated, bool& spoofed);
bool processAnswer(unsigned int depth, LWResult& lwr, const DNSName& qname, const QType qtype, DNSName& auth, bool wasForwarded, const boost::optional<Netmask> ednsmask, bool sendRDQuery, NsSet &nameservers, std::vector<DNSRecord>& ret, const DNSFilterEngine& dfe, bool* gotNewServers, int* rcode, vState& state, const ComboAddress& remoteIP);
int doResolve(const DNSName &qname, QType qtype, vector<DNSRecord>&ret, unsigned int depth, set<GetBestNSAnswer>& beenthere, vState& state);
class testSimpleForwardOverDoT(RecursorTest):
"""
- This forwarding to a DoT srever in avery basic way and is dependent on Quad9 working
+ This is forwarding to a DoT server in a very basic way and is dependent on Quad9 working
"""
_confdir = 'SimpleForwardOverDoT'
print(e.output)
raise
-