diff --git a/internal/dnsforward/dns.go b/internal/dnsforward/dns.go index 19d54d91..e049bef0 100644 --- a/internal/dnsforward/dns.go +++ b/internal/dnsforward/dns.go @@ -260,9 +260,8 @@ func (s *Server) processDDRQuery(ctx *dnsContext) (rc resultCode) { } if question.Name == ddrHostFQDN { - // TODO(a.garipov): Check DoQ support in next RFC drafts. - if s.dnsProxy.TLSListenAddr == nil && s.dnsProxy.HTTPSListenAddr == nil || - question.Qtype != dns.TypeSVCB { + if s.dnsProxy.TLSListenAddr == nil && s.dnsProxy.HTTPSListenAddr == nil && + s.dnsProxy.QUICListenAddr == nil || question.Qtype != dns.TypeSVCB { d.Res = s.makeResponse(d.Req) return resultCodeFinish @@ -314,6 +313,22 @@ func (s *Server) makeDDRResponse(req *dns.Msg) (resp *dns.Msg) { resp.Answer = append(resp.Answer, ans) } + for _, addr := range s.dnsProxy.QUICListenAddr { + values := []dns.SVCBKeyValue{ + &dns.SVCBAlpn{Alpn: []string{"doq"}}, + &dns.SVCBPort{Port: uint16(addr.Port)}, + } + + ans := &dns.SVCB{ + Hdr: s.hdr(req, dns.TypeSVCB), + Priority: 3, + Target: domainName, + Value: values, + } + + resp.Answer = append(resp.Answer, ans) + } + return resp } diff --git a/internal/dnsforward/dns_test.go b/internal/dnsforward/dns_test.go index 8ab7501c..b40b7bc2 100644 --- a/internal/dnsforward/dns_test.go +++ b/internal/dnsforward/dns_test.go @@ -36,6 +36,15 @@ func TestServer_ProcessDDRQuery(t *testing.T) { }, } + doqSVCB := &dns.SVCB{ + Priority: 3, + Target: ddrTestDomainName, + Value: []dns.SVCBKeyValue{ + &dns.SVCBAlpn{Alpn: []string{"doq"}}, + &dns.SVCBPort{Port: 8042}, + }, + } + testCases := []struct { name string host string @@ -43,6 +52,7 @@ func TestServer_ProcessDDRQuery(t *testing.T) { wantRes resultCode portDoH int portDoT int + portDoQ int qtype uint16 ddrEnabled bool }{{ @@ -88,6 +98,14 @@ func TestServer_ProcessDDRQuery(t *testing.T) { qtype: dns.TypeSVCB, ddrEnabled: true, portDoH: 8044, + }, { + name: "doq", + wantRes: resultCodeFinish, + want: []*dns.SVCB{doqSVCB}, + host: ddrHostFQDN, + qtype: dns.TypeSVCB, + ddrEnabled: true, + portDoQ: 8042, }, { name: "dot_doh", wantRes: resultCodeFinish, @@ -101,7 +119,7 @@ func TestServer_ProcessDDRQuery(t *testing.T) { for _, tc := range testCases { t.Run(tc.name, func(t *testing.T) { - s := prepareTestServer(t, tc.portDoH, tc.portDoT, tc.ddrEnabled) + s := prepareTestServer(t, tc.portDoH, tc.portDoT, tc.portDoQ, tc.ddrEnabled) req := createTestMessageWithType(tc.host, tc.qtype) @@ -130,7 +148,7 @@ func TestServer_ProcessDDRQuery(t *testing.T) { } } -func prepareTestServer(t *testing.T, portDoH, portDoT int, ddrEnabled bool) (s *Server) { +func prepareTestServer(t *testing.T, portDoH, portDoT, portDoQ int, ddrEnabled bool) (s *Server) { t.Helper() proxyConf := proxy.Config{} @@ -143,6 +161,10 @@ func prepareTestServer(t *testing.T, portDoH, portDoT int, ddrEnabled bool) (s * proxyConf.TLSListenAddr = []*net.TCPAddr{{Port: portDoT}} } + if portDoQ > 0 { + proxyConf.QUICListenAddr = []*net.UDPAddr{{Port: portDoQ}} + } + s = &Server{ dnsProxy: &proxy.Proxy{ Config: proxyConf,