internal bool EqualsBase(DnsResourceRecord other) { return(other != null && DomainName.Equals(other.DomainName) && DnsType.Equals(other.DnsType) && DnsClass.Equals(other.DnsClass)); }
/// <summary> /// Two DnsResourceDataUShortDomainName are equal iff their of the same type and their ushort values and domain names are equal. /// </summary> public bool Equals(DnsResourceDataUShortDomainName other) { return(other != null && GetType().Equals(other.GetType()) && Value.Equals(other.Value) && DomainName.Equals(other.DomainName)); }
public void SutDoesNotEqualAnonymousObject() { // Arrange var sut = new DomainName(Guid.NewGuid().ToString()); var anonymousObject = new object(); // Act bool result = sut.Equals(anonymousObject); // Assert Assert.False(result); }
public void SutDoesNotEqualOtherObjectWhenDomainNamesDiffer() { // Arrange var sut = new DomainName(Guid.NewGuid().ToString()); object other = new DomainName(Guid.NewGuid().ToString()); // Act bool result = sut.Equals(other); // Assert Assert.False(result); }
/// <summary> /// Determines whether the specified <see cref="System.Object" />, is equal to this instance. /// </summary> /// <param name="obj">The <see cref="System.Object" /> to compare with this instance.</param> /// <returns> /// <c>true</c> if the specified <see cref="System.Object" /> is equal to this instance; otherwise, <c>false</c>. /// </returns> public override bool Equals(object obj) { Domain domain = obj as Domain; if (DomainName.Equals(domain.DomainName)) { return(true); } return(false); }
public void SutDoesNotEqualOtherObjectWhenDomainNamesDiffer() { // Fixture setup var sut = new DomainName(Guid.NewGuid().ToString()); object other = new DomainName(Guid.NewGuid().ToString()); // Exercise system bool result = sut.Equals(other); // Verify outcome Assert.False(result); // Teardown }
private async Task <DnsSecValidationResult> ValidateNSecAsync(DomainName name, RecordType recordType, RecordClass recordClass, List <RrSigRecord> rrSigRecords, DomainName stop, DomainName zoneApex, DnsMessageBase msg, TState state, CancellationToken token) { List <NSecRecord> nsecRecords = msg.AuthorityRecords.OfType <NSecRecord>().ToList(); if (nsecRecords.Count == 0) { return(DnsSecValidationResult.Indeterminate); } foreach (var nsecGroup in nsecRecords.GroupBy(x => x.Name)) { DnsSecValidationResult validationResult = await ValidateRrSigAsync(nsecGroup.Key, RecordType.NSec, recordClass, nsecGroup.ToList(), rrSigRecords, zoneApex, msg, state, token); if (validationResult != DnsSecValidationResult.Signed) { return(validationResult); } } DomainName current = name; while (true) { if (current.Equals(stop)) { return(DnsSecValidationResult.Signed); } NSecRecord nsecRecord = nsecRecords.FirstOrDefault(x => x.Name.Equals(current)); if (nsecRecord != null) { return(nsecRecord.Types.Contains(recordType) ? DnsSecValidationResult.Bogus : DnsSecValidationResult.Signed); } else { nsecRecord = nsecRecords.FirstOrDefault(x => x.IsCovering(current, zoneApex)); if (nsecRecord == null) { return(DnsSecValidationResult.Bogus); } } // Updated the following lines to fix an issue where an NSEC entry is present for a parent domain but is not a wildcard entry. if (current.Labels[0] == "*") { current = current.GetParentName(); } else { current = DomainName.Asterisk + current.GetParentName(); } } }
public void SutDoesNotEqualAnonymousObject() { // Fixture setup var sut = new DomainName(Guid.NewGuid().ToString()); var anonymousObject = new object(); // Exercise system bool result = sut.Equals(anonymousObject); // Verify outcome Assert.False(result); // Teardown }
public void SutEqualsOtherSutWhenDomainNamesAreEqual() { // Arrange var domainName = Guid.NewGuid().ToString(); var sut = new DomainName(domainName); var other = new DomainName(domainName); // Act bool result = sut.Equals(other); // Assert Assert.True(result); }
public void SutEqualsOtherSutWhenDomainNamesAreEqual() { // Fixture setup var domainName = Guid.NewGuid().ToString(); var sut = new DomainName(domainName); var other = new DomainName(domainName); // Exercise system bool result = sut.Equals(other); // Verify outcome Assert.True(result); // Teardown }
public ContainsResult Contains(Host host) { if (host.Format != HostFormat.DomainName && host.Format != HostFormat.IPv4 && host.Format != HostFormat.IPv6) { throw new ArgumentException($"Format must be {HostFormat.DomainName}, {HostFormat.IPv4}, or {HostFormat.IPv6}."); } switch (host.Format) { case HostFormat.DomainName: switch (Format) { case HostFormat.DomainName: return(DomainName.Equals(host.DomainName, StringComparison.OrdinalIgnoreCase) ? ContainsResult.Yes : ContainsResult.No); case HostFormat.DomainNameSuffix: return(host.DomainName.EndsWith(DomainName, StringComparison.OrdinalIgnoreCase) ? ContainsResult.Yes : ContainsResult.No); } break; case HostFormat.IPv4: switch (Format) { case HostFormat.IPv4: return(IpAddress.Equals(host.IpAddress) ? ContainsResult.Yes : ContainsResult.No); case HostFormat.IPv4Cidr: // ReSharper disable once PossibleInvalidOperationException return(CidrMatches(IpAddress, host.IpAddress, MaskBits.Value, 32) ? ContainsResult.Yes : ContainsResult.No); } break; case HostFormat.IPv6: switch (Format) { case HostFormat.IPv6: return(IpAddress.Equals(host.IpAddress) ? ContainsResult.Yes : ContainsResult.No); case HostFormat.IPv6Cidr: // ReSharper disable once PossibleInvalidOperationException return(CidrMatches(IpAddress, host.IpAddress, MaskBits.Value, 128) ? ContainsResult.Yes : ContainsResult.No); } break; } return(ContainsResult.Inapplicable); }
public void Must_be_equatable() { DomainName a = "example.com"; DomainName b = "example.com"; DomainName c = "apple.com"; DomainName d = "orange.com"; (a == b).Should().BeTrue(); (b == a).Should().BeTrue(); a.Equals(b).Should().BeTrue(); b.Equals(a).Should().BeTrue(); (c != d).Should().BeTrue(); (d != c).Should().BeTrue(); c.Equals(d).Should().BeFalse(); d.Equals(c).Should().BeFalse(); }
private async Task <List <T> > ResolveAsyncInternal <T>(DomainName name, RecordType recordType, RecordClass recordClass, State state, CancellationToken token) where T : DnsRecordBase { List <T> cachedResults; if (_cache.TryGetRecords(name, recordType, recordClass, out cachedResults)) { return(cachedResults); } List <CNameRecord> cachedCNames; if (_cache.TryGetRecords(name, RecordType.CName, recordClass, out cachedCNames)) { return(await ResolveAsyncInternal <T>(cachedCNames.First().CanonicalName, recordType, recordClass, state, token)); } DnsMessage msg = await ResolveMessageAsync(name, recordType, recordClass, state, token); // check for cname List <DnsRecordBase> cNameRecords = msg.AnswerRecords.Where(x => (x.RecordType == RecordType.CName) && (x.RecordClass == recordClass) && x.Name.Equals(name)).ToList(); if (cNameRecords.Count > 0) { _cache.Add(name, RecordType.CName, recordClass, cNameRecords, DnsSecValidationResult.Indeterminate, cNameRecords.Min(x => x.TimeToLive)); DomainName canonicalName = ((CNameRecord)cNameRecords.First()).CanonicalName; List <DnsRecordBase> matchingAdditionalRecords = msg.AnswerRecords.Where(x => (x.RecordType == recordType) && (x.RecordClass == recordClass) && x.Name.Equals(canonicalName)).ToList(); if (matchingAdditionalRecords.Count > 0) { _cache.Add(canonicalName, recordType, recordClass, matchingAdditionalRecords, DnsSecValidationResult.Indeterminate, matchingAdditionalRecords.Min(x => x.TimeToLive)); return(matchingAdditionalRecords.OfType <T>().ToList()); } return(await ResolveAsyncInternal <T>(canonicalName, recordType, recordClass, state, token)); } // check for "normal" answer List <DnsRecordBase> answerRecords = msg.AnswerRecords.Where(x => (x.RecordType == recordType) && (x.RecordClass == recordClass) && x.Name.Equals(name)).ToList(); if (answerRecords.Count > 0) { _cache.Add(name, recordType, recordClass, answerRecords, DnsSecValidationResult.Indeterminate, answerRecords.Min(x => x.TimeToLive)); return(answerRecords.OfType <T>().ToList()); } // check for negative answer SoaRecord soaRecord = msg.AuthorityRecords .Where(x => (x.RecordType == RecordType.Soa) && (name.Equals(x.Name) || name.IsSubDomainOf(x.Name))) .OfType <SoaRecord>() .FirstOrDefault(); if (soaRecord != null) { _cache.Add(name, recordType, recordClass, new List <DnsRecordBase>(), DnsSecValidationResult.Indeterminate, soaRecord.NegativeCachingTTL); return(new List <T>()); } // authoritive response does not contain answer throw new Exception("Could not resolve " + name); }
private async Task <DnsMessage> ResolveMessageAsync(DomainName name, RecordType recordType, RecordClass recordClass, State state, CancellationToken token) { for (; state.QueryCount <= MaximumReferalCount; state.QueryCount++) { DnsMessage msg = await new DnsClient(GetBestNameservers(recordType == RecordType.Ds ? name.GetParentName() : name), QueryTimeout) { IsResponseValidationEnabled = IsResponseValidationEnabled, Is0x20ValidationEnabled = Is0x20ValidationEnabled }.ResolveAsync(name, recordType, recordClass, new DnsQueryOptions() { IsRecursionDesired = false, IsEDnsEnabled = true }, token); if ((msg != null) && ((msg.ReturnCode == ReturnCode.NoError) || (msg.ReturnCode == ReturnCode.NxDomain))) { if (msg.IsAuthoritiveAnswer) { return(msg); } List <NsRecord> referalRecords = msg.AuthorityRecords .Where(x => (x.RecordType == RecordType.Ns) && (name.Equals(x.Name) || name.IsSubDomainOf(x.Name))) .OfType <NsRecord>() .ToList(); if (referalRecords.Count > 0) { if (referalRecords.GroupBy(x => x.Name).Count() == 1) { var newServers = referalRecords.Join(msg.AdditionalRecords.OfType <AddressRecordBase>(), x => x.NameServer, x => x.Name, (x, y) => new { y.Address, TimeToLive = Math.Min(x.TimeToLive, y.TimeToLive) }).ToList(); if (newServers.Count > 0) { DomainName zone = referalRecords.First().Name; foreach (var newServer in newServers) { _nameserverCache.Add(zone, newServer.Address, newServer.TimeToLive); } continue; } else { NsRecord firstReferal = referalRecords.First(); var newLookedUpServers = await ResolveHostWithTtlAsync(firstReferal.NameServer, state, token); foreach (var newServer in newLookedUpServers) { _nameserverCache.Add(firstReferal.Name, newServer.Item1, Math.Min(firstReferal.TimeToLive, newServer.Item2)); } if (newLookedUpServers.Count > 0) { continue; } } } } // Response of best known server is not authoritive and has no referrals --> No chance to get a result throw new Exception("Could not resolve " + name); } } // query limit reached without authoritive answer throw new Exception("Could not resolve " + name); }
private async Task <SpfQualifier> CheckMechanismAsync(SpfMechanism mechanism, IPAddress ip, DomainName domain, string sender, State state, CancellationToken token) { switch (mechanism.Type) { case SpfMechanismType.All: return(mechanism.Qualifier); case SpfMechanismType.A: if (++state.DnsLookupCount > 10) { return(SpfQualifier.PermError); } DomainName aMechanismDomain = String.IsNullOrEmpty(mechanism.Domain) ? domain : await ExpandDomainAsync(mechanism.Domain, ip, domain, sender, token); bool?isAMatch = await IsIpMatchAsync(aMechanismDomain, ip, mechanism.Prefix, mechanism.Prefix6, token); if (!isAMatch.HasValue) { return(SpfQualifier.TempError); } if (isAMatch.Value) { return(mechanism.Qualifier); } break; case SpfMechanismType.Mx: if (++state.DnsLookupCount > 10) { return(SpfQualifier.PermError); } DomainName mxMechanismDomain = String.IsNullOrEmpty(mechanism.Domain) ? domain : await ExpandDomainAsync(mechanism.Domain, ip, domain, sender, token); DnsResolveResult <MxRecord> dnsMxResult = await ResolveDnsAsync <MxRecord>(mxMechanismDomain, RecordType.Mx, token); if ((dnsMxResult == null) || ((dnsMxResult.ReturnCode != ReturnCode.NoError) && (dnsMxResult.ReturnCode != ReturnCode.NxDomain))) { return(SpfQualifier.TempError); } int mxCheckedCount = 0; foreach (MxRecord mxRecord in dnsMxResult.Records) { if (++mxCheckedCount == 10) { break; } bool?isMxMatch = await IsIpMatchAsync(mxRecord.ExchangeDomainName, ip, mechanism.Prefix, mechanism.Prefix6, token); if (!isMxMatch.HasValue) { return(SpfQualifier.TempError); } if (isMxMatch.Value) { return(mechanism.Qualifier); } } break; case SpfMechanismType.Ip4: case SpfMechanismType.Ip6: IPAddress compareAddress; if (IPAddress.TryParse(mechanism.Domain, out compareAddress)) { if (ip.AddressFamily != compareAddress.AddressFamily) { return(SpfQualifier.None); } if (mechanism.Prefix.HasValue) { if ((mechanism.Prefix.Value < 0) || (mechanism.Prefix.Value > (compareAddress.AddressFamily == AddressFamily.InterNetworkV6 ? 128 : 32))) { return(SpfQualifier.PermError); } if (ip.GetNetworkAddress(mechanism.Prefix.Value).Equals(compareAddress.GetNetworkAddress(mechanism.Prefix.Value))) { return(mechanism.Qualifier); } } else if (ip.Equals(compareAddress)) { return(mechanism.Qualifier); } } else { return(SpfQualifier.PermError); } break; case SpfMechanismType.Ptr: if (++state.DnsLookupCount > 10) { return(SpfQualifier.PermError); } DnsResolveResult <PtrRecord> dnsPtrResult = await ResolveDnsAsync <PtrRecord>(ip.GetReverseLookupDomain(), RecordType.Ptr, token); if ((dnsPtrResult == null) || ((dnsPtrResult.ReturnCode != ReturnCode.NoError) && (dnsPtrResult.ReturnCode != ReturnCode.NxDomain))) { return(SpfQualifier.TempError); } DomainName ptrMechanismDomain = String.IsNullOrEmpty(mechanism.Domain) ? domain : await ExpandDomainAsync(mechanism.Domain, ip, domain, sender, token); int ptrCheckedCount = 0; foreach (PtrRecord ptrRecord in dnsPtrResult.Records) { if (++ptrCheckedCount == 10) { break; } bool?isPtrMatch = await IsIpMatchAsync(ptrRecord.PointerDomainName, ip, 0, 0, token); if (isPtrMatch.HasValue && isPtrMatch.Value) { if (ptrRecord.PointerDomainName.Equals(ptrMechanismDomain) || (ptrRecord.PointerDomainName.IsSubDomainOf(ptrMechanismDomain))) { return(mechanism.Qualifier); } } } break; case SpfMechanismType.Exist: if (++state.DnsLookupCount > 10) { return(SpfQualifier.PermError); } if (String.IsNullOrEmpty(mechanism.Domain)) { return(SpfQualifier.PermError); } DomainName existsMechanismDomain = String.IsNullOrEmpty(mechanism.Domain) ? domain : await ExpandDomainAsync(mechanism.Domain, ip, domain, sender, token); DnsResolveResult <ARecord> dnsAResult = await ResolveDnsAsync <ARecord>(existsMechanismDomain, RecordType.A, token); if ((dnsAResult == null) || ((dnsAResult.ReturnCode != ReturnCode.NoError) && (dnsAResult.ReturnCode != ReturnCode.NxDomain))) { return(SpfQualifier.TempError); } if (dnsAResult.Records.Count(record => (record.RecordType == RecordType.A)) > 0) { return(mechanism.Qualifier); } break; case SpfMechanismType.Include: if (++state.DnsLookupCount > 10) { return(SpfQualifier.PermError); } if (String.IsNullOrEmpty(mechanism.Domain)) { return(SpfQualifier.PermError); } DomainName includeMechanismDomain = String.IsNullOrEmpty(mechanism.Domain) ? domain : await ExpandDomainAsync(mechanism.Domain, ip, domain, sender, token); if (includeMechanismDomain.Equals(domain)) { return(SpfQualifier.PermError); } var includeResult = await CheckHostInternalAsync(ip, includeMechanismDomain, sender, false, state, token); switch (includeResult.Result) { case SpfQualifier.Pass: return(mechanism.Qualifier); case SpfQualifier.Fail: case SpfQualifier.SoftFail: case SpfQualifier.Neutral: return(SpfQualifier.None); case SpfQualifier.TempError: return(SpfQualifier.TempError); case SpfQualifier.PermError: case SpfQualifier.None: return(SpfQualifier.PermError); } break; default: return(SpfQualifier.PermError); } return(SpfQualifier.None); }
private async Task <ValidationResult> CheckHostInternalAsync(IPAddress ip, DomainName domain, string sender, bool expandExplanation, State state, CancellationToken token) { if ((domain == null) || (domain.Equals(DomainName.Root))) { return(new ValidationResult() { Result = SpfQualifier.None, Explanation = String.Empty }); } if (String.IsNullOrEmpty(sender)) { sender = "postmaster@unknown"; } else if (!sender.Contains('@')) { sender = "postmaster@" + sender; } LoadRecordResult loadResult = await LoadRecordsAsync(domain, token); if (!loadResult.CouldBeLoaded) { return(new ValidationResult() { Result = loadResult.ErrorResult, Explanation = String.Empty }); } T record = loadResult.Record; if ((record.Terms == null) || (record.Terms.Count == 0)) { return new ValidationResult() { Result = SpfQualifier.Neutral, Explanation = String.Empty } } ; if (record.Terms.OfType <SpfModifier>().GroupBy(m => m.Type).Where(g => (g.Key == SpfModifierType.Exp) || (g.Key == SpfModifierType.Redirect)).Any(g => g.Count() > 1)) { return new ValidationResult() { Result = SpfQualifier.PermError, Explanation = String.Empty } } ; ValidationResult result = new ValidationResult() { Result = loadResult.ErrorResult }; #region Evaluate mechanism foreach (SpfMechanism mechanism in record.Terms.OfType <SpfMechanism>()) { if (state.DnsLookupCount > DnsLookupLimit) { return new ValidationResult() { Result = SpfQualifier.PermError, Explanation = String.Empty } } ; SpfQualifier qualifier = await CheckMechanismAsync(mechanism, ip, domain, sender, state, token); if (qualifier != SpfQualifier.None) { result.Result = qualifier; break; } } #endregion #region Evaluate modifiers if (result.Result == SpfQualifier.None) { SpfModifier redirectModifier = record.Terms.OfType <SpfModifier>().FirstOrDefault(m => m.Type == SpfModifierType.Redirect); if (redirectModifier != null) { if (++state.DnsLookupCount > 10) { return new ValidationResult() { Result = SpfQualifier.PermError, Explanation = String.Empty } } ; DomainName redirectDomain = await ExpandDomainAsync(redirectModifier.Domain ?? String.Empty, ip, domain, sender, token); if ((redirectDomain == null) || (redirectDomain == DomainName.Root) || (redirectDomain.Equals(domain))) { result.Result = SpfQualifier.PermError; } else { result = await CheckHostInternalAsync(ip, redirectDomain, sender, expandExplanation, state, token); if (result.Result == SpfQualifier.None) { result.Result = SpfQualifier.PermError; } } } } else if ((result.Result == SpfQualifier.Fail) && expandExplanation) { SpfModifier expModifier = record.Terms.OfType <SpfModifier>().FirstOrDefault(m => m.Type == SpfModifierType.Exp); if (expModifier != null) { DomainName target = await ExpandDomainAsync(expModifier.Domain, ip, domain, sender, token); if ((target == null) || (target.Equals(DomainName.Root))) { result.Explanation = String.Empty; } else { DnsResolveResult <TxtRecord> dnsResult = await ResolveDnsAsync <TxtRecord>(target, RecordType.Txt, token); if ((dnsResult != null) && (dnsResult.ReturnCode == ReturnCode.NoError)) { TxtRecord txtRecord = dnsResult.Records.FirstOrDefault(); if (txtRecord != null) { result.Explanation = (await ExpandMacroAsync(txtRecord.TextData, ip, domain, sender, token)).ToString(); } } } } } #endregion if (result.Result == SpfQualifier.None) { result.Result = SpfQualifier.Neutral; } return(result); }
public void Must_be_equatable_to_String() { var a = new DomainName("example.com"); a.Equals("example.com").Should().Be(true); }
public void Must_be_equatable_to_Empty() { var a = new DomainName("example.com"); a.Equals(DomainName.Empty).Should().Be(false); }
public bool Equals(string userName, string domainName, string environmentName) { return((UserName != null) && UserName.Equals(userName, StringComparison.InvariantCultureIgnoreCase) && (DomainName != null) && DomainName.Equals(domainName, StringComparison.InvariantCultureIgnoreCase) && (EnvironmentName != null) && EnvironmentName.Equals(environmentName, StringComparison.InvariantCultureIgnoreCase)); }
private async Task <DnsSecResult <T> > ResolveAsyncInternal <T>(DomainName name, RecordType recordType, RecordClass recordClass, State state, CancellationToken token) where T : DnsRecordBase { DnsCacheRecordList <T> cachedResults; if (_cache.TryGetRecords(name, recordType, recordClass, out cachedResults)) { return(new DnsSecResult <T>(cachedResults, cachedResults.ValidationResult)); } DnsCacheRecordList <CNameRecord> cachedCNames; if (_cache.TryGetRecords(name, RecordType.CName, recordClass, out cachedCNames)) { var cNameResult = await ResolveAsyncInternal <T>(cachedCNames.First().CanonicalName, recordType, recordClass, state, token); return(new DnsSecResult <T>(cNameResult.Records, cachedCNames.ValidationResult == cNameResult.ValidationResult ? cachedCNames.ValidationResult : DnsSecValidationResult.Unsigned)); } DnsMessage msg = await ResolveMessageAsync(name, recordType, recordClass, state, token); // check for cname List <DnsRecordBase> cNameRecords = msg.AnswerRecords.Where(x => (x.RecordType == RecordType.CName) && (x.RecordClass == recordClass) && x.Name.Equals(name)).ToList(); if (cNameRecords.Count > 0) { DnsSecValidationResult cNameValidationResult = await _validator.ValidateAsync(name, RecordType.CName, recordClass, msg, cNameRecords, state, token); if ((cNameValidationResult == DnsSecValidationResult.Bogus) || (cNameValidationResult == DnsSecValidationResult.Indeterminate)) { throw new DnsSecValidationException("CNAME record could not be validated"); } _cache.Add(name, RecordType.CName, recordClass, cNameRecords, cNameValidationResult, cNameRecords.Min(x => x.TimeToLive)); DomainName canonicalName = ((CNameRecord)cNameRecords.First()).CanonicalName; List <DnsRecordBase> matchingAdditionalRecords = msg.AnswerRecords.Where(x => (x.RecordType == recordType) && (x.RecordClass == recordClass) && x.Name.Equals(canonicalName)).ToList(); if (matchingAdditionalRecords.Count > 0) { DnsSecValidationResult matchingValidationResult = await _validator.ValidateAsync(canonicalName, recordType, recordClass, msg, matchingAdditionalRecords, state, token); if ((matchingValidationResult == DnsSecValidationResult.Bogus) || (matchingValidationResult == DnsSecValidationResult.Indeterminate)) { throw new DnsSecValidationException("CNAME matching records could not be validated"); } DnsSecValidationResult validationResult = cNameValidationResult == matchingValidationResult ? cNameValidationResult : DnsSecValidationResult.Unsigned; _cache.Add(canonicalName, recordType, recordClass, matchingAdditionalRecords, validationResult, matchingAdditionalRecords.Min(x => x.TimeToLive)); return(new DnsSecResult <T>(matchingAdditionalRecords.OfType <T>().ToList(), validationResult)); } var cNameResults = await ResolveAsyncInternal <T>(canonicalName, recordType, recordClass, state, token); return(new DnsSecResult <T>(cNameResults.Records, cNameValidationResult == cNameResults.ValidationResult ? cNameValidationResult : DnsSecValidationResult.Unsigned)); } // check for "normal" answer List <DnsRecordBase> answerRecords = msg.AnswerRecords.Where(x => (x.RecordType == recordType) && (x.RecordClass == recordClass) && x.Name.Equals(name)).ToList(); if (answerRecords.Count > 0) { DnsSecValidationResult validationResult = await _validator.ValidateAsync(name, recordType, recordClass, msg, answerRecords, state, token); if ((validationResult == DnsSecValidationResult.Bogus) || (validationResult == DnsSecValidationResult.Indeterminate)) { throw new DnsSecValidationException("Response records could not be validated"); } _cache.Add(name, recordType, recordClass, answerRecords, validationResult, answerRecords.Min(x => x.TimeToLive)); return(new DnsSecResult <T>(answerRecords.OfType <T>().ToList(), validationResult)); } // check for negative answer SoaRecord soaRecord = msg.AuthorityRecords .Where(x => (x.RecordType == RecordType.Soa) && (name.Equals(x.Name) || name.IsSubDomainOf(x.Name))) .OfType <SoaRecord>() .FirstOrDefault(); if (soaRecord != null) { DnsSecValidationResult validationResult = await _validator.ValidateAsync(name, recordType, recordClass, msg, answerRecords, state, token); if ((validationResult == DnsSecValidationResult.Bogus) || (validationResult == DnsSecValidationResult.Indeterminate)) { throw new DnsSecValidationException("Negative answer could not be validated"); } _cache.Add(name, recordType, recordClass, new List <DnsRecordBase>(), validationResult, soaRecord.NegativeCachingTTL); return(new DnsSecResult <T>(new List <T>(), validationResult)); } // authoritive response does not contain answer throw new Exception("Could not resolve " + name); }
public override bool Equals(object obj) { CacheKey other = obj as CacheKey; if (other == null) { return(false); } return((_recordType == other._recordType) && (_recordClass == other._recordClass) && (_name.Equals(other._name))); }