From 8d6ea91f35ef649e4b69989a03af90cb3f6ddd96 Mon Sep 17 00:00:00 2001 From: Cuong Manh Le Date: Mon, 14 Apr 2025 16:51:38 +0700 Subject: [PATCH] Allowing bootstrap IPs for ControlD sub-domains So protocol which uses sub-domain like doq/dot could be bootstrap in case of no DNS available. --- config.go | 12 +++++------ config_internal_test.go | 45 +++++++++++++++++++++++++++++++---------- 2 files changed, 40 insertions(+), 17 deletions(-) diff --git a/config.go b/config.go index f208f0d..626fc32 100644 --- a/config.go +++ b/config.go @@ -446,7 +446,7 @@ func (uc *UpstreamConfig) SetupBootstrapIP() { uc.bootstrapIPs = uc.bootstrapIPs[:n] if len(uc.bootstrapIPs) == 0 { uc.bootstrapIPs = bootstrapIPsFromControlDDomain(uc.Domain) - ProxyLogger.Load().Warn().Msgf("no bootstrap IPs found for %q, fallback to direct IPs", uc.Domain) + ProxyLogger.Load().Warn().Msgf("no record found for %q, lookup from direct IP table", uc.Domain) } } if len(uc.bootstrapIPs) > 0 { @@ -951,14 +951,14 @@ func (uc *UpstreamConfig) String() string { // bootstrapIPsFromControlDDomain returns bootstrap IPs for ControlD domain. func bootstrapIPsFromControlDDomain(domain string) []string { - switch domain { - case PremiumDnsDomain: + switch { + case dns.IsSubDomain(PremiumDnsDomain, domain): return []string{PremiumDNSBoostrapIP, PremiumDNSBoostrapIPv6} - case FreeDnsDomain: + case dns.IsSubDomain(FreeDnsDomain, domain): return []string{FreeDNSBoostrapIP, FreeDNSBoostrapIPv6} - case premiumDnsDomainDev: + case dns.IsSubDomain(premiumDnsDomainDev, domain): return []string{premiumDNSBoostrapIP, premiumDNSBoostrapIPv6} - case freeDnsDomainDev: + case dns.IsSubDomain(freeDnsDomainDev, domain): return []string{freeDNSBoostrapIP, freeDNSBoostrapIPv6} } return nil diff --git a/config_internal_test.go b/config_internal_test.go index 7695eb5..3d1f0b7 100644 --- a/config_internal_test.go +++ b/config_internal_test.go @@ -8,19 +8,42 @@ import ( ) func TestUpstreamConfig_SetupBootstrapIP(t *testing.T) { - uc := &UpstreamConfig{ - Name: "test", - Type: ResolverTypeDOH, - Endpoint: "https://freedns.controld.com/p2", - Timeout: 5000, + tests := []struct { + name string + uc *UpstreamConfig + }{ + { + name: "doh/doh3", + uc: &UpstreamConfig{ + Name: "doh", + Type: ResolverTypeDOH, + Endpoint: "https://freedns.controld.com/p2", + Timeout: 5000, + }, + }, + { + name: "doq/dot", + uc: &UpstreamConfig{ + Name: "dot", + Type: ResolverTypeDOT, + Endpoint: "p2.freedns.controld.com", + Timeout: 5000, + }, + }, } - uc.Init() - uc.SetupBootstrapIP() - if len(uc.bootstrapIPs) == 0 { - t.Log(defaultNameservers()) - t.Fatal("could not bootstrap ip without bootstrap DNS") + for _, tc := range tests { + tc := tc + t.Run(tc.name, func(t *testing.T) { + t.Parallel() + tc.uc.Init() + tc.uc.SetupBootstrapIP() + if len(tc.uc.bootstrapIPs) == 0 { + t.Log(defaultNameservers()) + t.Fatalf("could not bootstrap ip: %s", tc.uc.String()) + } + }) } - t.Log(uc) + } func TestUpstreamConfig_Init(t *testing.T) {