diff --git a/src/DnsmasqWebUI.Tests/DnsmasqConfIncludeParserTests.cs b/src/DnsmasqWebUI.Tests/DnsmasqConfIncludeParserTests.cs index b4a3dbb..d5cef5d 100644 --- a/src/DnsmasqWebUI.Tests/DnsmasqConfIncludeParserTests.cs +++ b/src/DnsmasqWebUI.Tests/DnsmasqConfIncludeParserTests.cs @@ -687,4 +687,62 @@ public class DnsmasqConfIncludeParserTests Directory.Delete(dir, recursive: true); } } + + [Fact] + public void GetFlagFromConfigFiles_AllServers_WhenPresent_ReturnsTrue() + { + var dir = Path.Combine(Path.GetTempPath(), "dnsmasq-allsrv-" + Guid.NewGuid().ToString("N")); + Directory.CreateDirectory(dir); + var conf = Path.Combine(dir, "dnsmasq.conf"); + try + { + File.WriteAllText(conf, "all-servers\n"); + var result = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(new[] { conf }, DnsmasqConfKeys.AllServers); + Assert.True(result); + } + finally + { + Directory.Delete(dir, recursive: true); + } + } + + [Fact] + public void GetLastValueFromConfigFiles_LogQueries_ReturnsValue() + { + var dir = Path.Combine(Path.GetTempPath(), "dnsmasq-logq-" + Guid.NewGuid().ToString("N")); + Directory.CreateDirectory(dir); + var conf = Path.Combine(dir, "dnsmasq.conf"); + try + { + File.WriteAllText(conf, "log-queries=extra\n"); + var (value, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(new[] { conf }, DnsmasqConfKeys.LogQueries); + Assert.Equal("extra", value); + } + finally + { + Directory.Delete(dir, recursive: true); + } + } + + [Fact] + public void GetMultiValueFromConfigFiles_RevServer_ReturnsAllValues() + { + var dir = Path.Combine(Path.GetTempPath(), "dnsmasq-rev-" + Guid.NewGuid().ToString("N")); + Directory.CreateDirectory(dir); + var conf = Path.Combine(dir, "dnsmasq.conf"); + var v1 = "1.2.3.0/24,192.168.0.1"; + var v2 = "10.0.0.0/8,10.0.0.1"; + try + { + File.WriteAllText(conf, $"rev-server={v1}\nrev-server={v2}\n"); + var result = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(new[] { conf }, DnsmasqConfKeys.RevServer); + Assert.Equal(2, result.Count); + Assert.Equal(v1, result[0]); + Assert.Equal(v2, result[1]); + } + finally + { + Directory.Delete(dir, recursive: true); + } + } } diff --git a/src/DnsmasqWebUI.Tests/EffectiveDnsmasqConfigTests.cs b/src/DnsmasqWebUI.Tests/EffectiveDnsmasqConfigTests.cs index fbc7982..3084163 100644 --- a/src/DnsmasqWebUI.Tests/EffectiveDnsmasqConfigTests.cs +++ b/src/DnsmasqWebUI.Tests/EffectiveDnsmasqConfigTests.cs @@ -12,6 +12,7 @@ public class EffectiveDnsmasqConfigTests NoHosts: false, AddnHostsPaths: Array.Empty(), ServerLocalValues: Array.Empty(), + RevServerValues: Array.Empty(), AddressValues: Array.Empty(), Interfaces: Array.Empty(), ListenAddresses: Array.Empty(), @@ -20,14 +21,35 @@ public class EffectiveDnsmasqConfigTests DhcpHostLines: Array.Empty(), DhcpOptionLines: Array.Empty(), ResolvFiles: Array.Empty(), + RebindDomainOkValues: Array.Empty(), + BogusNxdomainValues: Array.Empty(), + IgnoreAddressValues: Array.Empty(), + AliasValues: Array.Empty(), + FilterRrValues: Array.Empty(), + CacheRrValues: Array.Empty(), + AuthServerValues: Array.Empty(), + NoDhcpInterfaceValues: Array.Empty(), + NoDhcpv4InterfaceValues: Array.Empty(), + NoDhcpv6InterfaceValues: Array.Empty(), ExpandHosts: false, BogusPriv: false, StrictOrder: false, + AllServers: false, NoResolv: false, DomainNeeded: false, NoPoll: false, BindInterfaces: false, + BindDynamic: false, NoNegcache: false, + DnsLoopDetect: false, + StopDnsRebind: false, + RebindLocalhostOk: false, + ClearOnReload: false, + Filterwin2k: false, + FilterA: false, + FilterAaaa: false, + LocaliseQueries: false, + LogDebug: false, DhcpAuthoritative: false, LeasefileRo: false, DhcpLeaseFilePath: null, @@ -38,6 +60,15 @@ public class EffectiveDnsmasqConfigTests User: null, Group: null, LogFacility: logFacility, + LogQueries: null, + AuthTtl: null, + EdnsPacketMax: null, + QueryPort: null, + PortLimit: null, + MinPort: null, + MaxPort: null, + LogAsync: null, + LocalService: null, DhcpLeaseMax: null, NegTtl: null, MaxTtl: null, diff --git a/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqConfKeys.cs b/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqConfKeys.cs index 0287c55..ede163d 100644 --- a/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqConfKeys.cs +++ b/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqConfKeys.cs @@ -22,24 +22,46 @@ public static class DnsmasqConfKeys // --- Multi-value (ARG_DUP) --- public const string Server = "server"; public const string Local = "local"; + public const string RevServer = "rev-server"; public const string Address = "address"; public const string Interface = "interface"; public const string ListenAddress = "listen-address"; public const string ExceptInterface = "except-interface"; + public const string NoDhcpInterface = "no-dhcp-interface"; + public const string NoDhcpv4Interface = "no-dhcpv4-interface"; + public const string NoDhcpv6Interface = "no-dhcpv6-interface"; + public const string AuthServer = "auth-server"; public const string DhcpRange = "dhcp-range"; public const string DhcpHost = "dhcp-host"; public const string DhcpOption = "dhcp-option"; public const string ResolvFile = "resolv-file"; + public const string RebindDomainOk = "rebind-domain-ok"; + public const string BogusNxdomain = "bogus-nxdomain"; + public const string IgnoreAddress = "ignore-address"; + public const string Alias = "alias"; + public const string FilterRr = "filter-rr"; + public const string CacheRr = "cache-rr"; // --- Flags (no value) --- public const string ExpandHosts = "expand-hosts"; public const string BogusPriv = "bogus-priv"; public const string StrictOrder = "strict-order"; + public const string AllServers = "all-servers"; public const string NoResolv = "no-resolv"; public const string DomainNeeded = "domain-needed"; public const string NoPoll = "no-poll"; public const string BindInterfaces = "bind-interfaces"; + public const string BindDynamic = "bind-dynamic"; public const string NoNegcache = "no-negcache"; + public const string DnsLoopDetect = "dns-loop-detect"; + public const string StopDnsRebind = "stop-dns-rebind"; + public const string RebindLocalhostOk = "rebind-localhost-ok"; + public const string ClearOnReload = "clear-on-reload"; + public const string Filterwin2k = "filterwin2k"; + public const string FilterA = "filter-A"; + public const string FilterAaaa = "filter-AAAA"; + public const string LocaliseQueries = "localise-queries"; + public const string LogDebug = "log-debug"; public const string DhcpAuthoritative = "dhcp-authoritative"; public const string LeasefileRo = "leasefile-ro"; @@ -47,10 +69,19 @@ public static class DnsmasqConfKeys public const string CacheSize = "cache-size"; public const string Port = "port"; public const string LocalTtl = "local-ttl"; + public const string AuthTtl = "auth-ttl"; + public const string EdnsPacketMax = "edns-packet-max"; + public const string QueryPort = "query-port"; + public const string PortLimit = "port-limit"; + public const string MinPort = "min-port"; + public const string MaxPort = "max-port"; + public const string LogAsync = "log-async"; + public const string LocalService = "local-service"; public const string PidFile = "pid-file"; public const string User = "user"; public const string Group = "group"; public const string LogFacility = "log-facility"; + public const string LogQueries = "log-queries"; public const string DhcpLeaseMax = "dhcp-lease-max"; public const string NegTtl = "neg-ttl"; public const string MaxTtl = "max-ttl"; diff --git a/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqOptionTooltips.cs b/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqOptionTooltips.cs index 4d57ea8..f0ed570 100644 --- a/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqOptionTooltips.cs +++ b/src/DnsmasqWebUI/Infrastructure/Helpers/Config/DnsmasqOptionTooltips.cs @@ -21,12 +21,39 @@ public static class DnsmasqOptionTooltips [DnsmasqConfKeys.ExpandHosts] = "Expand simple names in /etc/hosts with the local domain.", [DnsmasqConfKeys.BogusPriv] = "Do not forward reverse lookups for private IP ranges.", [DnsmasqConfKeys.StrictOrder] = "Query servers in the order specified; do not try the next on failure.", + [DnsmasqConfKeys.AllServers] = "Send each query to all upstream servers; use the first reply.", [DnsmasqConfKeys.NoResolv] = "Do not read /etc/resolv.conf; use only server= and resolv-file=.", [DnsmasqConfKeys.DomainNeeded] = "Never forward plain names (without a domain) to upstream.", [DnsmasqConfKeys.Port] = "Listen on this port for DNS queries (default 53).", + [DnsmasqConfKeys.LogQueries] = "Log DNS queries. Optional value: extra, proto, or auth.", [ServerLocalLabel] = "Upstream DNS servers (server=) and local-only domains (local=). Order is preserved.", + [DnsmasqConfKeys.RevServer] = "Reverse DNS server (e.g. rev-server=1.2.3.0/24,192.168.0.1). Can repeat.", [DnsmasqConfKeys.Address] = "Map a domain or hostname to an IP (e.g. for ad blocking or local names). Can repeat.", [DnsmasqConfKeys.ResolvFile] = "File(s) to read upstream server addresses from (e.g. from DHCP). Can repeat.", + [DnsmasqConfKeys.AuthTtl] = "TTL for answers from the authoritative server.", + [DnsmasqConfKeys.EdnsPacketMax] = "Largest EDNS.0 UDP packet size (default 1232).", + [DnsmasqConfKeys.QueryPort] = "Source port for outbound DNS queries (0 = single OS-allocated port).", + [DnsmasqConfKeys.PortLimit] = "Number of source ports for outbound queries.", + [DnsmasqConfKeys.MinPort] = "Minimum source port for outbound DNS queries.", + [DnsmasqConfKeys.MaxPort] = "Maximum source port for outbound DNS queries.", + [DnsmasqConfKeys.DnsLoopDetect] = "Detect DNS forwarding loops and disable bad upstream servers.", + [DnsmasqConfKeys.StopDnsRebind] = "Reject private-range addresses from upstream (anti-rebind).", + [DnsmasqConfKeys.RebindLocalhostOk] = "Allow 127.0.0.0/8 and ::1 in upstream replies.", + [DnsmasqConfKeys.ClearOnReload] = "Clear DNS cache when resolv.conf or servers are reloaded.", + [DnsmasqConfKeys.Filterwin2k] = "Filter Windows LDAP/SOA/SRV queries that trigger dial-on-demand.", + [DnsmasqConfKeys.FilterA] = "Remove A (IPv4) records from answers.", + [DnsmasqConfKeys.FilterAaaa] = "Remove AAAA (IPv6) records from answers.", + [DnsmasqConfKeys.LocaliseQueries] = "Return interface-specific answers from hosts/DHCP.", + [DnsmasqConfKeys.RebindDomainOk] = "Domains exempt from rebind checks. Can repeat.", + [DnsmasqConfKeys.BogusNxdomain] = "Transform replies containing these IPs to NXDOMAIN. Can repeat.", + [DnsmasqConfKeys.IgnoreAddress] = "Ignore A/AAAA replies containing these IPs. Can repeat.", + [DnsmasqConfKeys.Alias] = "Rewrite IPs in upstream replies (DNS doctoring). Can repeat.", + [DnsmasqConfKeys.FilterRr] = "Remove these RR types from answers. Can repeat.", + [DnsmasqConfKeys.CacheRr] = "Cache these RR types in addition to default. Can repeat.", + [DnsmasqConfKeys.AuthServer] = "Authoritative DNS mode (domain, interface/IP). Can repeat.", + [DnsmasqConfKeys.NoDhcpInterface] = "No DHCP/TFTP/RA on these interfaces; DNS only. Can repeat.", + [DnsmasqConfKeys.NoDhcpv4Interface] = "No DHCPv4 on these interfaces. Can repeat.", + [DnsmasqConfKeys.NoDhcpv6Interface] = "No DHCPv6/RA on these interfaces. Can repeat.", // --- DHCP --- [DnsmasqConfKeys.DhcpAuthoritative] = "DHCP server is authoritative; required for DHCP to work.", @@ -57,6 +84,10 @@ public static class DnsmasqOptionTooltips [DnsmasqConfKeys.User] = "Run as this user after startup (requires root).", [DnsmasqConfKeys.Group] = "Run as this group after startup (requires root).", [DnsmasqConfKeys.LogFacility] = "Syslog facility for dnsmasq logs (e.g. local0, daemon).", + [DnsmasqConfKeys.LogDebug] = "Extra debug logging.", + [DnsmasqConfKeys.LogAsync] = "Asynchronous logging; optional queue size.", + [DnsmasqConfKeys.BindDynamic] = "Bind per-interface; auto-add new interfaces (Linux).", + [DnsmasqConfKeys.LocalService] = "Restrict to local network or localhost (net|host).", }.ToFrozenDictionary(); /// Returns a short tooltip for the option, or null if none is defined. diff --git a/src/DnsmasqWebUI/Infrastructure/Helpers/Config/EffectiveConfigFieldBuilder.cs b/src/DnsmasqWebUI/Infrastructure/Helpers/Config/EffectiveConfigFieldBuilder.cs index e80b2d5..f1bcae8 100644 --- a/src/DnsmasqWebUI/Infrastructure/Helpers/Config/EffectiveConfigFieldBuilder.cs +++ b/src/DnsmasqWebUI/Infrastructure/Helpers/Config/EffectiveConfigFieldBuilder.cs @@ -51,10 +51,32 @@ public static class EffectiveConfigFieldBuilder list.Add(Single(SectionResolver, DnsmasqConfKeys.StrictOrder, status, s => Config(s)?.StrictOrder, s => Sources(s)?.StrictOrder, null)); list.Add(Single(SectionResolver, DnsmasqConfKeys.NoResolv, status, s => Config(s)?.NoResolv, s => Sources(s)?.NoResolv, null)); list.Add(Single(SectionResolver, DnsmasqConfKeys.DomainNeeded, status, s => Config(s)?.DomainNeeded, s => Sources(s)?.DomainNeeded, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.AllServers, status, s => Config(s)?.AllServers, s => Sources(s)?.AllServers, null)); list.Add(Single(SectionResolver, DnsmasqConfKeys.Port, status, s => Config(s)?.Port, s => Sources(s)?.Port, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.LogQueries, status, s => Config(s)?.LogQueries, s => Sources(s)?.LogQueries, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.AuthTtl, status, s => Config(s)?.AuthTtl, s => Sources(s)?.AuthTtl, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.EdnsPacketMax, status, s => Config(s)?.EdnsPacketMax, s => Sources(s)?.EdnsPacketMax, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.QueryPort, status, s => Config(s)?.QueryPort, s => Sources(s)?.QueryPort, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.PortLimit, status, s => Config(s)?.PortLimit, s => Sources(s)?.PortLimit, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.MinPort, status, s => Config(s)?.MinPort, s => Sources(s)?.MinPort, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.MaxPort, status, s => Config(s)?.MaxPort, s => Sources(s)?.MaxPort, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.DnsLoopDetect, status, s => Config(s)?.DnsLoopDetect, s => Sources(s)?.DnsLoopDetect, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.StopDnsRebind, status, s => Config(s)?.StopDnsRebind, s => Sources(s)?.StopDnsRebind, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.RebindLocalhostOk, status, s => Config(s)?.RebindLocalhostOk, s => Sources(s)?.RebindLocalhostOk, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.ClearOnReload, status, s => Config(s)?.ClearOnReload, s => Sources(s)?.ClearOnReload, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.Filterwin2k, status, s => Config(s)?.Filterwin2k, s => Sources(s)?.Filterwin2k, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.FilterA, status, s => Config(s)?.FilterA, s => Sources(s)?.FilterA, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.FilterAaaa, status, s => Config(s)?.FilterAaaa, s => Sources(s)?.FilterAaaa, null)); + list.Add(Single(SectionResolver, DnsmasqConfKeys.LocaliseQueries, status, s => Config(s)?.LocaliseQueries, s => Sources(s)?.LocaliseQueries, null)); list.Add(Multi(SectionResolver, "server / local", status, Items(ec => ec?.ServerLocalValues, src => src?.ServerLocalValues))); + list.Add(Multi(SectionResolver, DnsmasqConfKeys.RevServer, status, Items(ec => ec?.RevServerValues, src => src?.RevServerValues))); list.Add(Multi(SectionResolver, DnsmasqConfKeys.Address, status, Items(ec => ec?.AddressValues, src => src?.AddressValues))); list.Add(Multi(SectionResolver, DnsmasqConfKeys.ResolvFile, status, Items(ec => ec?.ResolvFiles, src => src?.ResolvFiles))); + list.Add(Multi(SectionResolver, DnsmasqConfKeys.RebindDomainOk, status, Items(ec => ec?.RebindDomainOkValues, src => src?.RebindDomainOkValues))); + list.Add(Multi(SectionResolver, DnsmasqConfKeys.BogusNxdomain, status, Items(ec => ec?.BogusNxdomainValues, src => src?.BogusNxdomainValues))); + list.Add(Multi(SectionResolver, DnsmasqConfKeys.IgnoreAddress, status, Items(ec => ec?.IgnoreAddressValues, src => src?.IgnoreAddressValues))); + list.Add(Multi(SectionResolver, DnsmasqConfKeys.Alias, status, Items(ec => ec?.AliasValues, src => src?.AliasValues))); + list.Add(Multi(SectionResolver, DnsmasqConfKeys.FilterRr, status, Items(ec => ec?.FilterRrValues, src => src?.FilterRrValues))); // --- DHCP --- list.Add(Single(SectionDhcp, DnsmasqConfKeys.DhcpAuthoritative, status, s => Config(s)?.DhcpAuthoritative, s => Sources(s)?.DhcpAuthoritative, null)); @@ -67,6 +89,7 @@ public static class EffectiveConfigFieldBuilder list.Add(Multi(SectionDhcp, DnsmasqConfKeys.DhcpOption, status, Items(ec => ec?.DhcpOptionLines, src => src?.DhcpOptionLines))); // --- Cache --- + list.Add(Multi(SectionCache, DnsmasqConfKeys.CacheRr, status, Items(ec => ec?.CacheRrValues, src => src?.CacheRrValues))); list.Add(Single(SectionCache, DnsmasqConfKeys.CacheSize, status, s => Config(s)?.CacheSize, s => Sources(s)?.CacheSize, null)); list.Add(Single(SectionCache, DnsmasqConfKeys.LocalTtl, status, s => Config(s)?.LocalTtl, s => Sources(s)?.LocalTtl, null)); list.Add(Single(SectionCache, DnsmasqConfKeys.NoNegcache, status, s => Config(s)?.NoNegcache, s => Sources(s)?.NoNegcache, null)); @@ -78,9 +101,17 @@ public static class EffectiveConfigFieldBuilder // --- Process & networking --- list.Add(Single(SectionProcess, DnsmasqConfKeys.NoPoll, status, s => Config(s)?.NoPoll, s => Sources(s)?.NoPoll, null)); list.Add(Single(SectionProcess, DnsmasqConfKeys.BindInterfaces, status, s => Config(s)?.BindInterfaces, s => Sources(s)?.BindInterfaces, null)); + list.Add(Single(SectionProcess, DnsmasqConfKeys.BindDynamic, status, s => Config(s)?.BindDynamic, s => Sources(s)?.BindDynamic, null)); + list.Add(Single(SectionProcess, DnsmasqConfKeys.LogDebug, status, s => Config(s)?.LogDebug, s => Sources(s)?.LogDebug, null)); + list.Add(Single(SectionProcess, DnsmasqConfKeys.LogAsync, status, s => Config(s)?.LogAsync, s => Sources(s)?.LogAsync, null)); + list.Add(Single(SectionProcess, DnsmasqConfKeys.LocalService, status, s => Config(s)?.LocalService, s => Sources(s)?.LocalService, null)); list.Add(Multi(SectionProcess, DnsmasqConfKeys.Interface, status, Items(ec => ec?.Interfaces, src => src?.Interfaces))); list.Add(Multi(SectionProcess, DnsmasqConfKeys.ListenAddress, status, Items(ec => ec?.ListenAddresses, src => src?.ListenAddresses))); list.Add(Multi(SectionProcess, DnsmasqConfKeys.ExceptInterface, status, Items(ec => ec?.ExceptInterfaces, src => src?.ExceptInterfaces))); + list.Add(Multi(SectionProcess, DnsmasqConfKeys.AuthServer, status, Items(ec => ec?.AuthServerValues, src => src?.AuthServerValues))); + list.Add(Multi(SectionProcess, DnsmasqConfKeys.NoDhcpInterface, status, Items(ec => ec?.NoDhcpInterfaceValues, src => src?.NoDhcpInterfaceValues))); + list.Add(Multi(SectionProcess, DnsmasqConfKeys.NoDhcpv4Interface, status, Items(ec => ec?.NoDhcpv4InterfaceValues, src => src?.NoDhcpv4InterfaceValues))); + list.Add(Multi(SectionProcess, DnsmasqConfKeys.NoDhcpv6Interface, status, Items(ec => ec?.NoDhcpv6InterfaceValues, src => src?.NoDhcpv6InterfaceValues))); list.Add(Single(SectionProcess, DnsmasqConfKeys.PidFile, status, s => Config(s)?.PidFilePath, s => Sources(s)?.PidFilePath, null)); list.Add(Single(SectionProcess, DnsmasqConfKeys.User, status, s => Config(s)?.User, s => Sources(s)?.User, null)); list.Add(Single(SectionProcess, DnsmasqConfKeys.Group, status, s => Config(s)?.Group, s => Sources(s)?.Group, null)); diff --git a/src/DnsmasqWebUI/Infrastructure/Services/ConfigSetCache.cs b/src/DnsmasqWebUI/Infrastructure/Services/ConfigSetCache.cs index 51802d4..59ff5d3 100644 --- a/src/DnsmasqWebUI/Infrastructure/Services/ConfigSetCache.cs +++ b/src/DnsmasqWebUI/Infrastructure/Services/ConfigSetCache.cs @@ -219,6 +219,7 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable var noHosts = DnsmasqConfIncludeParser.GetNoHostsFromConfigFiles(paths, pathToLines); var addnHosts = DnsmasqConfIncludeParser.GetAddnHostsPathsFromConfigFiles(paths, pathToLines); var serverLocal = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.ServerLocalKeys); + var revServer = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.RevServer); var addressValues = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.Address); var interfaces = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.Interface); var listenAddresses = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.ListenAddress); @@ -227,15 +228,36 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable var dhcpHostLines = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.DhcpHost); var dhcpOptionLines = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.DhcpOption); var resolvFiles = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.ResolvFile); + var rebindDomainOk = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.RebindDomainOk); + var bogusNxdomain = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.BogusNxdomain); + var ignoreAddress = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.IgnoreAddress); + var alias = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.Alias); + var filterRr = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.FilterRr); + var cacheRr = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.CacheRr); + var authServer = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.AuthServer); + var noDhcpInterface = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.NoDhcpInterface); + var noDhcpv4Interface = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.NoDhcpv4Interface); + var noDhcpv6Interface = DnsmasqConfIncludeParser.GetMultiValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.NoDhcpv6Interface); var expandHosts = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.ExpandHosts); var bogusPriv = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.BogusPriv); var strictOrder = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.StrictOrder); + var allServers = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.AllServers); var noResolv = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.NoResolv); var domainNeeded = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.DomainNeeded); var noPoll = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.NoPoll); var bindInterfaces = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.BindInterfaces); + var bindDynamic = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.BindDynamic); var noNegcache = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.NoNegcache); + var dnsLoopDetect = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.DnsLoopDetect); + var stopDnsRebind = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.StopDnsRebind); + var rebindLocalhostOk = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.RebindLocalhostOk); + var clearOnReload = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.ClearOnReload); + var filterwin2k = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.Filterwin2k); + var filterA = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.FilterA); + var filterAaaa = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.FilterAaaa); + var localiseQueries = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.LocaliseQueries); + var logDebug = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.LogDebug); var dhcpAuthoritative = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.DhcpAuthoritative); var leasefileRo = DnsmasqConfIncludeParser.GetFlagFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.LeasefileRo); @@ -255,6 +277,24 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable var group = string.IsNullOrWhiteSpace(groupVal) ? null : groupVal.Trim(); var (logFacVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.LogFacility); var logFacility = string.IsNullOrWhiteSpace(logFacVal) ? null : logFacVal.Trim(); + var (logQueriesVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.LogQueries); + var logQueries = string.IsNullOrWhiteSpace(logQueriesVal) ? null : logQueriesVal.Trim(); + var (authTtlVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.AuthTtl); + var authTtl = TryParseInt(authTtlVal); + var (ednsPacketMaxVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.EdnsPacketMax); + var ednsPacketMax = TryParseInt(ednsPacketMaxVal); + var (queryPortVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.QueryPort); + var queryPort = TryParseInt(queryPortVal); + var (portLimitVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.PortLimit); + var portLimit = TryParseInt(portLimitVal); + var (minPortVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.MinPort); + var minPort = TryParseInt(minPortVal); + var (maxPortVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.MaxPort); + var maxPort = TryParseInt(maxPortVal); + var (logAsyncVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.LogAsync); + var logAsync = string.IsNullOrWhiteSpace(logAsyncVal) ? null : logAsyncVal.Trim(); + var (localServiceVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.LocalService); + var localService = string.IsNullOrWhiteSpace(localServiceVal) ? null : localServiceVal.Trim(); var (leaseMaxVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.DhcpLeaseMax); var dhcpLeaseMax = TryParseInt(leaseMaxVal); var (negTtlVal, _) = DnsmasqConfIncludeParser.GetLastValueFromConfigFiles(paths, pathToLines, DnsmasqConfKeys.NegTtl); @@ -270,9 +310,12 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable return new EffectiveDnsmasqConfig( noHosts, addnHosts, - serverLocal, addressValues, interfaces, listenAddresses, exceptInterfaces, dhcpRanges, dhcpHostLines, dhcpOptionLines, resolvFiles, - expandHosts, bogusPriv, strictOrder, noResolv, domainNeeded, noPoll, bindInterfaces, noNegcache, dhcpAuthoritative, leasefileRo, - dhcpLeaseFilePath, cacheSize, port, localTtl, pidFilePath, user, group, logFacility, dhcpLeaseMax, + serverLocal, revServer, addressValues, interfaces, listenAddresses, exceptInterfaces, dhcpRanges, dhcpHostLines, dhcpOptionLines, resolvFiles, + rebindDomainOk, bogusNxdomain, ignoreAddress, alias, filterRr, cacheRr, authServer, noDhcpInterface, noDhcpv4Interface, noDhcpv6Interface, + expandHosts, bogusPriv, strictOrder, allServers, noResolv, domainNeeded, noPoll, bindInterfaces, bindDynamic, noNegcache, + dnsLoopDetect, stopDnsRebind, rebindLocalhostOk, clearOnReload, filterwin2k, filterA, filterAaaa, localiseQueries, logDebug, dhcpAuthoritative, leasefileRo, + dhcpLeaseFilePath, cacheSize, port, localTtl, pidFilePath, user, group, logFacility, logQueries, + authTtl, ednsPacketMax, queryPort, portLimit, minPort, maxPort, logAsync, localService, dhcpLeaseMax, negTtl, maxTtl, maxCacheTtl, minCacheTtl, dhcpTtl ); } @@ -282,6 +325,7 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable var (_, noHostsSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NoHosts, managedFilePath); var addnHostsWithSource = DnsmasqConfIncludeParser.GetAddnHostsPathsFromConfigFilesWithSource(paths, pathToLines, managedFilePath); var serverLocalWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.ServerLocalKeys, managedFilePath); + var revServerWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.RevServer, managedFilePath); var addressWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.Address, managedFilePath); var interfacesWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.Interface, managedFilePath); var listenAddressesWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.ListenAddress, managedFilePath); @@ -290,15 +334,36 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable var dhcpHostLinesWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.DhcpHost, managedFilePath); var dhcpOptionLinesWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.DhcpOption, managedFilePath); var resolvFilesWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.ResolvFile, managedFilePath); + var rebindDomainOkWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.RebindDomainOk, managedFilePath); + var bogusNxdomainWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.BogusNxdomain, managedFilePath); + var ignoreAddressWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.IgnoreAddress, managedFilePath); + var aliasWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.Alias, managedFilePath); + var filterRrWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.FilterRr, managedFilePath); + var cacheRrWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.CacheRr, managedFilePath); + var authServerWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.AuthServer, managedFilePath); + var noDhcpInterfaceWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NoDhcpInterface, managedFilePath); + var noDhcpv4InterfaceWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NoDhcpv4Interface, managedFilePath); + var noDhcpv6InterfaceWithSource = DnsmasqConfIncludeParser.GetMultiValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NoDhcpv6Interface, managedFilePath); var (_, expandHostsSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.ExpandHosts, managedFilePath); var (_, bogusPrivSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.BogusPriv, managedFilePath); var (_, strictOrderSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.StrictOrder, managedFilePath); + var (_, allServersSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.AllServers, managedFilePath); var (_, noResolvSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NoResolv, managedFilePath); var (_, domainNeededSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.DomainNeeded, managedFilePath); var (_, noPollSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NoPoll, managedFilePath); var (_, bindInterfacesSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.BindInterfaces, managedFilePath); + var (_, bindDynamicSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.BindDynamic, managedFilePath); var (_, noNegcacheSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NoNegcache, managedFilePath); + var (_, dnsLoopDetectSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.DnsLoopDetect, managedFilePath); + var (_, stopDnsRebindSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.StopDnsRebind, managedFilePath); + var (_, rebindLocalhostOkSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.RebindLocalhostOk, managedFilePath); + var (_, clearOnReloadSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.ClearOnReload, managedFilePath); + var (_, filterwin2kSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.Filterwin2k, managedFilePath); + var (_, filterASource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.FilterA, managedFilePath); + var (_, filterAaaaSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.FilterAaaa, managedFilePath); + var (_, localiseQueriesSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.LocaliseQueries, managedFilePath); + var (_, logDebugSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.LogDebug, managedFilePath); var (_, dhcpAuthoritativeSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.DhcpAuthoritative, managedFilePath); var (_, leasefileRoSource) = DnsmasqConfIncludeParser.GetFlagFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.LeasefileRo, managedFilePath); @@ -310,6 +375,15 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable var (_, userSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.User, managedFilePath); var (_, groupSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.Group, managedFilePath); var (_, logFacilitySource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.LogFacility, managedFilePath); + var (_, logQueriesSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.LogQueries, managedFilePath); + var (_, authTtlSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.AuthTtl, managedFilePath); + var (_, ednsPacketMaxSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.EdnsPacketMax, managedFilePath); + var (_, queryPortSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.QueryPort, managedFilePath); + var (_, portLimitSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.PortLimit, managedFilePath); + var (_, minPortSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.MinPort, managedFilePath); + var (_, maxPortSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.MaxPort, managedFilePath); + var (_, logAsyncSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.LogAsync, managedFilePath); + var (_, localServiceSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.LocalService, managedFilePath); var (_, dhcpLeaseMaxSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.DhcpLeaseMax, managedFilePath); var (_, negTtlSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.NegTtl, managedFilePath); var (_, maxTtlSource) = DnsmasqConfIncludeParser.GetLastValueFromConfigFilesWithSource(paths, pathToLines, DnsmasqConfKeys.MaxTtl, managedFilePath); @@ -320,6 +394,7 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable return new EffectiveConfigSources( noHostsSource, addnHostsWithSource.Select(t => new PathWithSource(t.Path, t.Source)).ToList(), serverLocalWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + revServerWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), addressWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), interfacesWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), listenAddressesWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), @@ -328,10 +403,22 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable dhcpHostLinesWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), dhcpOptionLinesWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), resolvFilesWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), - expandHostsSource, bogusPrivSource, strictOrderSource, noResolvSource, domainNeededSource, noPollSource, - bindInterfacesSource, noNegcacheSource, dhcpAuthoritativeSource, leasefileRoSource, + rebindDomainOkWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + bogusNxdomainWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + ignoreAddressWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + aliasWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + filterRrWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + cacheRrWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + authServerWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + noDhcpInterfaceWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + noDhcpv4InterfaceWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + noDhcpv6InterfaceWithSource.Select(t => new ValueWithSource(t.Value, t.Source)).ToList(), + expandHostsSource, bogusPrivSource, strictOrderSource, allServersSource, noResolvSource, domainNeededSource, noPollSource, + bindInterfacesSource, bindDynamicSource, noNegcacheSource, dnsLoopDetectSource, stopDnsRebindSource, rebindLocalhostOkSource, clearOnReloadSource, + filterwin2kSource, filterASource, filterAaaaSource, localiseQueriesSource, logDebugSource, dhcpAuthoritativeSource, leasefileRoSource, dhcpLeaseFilePathSource, cacheSizeSource, portSource, localTtlSource, pidFilePathSource, userSource, groupSource, - logFacilitySource, dhcpLeaseMaxSource, negTtlSource, maxTtlSource, maxCacheTtlSource, minCacheTtlSource, dhcpTtlSource + logFacilitySource, logQueriesSource, authTtlSource, ednsPacketMaxSource, queryPortSource, portLimitSource, minPortSource, maxPortSource, logAsyncSource, localServiceSource, + dhcpLeaseMaxSource, negTtlSource, maxTtlSource, maxCacheTtlSource, minCacheTtlSource, dhcpTtlSource ); } @@ -370,27 +457,37 @@ public sealed class ConfigSetCache : IConfigSetCache, IDisposable private static EffectiveDnsmasqConfig CreateDefaultEffectiveConfig() => new( NoHosts: false, AddnHostsPaths: Array.Empty(), - ServerLocalValues: Array.Empty(), AddressValues: Array.Empty(), Interfaces: Array.Empty(), + ServerLocalValues: Array.Empty(), RevServerValues: Array.Empty(), AddressValues: Array.Empty(), Interfaces: Array.Empty(), ListenAddresses: Array.Empty(), ExceptInterfaces: Array.Empty(), DhcpRanges: Array.Empty(), DhcpHostLines: Array.Empty(), DhcpOptionLines: Array.Empty(), ResolvFiles: Array.Empty(), - ExpandHosts: false, BogusPriv: false, StrictOrder: false, NoResolv: false, DomainNeeded: false, NoPoll: false, - BindInterfaces: false, NoNegcache: false, DhcpAuthoritative: false, LeasefileRo: false, + RebindDomainOkValues: Array.Empty(), BogusNxdomainValues: Array.Empty(), IgnoreAddressValues: Array.Empty(), + AliasValues: Array.Empty(), FilterRrValues: Array.Empty(), CacheRrValues: Array.Empty(), + AuthServerValues: Array.Empty(), NoDhcpInterfaceValues: Array.Empty(), NoDhcpv4InterfaceValues: Array.Empty(), NoDhcpv6InterfaceValues: Array.Empty(), + ExpandHosts: false, BogusPriv: false, StrictOrder: false, AllServers: false, NoResolv: false, DomainNeeded: false, NoPoll: false, + BindInterfaces: false, BindDynamic: false, NoNegcache: false, DnsLoopDetect: false, StopDnsRebind: false, RebindLocalhostOk: false, ClearOnReload: false, + Filterwin2k: false, FilterA: false, FilterAaaa: false, LocaliseQueries: false, LogDebug: false, DhcpAuthoritative: false, LeasefileRo: false, DhcpLeaseFilePath: null, CacheSize: null, Port: null, LocalTtl: null, PidFilePath: null, User: null, Group: null, - LogFacility: null, DhcpLeaseMax: null, NegTtl: null, MaxTtl: null, MaxCacheTtl: null, MinCacheTtl: null, DhcpTtl: null + LogFacility: null, LogQueries: null, AuthTtl: null, EdnsPacketMax: null, QueryPort: null, PortLimit: null, MinPort: null, MaxPort: null, LogAsync: null, LocalService: null, + DhcpLeaseMax: null, NegTtl: null, MaxTtl: null, MaxCacheTtl: null, MinCacheTtl: null, DhcpTtl: null ); private static EffectiveConfigSources CreateDefaultEffectiveConfigSources() => new( NoHosts: null, AddnHostsPaths: Array.Empty(), - ServerLocalValues: Array.Empty(), AddressValues: Array.Empty(), + ServerLocalValues: Array.Empty(), RevServerValues: Array.Empty(), AddressValues: Array.Empty(), Interfaces: Array.Empty(), ListenAddresses: Array.Empty(), ExceptInterfaces: Array.Empty(), DhcpRanges: Array.Empty(), DhcpHostLines: Array.Empty(), DhcpOptionLines: Array.Empty(), ResolvFiles: Array.Empty(), - ExpandHosts: null, BogusPriv: null, StrictOrder: null, NoResolv: null, DomainNeeded: null, NoPoll: null, - BindInterfaces: null, NoNegcache: null, DhcpAuthoritative: null, LeasefileRo: null, + RebindDomainOkValues: Array.Empty(), BogusNxdomainValues: Array.Empty(), IgnoreAddressValues: Array.Empty(), + AliasValues: Array.Empty(), FilterRrValues: Array.Empty(), CacheRrValues: Array.Empty(), + AuthServerValues: Array.Empty(), NoDhcpInterfaceValues: Array.Empty(), NoDhcpv4InterfaceValues: Array.Empty(), NoDhcpv6InterfaceValues: Array.Empty(), + ExpandHosts: null, BogusPriv: null, StrictOrder: null, AllServers: null, NoResolv: null, DomainNeeded: null, NoPoll: null, + BindInterfaces: null, BindDynamic: null, NoNegcache: null, DnsLoopDetect: null, StopDnsRebind: null, RebindLocalhostOk: null, ClearOnReload: null, + Filterwin2k: null, FilterA: null, FilterAaaa: null, LocaliseQueries: null, LogDebug: null, DhcpAuthoritative: null, LeasefileRo: null, DhcpLeaseFilePath: null, CacheSize: null, Port: null, LocalTtl: null, PidFilePath: null, User: null, Group: null, - LogFacility: null, DhcpLeaseMax: null, NegTtl: null, MaxTtl: null, MaxCacheTtl: null, MinCacheTtl: null, DhcpTtl: null + LogFacility: null, LogQueries: null, AuthTtl: null, EdnsPacketMax: null, QueryPort: null, PortLimit: null, MinPort: null, MaxPort: null, LogAsync: null, LocalService: null, + DhcpLeaseMax: null, NegTtl: null, MaxTtl: null, MaxCacheTtl: null, MinCacheTtl: null, DhcpTtl: null ); private static int? TryParseInt(string? value) diff --git a/src/DnsmasqWebUI/Infrastructure/Services/EffectiveConfigRenderFragmentRegistry.cs b/src/DnsmasqWebUI/Infrastructure/Services/EffectiveConfigRenderFragmentRegistry.cs index 80b24fc..0480900 100644 --- a/src/DnsmasqWebUI/Infrastructure/Services/EffectiveConfigRenderFragmentRegistry.cs +++ b/src/DnsmasqWebUI/Infrastructure/Services/EffectiveConfigRenderFragmentRegistry.cs @@ -25,11 +25,22 @@ public class EffectiveConfigRenderFragmentRegistry : IEffectiveConfigRenderFragm RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.ExpandHosts); RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.BogusPriv); RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.StrictOrder); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.AllServers); RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.NoResolv); RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.DomainNeeded); RegisterFlag(EffectiveConfigFieldBuilder.SectionCache, DnsmasqConfKeys.NoNegcache); RegisterFlag(EffectiveConfigFieldBuilder.SectionProcess, DnsmasqConfKeys.NoPoll); RegisterFlag(EffectiveConfigFieldBuilder.SectionProcess, DnsmasqConfKeys.BindInterfaces); + RegisterFlag(EffectiveConfigFieldBuilder.SectionProcess, DnsmasqConfKeys.BindDynamic); + RegisterFlag(EffectiveConfigFieldBuilder.SectionProcess, DnsmasqConfKeys.LogDebug); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.DnsLoopDetect); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.StopDnsRebind); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.RebindLocalhostOk); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.ClearOnReload); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.Filterwin2k); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.FilterA); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.FilterAaaa); + RegisterFlag(EffectiveConfigFieldBuilder.SectionResolver, DnsmasqConfKeys.LocaliseQueries); RegisterFlag(EffectiveConfigFieldBuilder.SectionDhcp, DnsmasqConfKeys.DhcpAuthoritative); RegisterFlag(EffectiveConfigFieldBuilder.SectionDhcp, DnsmasqConfKeys.LeasefileRo); } diff --git a/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveConfigSources.cs b/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveConfigSources.cs index b715fe6..572d768 100644 --- a/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveConfigSources.cs +++ b/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveConfigSources.cs @@ -16,6 +16,7 @@ public record EffectiveConfigSources( // --- Multi-value (ARG_DUP): source per value --- IReadOnlyList ServerLocalValues, + IReadOnlyList RevServerValues, IReadOnlyList AddressValues, IReadOnlyList Interfaces, IReadOnlyList ListenAddresses, @@ -24,16 +25,37 @@ public record EffectiveConfigSources( IReadOnlyList DhcpHostLines, IReadOnlyList DhcpOptionLines, IReadOnlyList ResolvFiles, + IReadOnlyList RebindDomainOkValues, + IReadOnlyList BogusNxdomainValues, + IReadOnlyList IgnoreAddressValues, + IReadOnlyList AliasValues, + IReadOnlyList FilterRrValues, + IReadOnlyList CacheRrValues, + IReadOnlyList AuthServerValues, + IReadOnlyList NoDhcpInterfaceValues, + IReadOnlyList NoDhcpv4InterfaceValues, + IReadOnlyList NoDhcpv6InterfaceValues, // --- Flags (set if any occurrence; source = first file that set it, so we know if readonly) --- ConfigValueSource? ExpandHosts, ConfigValueSource? BogusPriv, ConfigValueSource? StrictOrder, + ConfigValueSource? AllServers, ConfigValueSource? NoResolv, ConfigValueSource? DomainNeeded, ConfigValueSource? NoPoll, ConfigValueSource? BindInterfaces, + ConfigValueSource? BindDynamic, ConfigValueSource? NoNegcache, + ConfigValueSource? DnsLoopDetect, + ConfigValueSource? StopDnsRebind, + ConfigValueSource? RebindLocalhostOk, + ConfigValueSource? ClearOnReload, + ConfigValueSource? Filterwin2k, + ConfigValueSource? FilterA, + ConfigValueSource? FilterAaaa, + ConfigValueSource? LocaliseQueries, + ConfigValueSource? LogDebug, ConfigValueSource? DhcpAuthoritative, ConfigValueSource? LeasefileRo, @@ -46,6 +68,15 @@ public record EffectiveConfigSources( ConfigValueSource? User, ConfigValueSource? Group, ConfigValueSource? LogFacility, + ConfigValueSource? LogQueries, + ConfigValueSource? AuthTtl, + ConfigValueSource? EdnsPacketMax, + ConfigValueSource? QueryPort, + ConfigValueSource? PortLimit, + ConfigValueSource? MinPort, + ConfigValueSource? MaxPort, + ConfigValueSource? LogAsync, + ConfigValueSource? LocalService, ConfigValueSource? DhcpLeaseMax, ConfigValueSource? NegTtl, ConfigValueSource? MaxTtl, diff --git a/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveDnsmasqConfig.cs b/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveDnsmasqConfig.cs index 5846d0d..cbbd0ce 100644 --- a/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveDnsmasqConfig.cs +++ b/src/DnsmasqWebUI/Models/Dnsmasq/EffectiveConfig/EffectiveDnsmasqConfig.cs @@ -20,6 +20,7 @@ public record EffectiveDnsmasqConfig( // --- Multi-value (ARG_DUP): all occurrences in order --- IReadOnlyList ServerLocalValues, + IReadOnlyList RevServerValues, IReadOnlyList AddressValues, IReadOnlyList Interfaces, IReadOnlyList ListenAddresses, @@ -28,16 +29,37 @@ public record EffectiveDnsmasqConfig( IReadOnlyList DhcpHostLines, IReadOnlyList DhcpOptionLines, IReadOnlyList ResolvFiles, + IReadOnlyList RebindDomainOkValues, + IReadOnlyList BogusNxdomainValues, + IReadOnlyList IgnoreAddressValues, + IReadOnlyList AliasValues, + IReadOnlyList FilterRrValues, + IReadOnlyList CacheRrValues, + IReadOnlyList AuthServerValues, + IReadOnlyList NoDhcpInterfaceValues, + IReadOnlyList NoDhcpv4InterfaceValues, + IReadOnlyList NoDhcpv6InterfaceValues, // --- Boolean flags (set if any file contains the option) --- bool ExpandHosts, bool BogusPriv, bool StrictOrder, + bool AllServers, bool NoResolv, bool DomainNeeded, bool NoPoll, bool BindInterfaces, + bool BindDynamic, bool NoNegcache, + bool DnsLoopDetect, + bool StopDnsRebind, + bool RebindLocalhostOk, + bool ClearOnReload, + bool Filterwin2k, + bool FilterA, + bool FilterAaaa, + bool LocaliseQueries, + bool LogDebug, bool DhcpAuthoritative, bool LeasefileRo, @@ -50,6 +72,15 @@ public record EffectiveDnsmasqConfig( string? User, string? Group, string? LogFacility, + string? LogQueries, + int? AuthTtl, + int? EdnsPacketMax, + int? QueryPort, + int? PortLimit, + int? MinPort, + int? MaxPort, + string? LogAsync, + string? LocalService, int? DhcpLeaseMax, int? NegTtl, int? MaxTtl,