From dac4628cd0539e068a6b6f1df24caf1d31f4854b Mon Sep 17 00:00:00 2001 From: Sebastian Huber Date: Thu, 18 Jun 2020 13:13:40 +0200 Subject: mDNSResponder: Update to v878.270.2 The sources can be obtained via: https://opensource.apple.com/tarballs/mDNSResponder/mDNSResponder-878.270.2.tar.gz Update #4010. --- mDNSResponder/Makefile | 2 +- mDNSResponder/mDNSCore/DNSCommon.c | 15 ++- mDNSResponder/mDNSCore/DNSCommon.h | 2 + mDNSResponder/mDNSCore/dnssec.c | 2 +- mDNSResponder/mDNSCore/mDNS.c | 51 ++++---- mDNSResponder/mDNSCore/mDNSDebug.h | 1 + mDNSResponder/mDNSCore/mDNSEmbeddedAPI.h | 22 ++-- mDNSResponder/mDNSCore/uDNS.c | 136 +++++++++++---------- mDNSResponder/mDNSMacOSX/DNS64.c | 26 ++-- mDNSResponder/mDNSMacOSX/DNS64.h | 4 +- mDNSResponder/mDNSMacOSX/daemon.c | 6 +- mDNSResponder/mDNSMacOSX/mDNSMacOSX.c | 109 ++++++++++++----- mDNSResponder/mDNSMacOSX/mDNSMacOSX.h | 7 +- .../mDNSResponder.xcodeproj/project.pbxproj | 8 ++ mDNSResponder/mDNSPosix/mDNSPosix.c | 1 + mDNSResponder/mDNSShared/dns_sd.h | 2 +- mDNSResponder/mDNSShared/dnsextd.c | 2 +- mDNSResponder/mDNSShared/uds_daemon.c | 2 +- mDNSResponder/unittests/uds_daemon_ut.c | 2 +- 19 files changed, 245 insertions(+), 155 deletions(-) diff --git a/mDNSResponder/Makefile b/mDNSResponder/Makefile index b647c70a..68ba6b64 100644 --- a/mDNSResponder/Makefile +++ b/mDNSResponder/Makefile @@ -17,7 +17,7 @@ include $(MAKEFILEPATH)/pb_makefiles/platform.make -MVERS = "mDNSResponder-878.260.1" +MVERS = "mDNSResponder-878.270.2" VER = ifneq ($(strip $(GCC_VERSION)),) diff --git a/mDNSResponder/mDNSCore/DNSCommon.c b/mDNSResponder/mDNSCore/DNSCommon.c index f3150762..15a92200 100644 --- a/mDNSResponder/mDNSCore/DNSCommon.c +++ b/mDNSResponder/mDNSCore/DNSCommon.c @@ -1790,8 +1790,8 @@ mDNSexport mDNSBool SameNameRecordAnswersQuestion(const ResourceRecord *const rr // Resource record received via unicast, the resolver group ID should match ? if (!rr->InterfaceID) { - mDNSu16 idr = (rr->rDNSServer ? rr->rDNSServer->resGroupID : 0); - mDNSu16 idq = (q->qDNSServer ? q->qDNSServer->resGroupID : 0); + const mDNSu32 idr = rr->rDNSServer ? rr->rDNSServer->resGroupID : 0; + const mDNSu32 idq = q->qDNSServer ? q->qDNSServer->resGroupID : 0; if (idr != idq) return(mDNSfalse); if (!DNSSECRecordAnswersQuestion(rr, q, &checkType)) return mDNSfalse; } @@ -1924,8 +1924,8 @@ mDNSexport mDNSBool AnyTypeRecordAnswersQuestion(const ResourceRecord *const rr, // both the DNSServers are assumed to be NULL in that case if (!rr->InterfaceID) { - mDNSu16 idr = (rr->rDNSServer ? rr->rDNSServer->resGroupID : 0); - mDNSu16 idq = (q->qDNSServer ? q->qDNSServer->resGroupID : 0); + const mDNSu32 idr = rr->rDNSServer ? rr->rDNSServer->resGroupID : 0; + const mDNSu32 idq = q->qDNSServer ? q->qDNSServer->resGroupID : 0; if (idr != idq) return(mDNSfalse); } @@ -4551,3 +4551,10 @@ mDNSexport mDNSu32 mDNS_snprintf(char *sbuffer, mDNSu32 buflen, const char *fmt, return(length); } + +mDNSexport mDNSu32 mDNS_GetNextResolverGroupID(void) +{ + static mDNSu32 lastID = 0; + if (++lastID == 0) lastID = 1; // Valid resolver group IDs are non-zero. + return(lastID); +} diff --git a/mDNSResponder/mDNSCore/DNSCommon.h b/mDNSResponder/mDNSCore/DNSCommon.h index 48dfe102..4291577e 100644 --- a/mDNSResponder/mDNSCore/DNSCommon.h +++ b/mDNSResponder/mDNSCore/DNSCommon.h @@ -98,6 +98,8 @@ extern mDNSInterfaceID GetNextActiveInterfaceID(const NetworkInterfaceInfo *intf extern mDNSu32 mDNSRandom(mDNSu32 max); // Returns pseudo-random result from zero to max inclusive +extern mDNSu32 mDNS_GetNextResolverGroupID(void); + // *************************************************************************** #if COMPILER_LIKES_PRAGMA_MARK #pragma mark - diff --git a/mDNSResponder/mDNSCore/dnssec.c b/mDNSResponder/mDNSCore/dnssec.c index 9525655f..3010d6f2 100644 --- a/mDNSResponder/mDNSCore/dnssec.c +++ b/mDNSResponder/mDNSCore/dnssec.c @@ -3084,7 +3084,7 @@ mDNSexport void VerifySignature(mDNS *const m, DNSSECVerifier *dv, DNSQuestion * if (!dv) { first = mDNStrue; - if (!q->qDNSServer || q->qDNSServer->cellIntf) + if (!q->qDNSServer || q->qDNSServer->isCell) { LogDNSSEC("VerifySignature: Disabled"); return; diff --git a/mDNSResponder/mDNSCore/mDNS.c b/mDNSResponder/mDNSCore/mDNS.c index bf1bce2f..4e70ef83 100755 --- a/mDNSResponder/mDNSCore/mDNS.c +++ b/mDNSResponder/mDNSCore/mDNS.c @@ -4170,7 +4170,7 @@ mDNSexport void AnswerCurrentQuestionWithResourceRecord(mDNS *const m, CacheReco mDNSBool isForCellular; queryName = q->metrics.originalQName ? q->metrics.originalQName : &q->qname; - isForCellular = (q->qDNSServer && q->qDNSServer->cellIntf); + isForCellular = (q->qDNSServer && q->qDNSServer->isCell); if (!q->metrics.answered) { if (q->metrics.querySendCount > 0) @@ -4269,7 +4269,7 @@ mDNSexport void AnswerCurrentQuestionWithResourceRecord(mDNS *const m, CacheReco #if USE_DNS64 if (DNS64ShouldAnswerQuestion(q, &rr->resrec)) { - DNS64AnswerQuestion(m, q, &rr->resrec, AddRecord); + DNS64AnswerCurrentQuestion(m, &rr->resrec, AddRecord); } else #endif @@ -7410,8 +7410,8 @@ mDNSlocal CacheRecord *FindIdenticalRecordInCache(const mDNS *const m, const Res { if (!pktrr->InterfaceID) { - mDNSu16 id1 = (pktrr->rDNSServer ? pktrr->rDNSServer->resGroupID : 0); - mDNSu16 id2 = (rr->resrec.rDNSServer ? rr->resrec.rDNSServer->resGroupID : 0); + const mDNSu32 id1 = (pktrr->rDNSServer ? pktrr->rDNSServer->resGroupID : 0); + const mDNSu32 id2 = (rr->resrec.rDNSServer ? rr->resrec.rDNSServer->resGroupID : 0); match = (id1 == id2); } else match = (pktrr->InterfaceID == rr->resrec.InterfaceID); @@ -8737,8 +8737,8 @@ mDNSlocal CacheRecord* mDNSCoreReceiveCacheCheck(mDNS *const m, const DNSMessage // Resource record received via unicast, the resGroupID should match ? if (!InterfaceID) { - mDNSu16 id1 = (rr->resrec.rDNSServer ? rr->resrec.rDNSServer->resGroupID : 0); - mDNSu16 id2 = (m->rec.r.resrec.rDNSServer ? m->rec.r.resrec.rDNSServer->resGroupID : 0); + const mDNSu32 id1 = (rr->resrec.rDNSServer ? rr->resrec.rDNSServer->resGroupID : 0); + const mDNSu32 id2 = (m->rec.r.resrec.rDNSServer ? m->rec.r.resrec.rDNSServer->resGroupID : 0); match = (id1 == id2); } else @@ -11031,14 +11031,14 @@ mDNSexport mDNSBool DomainEnumQuery(const domainname *qname) // Note: InterfaceID is the InterfaceID of the question mDNSlocal mDNSBool DNSServerMatch(DNSServer *d, mDNSInterfaceID InterfaceID, mDNSs32 ServiceID) { - // 1) Unscoped questions (NULL InterfaceID) should consider *only* unscoped DNSServers ( DNSServer - // with "scoped" set to kScopeNone) + // 1) Unscoped questions (NULL InterfaceID) should consider *only* unscoped DNSServers ( DNSServer + // with scopeType set to kScopeNone) // // 2) Scoped questions (non-NULL InterfaceID) should consider *only* scoped DNSServers (DNSServer - // with "scoped" set to kScopeInterfaceId) and their InterfaceIDs should match. + // with scopeType set to kScopeInterfaceID) and their InterfaceIDs should match. // // 3) Scoped questions (non-zero ServiceID) should consider *only* scoped DNSServers (DNSServer - // with "scoped" set to kScopeServiceID) and their ServiceIDs should match. + // with scopeType set to kScopeServiceID) and their ServiceIDs should match. // // The first condition in the "if" statement checks to see if both the question and the DNSServer are // unscoped. The question is unscoped only if InterfaceID is zero and ServiceID is -1. @@ -11059,9 +11059,9 @@ mDNSlocal mDNSBool DNSServerMatch(DNSServer *d, mDNSInterfaceID InterfaceID, mDN // Note: mDNSInterface_Unicast is used only by .local unicast questions and are treated as unscoped. // If a question is scoped both to InterfaceID and ServiceID, the question will be scoped to InterfaceID. - if (((d->scoped == kScopeNone) && ((!InterfaceID && ServiceID == -1) || InterfaceID == mDNSInterface_Unicast)) || - ((d->scoped == kScopeInterfaceID) && d->interface == InterfaceID) || - ((d->scoped == kScopeServiceID) && d->serviceID == ServiceID)) + if (((d->scopeType == kScopeNone) && ((!InterfaceID && ServiceID == -1) || InterfaceID == mDNSInterface_Unicast)) || + ((d->scopeType == kScopeInterfaceID) && d->interface == InterfaceID) || + ((d->scopeType == kScopeServiceID) && d->serviceID == ServiceID)) { return mDNStrue; } @@ -11099,14 +11099,16 @@ mDNSexport mDNSu32 SetValidDNSServers(mDNS *m, DNSQuestion *question) // Note: DNS configuration change will help pick the new dns servers but currently it does not affect the timeout // Skip DNSServers that are InterfaceID Scoped but have no valid interfaceid set OR DNSServers that are ServiceID Scoped but have no valid serviceid set - if ((curr->scoped == kScopeInterfaceID && curr->interface == mDNSInterface_Any) || (curr->scoped == kScopeServiceID && curr->serviceID <= 0)) + if (((curr->scopeType == kScopeInterfaceID) && (curr->interface == mDNSInterface_Any)) || + ((curr->scopeType == kScopeServiceID) && (curr->serviceID <= 0))) { - LogInfo("SetValidDNSServers: ScopeType[%d] Skipping DNS server %#a (Domain %##s) Interface:[%p] Serviceid:[%d]", curr->scoped, &curr->addr, curr->domain.c, curr->interface, curr->serviceID); + LogInfo("SetValidDNSServers: ScopeType[%d] Skipping DNS server %#a (Domain %##s) Interface:[%p] Serviceid:[%d]", + (int)curr->scopeType, &curr->addr, curr->domain.c, curr->interface, curr->serviceID); continue; } currcount = CountLabels(&curr->domain); - if ((!curr->cellIntf || (!DEQuery && !(question->flags & kDNSServiceFlagsDenyCellular))) && + if ((!curr->isCell || (!DEQuery && !(question->flags & kDNSServiceFlagsDenyCellular))) && (!curr->isExpensive || !(question->flags & kDNSServiceFlagsDenyExpensive)) && DNSServerMatch(curr, question->InterfaceID, question->ServiceID)) { @@ -11130,7 +11132,7 @@ mDNSexport mDNSu32 SetValidDNSServers(mDNS *m, DNSQuestion *question) curr->interface); timeout += curr->timeout; if (DEQuery) - debugf("DomainEnumQuery: Question %##s, DNSServer %#a, cell %d", question->qname.c, &curr->addr, curr->cellIntf); + debugf("DomainEnumQuery: Question %##s, DNSServer %#a, cell %d", question->qname.c, &curr->addr, curr->isCell); bit_set_opaque128(question->validDNSServers, index); } } @@ -11999,7 +12001,7 @@ mDNSlocal void InitDNSSECProxyState(mDNS *const m, DNSQuestion *const question) // at ValidationRequired setting also. if (question->qDNSServer) { - if (question->qDNSServer->cellIntf) + if (question->qDNSServer->isCell) { debugf("InitDNSSECProxyState: Turning off validation for %##s (%s); going over cell", question->qname.c, DNSTypeName(question->qtype)); question->ValidationRequired = mDNSfalse; @@ -12234,7 +12236,7 @@ mDNSexport mStatus mDNS_StopQuery_internal(mDNS *const m, DNSQuestion *const que mDNSu32 durationMs; queryName = question->metrics.originalQName ? question->metrics.originalQName : &question->qname; - isForCell = (question->qDNSServer && question->qDNSServer->cellIntf); + isForCell = (question->qDNSServer && question->qDNSServer->isCell); durationMs = ((m->timenow - question->metrics.firstQueryTime) * 1000) / mDNSPlatformOneSecond; MetricsUpdateDNSQueryStats(queryName, question->qtype, mDNSNULL, question->metrics.querySendCount, question->metrics.expiredAnswerState, durationMs, isForCell); } @@ -13248,11 +13250,14 @@ mDNSexport void mDNS_DeregisterInterface(mDNS *const m, NetworkInterfaceInfo *se // so that mDNS_RegisterInterface() knows how swiftly it needs to reactivate them for (q = m->Questions; q; q=q->next) { - if (q->InterfaceID == set->InterfaceID) q->ThisQInterval = 0; - if (!q->InterfaceID || q->InterfaceID == set->InterfaceID) + if (mDNSOpaque16IsZero(q->TargetQID)) // Only deactivate multicast quesstions. (Unicast questions are stopped when/if the associated DNS server group goes away.) { - q->FlappingInterface2 = q->FlappingInterface1; - q->FlappingInterface1 = set->InterfaceID; // Keep history of the last two interfaces to go away + if (q->InterfaceID == set->InterfaceID) q->ThisQInterval = 0; + if (!q->InterfaceID || q->InterfaceID == set->InterfaceID) + { + q->FlappingInterface2 = q->FlappingInterface1; + q->FlappingInterface1 = set->InterfaceID; // Keep history of the last two interfaces to go away + } } } diff --git a/mDNSResponder/mDNSCore/mDNSDebug.h b/mDNSResponder/mDNSCore/mDNSDebug.h index d690fd2b..14b03c9e 100755 --- a/mDNSResponder/mDNSCore/mDNSDebug.h +++ b/mDNSResponder/mDNSCore/mDNSDebug.h @@ -166,6 +166,7 @@ extern void udns_validatelists(void *const v); extern void LogMemCorruption(const char *format, ...); #else #define mallocL(X,Y) malloc(Y) +#define callocL(X,Y) calloc(1, Y) #define freeL(X,Y) free(Y) #endif diff --git a/mDNSResponder/mDNSCore/mDNSEmbeddedAPI.h b/mDNSResponder/mDNSCore/mDNSEmbeddedAPI.h index e9f3bb8a..d714de49 100755 --- a/mDNSResponder/mDNSCore/mDNSEmbeddedAPI.h +++ b/mDNSResponder/mDNSCore/mDNSEmbeddedAPI.h @@ -1346,15 +1346,14 @@ enum { }; typedef mDNSu8 MortalityState; -// scoped values for DNSServer matching -enum +// ScopeType values for DNSServer matching +typedef enum { kScopeNone = 0, // DNS server used by unscoped questions kScopeInterfaceID = 1, // Scoped DNS server used only by scoped questions - kScopeServiceID = 2, // Service specific DNS server used only by questions + kScopeServiceID = 2 // Service specific DNS server used only by questions // have a matching serviceID - kScopesMaxCount = 3 // Max count for scopes enum -}; +} ScopeType; // Note: DNSSECAware is set if we are able to get a valid response to // a DNSSEC question. In some cases it is possible that the proxy @@ -1373,11 +1372,11 @@ typedef struct DNSServer mDNSu32 flags; // Set when we're planning to delete this from the list domainname domain; // name->server matching for "split dns" mDNSs32 penaltyTime; // amount of time this server is penalized - mDNSu32 scoped; // See the scoped enum above + ScopeType scopeType; // See the ScopeType enum above mDNSu32 timeout; // timeout value for questions - mDNSu16 resGroupID; // ID of the resolver group that contains this DNSServer + mDNSu32 resGroupID; // ID of the resolver group that contains this DNSServer mDNSu8 retransDO; // Total Retransmissions for queries sent with DO option - mDNSBool cellIntf; // Resolver from Cellular Interface? + mDNSBool isCell; // Resolver from Cellular Interface? mDNSBool req_A; // If set, send v4 query (DNSConfig allows A queries) mDNSBool req_AAAA; // If set, send v6 query (DNSConfig allows AAAA queries) mDNSBool req_DO; // If set, okay to send DNSSEC queries (EDNS DO bit is supported) @@ -2616,7 +2615,7 @@ extern const mDNSOpaque64 zeroOpaque64; extern const mDNSOpaque128 zeroOpaque128; extern mDNSBool StrictUnicastOrdering; -extern mDNSu8 NumUnicastDNSServers; +extern int NumUnicastDNSServers; #if APPLE_OSX_mDNSResponder extern mDNSu8 NumUnreachableDNSServers; #endif @@ -3072,8 +3071,8 @@ extern void mDNS_AddDynDNSHostName(mDNS *m, const domainname *fqdn, mDNSRecordCa extern void mDNS_RemoveDynDNSHostName(mDNS *m, const domainname *fqdn); extern void mDNS_SetPrimaryInterfaceInfo(mDNS *m, const mDNSAddr *v4addr, const mDNSAddr *v6addr, const mDNSAddr *router); extern DNSServer *mDNS_AddDNSServer(mDNS *const m, const domainname *d, const mDNSInterfaceID interface, mDNSs32 serviceID, const mDNSAddr *addr, - const mDNSIPPort port, mDNSu32 scoped, mDNSu32 timeout, mDNSBool cellIntf, mDNSBool isExpensive, mDNSBool isCLAT46, - mDNSu16 resGroupID, mDNSBool reqA, mDNSBool reqAAAA, mDNSBool reqDO); + const mDNSIPPort port, ScopeType scopeType, mDNSu32 timeout, mDNSBool cellIntf, mDNSBool isExpensive, mDNSBool isCLAT46, + mDNSu32 resGroupID, mDNSBool reqA, mDNSBool reqAAAA, mDNSBool reqDO); extern void PenalizeDNSServer(mDNS *const m, DNSQuestion *q, mDNSOpaque16 responseFlags); extern void mDNS_AddSearchDomain(const domainname *const domain, mDNSInterfaceID InterfaceID); @@ -3166,6 +3165,7 @@ extern void mDNSPlatformQsort (void *base, int nel, int width, int (*compa #define mDNSPlatformMemAllocate(X) mallocL(# X, X) #else extern void * mDNSPlatformMemAllocate (mDNSu32 len); +extern void * mDNSPlatformMemAllocateClear(mDNSu32 len); #endif extern void mDNSPlatformMemFree (void *mem); diff --git a/mDNSResponder/mDNSCore/uDNS.c b/mDNSResponder/mDNSCore/uDNS.c index 1f9b1543..6214c262 100755 --- a/mDNSResponder/mDNSCore/uDNS.c +++ b/mDNSResponder/mDNSCore/uDNS.c @@ -53,7 +53,7 @@ mDNSBool StrictUnicastOrdering = mDNSfalse; // question. Bit position is the index into the DNS server list. This is done so to try all // the servers exactly once before giving up. If we could allocate memory in the core, then // arbitrary limitation of 128 DNSServers can be removed. -mDNSu8 NumUnicastDNSServers = 0; +int NumUnicastDNSServers = 0; #define MAX_UNICAST_DNS_SERVERS 128 #if APPLE_OSX_mDNSResponder mDNSu8 NumUnreachableDNSServers = 0; @@ -118,11 +118,11 @@ mDNSlocal void SetRecordRetry(mDNS *const m, AuthRecord *rr, mDNSu32 random) #define TrueFalseStr(X) ((X) ? "true" : "false") mDNSexport DNSServer *mDNS_AddDNSServer(mDNS *const m, const domainname *d, const mDNSInterfaceID interface, const mDNSs32 serviceID, const mDNSAddr *addr, - const mDNSIPPort port, mDNSu32 scoped, mDNSu32 timeout, mDNSBool cellIntf, mDNSBool isExpensive, mDNSBool isCLAT46, - mDNSu16 resGroupID, mDNSBool reqA, mDNSBool reqAAAA, mDNSBool reqDO) + const mDNSIPPort port, ScopeType scopeType, mDNSu32 timeout, mDNSBool isCell, mDNSBool isExpensive, mDNSBool isCLAT46, + mDNSu32 resGroupID, mDNSBool reqA, mDNSBool reqAAAA, mDNSBool reqDO) { - DNSServer **p = &m->DNSServers; - DNSServer *tmp = mDNSNULL; + DNSServer **p; + DNSServer *server; if ((NumUnicastDNSServers + 1) > MAX_UNICAST_DNS_SERVERS) { @@ -133,29 +133,39 @@ mDNSexport DNSServer *mDNS_AddDNSServer(mDNS *const m, const domainname *d, cons if (!d) d = (const domainname *)""; - LogInfo("mDNS_AddDNSServer(%d): Adding %#a for %##s, InterfaceID %p, serviceID %u, scoped %d, resGroupID %d req_A %s, req_AAAA %s, cell %s, expensive %s, CLAT46 %s, req_DO %s", - NumUnicastDNSServers, addr, d->c, interface, serviceID, scoped, resGroupID, - TrueFalseStr(reqA), TrueFalseStr(reqAAAA), TrueFalseStr(cellIntf), TrueFalseStr(isExpensive), TrueFalseStr(isCLAT46), TrueFalseStr(reqDO)); + LogInfo("mDNS_AddDNSServer(%d): Adding %#a for %##s, InterfaceID %p, serviceID %u, scopeType %d, resGroupID %d req_A %s, req_AAAA %s, cell %s, expensive %s, CLAT46 %s, req_DO %s", + NumUnicastDNSServers, addr, d->c, interface, serviceID, (int)scopeType, resGroupID, + TrueFalseStr(reqA), TrueFalseStr(reqAAAA), TrueFalseStr(isCell), TrueFalseStr(isExpensive), TrueFalseStr(isCLAT46), TrueFalseStr(reqDO)); mDNS_CheckLock(m); - while (*p) // Check if we already have this {interface,address,port,domain} tuple registered + reqA/reqAAAA bits - { - if ((*p)->scoped == scoped && (*p)->interface == interface && (*p)->serviceID == serviceID && - mDNSSameAddress(&(*p)->addr, addr) && mDNSSameIPPort((*p)->port, port) && SameDomainName(&(*p)->domain, d) && - (*p)->req_A == reqA && (*p)->req_AAAA == reqAAAA) - { - if (!((*p)->flags & DNSServer_FlagDelete)) + for (p = &m->DNSServers; (server = *p) != mDNSNULL; p = &server->next) + { + if ((server->scopeType == scopeType) && + (server->interface == interface) && + (server->serviceID == serviceID) && + mDNSSameAddress(&server->addr, addr) && + mDNSSameIPPort(server->port, port) && + (server->timeout == timeout) && + (!!server->isCell == !!isCell) && + (!!server->isExpensive == !!isExpensive) && + (!!server->isCLAT46 == !!isCLAT46) && + (!!server->req_A == !!reqA) && + (!!server->req_AAAA == !!reqAAAA) && + (!!server->req_DO == !!reqDO) && + SameDomainName(&server->domain, d)) + { + if (!(server->flags & DNSServer_FlagDelete)) debugf("Note: DNS Server %#a:%d for domain %##s (%p) registered more than once", addr, mDNSVal16(port), d->c, interface); - tmp = *p; - *p = tmp->next; - tmp->next = mDNSNULL; - } - else - { - p=&(*p)->next; + *p = server->next; + server->next = mDNSNULL; + break; } } + while (*p) + { + p = &(*p)->next; + } // NumUnicastDNSServers is the count of active DNS servers i.e., ones that are not marked // with DNSServer_FlagDelete. We should increment it: @@ -167,61 +177,59 @@ mDNSexport DNSServer *mDNS_AddDNSServer(mDNS *const m, const domainname *d, cons // We have already accounted for it when it was added for the first time. This case happens when // we add DNS servers with the same address multiple times (mis-configuration). - if (!tmp || (tmp->flags & DNSServer_FlagDelete)) + if (!server || (server->flags & DNSServer_FlagDelete)) NumUnicastDNSServers++; - - if (tmp) + if (server) { -#if APPLE_OSX_mDNSResponder - if (tmp->flags & DNSServer_FlagDelete) + if (server->flags & DNSServer_FlagDelete) { - tmp->flags &= ~DNSServer_FlagUnreachable; - } +#if APPLE_OSX_mDNSResponder + server->flags &= ~DNSServer_FlagUnreachable; #endif - tmp->flags &= ~DNSServer_FlagDelete; - *p = tmp; // move to end of list, to ensure ordering from platform layer + server->flags &= ~DNSServer_FlagDelete; + } + *p = server; // move to end of list, to ensure ordering from platform layer } else { // allocate, add to list - *p = mDNSPlatformMemAllocate(sizeof(**p)); - if (!*p) + server = (DNSServer *)mDNSPlatformMemAllocateClear(sizeof(*server)); + if (!server) { LogMsg("Error: mDNS_AddDNSServer - malloc"); } else { - (*p)->scoped = scoped; - (*p)->interface = interface; - (*p)->serviceID = serviceID; - (*p)->addr = *addr; - (*p)->port = port; - (*p)->flags = DNSServer_FlagNew; - (*p)->timeout = timeout; - (*p)->cellIntf = cellIntf; - (*p)->isExpensive = isExpensive; - (*p)->isCLAT46 = isCLAT46; - (*p)->req_A = reqA; - (*p)->req_AAAA = reqAAAA; - (*p)->req_DO = reqDO; + server->scopeType = scopeType; + server->interface = interface; + server->serviceID = serviceID; + server->addr = *addr; + server->port = port; + server->flags = DNSServer_FlagNew; + server->timeout = timeout; + server->isCell = isCell; + server->isExpensive = isExpensive; + server->isCLAT46 = isCLAT46; + server->req_A = reqA; + server->req_AAAA = reqAAAA; + server->req_DO = reqDO; // We start off assuming that the DNS server is not DNSSEC aware and // when we receive the first response to a DNSSEC question, we set // it to true. - (*p)->DNSSECAware = mDNSfalse; - (*p)->retransDO = 0; - AssignDomainName(&(*p)->domain, d); - (*p)->next = mDNSNULL; + server->DNSSECAware = mDNSfalse; + server->retransDO = 0; + AssignDomainName(&server->domain, d); + *p = server; } } - if (*p) { - (*p)->penaltyTime = 0; - // We always update the ID (not just when we allocate a new instance) because we could - // be adding a new non-scoped resolver with a new ID and we want all the non-scoped - // resolvers belong to the same group. - (*p)->resGroupID = resGroupID; + if (server) { + server->penaltyTime = 0; + // We always update the ID (not just when we allocate a new instance) because we want + // all the resGroupIDs for a particular domain to match. + server->resGroupID = resGroupID; } - return(*p); + return(server); } // PenalizeDNSServer is called when the number of queries to the unicast @@ -1331,7 +1339,7 @@ mDNSlocal void tcpCallback(TCPSocket *sock, void *context, mDNSBool ConnectionEs // LLQ Polling mode or non-LLQ uDNS over TCP InitializeDNSMessage(&tcpInfo->request.h, q->TargetQID, (DNSSECQuestion(q) ? DNSSecQFlags : uQueryFlags)); end = putQuestion(&tcpInfo->request, tcpInfo->request.data, tcpInfo->request.data + AbsoluteMaxDNSMessageData, &q->qname, q->qtype, q->qclass); - if (DNSSECQuestion(q) && q->qDNSServer && !q->qDNSServer->cellIntf) + if (DNSSECQuestion(q) && q->qDNSServer && !q->qDNSServer->isCell) { if (q->ProxyQuestion) end = DNSProxySetAttributes(q, &tcpInfo->request.h, &tcpInfo->request, end, tcpInfo->request.data + AbsoluteMaxDNSMessageData); @@ -4725,7 +4733,7 @@ mDNSexport void uDNS_CheckCurrentQuestion(mDNS *const m) InitializeDNSMessage(&m->omsg.h, q->TargetQID, (DNSSECQuestion(q) ? DNSSecQFlags : uQueryFlags)); end = putQuestion(&m->omsg, m->omsg.data, m->omsg.data + AbsoluteMaxDNSMessageData, &q->qname, q->qtype, q->qclass); - if (DNSSECQuestion(q) && !q->qDNSServer->cellIntf) + if (DNSSECQuestion(q) && !q->qDNSServer->isCell) { if (q->ProxyQuestion) end = DNSProxySetAttributes(q, &m->omsg.h, &m->omsg, end, m->omsg.data + AbsoluteMaxDNSMessageData); @@ -4851,14 +4859,14 @@ mDNSexport void uDNS_CheckCurrentQuestion(mDNS *const m) q->ThisQInterval = LLQ_POLL_INTERVAL; LogInfo("uDNS_CheckCurrentQuestion: private non polling question for %##s (%s) will be retried in %d ms", q->qname.c, DNSTypeName(q->qtype), q->ThisQInterval); } - if (q->qDNSServer->cellIntf) + if (q->qDNSServer->isCell) { // We don't want to retransmit too soon. Schedule our first retransmisson at // MIN_UCAST_RETRANS_TIMEOUT seconds. if (q->ThisQInterval < MIN_UCAST_RETRANS_TIMEOUT) q->ThisQInterval = MIN_UCAST_RETRANS_TIMEOUT; } - debugf("uDNS_CheckCurrentQuestion: Increased ThisQInterval to %d for %##s (%s), cell %d", q->ThisQInterval, q->qname.c, DNSTypeName(q->qtype), q->qDNSServer->cellIntf); + debugf("uDNS_CheckCurrentQuestion: Increased ThisQInterval to %d for %##s (%s), cell %d", q->ThisQInterval, q->qname.c, DNSTypeName(q->qtype), q->qDNSServer->isCell); } q->LastQTime = m->timenow; } @@ -6205,7 +6213,7 @@ mDNSexport mStatus mDNS_StopNATOperation(mDNS *const m, NATTraversalInfo *traver } mDNSexport DNSServer *mDNS_AddDNSServer(mDNS *const m, const domainname *d, const mDNSInterfaceID interface, const mDNSs32 serviceID, const mDNSAddr *addr, - const mDNSIPPort port, mDNSu32 scoped, mDNSu32 timeout, mDNSBool cellIntf, mDNSBool isExpensive, mDNSu16 resGroupID, + const mDNSIPPort port, ScopeType scopeType, mDNSu32 timeout, mDNSBool isCell, mDNSBool isExpensive, mDNSu32 resGroupID, mDNSBool reqA, mDNSBool reqAAAA, mDNSBool reqDO) { (void) m; @@ -6214,9 +6222,9 @@ mDNSexport DNSServer *mDNS_AddDNSServer(mDNS *const m, const domainname *d, cons (void) serviceID; (void) addr; (void) port; - (void) scoped; + (void) scopeType; (void) timeout; - (void) cellIntf; + (void) isCell; (void) isExpensive; (void) resGroupID; (void) reqA; diff --git a/mDNSResponder/mDNSMacOSX/DNS64.c b/mDNSResponder/mDNSMacOSX/DNS64.c index 6fef38f8..e167cdde 100644 --- a/mDNSResponder/mDNSMacOSX/DNS64.c +++ b/mDNSResponder/mDNSMacOSX/DNS64.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017 Apple Inc. All rights reserved. + * Copyright (c) 2017-2019 Apple Inc. All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -54,12 +54,12 @@ check_compile_time(sizeof_field(DNS64, qnameStash) == kDNS64IPv4OnlyFQDNLength) // Local Prototypes //=========================================================================================================================== -mDNSlocal mStatus DNS64GetIPv6Addrs(mDNS *m, mDNSu16 inResGroupID, struct in6_addr **outAddrs, uint32_t *outAddrCount); -mDNSlocal mStatus DNS64GetPrefixes(mDNS *m, mDNSu16 inResGroupID, nw_nat64_prefix_t **outPrefixes, uint32_t *outPrefixCount); +mDNSlocal mStatus DNS64GetIPv6Addrs(mDNS *m, mDNSu32 inResGroupID, struct in6_addr **outAddrs, uint32_t *outAddrCount); +mDNSlocal mStatus DNS64GetPrefixes(mDNS *m, mDNSu32 inResGroupID, nw_nat64_prefix_t **outPrefixes, uint32_t *outPrefixCount); mDNSlocal mDNSBool DNS64GetReverseIPv6Addr(const domainname *inQName, struct in6_addr *outAddr); mDNSlocal mDNSu32 DNS64IPv4OnlyFQDNHash(void); mDNSlocal void DNS64RestartQuestion(mDNS *m, DNSQuestion *q, DNS64State newState); -mDNSlocal mDNSBool DNS64TestIPv6Synthesis(mDNS *m, mDNSu16 inResGroupID, const mDNSv4Addr *inV4Addr); +mDNSlocal mDNSBool DNS64TestIPv6Synthesis(mDNS *m, mDNSu32 inResGroupID, const mDNSv4Addr *inV4Addr); //=========================================================================================================================== // DNS64StateMachine @@ -174,10 +174,10 @@ mDNSexport mDNSBool DNS64StateMachine(mDNS *m, DNSQuestion *inQ, const ResourceR } //=========================================================================================================================== -// DNS64AnswerQuestion +// DNS64AnswerCurrentQuestion //=========================================================================================================================== -mDNSexport mStatus DNS64AnswerQuestion(mDNS *m, DNSQuestion *inQ, const ResourceRecord *inRR, QC_result inResult) +mDNSexport mStatus DNS64AnswerCurrentQuestion(mDNS *m, const ResourceRecord *inRR, QC_result inResult) { mStatus err; ResourceRecord newRR; @@ -187,10 +187,11 @@ mDNSexport mStatus DNS64AnswerQuestion(mDNS *m, DNSQuestion *inQ, const Resource uint32_t i; struct in_addr v4Addr; struct in6_addr synthV6; + DNSQuestion * const q = m->CurrentQuestion; - require_action_quiet(inQ->qDNSServer, exit, err = mStatus_BadParamErr); + require_action_quiet(q->qDNSServer, exit, err = mStatus_BadParamErr); - err = DNS64GetPrefixes(m, inQ->qDNSServer->resGroupID, &prefixes, &prefixCount); + err = DNS64GetPrefixes(m, q->qDNSServer->resGroupID, &prefixes, &prefixCount); require_noerr_quiet(err, exit); newRR = *inRR; @@ -205,7 +206,8 @@ mDNSexport mStatus DNS64AnswerQuestion(mDNS *m, DNSQuestion *inQ, const Resource if (nw_nat64_synthesize_v6(&prefixes[i], &v4Addr, &synthV6)) { memcpy(rdata.u.ipv6.b, synthV6.s6_addr, 16); - inQ->QuestionCallback(m, inQ, &newRR, inResult); + q->QuestionCallback(m, q, &newRR, inResult); + if (m->CurrentQuestion != q) break; } } err = mStatus_NoError; @@ -354,7 +356,7 @@ mDNSexport void DNS64RestartQuestions(mDNS *m) ((RR)->RecordType != kDNSRecordTypePacketNegative) && \ !(RR)->InterfaceID) -mDNSlocal mStatus DNS64GetIPv6Addrs(mDNS *m, const mDNSu16 inResGroupID, struct in6_addr **outAddrs, uint32_t *outAddrCount) +mDNSlocal mStatus DNS64GetIPv6Addrs(mDNS *m, const mDNSu32 inResGroupID, struct in6_addr **outAddrs, uint32_t *outAddrCount) { mStatus err; const CacheGroup * cg; @@ -403,7 +405,7 @@ exit: // DNS64GetPrefixes //=========================================================================================================================== -mDNSlocal mStatus DNS64GetPrefixes(mDNS *m, mDNSu16 inResGroupID, nw_nat64_prefix_t **outPrefixes, uint32_t *outPrefixCount) +mDNSlocal mStatus DNS64GetPrefixes(mDNS *m, mDNSu32 inResGroupID, nw_nat64_prefix_t **outPrefixes, uint32_t *outPrefixCount) { mStatus err; struct in6_addr * v6Addrs; @@ -535,7 +537,7 @@ mDNSlocal void DNS64RestartQuestion(mDNS *const m, DNSQuestion *inQ, DNS64State // DNS64TestIPv6Synthesis //=========================================================================================================================== -mDNSlocal mDNSBool DNS64TestIPv6Synthesis(mDNS *m, mDNSu16 inResGroupID, const mDNSv4Addr *inV4Addr) +mDNSlocal mDNSBool DNS64TestIPv6Synthesis(mDNS *m, mDNSu32 inResGroupID, const mDNSv4Addr *inV4Addr) { mStatus err; nw_nat64_prefix_t * prefixes = NULL; diff --git a/mDNSResponder/mDNSMacOSX/DNS64.h b/mDNSResponder/mDNSMacOSX/DNS64.h index 80eb7feb..dc07dcc1 100644 --- a/mDNSResponder/mDNSMacOSX/DNS64.h +++ b/mDNSResponder/mDNSMacOSX/DNS64.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017 Apple Inc. All rights reserved. + * Copyright (c) 2017-2019 Apple Inc. All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -27,7 +27,7 @@ extern "C" { #endif mDNSexport mDNSBool DNS64StateMachine(mDNS *m, DNSQuestion *inQ, const ResourceRecord *inRR, QC_result inResult); -mDNSexport mStatus DNS64AnswerQuestion(mDNS *m, DNSQuestion *inQ, const ResourceRecord *inRR, QC_result inResult); +mDNSexport mStatus DNS64AnswerCurrentQuestion(mDNS *m, const ResourceRecord *inRR, QC_result inResult); mDNSexport void DNS64HandleNewQuestion(mDNS *m, DNSQuestion *inQ); mDNSexport void DNS64ResetState(DNSQuestion *inQ); mDNSexport void DNS64RestartQuestions(mDNS *m); diff --git a/mDNSResponder/mDNSMacOSX/daemon.c b/mDNSResponder/mDNSMacOSX/daemon.c index 695e4114..233ffb99 100644 --- a/mDNSResponder/mDNSMacOSX/daemon.c +++ b/mDNSResponder/mDNSMacOSX/daemon.c @@ -517,13 +517,13 @@ mDNSexport void INFOCallback(void) for (s = mDNSStorage.DNSServers; s; s = s->next) { NetworkInterfaceInfoOSX *ifx = IfindexToInterfaceInfoOSX(s->interface); - LogMsgNoIdent("DNS Server %##s %s%s%#a:%d %d %s %d %d %s %s %s %s %s %s", + LogMsgNoIdent("DNS Server %##s %s%s%#a:%d %d %s %d %u %s %s %s %s %s %s", s->domain.c, ifx ? ifx->ifinfo.ifname : "", ifx ? " " : "", &s->addr, mDNSVal16(s->port), - s->penaltyTime ? s->penaltyTime - mDNS_TimeNow(&mDNSStorage) : 0, DNSScopeToString(s->scoped), + s->penaltyTime ? (s->penaltyTime - mDNS_TimeNow(&mDNSStorage)) : 0, DNSScopeToString(s->scopeType), s->timeout, s->resGroupID, s->req_A ? "v4" : "!v4", s->req_AAAA ? "v6" : "!v6", - s->cellIntf ? "cell" : "!cell", + s->isCell ? "cell" : "!cell", s->isExpensive ? "exp" : "!exp", s->isCLAT46 ? "clat46" : "!clat46", s->DNSSECAware ? "DNSSECAware" : "!DNSSECAware"); diff --git a/mDNSResponder/mDNSMacOSX/mDNSMacOSX.c b/mDNSResponder/mDNSMacOSX/mDNSMacOSX.c index b7e53032..126edd03 100644 --- a/mDNSResponder/mDNSMacOSX/mDNSMacOSX.c +++ b/mDNSResponder/mDNSMacOSX/mDNSMacOSX.c @@ -93,7 +93,6 @@ // Include definition of opaque_presence_indication for KEV_DL_NODE_PRESENCE handling logic. #include -#include // for nwi_state #if MDNSRESPONDER_BTMM_SUPPORT #include @@ -3626,7 +3625,6 @@ mDNSlocal NetworkInterfaceInfoOSX *AddInterfaceToList(struct ifaddrs *ifa, mDNSs i->isExpensive = (eflags & IFEF_EXPENSIVE) ? mDNStrue: mDNSfalse; i->isAWDL = (eflags & IFEF_AWDL) ? mDNStrue: mDNSfalse; - i->isCLAT46 = (eflags & IFEF_CLAT46) ? mDNStrue: mDNSfalse; if (eflags & IFEF_AWDL) { // Set SupportsUnicastMDNSResponse false for the AWDL interface since unicast reserves @@ -5410,7 +5408,7 @@ mDNSlocal void ConfigSearchDomains(dns_resolver_t *resolver, mDNSInterfaceID int { if (MakeDomainNameFromDNSNameString(&d, resolver->search[j]) != NULL) { - static char interface_buf[32]; + char interface_buf[32]; mDNS_snprintf(interface_buf, sizeof(interface_buf), "for interface %s", InterfaceNameForID(&mDNSStorage, interfaceId)); LogInfo("ConfigSearchDomains: (%s) configuring search domain %s %s (generation= %llu)", scopeString, resolver->search[j], (interfaceId == mDNSInterface_Any) ? "" : interface_buf, generation); @@ -5476,7 +5474,24 @@ mDNSlocal void ConfigNonUnicastResolver(dns_resolver_t *r) } } -mDNSlocal void ConfigDNSServers(dns_resolver_t *r, mDNSInterfaceID interface, mDNSu32 scope, mDNSu16 resGroupID) +#if !defined(NWI_IFSTATE_FLAGS_HAS_CLAT46) +#define NWI_IFSTATE_FLAGS_HAS_CLAT46 0x0040 +#endif + +mDNSlocal mDNSBool NWIInterfaceHasCLAT46(nwi_state_t state, uint32_t ifIndex) +{ + char ifNameBuf[IFNAMSIZ + 1]; + const char *ifNamePtr = if_indextoname(ifIndex, ifNameBuf); + if (!ifNamePtr) return(mDNSfalse); + + const nwi_ifstate_t ifState = nwi_state_get_ifstate(state, ifNamePtr); + if (!ifState) return(mDNSfalse); + + const nwi_ifstate_flags flags = nwi_ifstate_get_flags(ifState); + return((flags & NWI_IFSTATE_FLAGS_HAS_CLAT46) ? mDNStrue : mDNSfalse); +} + +mDNSlocal void ConfigDNSServers(dns_resolver_t *r, mDNSInterfaceID interface, mDNSu32 scope, mDNSu32 resGroupID) { int n; domainname d; @@ -5509,7 +5524,15 @@ mDNSlocal void ConfigDNSServers(dns_resolver_t *r, mDNSInterfaceID interface, mD reqAAAA = (r->flags & DNS_RESOLVER_FLAGS_REQUEST_AAAA_RECORDS ? mDNStrue : mDNSfalse); info = IfindexToInterfaceInfoOSX(interface); isExpensive = (info && info->isExpensive) ? mDNStrue : mDNSfalse; - isCLAT46 = (info && info->isCLAT46) ? mDNStrue : mDNSfalse; + if (mDNSStorage.p->NWIState && interface) + { + const uint32_t ifIndex = (uint32_t)((uintptr_t)interface); + isCLAT46 = NWIInterfaceHasCLAT46(mDNSStorage.p->NWIState, ifIndex); + } + else + { + isCLAT46 = mDNSfalse; + } for (n = 0; n < r->n_nameserver; n++) { @@ -5553,7 +5576,7 @@ mDNSlocal void ConfigDNSServers(dns_resolver_t *r, mDNSInterfaceID interface, mD // "service_specific_resolver" has entries that should be used for Service scoped question i.e., questions that specify // a service identifier (q->ServiceID) // -mDNSlocal void ConfigResolvers(dns_config_t *config, mDNSu32 scope, mDNSBool setsearch, mDNSBool setservers, MD5_CTX *sdc, mDNSu16 resGroupID) +mDNSlocal void ConfigResolvers(dns_config_t *config, mDNSu32 scope, mDNSBool setsearch, mDNSBool setservers, MD5_CTX *sdc) { int i; dns_resolver_t **resolver; @@ -5609,12 +5632,7 @@ mDNSlocal void ConfigResolvers(dns_config_t *config, mDNSu32 scope, mDNSBool set } else { - // Each scoped resolver gets its own ID (i.e., they are in their own group) so that responses from the - // scoped resolver are not used by other non-scoped or scoped resolvers. - if (scope != kScopeNone) - resGroupID++; - - ConfigDNSServers(r, interface, scope, resGroupID); + ConfigDNSServers(r, interface, scope, mDNS_GetNextResolverGroupID()); } } } @@ -5910,7 +5928,6 @@ mDNSexport mDNSBool mDNSPlatformSetDNSConfig(mDNSBool setservers, mDNSBool setse { mDNS *const m = &mDNSStorage; MD5_CTX sdc; // search domain context - static mDNSu16 resolverGroupID = 0; // Need to set these here because we need to do this even if SCDynamicStoreCreate() or SCDynamicStoreCopyValue() below don't succeed if (fqdn ) fqdn->c[0] = 0; @@ -6011,20 +6028,9 @@ mDNSexport mDNSBool mDNSPlatformSetDNSConfig(mDNSBool setservers, mDNSBool setse SetupActiveDirectoryDomain(config); #endif - // With scoped DNS, we don't want to answer a non-scoped question using a scoped cache entry - // and vice-versa. As we compare resolverGroupID for matching cache entry with question, we need - // to make sure that they don't match. We ensure this by always bumping up resolverGroupID between - // the two calls to ConfigResolvers DNSServers for scoped and non-scoped can never have the - // same resolverGroupID. - // - // All non-scoped resolvers use the same resolverGroupID i.e, we treat them all equally. - ConfigResolvers(config, kScopeNone, setsearch, setservers, &sdc, ++resolverGroupID); - resolverGroupID += config->n_resolver; - - ConfigResolvers(config, kScopeInterfaceID, setsearch, setservers, &sdc, resolverGroupID); - resolverGroupID += config->n_scoped_resolver; - - ConfigResolvers(config, kScopeServiceID, setsearch, setservers, &sdc, resolverGroupID); + ConfigResolvers(config, kScopeNone, setsearch, setservers, &sdc); + ConfigResolvers(config, kScopeInterfaceID, setsearch, setservers, &sdc); + ConfigResolvers(config, kScopeServiceID, setsearch, setservers, &sdc); // Acking provides a hint to other processes that the current DNS configuration has completed // its update. When configd receives the ack, it publishes a notification. @@ -9532,6 +9538,36 @@ mDNSlocal void RegisterLocalOnlyAAAARecord(const domainname *const name, const m } #endif +mDNSlocal void NWIEventHandler(void) +{ + mDNS * const m = &mDNSStorage; + nwi_state_t newState = nwi_state_copy(); + + KQueueLock(); + const nwi_state_t oldState = m->p->NWIState; + m->p->NWIState = newState; + if (m->p->NWIState) + { + uint32_t lastIfIndex = 0; + mDNSBool lastCLAT46 = mDNSfalse; + for (DNSServer *server = m->DNSServers; server; server = server->next) + { + const uint32_t ifIndex = (uint32_t)((uintptr_t)server->interface); + if (ifIndex == 0) continue; + if (ifIndex == lastIfIndex) + { + server->isCLAT46 = lastCLAT46; + continue; + } + server->isCLAT46 = NWIInterfaceHasCLAT46(m->p->NWIState, ifIndex); + lastIfIndex = ifIndex; + lastCLAT46 = server->isCLAT46; + } + } + KQueueUnlock("NWIEventHandler"); + if (oldState) nwi_state_release(oldState); +} + mDNSlocal mStatus mDNSPlatformInit_setup(mDNS *const m) { mStatus err; @@ -9672,6 +9708,18 @@ mDNSlocal mStatus mDNSPlatformInit_setup(mDNS *const m) err = WatchForSysEvents(m); if (err) { LogMsg("mDNSPlatformInit_setup: WatchForSysEvents failed %d", err); return(err); } + m->p->NWIState = nwi_state_copy(); + uint32_t status = notify_register_dispatch(nwi_state_get_notify_key(), &m->p->NWINotifyToken, dispatch_get_main_queue(), + ^(__unused int token) { NWIEventHandler(); }); + if (status == NOTIFY_STATUS_OK) + { + m->p->NWINotifyRegistered = mDNStrue; + } + else + { + LogMsg("mDNSPlatformInit_setup: notify_register_dispatch failed %u", status); + } + mDNSs32 utc = mDNSPlatformUTC(); m->SystemWakeOnLANEnabled = SystemWakeForNetworkAccess(); myGetIfAddrs(1); @@ -9868,7 +9916,11 @@ mDNSexport void mDNSPlatformClose(mDNS *const m) } if (m->p->SysEventNotifier >= 0) { close(m->p->SysEventNotifier); m->p->SysEventNotifier = -1; } - + if (m->p->NWINotifyRegistered) + { + notify_cancel(m->p->NWINotifyToken); + m->p->NWINotifyRegistered = mDNSfalse; + } terminateD2DPlugins(); mDNSs32 utc = mDNSPlatformUTC(); @@ -9981,6 +10033,7 @@ mDNSexport void mDNSPlatformQsort ( void *base, int nel, int width, in } #if !(APPLE_OSX_mDNSResponder && MACOSX_MDNS_MALLOC_DEBUGGING) mDNSexport void * mDNSPlatformMemAllocate(mDNSu32 len) { return(mallocL("mDNSPlatformMemAllocate", len)); } +mDNSexport void * mDNSPlatformMemAllocateClear(mDNSu32 len) { return(callocL("mDNSPlatformMemAllocateClear", len)); } #endif mDNSexport void mDNSPlatformMemFree (void *mem) { freeL("mDNSPlatformMemFree", mem); } diff --git a/mDNSResponder/mDNSMacOSX/mDNSMacOSX.h b/mDNSResponder/mDNSMacOSX/mDNSMacOSX.h index 82de4331..23368183 100644 --- a/mDNSResponder/mDNSMacOSX/mDNSMacOSX.h +++ b/mDNSResponder/mDNSMacOSX/mDNSMacOSX.h @@ -28,7 +28,8 @@ extern "C" { #include #include #include -#include "mDNSEmbeddedAPI.h" // for domain name structure +#include // for nwi_state +#include "mDNSEmbeddedAPI.h" // for domain name structure #include #include @@ -154,7 +155,6 @@ struct NetworkInterfaceInfoOSX_struct u_int BPF_len; mDNSBool isExpensive; // True if this interface has the IFEF_EXPENSIVE flag set. mDNSBool isAWDL; // True if this interface has the IFEF_AWDL flag set. - mDNSBool isCLAT46; // True if this interface has the IFEF_CLAT46 flag set. #ifdef MDNSRESPONDER_USES_LIB_DISPATCH_AS_PRIMARY_EVENT_LOOP_MECHANISM dispatch_source_t BPF_source; #else @@ -185,6 +185,9 @@ struct mDNS_PlatformSupport_struct SCDynamicStoreRef Store; CFRunLoopSourceRef StoreRLS; CFRunLoopSourceRef PMRLS; + nwi_state_t NWIState; + int NWINotifyToken; + mDNSBool NWINotifyRegistered; int SysEventNotifier; KQueueEntry SysEventKQueue; IONotificationPortRef PowerPortRef; diff --git a/mDNSResponder/mDNSMacOSX/mDNSResponder.xcodeproj/project.pbxproj b/mDNSResponder/mDNSMacOSX/mDNSResponder.xcodeproj/project.pbxproj index 8067d931..5df1073d 100644 --- a/mDNSResponder/mDNSMacOSX/mDNSResponder.xcodeproj/project.pbxproj +++ b/mDNSResponder/mDNSMacOSX/mDNSResponder.xcodeproj/project.pbxproj @@ -347,6 +347,8 @@ BDB04224203FF18000419961 /* dns_sd_private.h in Headers */ = {isa = PBXBuildFile; fileRef = BDA9A7871B3A923600523835 /* dns_sd_private.h */; settings = {ATTRIBUTES = (Private, ); }; }; BDB61845206ADB9D00AFF600 /* com.apple.mDNSResponder.plist in Copy Base Logging Profile */ = {isa = PBXBuildFile; fileRef = BDB61843206ADB7700AFF600 /* com.apple.mDNSResponder.plist */; }; BDBF9B941ED74B9C001498A8 /* DNS64State.h in Headers */ = {isa = PBXBuildFile; fileRef = BDBF9B931ED74B8C001498A8 /* DNS64State.h */; }; + BDE5BCCA226D7181009C723C /* DNSCommon.h in Headers */ = {isa = PBXBuildFile; fileRef = BDE5BCC9226D7181009C723C /* DNSCommon.h */; }; + BDE5BCCC226D7198009C723C /* uDNS.h in Headers */ = {isa = PBXBuildFile; fileRef = BDE5BCCB226D7197009C723C /* uDNS.h */; }; BDF8BB902208E2A800419B62 /* mDNSResponder.plist in Copy BATS test plist */ = {isa = PBXBuildFile; fileRef = BDF8BB8F2208E26E00419B62 /* mDNSResponder.plist */; }; D284BE540ADD80740027CCDF /* dnssd_ipc.h in Headers */ = {isa = PBXBuildFile; fileRef = F5E11B5B04A28126019798ED /* dnssd_ipc.h */; }; D284BE580ADD80740027CCDF /* mDNS.c in Sources */ = {isa = PBXBuildFile; fileRef = 6575FBE9022EAF5A00000109 /* mDNS.c */; }; @@ -1018,6 +1020,8 @@ BDB61846206ADDDF00AFF600 /* com.apple.mDNSResponder.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = com.apple.mDNSResponder.plist; sourceTree = ""; }; BDBF9B931ED74B8C001498A8 /* DNS64State.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DNS64State.h; sourceTree = ""; }; BDE238C11DF69D8300B9F696 /* dns_sd_internal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = dns_sd_internal.h; path = ../mDNSShared/dns_sd_internal.h; sourceTree = ""; }; + BDE5BCC9226D7181009C723C /* DNSCommon.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = DNSCommon.h; path = ../mDNSCore/DNSCommon.h; sourceTree = ""; }; + BDE5BCCB226D7197009C723C /* uDNS.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = uDNS.h; path = ../mDNSCore/uDNS.h; sourceTree = ""; }; BDF8BB8F2208E26E00419B62 /* mDNSResponder.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = mDNSResponder.plist; sourceTree = ""; }; D284BE730ADD80740027CCDF /* mDNSResponder */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = mDNSResponder; sourceTree = BUILT_PRODUCTS_DIR; }; D284BEB00ADD80920027CCDF /* dns-sd */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = "dns-sd"; sourceTree = BUILT_PRODUCTS_DIR; }; @@ -1347,6 +1351,7 @@ 84F4C08F188F04CF00D1E1DE /* dns_services.h */, 848DA5D516547F7200D2E8B4 /* dns_xpc.h */, 7F18A9F60587CEF6001880B3 /* DNSCommon.c */, + BDE5BCC9226D7181009C723C /* DNSCommon.h */, 7F461DB5062DBF2900672BF3 /* DNSDigest.c */, FF13FFEA0A5DA44A00897C81 /* dnsextd_lexer.l */, FF13FFEC0A5DA45500897C81 /* dnsextd_parser.y */, @@ -1398,6 +1403,7 @@ FFCB6D73075D539900B8AF62 /* PlatformCommon.c */, BD03E88C1AD31278005E8A81 /* SymptomReporter.c */, 7F18A9F70587CEF6001880B3 /* uDNS.c */, + BDE5BCCB226D7197009C723C /* uDNS.h */, 216D9ACD1720C9F5008066E1 /* uDNSPathEvalulation.c */, F525E72804AA167501F1CF4D /* uds_daemon.c */, 4A2E69DD0F5475A3004A87B0 /* uds_daemon.h */, @@ -1835,7 +1841,9 @@ 2ECC11A60C4FEC3800CB1885 /* helpermsg-types.h in Headers */, 21A57F4E145B2AE100939099 /* CryptoAlg.h in Headers */, 21A57F55145B2B1400939099 /* CryptoSupport.h in Headers */, + BDE5BCCA226D7181009C723C /* DNSCommon.h in Headers */, 2124FA2C1471E98C0021D7BB /* nsec.h in Headers */, + BDE5BCCC226D7198009C723C /* uDNS.h in Headers */, 2124FA301471E9B50021D7BB /* dnssec.h in Headers */, BD691B2B1ED2F4AB00E6F317 /* DNS64.h in Headers */, 218E8E53156D8C0300720DA0 /* dnsproxy.h in Headers */, diff --git a/mDNSResponder/mDNSPosix/mDNSPosix.c b/mDNSResponder/mDNSPosix/mDNSPosix.c index 5ed4a045..308252fb 100755 --- a/mDNSResponder/mDNSPosix/mDNSPosix.c +++ b/mDNSResponder/mDNSPosix/mDNSPosix.c @@ -1504,6 +1504,7 @@ mDNSexport void mDNSPlatformMemZero(void *dst, mDNSu32 len) } mDNSexport void * mDNSPlatformMemAllocate(mDNSu32 len) { return(malloc(len)); } +mDNSexport void * mDNSPlatformMemAllocateClear(mDNSu32 len) { return(calloc(1, len)); } mDNSexport void mDNSPlatformMemFree (void *mem) { free(mem); } #if _PLATFORM_HAS_STRONG_PRNG_ diff --git a/mDNSResponder/mDNSShared/dns_sd.h b/mDNSResponder/mDNSShared/dns_sd.h index 5989f17c..675eec51 100644 --- a/mDNSResponder/mDNSShared/dns_sd.h +++ b/mDNSResponder/mDNSShared/dns_sd.h @@ -66,7 +66,7 @@ */ #ifndef _DNS_SD_H -#define _DNS_SD_H 8806001 +#define _DNS_SD_H 8807002 #ifdef __cplusplus extern "C" { diff --git a/mDNSResponder/mDNSShared/dnsextd.c b/mDNSResponder/mDNSShared/dnsextd.c index 96ee520c..cbdab57c 100644 --- a/mDNSResponder/mDNSShared/dnsextd.c +++ b/mDNSResponder/mDNSShared/dnsextd.c @@ -3100,7 +3100,7 @@ void mDNSCoreReceive(mDNS *const m, DNSMessage *const msg, const mDNSu8 *const e const mDNSAddr *const dstaddr, const mDNSIPPort dstport, const mDNSInterfaceID iid) { ( void ) m; ( void ) msg; ( void ) end; ( void ) srcaddr; ( void ) srcport; ( void ) dstaddr; ( void ) dstport; ( void ) iid; } DNSServer *mDNS_AddDNSServer(mDNS *const m, const domainname *d, const mDNSInterfaceID interface, const int serviceID, const mDNSAddr *addr, const mDNSIPPort port, - mDNSu32 scoped, mDNSu32 timeout, mDNSBool cellIntf, mDNSBool isExpensive, mDNSBool isCLAT46, mDNSu16 resGroupID, mDNSBool reqA, mDNSBool reqAAAA, mDNSBool reqDO) + mDNSu32 scoped, mDNSu32 timeout, mDNSBool cellIntf, mDNSBool isExpensive, mDNSBool isCLAT46, mDNSu32 resGroupID, mDNSBool reqA, mDNSBool reqAAAA, mDNSBool reqDO) { ( void ) m; ( void ) d; ( void ) interface; ( void ) serviceID; ( void ) addr; ( void ) port; ( void ) scoped; ( void ) timeout; (void) cellIntf; (void) isExpensive; (void) isCLAT46; (void) resGroupID; (void) reqA; (void) reqAAAA; (void) reqDO; return(NULL); } void mDNS_AddSearchDomain(const domainname *const domain, mDNSInterfaceID InterfaceID) { (void)domain; (void) InterfaceID;} diff --git a/mDNSResponder/mDNSShared/uds_daemon.c b/mDNSResponder/mDNSShared/uds_daemon.c index d1fbc7f2..4d110e7a 100644 --- a/mDNSResponder/mDNSShared/uds_daemon.c +++ b/mDNSResponder/mDNSShared/uds_daemon.c @@ -5765,7 +5765,7 @@ mDNSexport void udsserver_info() const char *ifname; mDNSInterfaceID InterfaceID = cr->resrec.InterfaceID; mDNSu32 *const countPtr = InterfaceID ? &mcastRecordCount : &ucastRecordCount; - if (!InterfaceID && cr->resrec.rDNSServer && cr->resrec.rDNSServer->scoped) + if (!InterfaceID && cr->resrec.rDNSServer && (cr->resrec.rDNSServer->scopeType != kScopeNone)) InterfaceID = cr->resrec.rDNSServer->interface; ifname = InterfaceNameForID(m, InterfaceID); if (cr->CRActiveQuestion) CacheActive++; diff --git a/mDNSResponder/unittests/uds_daemon_ut.c b/mDNSResponder/unittests/uds_daemon_ut.c index 8a07e9ba..971a1419 100644 --- a/mDNSResponder/unittests/uds_daemon_ut.c +++ b/mDNSResponder/unittests/uds_daemon_ut.c @@ -23,7 +23,7 @@ mDNSexport void LogCacheRecords_ut(mDNSs32 now, mDNSu32* retCacheUsed, mDNSu32* const mDNSs32 remain = cr->resrec.rroriginalttl - (now - cr->TimeRcvd) / mDNSPlatformOneSecond; const char *ifname; mDNSInterfaceID InterfaceID = cr->resrec.InterfaceID; - if (!InterfaceID && cr->resrec.rDNSServer && cr->resrec.rDNSServer->scoped) + if (!InterfaceID && cr->resrec.rDNSServer && (cr->resrec.rDNSServer->scopeType != kScopeNone)) InterfaceID = cr->resrec.rDNSServer->interface; ifname = InterfaceNameForID(&mDNSStorage, InterfaceID); if (cr->CRActiveQuestion) CacheActive++; -- cgit v1.2.3