From: Otto Moerbeek Date: Mon, 27 Oct 2025 10:57:08 +0000 (+0100) Subject: Store if a RRSet was retrieved over TCP in the record cache X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=d36246413d010a181b6345ac5d9f2a44354b85b5;p=thirdparty%2Fpdns.git Store if a RRSet was retrieved over TCP in the record cache Signed-off-by: Otto Moerbeek --- diff --git a/pdns/recursordist/recursor_cache.cc b/pdns/recursordist/recursor_cache.cc index fc87608dac..517cbba56b 100644 --- a/pdns/recursordist/recursor_cache.cc +++ b/pdns/recursordist/recursor_cache.cc @@ -207,7 +207,7 @@ static void ptrAssign(T* ptr, const T& value) } } -time_t MemRecursorCache::handleHit(time_t now, MapCombo::LockedContent& content, OrderedTagIterator_t& entry, const DNSName& qname, uint32_t& origTTL, vector* res, SigRecs* signatures, AuthRecs* authorityRecs, bool* variable, boost::optional& state, bool* wasAuth, DNSName* fromAuthZone, ComboAddress* fromAuthIP) +time_t MemRecursorCache::handleHit(time_t now, MapCombo::LockedContent& content, OrderedTagIterator_t& entry, const DNSName& qname, uint32_t& origTTL, vector* res, SigRecs* signatures, AuthRecs* authorityRecs, bool* variable, boost::optional& state, bool* wasAuth, DNSName* fromAuthZone, ComboAddress* fromAuthIP, bool* tcp) { // MUTEX SHOULD BE ACQUIRED (as indicated by the reference to the content which is protected by a lock) if (entry->d_tooBig) { @@ -270,6 +270,7 @@ time_t MemRecursorCache::handleHit(time_t now, MapCombo::LockedContent& content, } ptrAssign(fromAuthZone, entry->d_authZone); ptrAssign(fromAuthIP, entry->d_from); + ptrAssign(tcp, entry->d_tcp); moveCacheItemToBack(content.d_map, entry); @@ -427,7 +428,7 @@ time_t MemRecursorCache::fakeTTD(MemRecursorCache::OrderedTagIterator_t& entry, } // returns -1 for no hits -time_t MemRecursorCache::get(time_t now, const DNSName& qname, const QType qtype, Flags flags, vector* res, const ComboAddress& who, const OptTag& routingTag, SigRecs* signatures, AuthRecs* authorityRecs, bool* variable, vState* state, bool* wasAuth, DNSName* fromAuthZone, ComboAddress* fromAuthIP) // NOLINT(readability-function-cognitive-complexity) +time_t MemRecursorCache::get(time_t now, const DNSName& qname, const QType qtype, Flags flags, vector* res, const ComboAddress& who, const OptTag& routingTag, SigRecs* signatures, AuthRecs* authorityRecs, bool* variable, vState* state, bool* wasAuth, DNSName* fromAuthZone, ComboAddress* fromAuthIP, bool* tcp) // NOLINT(readability-function-cognitive-complexity) { bool requireAuth = (flags & RequireAuth) != 0; bool refresh = (flags & Refresh) != 0; @@ -455,11 +456,11 @@ time_t MemRecursorCache::get(time_t now, const DNSName& qname, const QType qtype auto entryA = getEntryUsingECSIndex(*lockedShard, now, qname, QType::A, requireAuth, who, serveStale); if (entryA != lockedShard->d_map.end()) { - ret = handleHit(now, *lockedShard, entryA, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP); + ret = handleHit(now, *lockedShard, entryA, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP, tcp); } auto entryAAAA = getEntryUsingECSIndex(*lockedShard, now, qname, QType::AAAA, requireAuth, who, serveStale); if (entryAAAA != lockedShard->d_map.end()) { - time_t ttdAAAA = handleHit(now, *lockedShard, entryAAAA, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP); + time_t ttdAAAA = handleHit(now, *lockedShard, entryAAAA, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP, tcp); if (ret > 0) { ret = std::min(ret, ttdAAAA); } @@ -476,7 +477,7 @@ time_t MemRecursorCache::get(time_t now, const DNSName& qname, const QType qtype } auto entry = getEntryUsingECSIndex(*lockedShard, now, qname, qtype, requireAuth, who, serveStale); if (entry != lockedShard->d_map.end()) { - time_t ret = handleHit(now, *lockedShard, entry, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP); + time_t ret = handleHit(now, *lockedShard, entry, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP, tcp); if (cachedState && ret > now) { ptrAssign(state, *cachedState); } @@ -508,7 +509,7 @@ time_t MemRecursorCache::get(time_t now, const DNSName& qname, const QType qtype handleServeStaleBookkeeping(now, serveStale, firstIndexIterator); - ttd = handleHit(now, *lockedShard, firstIndexIterator, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP); + ttd = handleHit(now, *lockedShard, firstIndexIterator, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP, tcp); if (qtype == QType::ADDR && found == 2) { break; @@ -550,7 +551,7 @@ time_t MemRecursorCache::get(time_t now, const DNSName& qname, const QType qtype handleServeStaleBookkeeping(now, serveStale, firstIndexIterator); - ttd = handleHit(now, *lockedShard, firstIndexIterator, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP); + ttd = handleHit(now, *lockedShard, firstIndexIterator, qname, origTTL, res, signatures, authorityRecs, variable, cachedState, wasAuth, fromAuthZone, fromAuthIP, tcp); if (qtype == QType::ADDR && found == 2) { break; @@ -630,7 +631,7 @@ bool MemRecursorCache::replace(CacheEntry&& entry) return false; } -void MemRecursorCache::replace(time_t now, const DNSName& qname, const QType qtype, const vector& content, const SigRecsVec& signatures, const AuthRecsVec& authorityRecs, bool auth, const DNSName& authZone, boost::optional ednsmask, const OptTag& routingTag, vState state, boost::optional from, bool refresh, time_t ttl_time) +void MemRecursorCache::replace(time_t now, const DNSName& qname, const QType qtype, const vector& content, const SigRecsVec& signatures, const AuthRecsVec& authorityRecs, bool auth, const DNSName& authZone, boost::optional ednsmask, const OptTag& routingTag, vState state, boost::optional from, bool overTCP, bool refresh, time_t ttl_time) { auto& shard = getMap(qname); auto lockedShard = shard.lock(); @@ -744,6 +745,7 @@ void MemRecursorCache::replace(time_t now, const DNSName& qname, const QType qty } cacheEntry.d_submitted = false; cacheEntry.d_servedStale = 0; + cacheEntry.d_tcp = overTCP; lockedShard->d_map.replace(stored, cacheEntry); } @@ -927,7 +929,7 @@ uint64_t MemRecursorCache::doDump(int fileDesc, size_t maxCacheEntries) for (const auto& record : recordSet.d_records) { count++; try { - fprintf(filePtr.get(), "%s %" PRIu32 " %" PRId64 " IN %s %s ; (%s) auth=%i zone=%s from=%s nm=%s rtag=%s ss=%hd%s\n", recordSet.d_qname.toString().c_str(), recordSet.d_orig_ttl, static_cast(recordSet.d_ttd - now), recordSet.d_qtype.toString().c_str(), record->getZoneRepresentation().c_str(), vStateToString(recordSet.d_state).c_str(), static_cast(recordSet.d_auth), recordSet.d_authZone.toLogString().c_str(), recordSet.d_from.toString().c_str(), recordSet.d_netmask.empty() ? "" : recordSet.d_netmask.toString().c_str(), !recordSet.d_rtag ? "" : recordSet.d_rtag.get().c_str(), recordSet.d_servedStale, recordSet.d_tooBig ? " (too big!)" : ""); + fprintf(filePtr.get(), "%s %" PRIu32 " %" PRId64 " IN %s %s ; (%s) auth=%i zone=%s from=%s nm=%s rtag=%s ss=%hd%s%s\n", recordSet.d_qname.toString().c_str(), recordSet.d_orig_ttl, static_cast(recordSet.d_ttd - now), recordSet.d_qtype.toString().c_str(), record->getZoneRepresentation().c_str(), vStateToString(recordSet.d_state).c_str(), static_cast(recordSet.d_auth), recordSet.d_authZone.toLogString().c_str(), recordSet.d_from.toString().c_str(), recordSet.d_netmask.empty() ? "" : recordSet.d_netmask.toString().c_str(), !recordSet.d_rtag ? "" : recordSet.d_rtag.get().c_str(), recordSet.d_servedStale, recordSet.d_tooBig ? " (too big!)" : "", recordSet.d_tcp ? " tcp" : ""); } catch (...) { fprintf(filePtr.get(), "; error printing '%s'\n", recordSet.d_qname.empty() ? "EMPTY" : recordSet.d_qname.toString().c_str()); @@ -984,6 +986,7 @@ enum class PBCacheEntry : protozero::pbf_tag_type required_bool_auth = 14, required_bool_submitted = 15, required_bool_tooBig = 16, + optional_bool_tcp = 17, }; enum class PBAuthRecord : protozero::pbf_tag_type @@ -1036,6 +1039,7 @@ void MemRecursorCache::getRecordSet(T& message, U recordSet) message.add_bool(PBCacheEntry::required_bool_auth, recordSet->d_auth); message.add_bool(PBCacheEntry::required_bool_submitted, recordSet->d_submitted); message.add_bool(PBCacheEntry::required_bool_tooBig, recordSet->d_tooBig); + message.add_bool(PBCacheEntry::optional_bool_tcp, recordSet->d_tcp); } size_t MemRecursorCache::getRecordSets(size_t perShard, size_t maxSize, std::string& ret) @@ -1183,6 +1187,9 @@ bool MemRecursorCache::putRecordSet(T& message) case PBCacheEntry::required_bool_tooBig: cacheEntry.d_tooBig = message.get_bool(); break; + case PBCacheEntry::optional_bool_tcp: + cacheEntry.d_tcp = message.get_bool(); + break; default: break; } diff --git a/pdns/recursordist/recursor_cache.hh b/pdns/recursordist/recursor_cache.hh index db4e6d90de..cd3a3f0621 100644 --- a/pdns/recursordist/recursor_cache.hh +++ b/pdns/recursordist/recursor_cache.hh @@ -96,9 +96,9 @@ public: using SigRecs = std::shared_ptr; // Also const as it is shared const static SigRecs s_emptySigRecs; - [[nodiscard]] time_t get(time_t, const DNSName& qname, QType qtype, Flags flags, vector* res, const ComboAddress& who, const OptTag& routingTag = boost::none, SigRecs* signatures = nullptr, AuthRecs* authorityRecs = nullptr, bool* variable = nullptr, vState* state = nullptr, bool* wasAuth = nullptr, DNSName* fromAuthZone = nullptr, ComboAddress* fromAuthIP = nullptr); + [[nodiscard]] time_t get(time_t, const DNSName& qname, QType qtype, Flags flags, vector* res, const ComboAddress& who, const OptTag& routingTag = boost::none, SigRecs* signatures = nullptr, AuthRecs* authorityRecs = nullptr, bool* variable = nullptr, vState* state = nullptr, bool* wasAuth = nullptr, DNSName* fromAuthZone = nullptr, ComboAddress* fromAuthIP = nullptr, bool *tcp = nullptr); - void replace(time_t, const DNSName& qname, QType qtype, const vector& content, const SigRecsVec& signatures, const AuthRecsVec& authorityRecs, bool auth, const DNSName& authZone, boost::optional ednsmask = boost::none, const OptTag& routingTag = boost::none, vState state = vState::Indeterminate, boost::optional from = boost::none, bool refresh = false, time_t ttl_time = time(nullptr)); + void replace(time_t, const DNSName& qname, QType qtype, const vector& content, const SigRecsVec& signatures, const AuthRecsVec& authorityRecs, bool auth, const DNSName& authZone, boost::optional ednsmask = boost::none, const OptTag& routingTag = boost::none, vState state = vState::Indeterminate, boost::optional from = boost::none, bool overTCP = false, bool refresh = false, time_t ttl_time = time(nullptr)); void doPrune(time_t now, size_t keep); uint64_t doDump(int fileDesc, size_t maxCacheEntries); @@ -180,6 +180,7 @@ private: bool d_auth; // 1 mutable bool d_submitted{false}; // 1, whether this entry has been queued for refetch bool d_tooBig{false}; // 1 + bool d_tcp{false}; // 1 was entry received over TCP? }; bool replace(CacheEntry&& entry); @@ -378,7 +379,7 @@ private: static Entries getEntries(MapCombo::LockedContent& map, const DNSName& qname, QType qtype, const OptTag& rtag); static cache_t::const_iterator getEntryUsingECSIndex(MapCombo::LockedContent& map, time_t now, const DNSName& qname, QType qtype, bool requireAuth, const ComboAddress& who, bool serveStale); - static time_t handleHit(time_t now, MapCombo::LockedContent& content, OrderedTagIterator_t& entry, const DNSName& qname, uint32_t& origTTL, vector* res, SigRecs* signatures, AuthRecs* authorityRecs, bool* variable, boost::optional& state, bool* wasAuth, DNSName* authZone, ComboAddress* fromAuthIP); + static time_t handleHit(time_t now, MapCombo::LockedContent& content, OrderedTagIterator_t& entry, const DNSName& qname, uint32_t& origTTL, vector* res, SigRecs* signatures, AuthRecs* authorityRecs, bool* variable, boost::optional& state, bool* wasAuth, DNSName* authZone, ComboAddress* fromAuthIP, bool* tcp); static void updateStaleEntry(time_t now, OrderedTagIterator_t& entry); static void handleServeStaleBookkeeping(time_t, bool, OrderedTagIterator_t&); }; diff --git a/pdns/recursordist/syncres.cc b/pdns/recursordist/syncres.cc index 1e77cb0ca6..a16317bb85 100644 --- a/pdns/recursordist/syncres.cc +++ b/pdns/recursordist/syncres.cc @@ -4461,7 +4461,7 @@ void SyncRes::rememberParentSetIfNeeded(const DNSName& domain, const vector& ednsmask, vState& state, bool& needWildcardProof, bool& gatherWildcardProof, unsigned int& wildcardLabelsCount, bool rdQuery, const ComboAddress& remoteIP) // NOLINT(readability-function-cognitive-complexity) +RCode::rcodes_ SyncRes::updateCacheFromRecords(unsigned int depth, const string& prefix, LWResult& lwr, const DNSName& qname, const QType qtype, const DNSName& auth, bool wasForwarded, const boost::optional& ednsmask, vState& state, bool& needWildcardProof, bool& gatherWildcardProof, unsigned int& wildcardLabelsCount, bool rdQuery, const ComboAddress& remoteIP, bool overTCP) // NOLINT(readability-function-cognitive-complexity) { bool wasForwardRecurse = wasForwarded && rdQuery; tcache_t tcache; @@ -4821,7 +4821,7 @@ RCode::rcodes_ SyncRes::updateCacheFromRecords(unsigned int depth, const string& thisRRNeedsWildcardProof = true; } } - g_recCache->replace(d_now.tv_sec, tCacheEntry->first.name, tCacheEntry->first.type, tCacheEntry->second.records, tCacheEntry->second.signatures, thisRRNeedsWildcardProof ? authorityRecs : *MemRecursorCache::s_emptyAuthRecs, tCacheEntry->first.type == QType::DS ? true : isAA, auth, tCacheEntry->first.place == DNSResourceRecord::ANSWER ? ednsmask : boost::none, d_routingTag, recordState, remoteIP, d_refresh, tCacheEntry->second.d_ttl_time); + g_recCache->replace(d_now.tv_sec, tCacheEntry->first.name, tCacheEntry->first.type, tCacheEntry->second.records, tCacheEntry->second.signatures, thisRRNeedsWildcardProof ? authorityRecs : *MemRecursorCache::s_emptyAuthRecs, tCacheEntry->first.type == QType::DS ? true : isAA, auth, tCacheEntry->first.place == DNSResourceRecord::ANSWER ? ednsmask : boost::none, d_routingTag, recordState, remoteIP, overTCP, d_refresh, tCacheEntry->second.d_ttl_time); // Delete potential negcache entry. When a record recovers with serve-stale the negcache entry can cause the wrong entry to // be served, as negcache entries are checked before record cache entries @@ -4846,7 +4846,7 @@ RCode::rcodes_ SyncRes::updateCacheFromRecords(unsigned int depth, const string& content.push_back(std::move(nonExpandedRecord)); } - g_recCache->replace(d_now.tv_sec, realOwner, QType(tCacheEntry->first.type), content, tCacheEntry->second.signatures, /* no additional records in that case */ {}, tCacheEntry->first.type == QType::DS ? true : isAA, auth, boost::none, boost::none, recordState, remoteIP, d_refresh, tCacheEntry->second.d_ttl_time); + g_recCache->replace(d_now.tv_sec, realOwner, QType(tCacheEntry->first.type), content, tCacheEntry->second.signatures, /* no additional records in that case */ {}, tCacheEntry->first.type == QType::DS ? true : isAA, auth, boost::none, boost::none, recordState, remoteIP, overTCP, d_refresh, tCacheEntry->second.d_ttl_time); } } } @@ -5695,7 +5695,7 @@ void SyncRes::handleNewTarget(const std::string& prefix, const DNSName& qname, c updateValidationState(qname, state, cnameContext.state, prefix); } -bool SyncRes::processAnswer(unsigned int depth, const string& prefix, LWResult& lwr, const DNSName& qname, const QType qtype, DNSName& auth, bool wasForwarded, const boost::optional& ednsmask, bool sendRDQuery, NsSet& nameservers, std::vector& ret, const DNSFilterEngine& dfe, bool* gotNewServers, int* rcode, vState& state, const ComboAddress& remoteIP) +bool SyncRes::processAnswer(unsigned int depth, const string& prefix, LWResult& lwr, const DNSName& qname, const QType qtype, DNSName& auth, bool wasForwarded, const boost::optional& ednsmask, bool sendRDQuery, NsSet& nameservers, std::vector& ret, const DNSFilterEngine& dfe, bool* gotNewServers, int* rcode, vState& state, const ComboAddress& remoteIP, bool overTCP) { if (s_minimumTTL != 0) { for (auto& rec : lwr.d_records) { @@ -5716,7 +5716,7 @@ bool SyncRes::processAnswer(unsigned int depth, const string& prefix, LWResult& bool needWildcardProof = false; bool gatherWildcardProof = false; unsigned int wildcardLabelsCount = 0; - *rcode = updateCacheFromRecords(depth, prefix, lwr, qname, qtype, auth, wasForwarded, ednsmask, state, needWildcardProof, gatherWildcardProof, wildcardLabelsCount, sendRDQuery, remoteIP); + *rcode = updateCacheFromRecords(depth, prefix, lwr, qname, qtype, auth, wasForwarded, ednsmask, state, needWildcardProof, gatherWildcardProof, wildcardLabelsCount, sendRDQuery, remoteIP, overTCP); if (*rcode != RCode::NoError) { return true; } @@ -5920,7 +5920,7 @@ int SyncRes::doResolveAt(NsSet& nameservers, DNSName auth, bool flawedNSSet, con lwr.d_aabit = true; /* we have received an answer, are we done ? */ - bool done = processAnswer(depth, prefix, lwr, qname, qtype, auth, false, ednsmask, sendRDQuery, nameservers, ret, luaconfsLocal->dfe, &gotNewServers, &rcode, context.state, s_oobRemote); + bool done = processAnswer(depth, prefix, lwr, qname, qtype, auth, false, ednsmask, sendRDQuery, nameservers, ret, luaconfsLocal->dfe, &gotNewServers, &rcode, context.state, s_oobRemote, false); if (done) { return rcode; } @@ -5996,6 +5996,7 @@ int SyncRes::doResolveAt(NsSet& nameservers, DNSName auth, bool flawedNSSet, con if (!doDoT && s_max_busy_dot_probes > 0) { submitTryDotTask(*remoteIP, auth, tns->first, d_now.tv_sec); } + bool overTCP = false; if (!forceTCP) { gotAnswer = doResolveAtThisIP(prefix, qname, qtype, lwr, ednsmask, auth, sendRDQuery, wasForwarded, tns->first, *remoteIP, false, false, truncated, spoofed, context.extendedError); @@ -6007,6 +6008,7 @@ int SyncRes::doResolveAt(NsSet& nameservers, DNSName auth, bool flawedNSSet, con /* retry, over TCP this time */ gotAnswer = doResolveAtThisIP(prefix, qname, qtype, lwr, ednsmask, auth, sendRDQuery, wasForwarded, tns->first, *remoteIP, true, doDoT, truncated, spoofed, context.extendedError); + overTCP = true; } if (!gotAnswer) { @@ -6031,7 +6033,7 @@ int SyncRes::doResolveAt(NsSet& nameservers, DNSName auth, bool flawedNSSet, con s_nsSpeeds.lock()->find_or_enter(tns->first.empty() ? DNSName(remoteIP->toStringWithPort()) : tns->first, d_now).submit(*remoteIP, static_cast(lwr.d_usec), d_now); /* we have received an answer, are we done ? */ - bool done = processAnswer(depth, prefix, lwr, qname, qtype, auth, wasForwarded, ednsmask, sendRDQuery, nameservers, ret, luaconfsLocal->dfe, &gotNewServers, &rcode, context.state, *remoteIP); + bool done = processAnswer(depth, prefix, lwr, qname, qtype, auth, wasForwarded, ednsmask, sendRDQuery, nameservers, ret, luaconfsLocal->dfe, &gotNewServers, &rcode, context.state, *remoteIP, overTCP); if (done) { return rcode; } diff --git a/pdns/recursordist/syncres.hh b/pdns/recursordist/syncres.hh index dc740b966d..d9c57f6d82 100644 --- a/pdns/recursordist/syncres.hh +++ b/pdns/recursordist/syncres.hh @@ -647,7 +647,7 @@ private: void incTimeoutStats(const ComboAddress& remoteIP); void checkTotalTime(const DNSName& qname, QType qtype, boost::optional& extendedError) const; bool doResolveAtThisIP(const std::string& prefix, const DNSName& qname, QType qtype, LWResult& lwr, boost::optional& ednsmask, const DNSName& auth, bool sendRDQuery, bool wasForwarded, const DNSName& nsName, const ComboAddress& remoteIP, bool doTCP, bool doDoT, bool& truncated, bool& spoofed, boost::optional& extendedError, bool dontThrottle = false); - bool processAnswer(unsigned int depth, const string& prefix, LWResult& lwr, const DNSName& qname, QType qtype, DNSName& auth, bool wasForwarded, const boost::optional& ednsmask, bool sendRDQuery, NsSet& nameservers, std::vector& ret, const DNSFilterEngine& dfe, bool* gotNewServers, int* rcode, vState& state, const ComboAddress& remoteIP); + bool processAnswer(unsigned int depth, const string& prefix, LWResult& lwr, const DNSName& qname, QType qtype, DNSName& auth, bool wasForwarded, const boost::optional& ednsmask, bool sendRDQuery, NsSet& nameservers, std::vector& ret, const DNSFilterEngine& dfe, bool* gotNewServers, int* rcode, vState& state, const ComboAddress& remoteIP, bool overTCP); int doResolve(const DNSName& qname, QType qtype, vector& ret, unsigned int depth, set& beenthere, Context& context); int doResolveNoQNameMinimization(const DNSName& qname, QType qtype, vector& ret, unsigned int depth, set& beenthere, Context& context, bool* fromCache = nullptr, StopAtDelegation* stopAtDelegation = nullptr); @@ -681,7 +681,7 @@ private: This is unfortunately needed to deal with very crappy so-called DNS servers */ void fixupAnswer(const std::string& prefix, LWResult& lwr, const DNSName& qname, QType qtype, const DNSName& auth, bool wasForwarded, bool rdQuery); void rememberParentSetIfNeeded(const DNSName& domain, const vector& newRecords, unsigned int depth, const string& prefix); - RCode::rcodes_ updateCacheFromRecords(unsigned int depth, const string& prefix, LWResult& lwr, const DNSName& qname, QType qtype, const DNSName& auth, bool wasForwarded, const boost::optional&, vState& state, bool& needWildcardProof, bool& gatherWildcardProof, unsigned int& wildcardLabelsCount, bool sendRDQuery, const ComboAddress& remoteIP); + RCode::rcodes_ updateCacheFromRecords(unsigned int depth, const string& prefix, LWResult& lwr, const DNSName& qname, QType qtype, const DNSName& auth, bool wasForwarded, const boost::optional&, vState& state, bool& needWildcardProof, bool& gatherWildcardProof, unsigned int& wildcardLabelsCount, bool sendRDQuery, const ComboAddress& remoteIP, bool overTCP); bool processRecords(const std::string& prefix, const DNSName& qname, QType qtype, const DNSName& auth, LWResult& lwr, bool sendRDQuery, vector& ret, set& nsset, DNSName& newtarget, DNSName& newauth, bool& realreferral, bool& negindic, vState& state, bool needWildcardProof, bool gatherwildcardProof, unsigned int wildcardLabelsCount, int& rcode, bool& negIndicHasSignatures, unsigned int depth); bool doSpecialNamesResolve(const DNSName& qname, QType qtype, QClass qclass, vector& ret);