Merge pull request #47485 from vvoland/vendor-dns
vendor: github.com/miekg/dns v1.1.57
This commit is contained in:
commit
046827c657
38 changed files with 1837 additions and 796 deletions
|
@ -57,7 +57,7 @@ require (
|
|||
github.com/hashicorp/serf v0.8.5
|
||||
github.com/ishidawataru/sctp v0.0.0-20230406120618-7ff4192f6ff2
|
||||
github.com/klauspost/compress v1.17.4
|
||||
github.com/miekg/dns v1.1.43
|
||||
github.com/miekg/dns v1.1.57
|
||||
github.com/mistifyio/go-zfs/v3 v3.0.1
|
||||
github.com/mitchellh/copystructure v1.2.0
|
||||
github.com/moby/buildkit v0.13.0-rc3
|
||||
|
|
|
@ -458,8 +458,8 @@ github.com/matttproud/golang_protobuf_extensions v1.0.4 h1:mmDVorXM7PCGKw94cs5zk
|
|||
github.com/matttproud/golang_protobuf_extensions v1.0.4/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4=
|
||||
github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
|
||||
github.com/miekg/dns v1.1.26/go.mod h1:bPDLeHnStXmXAq1m/Ch/hvfNHr14JKNPMBo3VZKjuso=
|
||||
github.com/miekg/dns v1.1.43 h1:JKfpVSCB84vrAmHzyrsxB5NAr5kLoMXZArPSw7Qlgyg=
|
||||
github.com/miekg/dns v1.1.43/go.mod h1:+evo5L0630/F6ca/Z9+GAqzhjGyn8/c+TBaOyfEl0V4=
|
||||
github.com/miekg/dns v1.1.57 h1:Jzi7ApEIzwEPLHWRcafCN9LZSBbqQpxjt/wpgvg7wcM=
|
||||
github.com/miekg/dns v1.1.57/go.mod h1:uqRjCRUuEAA6qsOiJvDd+CFo/vW+y5WR6SNmHE55hZk=
|
||||
github.com/mistifyio/go-zfs/v3 v3.0.1 h1:YaoXgBePoMA12+S1u/ddkv+QqxcfiZK4prI6HPnkFiU=
|
||||
github.com/mistifyio/go-zfs/v3 v3.0.1/go.mod h1:CzVgeB0RvF2EGzQnytKVvVSDwmKJXxkOTUGbNrTja/k=
|
||||
github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc=
|
||||
|
@ -918,7 +918,6 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w
|
|||
golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210303074136-134d130e1a04/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210403161142-5e06dd20ab57/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
|
|
49
vendor/github.com/miekg/dns/LICENSE
generated
vendored
49
vendor/github.com/miekg/dns/LICENSE
generated
vendored
|
@ -1,30 +1,29 @@
|
|||
Copyright (c) 2009 The Go Authors. All rights reserved.
|
||||
BSD 3-Clause License
|
||||
|
||||
Copyright (c) 2009, The Go Authors. Extensions copyright (c) 2011, Miek Gieben.
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are
|
||||
met:
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
|
||||
* Redistributions of source code must retain the above copyright
|
||||
notice, this list of conditions and the following disclaimer.
|
||||
* Redistributions in binary form must reproduce the above
|
||||
copyright notice, this list of conditions and the following disclaimer
|
||||
in the documentation and/or other materials provided with the
|
||||
distribution.
|
||||
* Neither the name of Google Inc. nor the names of its
|
||||
contributors may be used to endorse or promote products derived from
|
||||
this software without specific prior written permission.
|
||||
1. Redistributions of source code must retain the above copyright notice, this
|
||||
list of conditions and the following disclaimer.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
3. Neither the name of the copyright holder nor the names of its
|
||||
contributors may be used to endorse or promote products derived from
|
||||
this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
As this is fork of the official Go code the same license applies.
|
||||
Extensions of the original work are copyright (c) 2011 Miek Gieben
|
||||
|
|
11
vendor/github.com/miekg/dns/README.md
generated
vendored
11
vendor/github.com/miekg/dns/README.md
generated
vendored
|
@ -73,6 +73,15 @@ A not-so-up-to-date-list-that-may-be-actually-current:
|
|||
* https://github.com/bodgit/tsig
|
||||
* https://github.com/v2fly/v2ray-core (test only)
|
||||
* https://kuma.io/
|
||||
* https://www.misaka.io/services/dns
|
||||
* https://ping.sx/dig
|
||||
* https://fleetdeck.io/
|
||||
* https://github.com/markdingo/autoreverse
|
||||
* https://github.com/slackhq/nebula
|
||||
* https://addr.tools/
|
||||
* https://dnscheck.tools/
|
||||
* https://github.com/egbakou/domainverifier
|
||||
* https://github.com/semihalev/sdns
|
||||
|
||||
|
||||
Send pull request if you want to be listed here.
|
||||
|
@ -136,6 +145,7 @@ Example programs can be found in the `github.com/miekg/exdns` repository.
|
|||
* 340{1,2,3} - NAPTR record
|
||||
* 3445 - Limiting the scope of (DNS)KEY
|
||||
* 3597 - Unknown RRs
|
||||
* 4025 - A Method for Storing IPsec Keying Material in DNS
|
||||
* 403{3,4,5} - DNSSEC + validation functions
|
||||
* 4255 - SSHFP record
|
||||
* 4343 - Case insensitivity
|
||||
|
@ -171,6 +181,7 @@ Example programs can be found in the `github.com/miekg/exdns` repository.
|
|||
* 8080 - EdDSA for DNSSEC
|
||||
* 8499 - DNS Terminology
|
||||
* 8659 - DNS Certification Authority Authorization (CAA) Resource Record
|
||||
* 8777 - DNS Reverse IP Automatic Multicast Tunneling (AMT) Discovery
|
||||
* 8914 - Extended DNS Errors
|
||||
* 8976 - Message Digest for DNS Zones (ZONEMD RR)
|
||||
|
||||
|
|
5
vendor/github.com/miekg/dns/acceptfunc.go
generated
vendored
5
vendor/github.com/miekg/dns/acceptfunc.go
generated
vendored
|
@ -10,16 +10,13 @@ type MsgAcceptFunc func(dh Header) MsgAcceptAction
|
|||
//
|
||||
// * opcode isn't OpcodeQuery or OpcodeNotify
|
||||
//
|
||||
// * Zero bit isn't zero
|
||||
//
|
||||
// * has more than 1 question in the question section
|
||||
// * does not have exactly 1 question in the question section
|
||||
//
|
||||
// * has more than 1 RR in the Answer section
|
||||
//
|
||||
// * has more than 0 RRs in the Authority section
|
||||
//
|
||||
// * has more than 2 RRs in the Additional section
|
||||
//
|
||||
var DefaultMsgAcceptFunc MsgAcceptFunc = defaultMsgAcceptFunc
|
||||
|
||||
// MsgAcceptAction represents the action to be taken.
|
||||
|
|
152
vendor/github.com/miekg/dns/client.go
generated
vendored
152
vendor/github.com/miekg/dns/client.go
generated
vendored
|
@ -6,7 +6,6 @@ import (
|
|||
"context"
|
||||
"crypto/tls"
|
||||
"encoding/binary"
|
||||
"fmt"
|
||||
"io"
|
||||
"net"
|
||||
"strings"
|
||||
|
@ -18,6 +17,18 @@ const (
|
|||
tcpIdleTimeout time.Duration = 8 * time.Second
|
||||
)
|
||||
|
||||
func isPacketConn(c net.Conn) bool {
|
||||
if _, ok := c.(net.PacketConn); !ok {
|
||||
return false
|
||||
}
|
||||
|
||||
if ua, ok := c.LocalAddr().(*net.UnixAddr); ok {
|
||||
return ua.Net == "unixgram" || ua.Net == "unixpacket"
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
// A Conn represents a connection to a DNS server.
|
||||
type Conn struct {
|
||||
net.Conn // a net.Conn holding the connection
|
||||
|
@ -27,6 +38,14 @@ type Conn struct {
|
|||
tsigRequestMAC string
|
||||
}
|
||||
|
||||
func (co *Conn) tsigProvider() TsigProvider {
|
||||
if co.TsigProvider != nil {
|
||||
return co.TsigProvider
|
||||
}
|
||||
// tsigSecretProvider will return ErrSecret if co.TsigSecret is nil.
|
||||
return tsigSecretProvider(co.TsigSecret)
|
||||
}
|
||||
|
||||
// A Client defines parameters for a DNS client.
|
||||
type Client struct {
|
||||
Net string // if "tcp" or "tcp-tls" (DNS over TLS) a TCP query will be initiated, otherwise an UDP one (default is "" for UDP)
|
||||
|
@ -36,14 +55,20 @@ type Client struct {
|
|||
// Timeout is a cumulative timeout for dial, write and read, defaults to 0 (disabled) - overrides DialTimeout, ReadTimeout,
|
||||
// WriteTimeout when non-zero. Can be overridden with net.Dialer.Timeout (see Client.ExchangeWithDialer and
|
||||
// Client.Dialer) or context.Context.Deadline (see ExchangeContext)
|
||||
Timeout time.Duration
|
||||
DialTimeout time.Duration // net.DialTimeout, defaults to 2 seconds, or net.Dialer.Timeout if expiring earlier - overridden by Timeout when that value is non-zero
|
||||
ReadTimeout time.Duration // net.Conn.SetReadTimeout value for connections, defaults to 2 seconds - overridden by Timeout when that value is non-zero
|
||||
WriteTimeout time.Duration // net.Conn.SetWriteTimeout value for connections, defaults to 2 seconds - overridden by Timeout when that value is non-zero
|
||||
TsigSecret map[string]string // secret(s) for Tsig map[<zonename>]<base64 secret>, zonename must be in canonical form (lowercase, fqdn, see RFC 4034 Section 6.2)
|
||||
TsigProvider TsigProvider // An implementation of the TsigProvider interface. If defined it replaces TsigSecret and is used for all TSIG operations.
|
||||
SingleInflight bool // if true suppress multiple outstanding queries for the same Qname, Qtype and Qclass
|
||||
group singleflight
|
||||
Timeout time.Duration
|
||||
DialTimeout time.Duration // net.DialTimeout, defaults to 2 seconds, or net.Dialer.Timeout if expiring earlier - overridden by Timeout when that value is non-zero
|
||||
ReadTimeout time.Duration // net.Conn.SetReadTimeout value for connections, defaults to 2 seconds - overridden by Timeout when that value is non-zero
|
||||
WriteTimeout time.Duration // net.Conn.SetWriteTimeout value for connections, defaults to 2 seconds - overridden by Timeout when that value is non-zero
|
||||
TsigSecret map[string]string // secret(s) for Tsig map[<zonename>]<base64 secret>, zonename must be in canonical form (lowercase, fqdn, see RFC 4034 Section 6.2)
|
||||
TsigProvider TsigProvider // An implementation of the TsigProvider interface. If defined it replaces TsigSecret and is used for all TSIG operations.
|
||||
|
||||
// SingleInflight previously serialised multiple concurrent queries for the
|
||||
// same Qname, Qtype and Qclass to ensure only one would be in flight at a
|
||||
// time.
|
||||
//
|
||||
// Deprecated: This is a no-op. Callers should implement their own in flight
|
||||
// query caching if needed. See github.com/miekg/dns/issues/1449.
|
||||
SingleInflight bool
|
||||
}
|
||||
|
||||
// Exchange performs a synchronous UDP query. It sends the message m to the address
|
||||
|
@ -82,6 +107,11 @@ func (c *Client) writeTimeout() time.Duration {
|
|||
|
||||
// Dial connects to the address on the named network.
|
||||
func (c *Client) Dial(address string) (conn *Conn, err error) {
|
||||
return c.DialContext(context.Background(), address)
|
||||
}
|
||||
|
||||
// DialContext connects to the address on the named network, with a context.Context.
|
||||
func (c *Client) DialContext(ctx context.Context, address string) (conn *Conn, err error) {
|
||||
// create a new dialer with the appropriate timeout
|
||||
var d net.Dialer
|
||||
if c.Dialer == nil {
|
||||
|
@ -101,9 +131,13 @@ func (c *Client) Dial(address string) (conn *Conn, err error) {
|
|||
if useTLS {
|
||||
network = strings.TrimSuffix(network, "-tls")
|
||||
|
||||
conn.Conn, err = tls.DialWithDialer(&d, network, address, c.TLSConfig)
|
||||
tlsDialer := tls.Dialer{
|
||||
NetDialer: &d,
|
||||
Config: c.TLSConfig,
|
||||
}
|
||||
conn.Conn, err = tlsDialer.DialContext(ctx, network, address)
|
||||
} else {
|
||||
conn.Conn, err = d.Dial(network, address)
|
||||
conn.Conn, err = d.DialContext(ctx, network, address)
|
||||
}
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
@ -139,34 +173,23 @@ func (c *Client) Exchange(m *Msg, address string) (r *Msg, rtt time.Duration, er
|
|||
// ExchangeWithConn has the same behavior as Exchange, just with a predetermined connection
|
||||
// that will be used instead of creating a new one.
|
||||
// Usage pattern with a *dns.Client:
|
||||
//
|
||||
// c := new(dns.Client)
|
||||
// // connection management logic goes here
|
||||
//
|
||||
// conn := c.Dial(address)
|
||||
// in, rtt, err := c.ExchangeWithConn(message, conn)
|
||||
//
|
||||
// This allows users of the library to implement their own connection management,
|
||||
// as opposed to Exchange, which will always use new connections and incur the added overhead
|
||||
// that entails when using "tcp" and especially "tcp-tls" clients.
|
||||
// This allows users of the library to implement their own connection management,
|
||||
// as opposed to Exchange, which will always use new connections and incur the added overhead
|
||||
// that entails when using "tcp" and especially "tcp-tls" clients.
|
||||
func (c *Client) ExchangeWithConn(m *Msg, conn *Conn) (r *Msg, rtt time.Duration, err error) {
|
||||
if !c.SingleInflight {
|
||||
return c.exchange(m, conn)
|
||||
}
|
||||
|
||||
q := m.Question[0]
|
||||
key := fmt.Sprintf("%s:%d:%d", q.Name, q.Qtype, q.Qclass)
|
||||
r, rtt, err, shared := c.group.Do(key, func() (*Msg, time.Duration, error) {
|
||||
return c.exchange(m, conn)
|
||||
})
|
||||
if r != nil && shared {
|
||||
r = r.Copy()
|
||||
}
|
||||
|
||||
return r, rtt, err
|
||||
return c.ExchangeWithConnContext(context.Background(), m, conn)
|
||||
}
|
||||
|
||||
func (c *Client) exchange(m *Msg, co *Conn) (r *Msg, rtt time.Duration, err error) {
|
||||
|
||||
// ExchangeWithConnContext has the same behaviour as ExchangeWithConn and
|
||||
// additionally obeys deadlines from the passed Context.
|
||||
func (c *Client) ExchangeWithConnContext(ctx context.Context, m *Msg, co *Conn) (r *Msg, rtt time.Duration, err error) {
|
||||
opt := m.IsEdns0()
|
||||
// If EDNS0 is used use that for size.
|
||||
if opt != nil && opt.UDPSize() >= MinMsgSize {
|
||||
|
@ -177,16 +200,28 @@ func (c *Client) exchange(m *Msg, co *Conn) (r *Msg, rtt time.Duration, err erro
|
|||
co.UDPSize = c.UDPSize
|
||||
}
|
||||
|
||||
co.TsigSecret, co.TsigProvider = c.TsigSecret, c.TsigProvider
|
||||
t := time.Now()
|
||||
// write with the appropriate write timeout
|
||||
co.SetWriteDeadline(t.Add(c.getTimeoutForRequest(c.writeTimeout())))
|
||||
t := time.Now()
|
||||
writeDeadline := t.Add(c.getTimeoutForRequest(c.writeTimeout()))
|
||||
readDeadline := t.Add(c.getTimeoutForRequest(c.readTimeout()))
|
||||
if deadline, ok := ctx.Deadline(); ok {
|
||||
if deadline.Before(writeDeadline) {
|
||||
writeDeadline = deadline
|
||||
}
|
||||
if deadline.Before(readDeadline) {
|
||||
readDeadline = deadline
|
||||
}
|
||||
}
|
||||
co.SetWriteDeadline(writeDeadline)
|
||||
co.SetReadDeadline(readDeadline)
|
||||
|
||||
co.TsigSecret, co.TsigProvider = c.TsigSecret, c.TsigProvider
|
||||
|
||||
if err = co.WriteMsg(m); err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
co.SetReadDeadline(time.Now().Add(c.getTimeoutForRequest(c.readTimeout())))
|
||||
if _, ok := co.Conn.(net.PacketConn); ok {
|
||||
if isPacketConn(co.Conn) {
|
||||
for {
|
||||
r, err = co.ReadMsg()
|
||||
// Ignore replies with mismatched IDs because they might be
|
||||
|
@ -224,15 +259,8 @@ func (co *Conn) ReadMsg() (*Msg, error) {
|
|||
return m, err
|
||||
}
|
||||
if t := m.IsTsig(); t != nil {
|
||||
if co.TsigProvider != nil {
|
||||
err = tsigVerifyProvider(p, co.TsigProvider, co.tsigRequestMAC, false)
|
||||
} else {
|
||||
if _, ok := co.TsigSecret[t.Hdr.Name]; !ok {
|
||||
return m, ErrSecret
|
||||
}
|
||||
// Need to work on the original message p, as that was used to calculate the tsig.
|
||||
err = TsigVerify(p, co.TsigSecret[t.Hdr.Name], co.tsigRequestMAC, false)
|
||||
}
|
||||
// Need to work on the original message p, as that was used to calculate the tsig.
|
||||
err = TsigVerifyWithProvider(p, co.tsigProvider(), co.tsigRequestMAC, false)
|
||||
}
|
||||
return m, err
|
||||
}
|
||||
|
@ -247,7 +275,7 @@ func (co *Conn) ReadMsgHeader(hdr *Header) ([]byte, error) {
|
|||
err error
|
||||
)
|
||||
|
||||
if _, ok := co.Conn.(net.PacketConn); ok {
|
||||
if isPacketConn(co.Conn) {
|
||||
if co.UDPSize > MinMsgSize {
|
||||
p = make([]byte, co.UDPSize)
|
||||
} else {
|
||||
|
@ -287,7 +315,7 @@ func (co *Conn) Read(p []byte) (n int, err error) {
|
|||
return 0, ErrConnEmpty
|
||||
}
|
||||
|
||||
if _, ok := co.Conn.(net.PacketConn); ok {
|
||||
if isPacketConn(co.Conn) {
|
||||
// UDP connection
|
||||
return co.Conn.Read(p)
|
||||
}
|
||||
|
@ -309,17 +337,8 @@ func (co *Conn) Read(p []byte) (n int, err error) {
|
|||
func (co *Conn) WriteMsg(m *Msg) (err error) {
|
||||
var out []byte
|
||||
if t := m.IsTsig(); t != nil {
|
||||
mac := ""
|
||||
if co.TsigProvider != nil {
|
||||
out, mac, err = tsigGenerateProvider(m, co.TsigProvider, co.tsigRequestMAC, false)
|
||||
} else {
|
||||
if _, ok := co.TsigSecret[t.Hdr.Name]; !ok {
|
||||
return ErrSecret
|
||||
}
|
||||
out, mac, err = TsigGenerate(m, co.TsigSecret[t.Hdr.Name], co.tsigRequestMAC, false)
|
||||
}
|
||||
// Set for the next read, although only used in zone transfers
|
||||
co.tsigRequestMAC = mac
|
||||
// Set tsigRequestMAC for the next read, although only used in zone transfers.
|
||||
out, co.tsigRequestMAC, err = TsigGenerateWithProvider(m, co.tsigProvider(), co.tsigRequestMAC, false)
|
||||
} else {
|
||||
out, err = m.Pack()
|
||||
}
|
||||
|
@ -336,7 +355,7 @@ func (co *Conn) Write(p []byte) (int, error) {
|
|||
return 0, &Error{err: "message too large"}
|
||||
}
|
||||
|
||||
if _, ok := co.Conn.(net.PacketConn); ok {
|
||||
if isPacketConn(co.Conn) {
|
||||
return co.Conn.Write(p)
|
||||
}
|
||||
|
||||
|
@ -392,7 +411,6 @@ func ExchangeContext(ctx context.Context, m *Msg, a string) (r *Msg, err error)
|
|||
// co.WriteMsg(m)
|
||||
// in, _ := co.ReadMsg()
|
||||
// co.Close()
|
||||
//
|
||||
func ExchangeConn(c net.Conn, m *Msg) (r *Msg, err error) {
|
||||
println("dns: ExchangeConn: this function is deprecated")
|
||||
co := new(Conn)
|
||||
|
@ -435,15 +453,11 @@ func DialTimeoutWithTLS(network, address string, tlsConfig *tls.Config, timeout
|
|||
// context, if present. If there is both a context deadline and a configured
|
||||
// timeout on the client, the earliest of the two takes effect.
|
||||
func (c *Client) ExchangeContext(ctx context.Context, m *Msg, a string) (r *Msg, rtt time.Duration, err error) {
|
||||
var timeout time.Duration
|
||||
if deadline, ok := ctx.Deadline(); !ok {
|
||||
timeout = 0
|
||||
} else {
|
||||
timeout = time.Until(deadline)
|
||||
conn, err := c.DialContext(ctx, a)
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
// not passing the context to the underlying calls, as the API does not support
|
||||
// context. For timeouts you should set up Client.Dialer and call Client.Exchange.
|
||||
// TODO(tmthrgd,miekg): this is a race condition.
|
||||
c.Dialer = &net.Dialer{Timeout: timeout}
|
||||
return c.Exchange(m, a)
|
||||
defer conn.Close()
|
||||
|
||||
return c.ExchangeWithConnContext(ctx, m, conn)
|
||||
}
|
||||
|
|
2
vendor/github.com/miekg/dns/clientconfig.go
generated
vendored
2
vendor/github.com/miekg/dns/clientconfig.go
generated
vendored
|
@ -68,7 +68,7 @@ func ClientConfigFromReader(resolvconf io.Reader) (*ClientConfig, error) {
|
|||
}
|
||||
|
||||
case "search": // set search path to given servers
|
||||
c.Search = append([]string(nil), f[1:]...)
|
||||
c.Search = cloneSlice(f[1:])
|
||||
|
||||
case "options": // magic options
|
||||
for _, s := range f[1:] {
|
||||
|
|
59
vendor/github.com/miekg/dns/defaults.go
generated
vendored
59
vendor/github.com/miekg/dns/defaults.go
generated
vendored
|
@ -22,8 +22,7 @@ func (dns *Msg) SetReply(request *Msg) *Msg {
|
|||
}
|
||||
dns.Rcode = RcodeSuccess
|
||||
if len(request.Question) > 0 {
|
||||
dns.Question = make([]Question, 1)
|
||||
dns.Question[0] = request.Question[0]
|
||||
dns.Question = []Question{request.Question[0]}
|
||||
}
|
||||
return dns
|
||||
}
|
||||
|
@ -208,7 +207,7 @@ func IsDomainName(s string) (labels int, ok bool) {
|
|||
}
|
||||
|
||||
// check for \DDD
|
||||
if i+3 < len(s) && isDigit(s[i+1]) && isDigit(s[i+2]) && isDigit(s[i+3]) {
|
||||
if isDDD(s[i+1:]) {
|
||||
i += 3
|
||||
begin += 3
|
||||
} else {
|
||||
|
@ -218,6 +217,11 @@ func IsDomainName(s string) (labels int, ok bool) {
|
|||
|
||||
wasDot = false
|
||||
case '.':
|
||||
if i == 0 && len(s) > 1 {
|
||||
// leading dots are not legal except for the root zone
|
||||
return labels, false
|
||||
}
|
||||
|
||||
if wasDot {
|
||||
// two dots back to back is not legal
|
||||
return labels, false
|
||||
|
@ -267,40 +271,39 @@ func IsMsg(buf []byte) error {
|
|||
|
||||
// IsFqdn checks if a domain name is fully qualified.
|
||||
func IsFqdn(s string) bool {
|
||||
s2 := strings.TrimSuffix(s, ".")
|
||||
if s == s2 {
|
||||
// Check for (and remove) a trailing dot, returning if there isn't one.
|
||||
if s == "" || s[len(s)-1] != '.' {
|
||||
return false
|
||||
}
|
||||
s = s[:len(s)-1]
|
||||
|
||||
i := strings.LastIndexFunc(s2, func(r rune) bool {
|
||||
// If we don't have an escape sequence before the final dot, we know it's
|
||||
// fully qualified and can return here.
|
||||
if s == "" || s[len(s)-1] != '\\' {
|
||||
return true
|
||||
}
|
||||
|
||||
// Otherwise we have to check if the dot is escaped or not by checking if
|
||||
// there are an odd or even number of escape sequences before the dot.
|
||||
i := strings.LastIndexFunc(s, func(r rune) bool {
|
||||
return r != '\\'
|
||||
})
|
||||
|
||||
// Test whether we have an even number of escape sequences before
|
||||
// the dot or none.
|
||||
return (len(s2)-i)%2 != 0
|
||||
return (len(s)-i)%2 != 0
|
||||
}
|
||||
|
||||
// IsRRset checks if a set of RRs is a valid RRset as defined by RFC 2181.
|
||||
// This means the RRs need to have the same type, name, and class. Returns true
|
||||
// if the RR set is valid, otherwise false.
|
||||
// IsRRset reports whether a set of RRs is a valid RRset as defined by RFC 2181.
|
||||
// This means the RRs need to have the same type, name, and class.
|
||||
func IsRRset(rrset []RR) bool {
|
||||
if len(rrset) == 0 {
|
||||
return false
|
||||
}
|
||||
if len(rrset) == 1 {
|
||||
return true
|
||||
}
|
||||
rrHeader := rrset[0].Header()
|
||||
rrType := rrHeader.Rrtype
|
||||
rrClass := rrHeader.Class
|
||||
rrName := rrHeader.Name
|
||||
|
||||
baseH := rrset[0].Header()
|
||||
for _, rr := range rrset[1:] {
|
||||
curRRHeader := rr.Header()
|
||||
if curRRHeader.Rrtype != rrType || curRRHeader.Class != rrClass || curRRHeader.Name != rrName {
|
||||
curH := rr.Header()
|
||||
if curH.Rrtype != baseH.Rrtype || curH.Class != baseH.Class || curH.Name != baseH.Name {
|
||||
// Mismatch between the records, so this is not a valid rrset for
|
||||
//signing/verifying
|
||||
// signing/verifying
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
@ -318,9 +321,15 @@ func Fqdn(s string) string {
|
|||
}
|
||||
|
||||
// CanonicalName returns the domain name in canonical form. A name in canonical
|
||||
// form is lowercase and fully qualified. See Section 6.2 in RFC 4034.
|
||||
// form is lowercase and fully qualified. Only US-ASCII letters are affected. See
|
||||
// Section 6.2 in RFC 4034.
|
||||
func CanonicalName(s string) string {
|
||||
return strings.ToLower(Fqdn(s))
|
||||
return strings.Map(func(r rune) rune {
|
||||
if r >= 'A' && r <= 'Z' {
|
||||
r += 'a' - 'A'
|
||||
}
|
||||
return r
|
||||
}, Fqdn(s))
|
||||
}
|
||||
|
||||
// Copied from the official Go code.
|
||||
|
|
62
vendor/github.com/miekg/dns/dnssec.go
generated
vendored
62
vendor/github.com/miekg/dns/dnssec.go
generated
vendored
|
@ -65,6 +65,9 @@ var AlgorithmToString = map[uint8]string{
|
|||
}
|
||||
|
||||
// AlgorithmToHash is a map of algorithm crypto hash IDs to crypto.Hash's.
|
||||
// For newer algorithm that do their own hashing (i.e. ED25519) the returned value
|
||||
// is 0, implying no (external) hashing should occur. The non-exported identityHash is then
|
||||
// used.
|
||||
var AlgorithmToHash = map[uint8]crypto.Hash{
|
||||
RSAMD5: crypto.MD5, // Deprecated in RFC 6725
|
||||
DSA: crypto.SHA1,
|
||||
|
@ -74,7 +77,7 @@ var AlgorithmToHash = map[uint8]crypto.Hash{
|
|||
ECDSAP256SHA256: crypto.SHA256,
|
||||
ECDSAP384SHA384: crypto.SHA384,
|
||||
RSASHA512: crypto.SHA512,
|
||||
ED25519: crypto.Hash(0),
|
||||
ED25519: 0,
|
||||
}
|
||||
|
||||
// DNSSEC hashing algorithm codes.
|
||||
|
@ -125,10 +128,6 @@ type dnskeyWireFmt struct {
|
|||
/* Nothing is left out */
|
||||
}
|
||||
|
||||
func divRoundUp(a, b int) int {
|
||||
return (a + b - 1) / b
|
||||
}
|
||||
|
||||
// KeyTag calculates the keytag (or key-id) of the DNSKEY.
|
||||
func (k *DNSKEY) KeyTag() uint16 {
|
||||
if k == nil {
|
||||
|
@ -137,12 +136,12 @@ func (k *DNSKEY) KeyTag() uint16 {
|
|||
var keytag int
|
||||
switch k.Algorithm {
|
||||
case RSAMD5:
|
||||
// Look at the bottom two bytes of the modules, which the last
|
||||
// item in the pubkey.
|
||||
// This algorithm has been deprecated, but keep this key-tag calculation.
|
||||
// Look at the bottom two bytes of the modules, which the last item in the pubkey.
|
||||
// See https://www.rfc-editor.org/errata/eid193 .
|
||||
modulus, _ := fromBase64([]byte(k.PublicKey))
|
||||
if len(modulus) > 1 {
|
||||
x := binary.BigEndian.Uint16(modulus[len(modulus)-2:])
|
||||
x := binary.BigEndian.Uint16(modulus[len(modulus)-3:])
|
||||
keytag = int(x)
|
||||
}
|
||||
default:
|
||||
|
@ -296,35 +295,20 @@ func (rr *RRSIG) Sign(k crypto.Signer, rrset []RR) error {
|
|||
return err
|
||||
}
|
||||
|
||||
hash, ok := AlgorithmToHash[rr.Algorithm]
|
||||
if !ok {
|
||||
return ErrAlg
|
||||
h, cryptohash, err := hashFromAlgorithm(rr.Algorithm)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
switch rr.Algorithm {
|
||||
case ED25519:
|
||||
// ed25519 signs the raw message and performs hashing internally.
|
||||
// All other supported signature schemes operate over the pre-hashed
|
||||
// message, and thus ed25519 must be handled separately here.
|
||||
//
|
||||
// The raw message is passed directly into sign and crypto.Hash(0) is
|
||||
// used to signal to the crypto.Signer that the data has not been hashed.
|
||||
signature, err := sign(k, append(signdata, wire...), crypto.Hash(0), rr.Algorithm)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
rr.Signature = toBase64(signature)
|
||||
return nil
|
||||
case RSAMD5, DSA, DSANSEC3SHA1:
|
||||
// See RFC 6944.
|
||||
return ErrAlg
|
||||
default:
|
||||
h := hash.New()
|
||||
h.Write(signdata)
|
||||
h.Write(wire)
|
||||
|
||||
signature, err := sign(k, h.Sum(nil), hash, rr.Algorithm)
|
||||
signature, err := sign(k, h.Sum(nil), cryptohash, rr.Algorithm)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -341,7 +325,7 @@ func sign(k crypto.Signer, hashed []byte, hash crypto.Hash, alg uint8) ([]byte,
|
|||
}
|
||||
|
||||
switch alg {
|
||||
case RSASHA1, RSASHA1NSEC3SHA1, RSASHA256, RSASHA512:
|
||||
case RSASHA1, RSASHA1NSEC3SHA1, RSASHA256, RSASHA512, ED25519:
|
||||
return signature, nil
|
||||
case ECDSAP256SHA256, ECDSAP384SHA384:
|
||||
ecdsaSignature := &struct {
|
||||
|
@ -362,8 +346,6 @@ func sign(k crypto.Signer, hashed []byte, hash crypto.Hash, alg uint8) ([]byte,
|
|||
signature := intToBytes(ecdsaSignature.R, intlen)
|
||||
signature = append(signature, intToBytes(ecdsaSignature.S, intlen)...)
|
||||
return signature, nil
|
||||
case ED25519:
|
||||
return signature, nil
|
||||
default:
|
||||
return nil, ErrAlg
|
||||
}
|
||||
|
@ -431,15 +413,15 @@ func (rr *RRSIG) Verify(k *DNSKEY, rrset []RR) error {
|
|||
return err
|
||||
}
|
||||
|
||||
sigbuf := rr.sigBuf() // Get the binary signature data
|
||||
if rr.Algorithm == PRIVATEDNS { // PRIVATEOID
|
||||
// TODO(miek)
|
||||
// remove the domain name and assume its ours?
|
||||
}
|
||||
sigbuf := rr.sigBuf() // Get the binary signature data
|
||||
// TODO(miek)
|
||||
// remove the domain name and assume its ours?
|
||||
// if rr.Algorithm == PRIVATEDNS { // PRIVATEOID
|
||||
// }
|
||||
|
||||
hash, ok := AlgorithmToHash[rr.Algorithm]
|
||||
if !ok {
|
||||
return ErrAlg
|
||||
h, cryptohash, err := hashFromAlgorithm(rr.Algorithm)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
switch rr.Algorithm {
|
||||
|
@ -450,10 +432,9 @@ func (rr *RRSIG) Verify(k *DNSKEY, rrset []RR) error {
|
|||
return ErrKey
|
||||
}
|
||||
|
||||
h := hash.New()
|
||||
h.Write(signeddata)
|
||||
h.Write(wire)
|
||||
return rsa.VerifyPKCS1v15(pubkey, hash, h.Sum(nil), sigbuf)
|
||||
return rsa.VerifyPKCS1v15(pubkey, cryptohash, h.Sum(nil), sigbuf)
|
||||
|
||||
case ECDSAP256SHA256, ECDSAP384SHA384:
|
||||
pubkey := k.publicKeyECDSA()
|
||||
|
@ -465,7 +446,6 @@ func (rr *RRSIG) Verify(k *DNSKEY, rrset []RR) error {
|
|||
r := new(big.Int).SetBytes(sigbuf[:len(sigbuf)/2])
|
||||
s := new(big.Int).SetBytes(sigbuf[len(sigbuf)/2:])
|
||||
|
||||
h := hash.New()
|
||||
h.Write(signeddata)
|
||||
h.Write(wire)
|
||||
if ecdsa.Verify(pubkey, h.Sum(nil), r, s) {
|
||||
|
|
3
vendor/github.com/miekg/dns/dnssec_keyscan.go
generated
vendored
3
vendor/github.com/miekg/dns/dnssec_keyscan.go
generated
vendored
|
@ -37,7 +37,8 @@ func (k *DNSKEY) ReadPrivateKey(q io.Reader, file string) (crypto.PrivateKey, er
|
|||
return nil, ErrPrivKey
|
||||
}
|
||||
// TODO(mg): check if the pubkey matches the private key
|
||||
algo, err := strconv.ParseUint(strings.SplitN(m["algorithm"], " ", 2)[0], 10, 8)
|
||||
algoStr, _, _ := strings.Cut(m["algorithm"], " ")
|
||||
algo, err := strconv.ParseUint(algoStr, 10, 8)
|
||||
if err != nil {
|
||||
return nil, ErrPrivKey
|
||||
}
|
||||
|
|
88
vendor/github.com/miekg/dns/doc.go
generated
vendored
88
vendor/github.com/miekg/dns/doc.go
generated
vendored
|
@ -13,28 +13,28 @@ names in a message will result in a packing failure.
|
|||
Resource records are native types. They are not stored in wire format. Basic
|
||||
usage pattern for creating a new resource record:
|
||||
|
||||
r := new(dns.MX)
|
||||
r.Hdr = dns.RR_Header{Name: "miek.nl.", Rrtype: dns.TypeMX, Class: dns.ClassINET, Ttl: 3600}
|
||||
r.Preference = 10
|
||||
r.Mx = "mx.miek.nl."
|
||||
r := new(dns.MX)
|
||||
r.Hdr = dns.RR_Header{Name: "miek.nl.", Rrtype: dns.TypeMX, Class: dns.ClassINET, Ttl: 3600}
|
||||
r.Preference = 10
|
||||
r.Mx = "mx.miek.nl."
|
||||
|
||||
Or directly from a string:
|
||||
|
||||
mx, err := dns.NewRR("miek.nl. 3600 IN MX 10 mx.miek.nl.")
|
||||
mx, err := dns.NewRR("miek.nl. 3600 IN MX 10 mx.miek.nl.")
|
||||
|
||||
Or when the default origin (.) and TTL (3600) and class (IN) suit you:
|
||||
|
||||
mx, err := dns.NewRR("miek.nl MX 10 mx.miek.nl")
|
||||
mx, err := dns.NewRR("miek.nl MX 10 mx.miek.nl")
|
||||
|
||||
Or even:
|
||||
|
||||
mx, err := dns.NewRR("$ORIGIN nl.\nmiek 1H IN MX 10 mx.miek")
|
||||
mx, err := dns.NewRR("$ORIGIN nl.\nmiek 1H IN MX 10 mx.miek")
|
||||
|
||||
In the DNS messages are exchanged, these messages contain resource records
|
||||
(sets). Use pattern for creating a message:
|
||||
|
||||
m := new(dns.Msg)
|
||||
m.SetQuestion("miek.nl.", dns.TypeMX)
|
||||
m := new(dns.Msg)
|
||||
m.SetQuestion("miek.nl.", dns.TypeMX)
|
||||
|
||||
Or when not certain if the domain name is fully qualified:
|
||||
|
||||
|
@ -45,17 +45,17 @@ records for the miek.nl. zone.
|
|||
|
||||
The following is slightly more verbose, but more flexible:
|
||||
|
||||
m1 := new(dns.Msg)
|
||||
m1.Id = dns.Id()
|
||||
m1.RecursionDesired = true
|
||||
m1.Question = make([]dns.Question, 1)
|
||||
m1.Question[0] = dns.Question{"miek.nl.", dns.TypeMX, dns.ClassINET}
|
||||
m1 := new(dns.Msg)
|
||||
m1.Id = dns.Id()
|
||||
m1.RecursionDesired = true
|
||||
m1.Question = make([]dns.Question, 1)
|
||||
m1.Question[0] = dns.Question{"miek.nl.", dns.TypeMX, dns.ClassINET}
|
||||
|
||||
After creating a message it can be sent. Basic use pattern for synchronous
|
||||
querying the DNS at a server configured on 127.0.0.1 and port 53:
|
||||
|
||||
c := new(dns.Client)
|
||||
in, rtt, err := c.Exchange(m1, "127.0.0.1:53")
|
||||
c := new(dns.Client)
|
||||
in, rtt, err := c.Exchange(m1, "127.0.0.1:53")
|
||||
|
||||
Suppressing multiple outstanding queries (with the same question, type and
|
||||
class) is as easy as setting:
|
||||
|
@ -72,7 +72,7 @@ and port to use for the connection:
|
|||
Port: 12345,
|
||||
Zone: "",
|
||||
}
|
||||
c.Dialer := &net.Dialer{
|
||||
c.Dialer = &net.Dialer{
|
||||
Timeout: 200 * time.Millisecond,
|
||||
LocalAddr: &laddr,
|
||||
}
|
||||
|
@ -96,7 +96,7 @@ the Answer section:
|
|||
// do something with t.Txt
|
||||
}
|
||||
|
||||
Domain Name and TXT Character String Representations
|
||||
# Domain Name and TXT Character String Representations
|
||||
|
||||
Both domain names and TXT character strings are converted to presentation form
|
||||
both when unpacked and when converted to strings.
|
||||
|
@ -108,7 +108,7 @@ be escaped. Bytes below 32 and above 127 will be converted to \DDD form.
|
|||
For domain names, in addition to the above rules brackets, periods, spaces,
|
||||
semicolons and the at symbol are escaped.
|
||||
|
||||
DNSSEC
|
||||
# DNSSEC
|
||||
|
||||
DNSSEC (DNS Security Extension) adds a layer of security to the DNS. It uses
|
||||
public key cryptography to sign resource records. The public keys are stored in
|
||||
|
@ -117,12 +117,12 @@ DNSKEY records and the signatures in RRSIG records.
|
|||
Requesting DNSSEC information for a zone is done by adding the DO (DNSSEC OK)
|
||||
bit to a request.
|
||||
|
||||
m := new(dns.Msg)
|
||||
m.SetEdns0(4096, true)
|
||||
m := new(dns.Msg)
|
||||
m.SetEdns0(4096, true)
|
||||
|
||||
Signature generation, signature verification and key generation are all supported.
|
||||
|
||||
DYNAMIC UPDATES
|
||||
# DYNAMIC UPDATES
|
||||
|
||||
Dynamic updates reuses the DNS message format, but renames three of the
|
||||
sections. Question is Zone, Answer is Prerequisite, Authority is Update, only
|
||||
|
@ -133,30 +133,30 @@ certain resource records or names in a zone to specify if resource records
|
|||
should be added or removed. The table from RFC 2136 supplemented with the Go
|
||||
DNS function shows which functions exist to specify the prerequisites.
|
||||
|
||||
3.2.4 - Table Of Metavalues Used In Prerequisite Section
|
||||
3.2.4 - Table Of Metavalues Used In Prerequisite Section
|
||||
|
||||
CLASS TYPE RDATA Meaning Function
|
||||
--------------------------------------------------------------
|
||||
ANY ANY empty Name is in use dns.NameUsed
|
||||
ANY rrset empty RRset exists (value indep) dns.RRsetUsed
|
||||
NONE ANY empty Name is not in use dns.NameNotUsed
|
||||
NONE rrset empty RRset does not exist dns.RRsetNotUsed
|
||||
zone rrset rr RRset exists (value dep) dns.Used
|
||||
CLASS TYPE RDATA Meaning Function
|
||||
--------------------------------------------------------------
|
||||
ANY ANY empty Name is in use dns.NameUsed
|
||||
ANY rrset empty RRset exists (value indep) dns.RRsetUsed
|
||||
NONE ANY empty Name is not in use dns.NameNotUsed
|
||||
NONE rrset empty RRset does not exist dns.RRsetNotUsed
|
||||
zone rrset rr RRset exists (value dep) dns.Used
|
||||
|
||||
The prerequisite section can also be left empty. If you have decided on the
|
||||
prerequisites you can tell what RRs should be added or deleted. The next table
|
||||
shows the options you have and what functions to call.
|
||||
|
||||
3.4.2.6 - Table Of Metavalues Used In Update Section
|
||||
3.4.2.6 - Table Of Metavalues Used In Update Section
|
||||
|
||||
CLASS TYPE RDATA Meaning Function
|
||||
---------------------------------------------------------------
|
||||
ANY ANY empty Delete all RRsets from name dns.RemoveName
|
||||
ANY rrset empty Delete an RRset dns.RemoveRRset
|
||||
NONE rrset rr Delete an RR from RRset dns.Remove
|
||||
zone rrset rr Add to an RRset dns.Insert
|
||||
CLASS TYPE RDATA Meaning Function
|
||||
---------------------------------------------------------------
|
||||
ANY ANY empty Delete all RRsets from name dns.RemoveName
|
||||
ANY rrset empty Delete an RRset dns.RemoveRRset
|
||||
NONE rrset rr Delete an RR from RRset dns.Remove
|
||||
zone rrset rr Add to an RRset dns.Insert
|
||||
|
||||
TRANSACTION SIGNATURE
|
||||
# TRANSACTION SIGNATURE
|
||||
|
||||
An TSIG or transaction signature adds a HMAC TSIG record to each message sent.
|
||||
The supported algorithms include: HmacSHA1, HmacSHA256 and HmacSHA512.
|
||||
|
@ -239,7 +239,7 @@ Basic use pattern validating and replying to a message that has TSIG set.
|
|||
w.WriteMsg(m)
|
||||
}
|
||||
|
||||
PRIVATE RRS
|
||||
# PRIVATE RRS
|
||||
|
||||
RFC 6895 sets aside a range of type codes for private use. This range is 65,280
|
||||
- 65,534 (0xFF00 - 0xFFFE). When experimenting with new Resource Records these
|
||||
|
@ -248,10 +248,10 @@ can be used, before requesting an official type code from IANA.
|
|||
See https://miek.nl/2014/september/21/idn-and-private-rr-in-go-dns/ for more
|
||||
information.
|
||||
|
||||
EDNS0
|
||||
# EDNS0
|
||||
|
||||
EDNS0 is an extension mechanism for the DNS defined in RFC 2671 and updated by
|
||||
RFC 6891. It defines an new RR type, the OPT RR, which is then completely
|
||||
RFC 6891. It defines a new RR type, the OPT RR, which is then completely
|
||||
abused.
|
||||
|
||||
Basic use pattern for creating an (empty) OPT RR:
|
||||
|
@ -279,9 +279,9 @@ SIG(0)
|
|||
|
||||
From RFC 2931:
|
||||
|
||||
SIG(0) provides protection for DNS transactions and requests ....
|
||||
... protection for glue records, DNS requests, protection for message headers
|
||||
on requests and responses, and protection of the overall integrity of a response.
|
||||
SIG(0) provides protection for DNS transactions and requests ....
|
||||
... protection for glue records, DNS requests, protection for message headers
|
||||
on requests and responses, and protection of the overall integrity of a response.
|
||||
|
||||
It works like TSIG, except that SIG(0) uses public key cryptography, instead of
|
||||
the shared secret approach in TSIG. Supported algorithms: ECDSAP256SHA256,
|
||||
|
|
153
vendor/github.com/miekg/dns/edns.go
generated
vendored
153
vendor/github.com/miekg/dns/edns.go
generated
vendored
|
@ -14,6 +14,7 @@ const (
|
|||
EDNS0LLQ = 0x1 // long lived queries: http://tools.ietf.org/html/draft-sekar-dns-llq-01
|
||||
EDNS0UL = 0x2 // update lease draft: http://files.dns-sd.org/draft-sekar-dns-ul.txt
|
||||
EDNS0NSID = 0x3 // nsid (See RFC 5001)
|
||||
EDNS0ESU = 0x4 // ENUM Source-URI draft: https://datatracker.ietf.org/doc/html/draft-kaplan-enum-source-uri-00
|
||||
EDNS0DAU = 0x5 // DNSSEC Algorithm Understood
|
||||
EDNS0DHU = 0x6 // DS Hash Understood
|
||||
EDNS0N3U = 0x7 // NSEC3 Hash Understood
|
||||
|
@ -56,6 +57,8 @@ func makeDataOpt(code uint16) EDNS0 {
|
|||
return new(EDNS0_PADDING)
|
||||
case EDNS0EDE:
|
||||
return new(EDNS0_EDE)
|
||||
case EDNS0ESU:
|
||||
return &EDNS0_ESU{Code: EDNS0ESU}
|
||||
default:
|
||||
e := new(EDNS0_LOCAL)
|
||||
e.Code = code
|
||||
|
@ -75,7 +78,10 @@ func (rr *OPT) String() string {
|
|||
if rr.Do() {
|
||||
s += "flags: do; "
|
||||
} else {
|
||||
s += "flags: ; "
|
||||
s += "flags:; "
|
||||
}
|
||||
if rr.Hdr.Ttl&0x7FFF != 0 {
|
||||
s += fmt.Sprintf("MBZ: 0x%04x, ", rr.Hdr.Ttl&0x7FFF)
|
||||
}
|
||||
s += "udp: " + strconv.Itoa(int(rr.UDPSize()))
|
||||
|
||||
|
@ -95,6 +101,10 @@ func (rr *OPT) String() string {
|
|||
s += "\n; SUBNET: " + o.String()
|
||||
case *EDNS0_COOKIE:
|
||||
s += "\n; COOKIE: " + o.String()
|
||||
case *EDNS0_EXPIRE:
|
||||
s += "\n; EXPIRE: " + o.String()
|
||||
case *EDNS0_TCP_KEEPALIVE:
|
||||
s += "\n; KEEPALIVE: " + o.String()
|
||||
case *EDNS0_UL:
|
||||
s += "\n; UPDATE LEASE: " + o.String()
|
||||
case *EDNS0_LLQ:
|
||||
|
@ -111,6 +121,8 @@ func (rr *OPT) String() string {
|
|||
s += "\n; PADDING: " + o.String()
|
||||
case *EDNS0_EDE:
|
||||
s += "\n; EDE: " + o.String()
|
||||
case *EDNS0_ESU:
|
||||
s += "\n; ESU: " + o.String()
|
||||
}
|
||||
}
|
||||
return s
|
||||
|
@ -173,7 +185,7 @@ func (rr *OPT) Do() bool {
|
|||
|
||||
// SetDo sets the DO (DNSSEC OK) bit.
|
||||
// If we pass an argument, set the DO bit to that value.
|
||||
// It is possible to pass 2 or more arguments. Any arguments after the 1st is silently ignored.
|
||||
// It is possible to pass 2 or more arguments, but they will be ignored.
|
||||
func (rr *OPT) SetDo(do ...bool) {
|
||||
if len(do) == 1 {
|
||||
if do[0] {
|
||||
|
@ -251,7 +263,7 @@ func (e *EDNS0_NSID) copy() EDNS0 { return &EDNS0_NSID{e.Code, e.Nsid}
|
|||
// o.Hdr.Name = "."
|
||||
// o.Hdr.Rrtype = dns.TypeOPT
|
||||
// e := new(dns.EDNS0_SUBNET)
|
||||
// e.Code = dns.EDNS0SUBNET
|
||||
// e.Code = dns.EDNS0SUBNET // by default this is filled in through unpacking OPT packets (unpackDataOpt)
|
||||
// e.Family = 1 // 1 for IPv4 source address, 2 for IPv6
|
||||
// e.SourceNetmask = 32 // 32 for IPV4, 128 for IPv6
|
||||
// e.SourceScope = 0
|
||||
|
@ -496,6 +508,7 @@ func (e *EDNS0_LLQ) String() string {
|
|||
" " + strconv.FormatUint(uint64(e.LeaseLife), 10)
|
||||
return s
|
||||
}
|
||||
|
||||
func (e *EDNS0_LLQ) copy() EDNS0 {
|
||||
return &EDNS0_LLQ{e.Code, e.Version, e.Opcode, e.Error, e.Id, e.LeaseLife}
|
||||
}
|
||||
|
@ -508,8 +521,8 @@ type EDNS0_DAU struct {
|
|||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_DAU) Option() uint16 { return EDNS0DAU }
|
||||
func (e *EDNS0_DAU) pack() ([]byte, error) { return e.AlgCode, nil }
|
||||
func (e *EDNS0_DAU) unpack(b []byte) error { e.AlgCode = b; return nil }
|
||||
func (e *EDNS0_DAU) pack() ([]byte, error) { return cloneSlice(e.AlgCode), nil }
|
||||
func (e *EDNS0_DAU) unpack(b []byte) error { e.AlgCode = cloneSlice(b); return nil }
|
||||
|
||||
func (e *EDNS0_DAU) String() string {
|
||||
s := ""
|
||||
|
@ -532,8 +545,8 @@ type EDNS0_DHU struct {
|
|||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_DHU) Option() uint16 { return EDNS0DHU }
|
||||
func (e *EDNS0_DHU) pack() ([]byte, error) { return e.AlgCode, nil }
|
||||
func (e *EDNS0_DHU) unpack(b []byte) error { e.AlgCode = b; return nil }
|
||||
func (e *EDNS0_DHU) pack() ([]byte, error) { return cloneSlice(e.AlgCode), nil }
|
||||
func (e *EDNS0_DHU) unpack(b []byte) error { e.AlgCode = cloneSlice(b); return nil }
|
||||
|
||||
func (e *EDNS0_DHU) String() string {
|
||||
s := ""
|
||||
|
@ -556,8 +569,8 @@ type EDNS0_N3U struct {
|
|||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_N3U) Option() uint16 { return EDNS0N3U }
|
||||
func (e *EDNS0_N3U) pack() ([]byte, error) { return e.AlgCode, nil }
|
||||
func (e *EDNS0_N3U) unpack(b []byte) error { e.AlgCode = b; return nil }
|
||||
func (e *EDNS0_N3U) pack() ([]byte, error) { return cloneSlice(e.AlgCode), nil }
|
||||
func (e *EDNS0_N3U) unpack(b []byte) error { e.AlgCode = cloneSlice(b); return nil }
|
||||
|
||||
func (e *EDNS0_N3U) String() string {
|
||||
// Re-use the hash map
|
||||
|
@ -577,14 +590,17 @@ func (e *EDNS0_N3U) copy() EDNS0 { return &EDNS0_N3U{e.Code, e.AlgCode} }
|
|||
type EDNS0_EXPIRE struct {
|
||||
Code uint16 // Always EDNS0EXPIRE
|
||||
Expire uint32
|
||||
Empty bool // Empty is used to signal an empty Expire option in a backwards compatible way, it's not used on the wire.
|
||||
}
|
||||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_EXPIRE) Option() uint16 { return EDNS0EXPIRE }
|
||||
func (e *EDNS0_EXPIRE) String() string { return strconv.FormatUint(uint64(e.Expire), 10) }
|
||||
func (e *EDNS0_EXPIRE) copy() EDNS0 { return &EDNS0_EXPIRE{e.Code, e.Expire} }
|
||||
func (e *EDNS0_EXPIRE) copy() EDNS0 { return &EDNS0_EXPIRE{e.Code, e.Expire, e.Empty} }
|
||||
|
||||
func (e *EDNS0_EXPIRE) pack() ([]byte, error) {
|
||||
if e.Empty {
|
||||
return []byte{}, nil
|
||||
}
|
||||
b := make([]byte, 4)
|
||||
binary.BigEndian.PutUint32(b, e.Expire)
|
||||
return b, nil
|
||||
|
@ -593,15 +609,24 @@ func (e *EDNS0_EXPIRE) pack() ([]byte, error) {
|
|||
func (e *EDNS0_EXPIRE) unpack(b []byte) error {
|
||||
if len(b) == 0 {
|
||||
// zero-length EXPIRE query, see RFC 7314 Section 2
|
||||
e.Empty = true
|
||||
return nil
|
||||
}
|
||||
if len(b) < 4 {
|
||||
return ErrBuf
|
||||
}
|
||||
e.Expire = binary.BigEndian.Uint32(b)
|
||||
e.Empty = false
|
||||
return nil
|
||||
}
|
||||
|
||||
func (e *EDNS0_EXPIRE) String() (s string) {
|
||||
if e.Empty {
|
||||
return ""
|
||||
}
|
||||
return strconv.FormatUint(uint64(e.Expire), 10)
|
||||
}
|
||||
|
||||
// The EDNS0_LOCAL option is used for local/experimental purposes. The option
|
||||
// code is recommended to be within the range [EDNS0LOCALSTART, EDNS0LOCALEND]
|
||||
// (RFC6891), although any unassigned code can actually be used. The content of
|
||||
|
@ -622,87 +647,73 @@ type EDNS0_LOCAL struct {
|
|||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_LOCAL) Option() uint16 { return e.Code }
|
||||
|
||||
func (e *EDNS0_LOCAL) String() string {
|
||||
return strconv.FormatInt(int64(e.Code), 10) + ":0x" + hex.EncodeToString(e.Data)
|
||||
}
|
||||
|
||||
func (e *EDNS0_LOCAL) copy() EDNS0 {
|
||||
b := make([]byte, len(e.Data))
|
||||
copy(b, e.Data)
|
||||
return &EDNS0_LOCAL{e.Code, b}
|
||||
return &EDNS0_LOCAL{e.Code, cloneSlice(e.Data)}
|
||||
}
|
||||
|
||||
func (e *EDNS0_LOCAL) pack() ([]byte, error) {
|
||||
b := make([]byte, len(e.Data))
|
||||
copied := copy(b, e.Data)
|
||||
if copied != len(e.Data) {
|
||||
return nil, ErrBuf
|
||||
}
|
||||
return b, nil
|
||||
return cloneSlice(e.Data), nil
|
||||
}
|
||||
|
||||
func (e *EDNS0_LOCAL) unpack(b []byte) error {
|
||||
e.Data = make([]byte, len(b))
|
||||
copied := copy(e.Data, b)
|
||||
if copied != len(b) {
|
||||
return ErrBuf
|
||||
}
|
||||
e.Data = cloneSlice(b)
|
||||
return nil
|
||||
}
|
||||
|
||||
// EDNS0_TCP_KEEPALIVE is an EDNS0 option that instructs the server to keep
|
||||
// the TCP connection alive. See RFC 7828.
|
||||
type EDNS0_TCP_KEEPALIVE struct {
|
||||
Code uint16 // Always EDNSTCPKEEPALIVE
|
||||
Length uint16 // the value 0 if the TIMEOUT is omitted, the value 2 if it is present;
|
||||
Timeout uint16 // an idle timeout value for the TCP connection, specified in units of 100 milliseconds, encoded in network byte order.
|
||||
Code uint16 // Always EDNSTCPKEEPALIVE
|
||||
|
||||
// Timeout is an idle timeout value for the TCP connection, specified in
|
||||
// units of 100 milliseconds, encoded in network byte order. If set to 0,
|
||||
// pack will return a nil slice.
|
||||
Timeout uint16
|
||||
|
||||
// Length is the option's length.
|
||||
// Deprecated: this field is deprecated and is always equal to 0.
|
||||
Length uint16
|
||||
}
|
||||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_TCP_KEEPALIVE) Option() uint16 { return EDNS0TCPKEEPALIVE }
|
||||
|
||||
func (e *EDNS0_TCP_KEEPALIVE) pack() ([]byte, error) {
|
||||
if e.Timeout != 0 && e.Length != 2 {
|
||||
return nil, errors.New("dns: timeout specified but length is not 2")
|
||||
if e.Timeout > 0 {
|
||||
b := make([]byte, 2)
|
||||
binary.BigEndian.PutUint16(b, e.Timeout)
|
||||
return b, nil
|
||||
}
|
||||
if e.Timeout == 0 && e.Length != 0 {
|
||||
return nil, errors.New("dns: timeout not specified but length is not 0")
|
||||
}
|
||||
b := make([]byte, 4+e.Length)
|
||||
binary.BigEndian.PutUint16(b[0:], e.Code)
|
||||
binary.BigEndian.PutUint16(b[2:], e.Length)
|
||||
if e.Length == 2 {
|
||||
binary.BigEndian.PutUint16(b[4:], e.Timeout)
|
||||
}
|
||||
return b, nil
|
||||
return nil, nil
|
||||
}
|
||||
|
||||
func (e *EDNS0_TCP_KEEPALIVE) unpack(b []byte) error {
|
||||
if len(b) < 4 {
|
||||
return ErrBuf
|
||||
}
|
||||
e.Length = binary.BigEndian.Uint16(b[2:4])
|
||||
if e.Length != 0 && e.Length != 2 {
|
||||
return errors.New("dns: length mismatch, want 0/2 but got " + strconv.FormatUint(uint64(e.Length), 10))
|
||||
}
|
||||
if e.Length == 2 {
|
||||
if len(b) < 6 {
|
||||
return ErrBuf
|
||||
}
|
||||
e.Timeout = binary.BigEndian.Uint16(b[4:6])
|
||||
switch len(b) {
|
||||
case 0:
|
||||
case 2:
|
||||
e.Timeout = binary.BigEndian.Uint16(b)
|
||||
default:
|
||||
return fmt.Errorf("dns: length mismatch, want 0/2 but got %d", len(b))
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (e *EDNS0_TCP_KEEPALIVE) String() (s string) {
|
||||
s = "use tcp keep-alive"
|
||||
if e.Length == 0 {
|
||||
func (e *EDNS0_TCP_KEEPALIVE) String() string {
|
||||
s := "use tcp keep-alive"
|
||||
if e.Timeout == 0 {
|
||||
s += ", timeout omitted"
|
||||
} else {
|
||||
s += fmt.Sprintf(", timeout %dms", e.Timeout*100)
|
||||
}
|
||||
return
|
||||
return s
|
||||
}
|
||||
func (e *EDNS0_TCP_KEEPALIVE) copy() EDNS0 { return &EDNS0_TCP_KEEPALIVE{e.Code, e.Length, e.Timeout} }
|
||||
|
||||
func (e *EDNS0_TCP_KEEPALIVE) copy() EDNS0 { return &EDNS0_TCP_KEEPALIVE{e.Code, e.Timeout, e.Length} }
|
||||
|
||||
// EDNS0_PADDING option is used to add padding to a request/response. The default
|
||||
// value of padding SHOULD be 0x0 but other values MAY be used, for instance if
|
||||
|
@ -713,14 +724,10 @@ type EDNS0_PADDING struct {
|
|||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_PADDING) Option() uint16 { return EDNS0PADDING }
|
||||
func (e *EDNS0_PADDING) pack() ([]byte, error) { return e.Padding, nil }
|
||||
func (e *EDNS0_PADDING) unpack(b []byte) error { e.Padding = b; return nil }
|
||||
func (e *EDNS0_PADDING) pack() ([]byte, error) { return cloneSlice(e.Padding), nil }
|
||||
func (e *EDNS0_PADDING) unpack(b []byte) error { e.Padding = cloneSlice(b); return nil }
|
||||
func (e *EDNS0_PADDING) String() string { return fmt.Sprintf("%0X", e.Padding) }
|
||||
func (e *EDNS0_PADDING) copy() EDNS0 {
|
||||
b := make([]byte, len(e.Padding))
|
||||
copy(b, e.Padding)
|
||||
return &EDNS0_PADDING{b}
|
||||
}
|
||||
func (e *EDNS0_PADDING) copy() EDNS0 { return &EDNS0_PADDING{cloneSlice(e.Padding)} }
|
||||
|
||||
// Extended DNS Error Codes (RFC 8914).
|
||||
const (
|
||||
|
@ -807,7 +814,7 @@ func (e *EDNS0_EDE) String() string {
|
|||
func (e *EDNS0_EDE) pack() ([]byte, error) {
|
||||
b := make([]byte, 2+len(e.ExtraText))
|
||||
binary.BigEndian.PutUint16(b[0:], e.InfoCode)
|
||||
copy(b[2:], []byte(e.ExtraText))
|
||||
copy(b[2:], e.ExtraText)
|
||||
return b, nil
|
||||
}
|
||||
|
||||
|
@ -819,3 +826,19 @@ func (e *EDNS0_EDE) unpack(b []byte) error {
|
|||
e.ExtraText = string(b[2:])
|
||||
return nil
|
||||
}
|
||||
|
||||
// The EDNS0_ESU option for ENUM Source-URI Extension
|
||||
type EDNS0_ESU struct {
|
||||
Code uint16
|
||||
Uri string
|
||||
}
|
||||
|
||||
// Option implements the EDNS0 interface.
|
||||
func (e *EDNS0_ESU) Option() uint16 { return EDNS0ESU }
|
||||
func (e *EDNS0_ESU) String() string { return e.Uri }
|
||||
func (e *EDNS0_ESU) copy() EDNS0 { return &EDNS0_ESU{e.Code, e.Uri} }
|
||||
func (e *EDNS0_ESU) pack() ([]byte, error) { return []byte(e.Uri), nil }
|
||||
func (e *EDNS0_ESU) unpack(b []byte) error {
|
||||
e.Uri = string(b)
|
||||
return nil
|
||||
}
|
||||
|
|
1
vendor/github.com/miekg/dns/fuzz.go
generated
vendored
1
vendor/github.com/miekg/dns/fuzz.go
generated
vendored
|
@ -1,3 +1,4 @@
|
|||
//go:build fuzz
|
||||
// +build fuzz
|
||||
|
||||
package dns
|
||||
|
|
33
vendor/github.com/miekg/dns/generate.go
generated
vendored
33
vendor/github.com/miekg/dns/generate.go
generated
vendored
|
@ -35,17 +35,17 @@ func (zp *ZoneParser) generate(l lex) (RR, bool) {
|
|||
token = token[:i]
|
||||
}
|
||||
|
||||
sx := strings.SplitN(token, "-", 2)
|
||||
if len(sx) != 2 {
|
||||
startStr, endStr, ok := strings.Cut(token, "-")
|
||||
if !ok {
|
||||
return zp.setParseError("bad start-stop in $GENERATE range", l)
|
||||
}
|
||||
|
||||
start, err := strconv.ParseInt(sx[0], 10, 64)
|
||||
start, err := strconv.ParseInt(startStr, 10, 64)
|
||||
if err != nil {
|
||||
return zp.setParseError("bad start in $GENERATE range", l)
|
||||
}
|
||||
|
||||
end, err := strconv.ParseInt(sx[1], 10, 64)
|
||||
end, err := strconv.ParseInt(endStr, 10, 64)
|
||||
if err != nil {
|
||||
return zp.setParseError("bad stop in $GENERATE range", l)
|
||||
}
|
||||
|
@ -54,7 +54,7 @@ func (zp *ZoneParser) generate(l lex) (RR, bool) {
|
|||
}
|
||||
|
||||
// _BLANK
|
||||
l, ok := zp.c.Next()
|
||||
l, ok = zp.c.Next()
|
||||
if !ok || l.value != zBlank {
|
||||
return zp.setParseError("garbage after $GENERATE range", l)
|
||||
}
|
||||
|
@ -211,15 +211,16 @@ func (r *generateReader) ReadByte() (byte, error) {
|
|||
func modToPrintf(s string) (string, int64, string) {
|
||||
// Modifier is { offset [ ,width [ ,base ] ] } - provide default
|
||||
// values for optional width and type, if necessary.
|
||||
var offStr, widthStr, base string
|
||||
switch xs := strings.Split(s, ","); len(xs) {
|
||||
case 1:
|
||||
offStr, widthStr, base = xs[0], "0", "d"
|
||||
case 2:
|
||||
offStr, widthStr, base = xs[0], xs[1], "d"
|
||||
case 3:
|
||||
offStr, widthStr, base = xs[0], xs[1], xs[2]
|
||||
default:
|
||||
offStr, s, ok0 := strings.Cut(s, ",")
|
||||
widthStr, s, ok1 := strings.Cut(s, ",")
|
||||
base, _, ok2 := strings.Cut(s, ",")
|
||||
if !ok0 {
|
||||
widthStr = "0"
|
||||
}
|
||||
if !ok1 {
|
||||
base = "d"
|
||||
}
|
||||
if ok2 {
|
||||
return "", 0, "bad modifier in $GENERATE"
|
||||
}
|
||||
|
||||
|
@ -234,8 +235,8 @@ func modToPrintf(s string) (string, int64, string) {
|
|||
return "", 0, "bad offset in $GENERATE"
|
||||
}
|
||||
|
||||
width, err := strconv.ParseInt(widthStr, 10, 64)
|
||||
if err != nil || width < 0 || width > 255 {
|
||||
width, err := strconv.ParseUint(widthStr, 10, 8)
|
||||
if err != nil {
|
||||
return "", 0, "bad width in $GENERATE"
|
||||
}
|
||||
|
||||
|
|
31
vendor/github.com/miekg/dns/hash.go
generated
vendored
Normal file
31
vendor/github.com/miekg/dns/hash.go
generated
vendored
Normal file
|
@ -0,0 +1,31 @@
|
|||
package dns
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"crypto"
|
||||
"hash"
|
||||
)
|
||||
|
||||
// identityHash will not hash, it only buffers the data written into it and returns it as-is.
|
||||
type identityHash struct {
|
||||
b *bytes.Buffer
|
||||
}
|
||||
|
||||
// Implement the hash.Hash interface.
|
||||
|
||||
func (i identityHash) Write(b []byte) (int, error) { return i.b.Write(b) }
|
||||
func (i identityHash) Size() int { return i.b.Len() }
|
||||
func (i identityHash) BlockSize() int { return 1024 }
|
||||
func (i identityHash) Reset() { i.b.Reset() }
|
||||
func (i identityHash) Sum(b []byte) []byte { return append(b, i.b.Bytes()...) }
|
||||
|
||||
func hashFromAlgorithm(alg uint8) (hash.Hash, crypto.Hash, error) {
|
||||
hashnumber, ok := AlgorithmToHash[alg]
|
||||
if !ok {
|
||||
return nil, 0, ErrAlg
|
||||
}
|
||||
if hashnumber == 0 {
|
||||
return identityHash{b: &bytes.Buffer{}}, hashnumber, nil
|
||||
}
|
||||
return hashnumber.New(), hashnumber, nil
|
||||
}
|
2
vendor/github.com/miekg/dns/labels.go
generated
vendored
2
vendor/github.com/miekg/dns/labels.go
generated
vendored
|
@ -122,7 +122,7 @@ func Split(s string) []int {
|
|||
}
|
||||
|
||||
// NextLabel returns the index of the start of the next label in the
|
||||
// string s starting at offset.
|
||||
// string s starting at offset. A negative offset will cause a panic.
|
||||
// The bool end is true when the end of the string has been reached.
|
||||
// Also see PrevLabel.
|
||||
func NextLabel(s string, offset int) (i int, end bool) {
|
||||
|
|
13
vendor/github.com/miekg/dns/listen_no_reuseport.go
generated
vendored
13
vendor/github.com/miekg/dns/listen_no_reuseport.go
generated
vendored
|
@ -1,4 +1,5 @@
|
|||
// +build !go1.11 !aix,!darwin,!dragonfly,!freebsd,!linux,!netbsd,!openbsd
|
||||
//go:build !aix && !darwin && !dragonfly && !freebsd && !linux && !netbsd && !openbsd
|
||||
// +build !aix,!darwin,!dragonfly,!freebsd,!linux,!netbsd,!openbsd
|
||||
|
||||
package dns
|
||||
|
||||
|
@ -6,16 +7,18 @@ import "net"
|
|||
|
||||
const supportsReusePort = false
|
||||
|
||||
func listenTCP(network, addr string, reuseport bool) (net.Listener, error) {
|
||||
if reuseport {
|
||||
func listenTCP(network, addr string, reuseport, reuseaddr bool) (net.Listener, error) {
|
||||
if reuseport || reuseaddr {
|
||||
// TODO(tmthrgd): return an error?
|
||||
}
|
||||
|
||||
return net.Listen(network, addr)
|
||||
}
|
||||
|
||||
func listenUDP(network, addr string, reuseport bool) (net.PacketConn, error) {
|
||||
if reuseport {
|
||||
const supportsReuseAddr = false
|
||||
|
||||
func listenUDP(network, addr string, reuseport, reuseaddr bool) (net.PacketConn, error) {
|
||||
if reuseport || reuseaddr {
|
||||
// TODO(tmthrgd): return an error?
|
||||
}
|
||||
|
||||
|
|
32
vendor/github.com/miekg/dns/listen_reuseport.go
generated
vendored
32
vendor/github.com/miekg/dns/listen_reuseport.go
generated
vendored
|
@ -1,4 +1,4 @@
|
|||
// +build go1.11
|
||||
//go:build aix || darwin || dragonfly || freebsd || linux || netbsd || openbsd
|
||||
// +build aix darwin dragonfly freebsd linux netbsd openbsd
|
||||
|
||||
package dns
|
||||
|
@ -25,19 +25,41 @@ func reuseportControl(network, address string, c syscall.RawConn) error {
|
|||
return opErr
|
||||
}
|
||||
|
||||
func listenTCP(network, addr string, reuseport bool) (net.Listener, error) {
|
||||
const supportsReuseAddr = true
|
||||
|
||||
func reuseaddrControl(network, address string, c syscall.RawConn) error {
|
||||
var opErr error
|
||||
err := c.Control(func(fd uintptr) {
|
||||
opErr = unix.SetsockoptInt(int(fd), unix.SOL_SOCKET, unix.SO_REUSEADDR, 1)
|
||||
})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return opErr
|
||||
}
|
||||
|
||||
func listenTCP(network, addr string, reuseport, reuseaddr bool) (net.Listener, error) {
|
||||
var lc net.ListenConfig
|
||||
if reuseport {
|
||||
switch {
|
||||
case reuseaddr && reuseport:
|
||||
case reuseport:
|
||||
lc.Control = reuseportControl
|
||||
case reuseaddr:
|
||||
lc.Control = reuseaddrControl
|
||||
}
|
||||
|
||||
return lc.Listen(context.Background(), network, addr)
|
||||
}
|
||||
|
||||
func listenUDP(network, addr string, reuseport bool) (net.PacketConn, error) {
|
||||
func listenUDP(network, addr string, reuseport, reuseaddr bool) (net.PacketConn, error) {
|
||||
var lc net.ListenConfig
|
||||
if reuseport {
|
||||
switch {
|
||||
case reuseaddr && reuseport:
|
||||
case reuseport:
|
||||
lc.Control = reuseportControl
|
||||
case reuseaddr:
|
||||
lc.Control = reuseaddrControl
|
||||
}
|
||||
|
||||
return lc.ListenPacket(context.Background(), network, addr)
|
||||
|
|
125
vendor/github.com/miekg/dns/msg.go
generated
vendored
125
vendor/github.com/miekg/dns/msg.go
generated
vendored
|
@ -252,7 +252,7 @@ loop:
|
|||
}
|
||||
|
||||
// check for \DDD
|
||||
if i+3 < ls && isDigit(bs[i+1]) && isDigit(bs[i+2]) && isDigit(bs[i+3]) {
|
||||
if isDDD(bs[i+1:]) {
|
||||
bs[i] = dddToByte(bs[i+1:])
|
||||
copy(bs[i+1:ls-3], bs[i+4:])
|
||||
ls -= 3
|
||||
|
@ -265,6 +265,11 @@ loop:
|
|||
|
||||
wasDot = false
|
||||
case '.':
|
||||
if i == 0 && len(s) > 1 {
|
||||
// leading dots are not legal except for the root zone
|
||||
return len(msg), ErrRdata
|
||||
}
|
||||
|
||||
if wasDot {
|
||||
// two dots back to back is not legal
|
||||
return len(msg), ErrRdata
|
||||
|
@ -443,7 +448,7 @@ Loop:
|
|||
return string(s), off1, nil
|
||||
}
|
||||
|
||||
func packTxt(txt []string, msg []byte, offset int, tmp []byte) (int, error) {
|
||||
func packTxt(txt []string, msg []byte, offset int) (int, error) {
|
||||
if len(txt) == 0 {
|
||||
if offset >= len(msg) {
|
||||
return offset, ErrBuf
|
||||
|
@ -453,10 +458,7 @@ func packTxt(txt []string, msg []byte, offset int, tmp []byte) (int, error) {
|
|||
}
|
||||
var err error
|
||||
for _, s := range txt {
|
||||
if len(s) > len(tmp) {
|
||||
return offset, ErrBuf
|
||||
}
|
||||
offset, err = packTxtString(s, msg, offset, tmp)
|
||||
offset, err = packTxtString(s, msg, offset)
|
||||
if err != nil {
|
||||
return offset, err
|
||||
}
|
||||
|
@ -464,32 +466,30 @@ func packTxt(txt []string, msg []byte, offset int, tmp []byte) (int, error) {
|
|||
return offset, nil
|
||||
}
|
||||
|
||||
func packTxtString(s string, msg []byte, offset int, tmp []byte) (int, error) {
|
||||
func packTxtString(s string, msg []byte, offset int) (int, error) {
|
||||
lenByteOffset := offset
|
||||
if offset >= len(msg) || len(s) > len(tmp) {
|
||||
if offset >= len(msg) || len(s) > 256*4+1 /* If all \DDD */ {
|
||||
return offset, ErrBuf
|
||||
}
|
||||
offset++
|
||||
bs := tmp[:len(s)]
|
||||
copy(bs, s)
|
||||
for i := 0; i < len(bs); i++ {
|
||||
for i := 0; i < len(s); i++ {
|
||||
if len(msg) <= offset {
|
||||
return offset, ErrBuf
|
||||
}
|
||||
if bs[i] == '\\' {
|
||||
if s[i] == '\\' {
|
||||
i++
|
||||
if i == len(bs) {
|
||||
if i == len(s) {
|
||||
break
|
||||
}
|
||||
// check for \DDD
|
||||
if i+2 < len(bs) && isDigit(bs[i]) && isDigit(bs[i+1]) && isDigit(bs[i+2]) {
|
||||
msg[offset] = dddToByte(bs[i:])
|
||||
if isDDD(s[i:]) {
|
||||
msg[offset] = dddToByte(s[i:])
|
||||
i += 2
|
||||
} else {
|
||||
msg[offset] = bs[i]
|
||||
msg[offset] = s[i]
|
||||
}
|
||||
} else {
|
||||
msg[offset] = bs[i]
|
||||
msg[offset] = s[i]
|
||||
}
|
||||
offset++
|
||||
}
|
||||
|
@ -501,30 +501,28 @@ func packTxtString(s string, msg []byte, offset int, tmp []byte) (int, error) {
|
|||
return offset, nil
|
||||
}
|
||||
|
||||
func packOctetString(s string, msg []byte, offset int, tmp []byte) (int, error) {
|
||||
if offset >= len(msg) || len(s) > len(tmp) {
|
||||
func packOctetString(s string, msg []byte, offset int) (int, error) {
|
||||
if offset >= len(msg) || len(s) > 256*4+1 {
|
||||
return offset, ErrBuf
|
||||
}
|
||||
bs := tmp[:len(s)]
|
||||
copy(bs, s)
|
||||
for i := 0; i < len(bs); i++ {
|
||||
for i := 0; i < len(s); i++ {
|
||||
if len(msg) <= offset {
|
||||
return offset, ErrBuf
|
||||
}
|
||||
if bs[i] == '\\' {
|
||||
if s[i] == '\\' {
|
||||
i++
|
||||
if i == len(bs) {
|
||||
if i == len(s) {
|
||||
break
|
||||
}
|
||||
// check for \DDD
|
||||
if i+2 < len(bs) && isDigit(bs[i]) && isDigit(bs[i+1]) && isDigit(bs[i+2]) {
|
||||
msg[offset] = dddToByte(bs[i:])
|
||||
if isDDD(s[i:]) {
|
||||
msg[offset] = dddToByte(s[i:])
|
||||
i += 2
|
||||
} else {
|
||||
msg[offset] = bs[i]
|
||||
msg[offset] = s[i]
|
||||
}
|
||||
} else {
|
||||
msg[offset] = bs[i]
|
||||
msg[offset] = s[i]
|
||||
}
|
||||
offset++
|
||||
}
|
||||
|
@ -546,12 +544,11 @@ func unpackTxt(msg []byte, off0 int) (ss []string, off int, err error) {
|
|||
// Helpers for dealing with escaped bytes
|
||||
func isDigit(b byte) bool { return b >= '0' && b <= '9' }
|
||||
|
||||
func dddToByte(s []byte) byte {
|
||||
_ = s[2] // bounds check hint to compiler; see golang.org/issue/14808
|
||||
return byte((s[0]-'0')*100 + (s[1]-'0')*10 + (s[2] - '0'))
|
||||
func isDDD[T ~[]byte | ~string](s T) bool {
|
||||
return len(s) >= 3 && isDigit(s[0]) && isDigit(s[1]) && isDigit(s[2])
|
||||
}
|
||||
|
||||
func dddStringToByte(s string) byte {
|
||||
func dddToByte[T ~[]byte | ~string](s T) byte {
|
||||
_ = s[2] // bounds check hint to compiler; see golang.org/issue/14808
|
||||
return byte((s[0]-'0')*100 + (s[1]-'0')*10 + (s[2] - '0'))
|
||||
}
|
||||
|
@ -675,9 +672,9 @@ func unpackRRslice(l int, msg []byte, off int) (dst1 []RR, off1 int, err error)
|
|||
|
||||
// Convert a MsgHdr to a string, with dig-like headers:
|
||||
//
|
||||
//;; opcode: QUERY, status: NOERROR, id: 48404
|
||||
// ;; opcode: QUERY, status: NOERROR, id: 48404
|
||||
//
|
||||
//;; flags: qr aa rd ra;
|
||||
// ;; flags: qr aa rd ra;
|
||||
func (h *MsgHdr) String() string {
|
||||
if h == nil {
|
||||
return "<nil> MsgHdr"
|
||||
|
@ -861,7 +858,7 @@ func (dns *Msg) unpack(dh Header, msg []byte, off int) (err error) {
|
|||
// The header counts might have been wrong so we need to update it
|
||||
dh.Nscount = uint16(len(dns.Ns))
|
||||
if err == nil {
|
||||
dns.Extra, off, err = unpackRRslice(int(dh.Arcount), msg, off)
|
||||
dns.Extra, _, err = unpackRRslice(int(dh.Arcount), msg, off)
|
||||
}
|
||||
// The header counts might have been wrong so we need to update it
|
||||
dh.Arcount = uint16(len(dns.Extra))
|
||||
|
@ -871,11 +868,11 @@ func (dns *Msg) unpack(dh Header, msg []byte, off int) (err error) {
|
|||
dns.Rcode |= opt.ExtendedRcode()
|
||||
}
|
||||
|
||||
if off != len(msg) {
|
||||
// TODO(miek) make this an error?
|
||||
// use PackOpt to let people tell how detailed the error reporting should be?
|
||||
// println("dns: extra bytes in dns packet", off, "<", len(msg))
|
||||
}
|
||||
// TODO(miek) make this an error?
|
||||
// use PackOpt to let people tell how detailed the error reporting should be?
|
||||
// if off != len(msg) {
|
||||
// // println("dns: extra bytes in dns packet", off, "<", len(msg))
|
||||
// }
|
||||
return err
|
||||
|
||||
}
|
||||
|
@ -897,18 +894,38 @@ func (dns *Msg) String() string {
|
|||
return "<nil> MsgHdr"
|
||||
}
|
||||
s := dns.MsgHdr.String() + " "
|
||||
s += "QUERY: " + strconv.Itoa(len(dns.Question)) + ", "
|
||||
s += "ANSWER: " + strconv.Itoa(len(dns.Answer)) + ", "
|
||||
s += "AUTHORITY: " + strconv.Itoa(len(dns.Ns)) + ", "
|
||||
s += "ADDITIONAL: " + strconv.Itoa(len(dns.Extra)) + "\n"
|
||||
if dns.MsgHdr.Opcode == OpcodeUpdate {
|
||||
s += "ZONE: " + strconv.Itoa(len(dns.Question)) + ", "
|
||||
s += "PREREQ: " + strconv.Itoa(len(dns.Answer)) + ", "
|
||||
s += "UPDATE: " + strconv.Itoa(len(dns.Ns)) + ", "
|
||||
s += "ADDITIONAL: " + strconv.Itoa(len(dns.Extra)) + "\n"
|
||||
} else {
|
||||
s += "QUERY: " + strconv.Itoa(len(dns.Question)) + ", "
|
||||
s += "ANSWER: " + strconv.Itoa(len(dns.Answer)) + ", "
|
||||
s += "AUTHORITY: " + strconv.Itoa(len(dns.Ns)) + ", "
|
||||
s += "ADDITIONAL: " + strconv.Itoa(len(dns.Extra)) + "\n"
|
||||
}
|
||||
opt := dns.IsEdns0()
|
||||
if opt != nil {
|
||||
// OPT PSEUDOSECTION
|
||||
s += opt.String() + "\n"
|
||||
}
|
||||
if len(dns.Question) > 0 {
|
||||
s += "\n;; QUESTION SECTION:\n"
|
||||
if dns.MsgHdr.Opcode == OpcodeUpdate {
|
||||
s += "\n;; ZONE SECTION:\n"
|
||||
} else {
|
||||
s += "\n;; QUESTION SECTION:\n"
|
||||
}
|
||||
for _, r := range dns.Question {
|
||||
s += r.String() + "\n"
|
||||
}
|
||||
}
|
||||
if len(dns.Answer) > 0 {
|
||||
s += "\n;; ANSWER SECTION:\n"
|
||||
if dns.MsgHdr.Opcode == OpcodeUpdate {
|
||||
s += "\n;; PREREQUISITE SECTION:\n"
|
||||
} else {
|
||||
s += "\n;; ANSWER SECTION:\n"
|
||||
}
|
||||
for _, r := range dns.Answer {
|
||||
if r != nil {
|
||||
s += r.String() + "\n"
|
||||
|
@ -916,17 +933,21 @@ func (dns *Msg) String() string {
|
|||
}
|
||||
}
|
||||
if len(dns.Ns) > 0 {
|
||||
s += "\n;; AUTHORITY SECTION:\n"
|
||||
if dns.MsgHdr.Opcode == OpcodeUpdate {
|
||||
s += "\n;; UPDATE SECTION:\n"
|
||||
} else {
|
||||
s += "\n;; AUTHORITY SECTION:\n"
|
||||
}
|
||||
for _, r := range dns.Ns {
|
||||
if r != nil {
|
||||
s += r.String() + "\n"
|
||||
}
|
||||
}
|
||||
}
|
||||
if len(dns.Extra) > 0 {
|
||||
if len(dns.Extra) > 0 && (opt == nil || len(dns.Extra) > 1) {
|
||||
s += "\n;; ADDITIONAL SECTION:\n"
|
||||
for _, r := range dns.Extra {
|
||||
if r != nil {
|
||||
if r != nil && r.Header().Rrtype != TypeOPT {
|
||||
s += r.String() + "\n"
|
||||
}
|
||||
}
|
||||
|
@ -1014,7 +1035,7 @@ func escapedNameLen(s string) int {
|
|||
continue
|
||||
}
|
||||
|
||||
if i+3 < len(s) && isDigit(s[i+1]) && isDigit(s[i+2]) && isDigit(s[i+3]) {
|
||||
if isDDD(s[i+1:]) {
|
||||
nameLen -= 3
|
||||
i += 3
|
||||
} else {
|
||||
|
@ -1055,8 +1076,8 @@ func (dns *Msg) CopyTo(r1 *Msg) *Msg {
|
|||
r1.Compress = dns.Compress
|
||||
|
||||
if len(dns.Question) > 0 {
|
||||
r1.Question = make([]Question, len(dns.Question))
|
||||
copy(r1.Question, dns.Question) // TODO(miek): Question is an immutable value, ok to do a shallow-copy
|
||||
// TODO(miek): Question is an immutable value, ok to do a shallow-copy
|
||||
r1.Question = cloneSlice(dns.Question)
|
||||
}
|
||||
|
||||
rrArr := make([]RR, len(dns.Answer)+len(dns.Ns)+len(dns.Extra))
|
||||
|
|
118
vendor/github.com/miekg/dns/msg_helpers.go
generated
vendored
118
vendor/github.com/miekg/dns/msg_helpers.go
generated
vendored
|
@ -20,9 +20,7 @@ func unpackDataA(msg []byte, off int) (net.IP, int, error) {
|
|||
if off+net.IPv4len > len(msg) {
|
||||
return nil, len(msg), &Error{err: "overflow unpacking a"}
|
||||
}
|
||||
a := append(make(net.IP, 0, net.IPv4len), msg[off:off+net.IPv4len]...)
|
||||
off += net.IPv4len
|
||||
return a, off, nil
|
||||
return cloneSlice(msg[off : off+net.IPv4len]), off + net.IPv4len, nil
|
||||
}
|
||||
|
||||
func packDataA(a net.IP, msg []byte, off int) (int, error) {
|
||||
|
@ -47,9 +45,7 @@ func unpackDataAAAA(msg []byte, off int) (net.IP, int, error) {
|
|||
if off+net.IPv6len > len(msg) {
|
||||
return nil, len(msg), &Error{err: "overflow unpacking aaaa"}
|
||||
}
|
||||
aaaa := append(make(net.IP, 0, net.IPv6len), msg[off:off+net.IPv6len]...)
|
||||
off += net.IPv6len
|
||||
return aaaa, off, nil
|
||||
return cloneSlice(msg[off : off+net.IPv6len]), off + net.IPv6len, nil
|
||||
}
|
||||
|
||||
func packDataAAAA(aaaa net.IP, msg []byte, off int) (int, error) {
|
||||
|
@ -299,8 +295,7 @@ func unpackString(msg []byte, off int) (string, int, error) {
|
|||
}
|
||||
|
||||
func packString(s string, msg []byte, off int) (int, error) {
|
||||
txtTmp := make([]byte, 256*4+1)
|
||||
off, err := packTxtString(s, msg, off, txtTmp)
|
||||
off, err := packTxtString(s, msg, off)
|
||||
if err != nil {
|
||||
return len(msg), err
|
||||
}
|
||||
|
@ -402,8 +397,7 @@ func unpackStringTxt(msg []byte, off int) ([]string, int, error) {
|
|||
}
|
||||
|
||||
func packStringTxt(s []string, msg []byte, off int) (int, error) {
|
||||
txtTmp := make([]byte, 256*4+1) // If the whole string consists out of \DDD we need this many.
|
||||
off, err := packTxt(s, msg, off, txtTmp)
|
||||
off, err := packTxt(s, msg, off)
|
||||
if err != nil {
|
||||
return len(msg), err
|
||||
}
|
||||
|
@ -412,29 +406,24 @@ func packStringTxt(s []string, msg []byte, off int) (int, error) {
|
|||
|
||||
func unpackDataOpt(msg []byte, off int) ([]EDNS0, int, error) {
|
||||
var edns []EDNS0
|
||||
Option:
|
||||
var code uint16
|
||||
if off+4 > len(msg) {
|
||||
return nil, len(msg), &Error{err: "overflow unpacking opt"}
|
||||
for off < len(msg) {
|
||||
if off+4 > len(msg) {
|
||||
return nil, len(msg), &Error{err: "overflow unpacking opt"}
|
||||
}
|
||||
code := binary.BigEndian.Uint16(msg[off:])
|
||||
off += 2
|
||||
optlen := binary.BigEndian.Uint16(msg[off:])
|
||||
off += 2
|
||||
if off+int(optlen) > len(msg) {
|
||||
return nil, len(msg), &Error{err: "overflow unpacking opt"}
|
||||
}
|
||||
opt := makeDataOpt(code)
|
||||
if err := opt.unpack(msg[off : off+int(optlen)]); err != nil {
|
||||
return nil, len(msg), err
|
||||
}
|
||||
edns = append(edns, opt)
|
||||
off += int(optlen)
|
||||
}
|
||||
code = binary.BigEndian.Uint16(msg[off:])
|
||||
off += 2
|
||||
optlen := binary.BigEndian.Uint16(msg[off:])
|
||||
off += 2
|
||||
if off+int(optlen) > len(msg) {
|
||||
return nil, len(msg), &Error{err: "overflow unpacking opt"}
|
||||
}
|
||||
e := makeDataOpt(code)
|
||||
if err := e.unpack(msg[off : off+int(optlen)]); err != nil {
|
||||
return nil, len(msg), err
|
||||
}
|
||||
edns = append(edns, e)
|
||||
off += int(optlen)
|
||||
|
||||
if off < len(msg) {
|
||||
goto Option
|
||||
}
|
||||
|
||||
return edns, off, nil
|
||||
}
|
||||
|
||||
|
@ -463,8 +452,7 @@ func unpackStringOctet(msg []byte, off int) (string, int, error) {
|
|||
}
|
||||
|
||||
func packStringOctet(s string, msg []byte, off int) (int, error) {
|
||||
txtTmp := make([]byte, 256*4+1)
|
||||
off, err := packOctetString(s, msg, off, txtTmp)
|
||||
off, err := packOctetString(s, msg, off)
|
||||
if err != nil {
|
||||
return len(msg), err
|
||||
}
|
||||
|
@ -476,7 +464,7 @@ func unpackDataNsec(msg []byte, off int) ([]uint16, int, error) {
|
|||
length, window, lastwindow := 0, 0, -1
|
||||
for off < len(msg) {
|
||||
if off+2 > len(msg) {
|
||||
return nsec, len(msg), &Error{err: "overflow unpacking nsecx"}
|
||||
return nsec, len(msg), &Error{err: "overflow unpacking NSEC(3)"}
|
||||
}
|
||||
window = int(msg[off])
|
||||
length = int(msg[off+1])
|
||||
|
@ -484,17 +472,17 @@ func unpackDataNsec(msg []byte, off int) ([]uint16, int, error) {
|
|||
if window <= lastwindow {
|
||||
// RFC 4034: Blocks are present in the NSEC RR RDATA in
|
||||
// increasing numerical order.
|
||||
return nsec, len(msg), &Error{err: "out of order NSEC block"}
|
||||
return nsec, len(msg), &Error{err: "out of order NSEC(3) block in type bitmap"}
|
||||
}
|
||||
if length == 0 {
|
||||
// RFC 4034: Blocks with no types present MUST NOT be included.
|
||||
return nsec, len(msg), &Error{err: "empty NSEC block"}
|
||||
return nsec, len(msg), &Error{err: "empty NSEC(3) block in type bitmap"}
|
||||
}
|
||||
if length > 32 {
|
||||
return nsec, len(msg), &Error{err: "NSEC block too long"}
|
||||
return nsec, len(msg), &Error{err: "NSEC(3) block too long in type bitmap"}
|
||||
}
|
||||
if off+length > len(msg) {
|
||||
return nsec, len(msg), &Error{err: "overflowing NSEC block"}
|
||||
return nsec, len(msg), &Error{err: "overflowing NSEC(3) block in type bitmap"}
|
||||
}
|
||||
|
||||
// Walk the bytes in the window and extract the type bits
|
||||
|
@ -558,6 +546,16 @@ func packDataNsec(bitmap []uint16, msg []byte, off int) (int, error) {
|
|||
if len(bitmap) == 0 {
|
||||
return off, nil
|
||||
}
|
||||
if off > len(msg) {
|
||||
return off, &Error{err: "overflow packing nsec"}
|
||||
}
|
||||
toZero := msg[off:]
|
||||
if maxLen := typeBitMapLen(bitmap); maxLen < len(toZero) {
|
||||
toZero = toZero[:maxLen]
|
||||
}
|
||||
for i := range toZero {
|
||||
toZero[i] = 0
|
||||
}
|
||||
var lastwindow, lastlength uint16
|
||||
for _, t := range bitmap {
|
||||
window := t / 256
|
||||
|
@ -615,7 +613,7 @@ func unpackDataSVCB(msg []byte, off int) ([]SVCBKeyValue, int, error) {
|
|||
}
|
||||
|
||||
func packDataSVCB(pairs []SVCBKeyValue, msg []byte, off int) (int, error) {
|
||||
pairs = append([]SVCBKeyValue(nil), pairs...)
|
||||
pairs = cloneSlice(pairs)
|
||||
sort.Slice(pairs, func(i, j int) bool {
|
||||
return pairs[i].Key() < pairs[j].Key()
|
||||
})
|
||||
|
@ -781,6 +779,8 @@ func unpackDataAplPrefix(msg []byte, off int) (APLPrefix, int, error) {
|
|||
if off+afdlen > len(msg) {
|
||||
return APLPrefix{}, len(msg), &Error{err: "overflow unpacking APL address"}
|
||||
}
|
||||
|
||||
// Address MUST NOT contain trailing zero bytes per RFC3123 Sections 4.1 and 4.2.
|
||||
off += copy(ip, msg[off:off+afdlen])
|
||||
if afdlen > 0 {
|
||||
last := ip[afdlen-1]
|
||||
|
@ -792,13 +792,43 @@ func unpackDataAplPrefix(msg []byte, off int) (APLPrefix, int, error) {
|
|||
IP: ip,
|
||||
Mask: net.CIDRMask(int(prefix), 8*len(ip)),
|
||||
}
|
||||
network := ipnet.IP.Mask(ipnet.Mask)
|
||||
if !network.Equal(ipnet.IP) {
|
||||
return APLPrefix{}, len(msg), &Error{err: "invalid APL address length"}
|
||||
}
|
||||
|
||||
return APLPrefix{
|
||||
Negation: (nlen & 0x80) != 0,
|
||||
Network: ipnet,
|
||||
}, off, nil
|
||||
}
|
||||
|
||||
func unpackIPSECGateway(msg []byte, off int, gatewayType uint8) (net.IP, string, int, error) {
|
||||
var retAddr net.IP
|
||||
var retString string
|
||||
var err error
|
||||
|
||||
switch gatewayType {
|
||||
case IPSECGatewayNone: // do nothing
|
||||
case IPSECGatewayIPv4:
|
||||
retAddr, off, err = unpackDataA(msg, off)
|
||||
case IPSECGatewayIPv6:
|
||||
retAddr, off, err = unpackDataAAAA(msg, off)
|
||||
case IPSECGatewayHost:
|
||||
retString, off, err = UnpackDomainName(msg, off)
|
||||
}
|
||||
|
||||
return retAddr, retString, off, err
|
||||
}
|
||||
|
||||
func packIPSECGateway(gatewayAddr net.IP, gatewayString string, msg []byte, off int, gatewayType uint8, compression compressionMap, compress bool) (int, error) {
|
||||
var err error
|
||||
|
||||
switch gatewayType {
|
||||
case IPSECGatewayNone: // do nothing
|
||||
case IPSECGatewayIPv4:
|
||||
off, err = packDataA(gatewayAddr, msg, off)
|
||||
case IPSECGatewayIPv6:
|
||||
off, err = packDataAAAA(gatewayAddr, msg, off)
|
||||
case IPSECGatewayHost:
|
||||
off, err = packDomainName(gatewayString, msg, off, compression, compress)
|
||||
}
|
||||
|
||||
return off, err
|
||||
}
|
||||
|
|
71
vendor/github.com/miekg/dns/scan.go
generated
vendored
71
vendor/github.com/miekg/dns/scan.go
generated
vendored
|
@ -10,13 +10,13 @@ import (
|
|||
"strings"
|
||||
)
|
||||
|
||||
const maxTok = 2048 // Largest token we can return.
|
||||
const maxTok = 512 // Token buffer start size, and growth size amount.
|
||||
|
||||
// The maximum depth of $INCLUDE directives supported by the
|
||||
// ZoneParser API.
|
||||
const maxIncludeDepth = 7
|
||||
|
||||
// Tokinize a RFC 1035 zone file. The tokenizer will normalize it:
|
||||
// Tokenize a RFC 1035 zone file. The tokenizer will normalize it:
|
||||
// * Add ownernames if they are left blank;
|
||||
// * Suppress sequences of spaces;
|
||||
// * Make each RR fit on one line (_NEWLINE is send as last)
|
||||
|
@ -605,8 +605,6 @@ func (zp *ZoneParser) Next() (RR, bool) {
|
|||
if !isPrivate && zp.c.Peek().token == "" {
|
||||
// This is a dynamic update rr.
|
||||
|
||||
// TODO(tmthrgd): Previously slurpRemainder was only called
|
||||
// for certain RR types, which may have been important.
|
||||
if err := slurpRemainder(zp.c); err != nil {
|
||||
return zp.setParseError(err.err, err.lex)
|
||||
}
|
||||
|
@ -765,8 +763,8 @@ func (zl *zlexer) Next() (lex, bool) {
|
|||
}
|
||||
|
||||
var (
|
||||
str [maxTok]byte // Hold string text
|
||||
com [maxTok]byte // Hold comment text
|
||||
str = make([]byte, maxTok) // Hold string text
|
||||
com = make([]byte, maxTok) // Hold comment text
|
||||
|
||||
stri int // Offset in str (0 means empty)
|
||||
comi int // Offset in com (0 means empty)
|
||||
|
@ -785,14 +783,12 @@ func (zl *zlexer) Next() (lex, bool) {
|
|||
l.line, l.column = zl.line, zl.column
|
||||
|
||||
if stri >= len(str) {
|
||||
l.token = "token length insufficient for parsing"
|
||||
l.err = true
|
||||
return *l, true
|
||||
// if buffer length is insufficient, increase it.
|
||||
str = append(str[:], make([]byte, maxTok)...)
|
||||
}
|
||||
if comi >= len(com) {
|
||||
l.token = "comment length insufficient for parsing"
|
||||
l.err = true
|
||||
return *l, true
|
||||
// if buffer length is insufficient, increase it.
|
||||
com = append(com[:], make([]byte, maxTok)...)
|
||||
}
|
||||
|
||||
switch x {
|
||||
|
@ -816,7 +812,7 @@ func (zl *zlexer) Next() (lex, bool) {
|
|||
if stri == 0 {
|
||||
// Space directly in the beginning, handled in the grammar
|
||||
} else if zl.owner {
|
||||
// If we have a string and its the first, make it an owner
|
||||
// If we have a string and it's the first, make it an owner
|
||||
l.value = zOwner
|
||||
l.token = string(str[:stri])
|
||||
|
||||
|
@ -1218,42 +1214,34 @@ func stringToCm(token string) (e, m uint8, ok bool) {
|
|||
if token[len(token)-1] == 'M' || token[len(token)-1] == 'm' {
|
||||
token = token[0 : len(token)-1]
|
||||
}
|
||||
s := strings.SplitN(token, ".", 2)
|
||||
var meters, cmeters, val int
|
||||
var err error
|
||||
switch len(s) {
|
||||
case 2:
|
||||
if cmeters, err = strconv.Atoi(s[1]); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
var (
|
||||
meters, cmeters, val int
|
||||
err error
|
||||
)
|
||||
mStr, cmStr, hasCM := strings.Cut(token, ".")
|
||||
if hasCM {
|
||||
// There's no point in having more than 2 digits in this part, and would rather make the implementation complicated ('123' should be treated as '12').
|
||||
// So we simply reject it.
|
||||
// We also make sure the first character is a digit to reject '+-' signs.
|
||||
if len(s[1]) > 2 || s[1][0] < '0' || s[1][0] > '9' {
|
||||
cmeters, err = strconv.Atoi(cmStr)
|
||||
if err != nil || len(cmStr) > 2 || cmStr[0] < '0' || cmStr[0] > '9' {
|
||||
return
|
||||
}
|
||||
if len(s[1]) == 1 {
|
||||
if len(cmStr) == 1 {
|
||||
// 'nn.1' must be treated as 'nn-meters and 10cm, not 1cm.
|
||||
cmeters *= 10
|
||||
}
|
||||
if s[0] == "" {
|
||||
// This will allow omitting the 'meter' part, like .01 (meaning 0.01m = 1cm).
|
||||
break
|
||||
}
|
||||
fallthrough
|
||||
case 1:
|
||||
if meters, err = strconv.Atoi(s[0]); err != nil {
|
||||
return
|
||||
}
|
||||
// RFC1876 states the max value is 90000000.00. The latter two conditions enforce it.
|
||||
if s[0][0] < '0' || s[0][0] > '9' || meters > 90000000 || (meters == 90000000 && cmeters != 0) {
|
||||
return
|
||||
}
|
||||
case 0:
|
||||
// huh?
|
||||
return 0, 0, false
|
||||
}
|
||||
ok = true
|
||||
// This slighly ugly condition will allow omitting the 'meter' part, like .01 (meaning 0.01m = 1cm).
|
||||
if !hasCM || mStr != "" {
|
||||
meters, err = strconv.Atoi(mStr)
|
||||
// RFC1876 states the max value is 90000000.00. The latter two conditions enforce it.
|
||||
if err != nil || mStr[0] < '0' || mStr[0] > '9' || meters > 90000000 || (meters == 90000000 && cmeters != 0) {
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
if meters > 0 {
|
||||
e = 2
|
||||
val = meters
|
||||
|
@ -1265,8 +1253,7 @@ func stringToCm(token string) (e, m uint8, ok bool) {
|
|||
e++
|
||||
val /= 10
|
||||
}
|
||||
m = uint8(val)
|
||||
return
|
||||
return e, uint8(val), true
|
||||
}
|
||||
|
||||
func toAbsoluteName(name, origin string) (absolute string, ok bool) {
|
||||
|
|
134
vendor/github.com/miekg/dns/scan_rr.go
generated
vendored
134
vendor/github.com/miekg/dns/scan_rr.go
generated
vendored
|
@ -1,8 +1,8 @@
|
|||
package dns
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/base64"
|
||||
"errors"
|
||||
"net"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
@ -11,15 +11,15 @@ import (
|
|||
// A remainder of the rdata with embedded spaces, return the parsed string (sans the spaces)
|
||||
// or an error
|
||||
func endingToString(c *zlexer, errstr string) (string, *ParseError) {
|
||||
var buffer bytes.Buffer
|
||||
var s strings.Builder
|
||||
l, _ := c.Next() // zString
|
||||
for l.value != zNewline && l.value != zEOF {
|
||||
if l.err {
|
||||
return buffer.String(), &ParseError{"", errstr, l}
|
||||
return s.String(), &ParseError{"", errstr, l}
|
||||
}
|
||||
switch l.value {
|
||||
case zString:
|
||||
buffer.WriteString(l.token)
|
||||
s.WriteString(l.token)
|
||||
case zBlank: // Ok
|
||||
default:
|
||||
return "", &ParseError{"", errstr, l}
|
||||
|
@ -27,7 +27,7 @@ func endingToString(c *zlexer, errstr string) (string, *ParseError) {
|
|||
l, _ = c.Next()
|
||||
}
|
||||
|
||||
return buffer.String(), nil
|
||||
return s.String(), nil
|
||||
}
|
||||
|
||||
// A remainder of the rdata with embedded spaces, split on unquoted whitespace
|
||||
|
@ -903,11 +903,18 @@ func (rr *RRSIG) parse(c *zlexer, o string) *ParseError {
|
|||
|
||||
c.Next() // zBlank
|
||||
l, _ = c.Next()
|
||||
i, e := strconv.ParseUint(l.token, 10, 8)
|
||||
if e != nil || l.err {
|
||||
if l.err {
|
||||
return &ParseError{"", "bad RRSIG Algorithm", l}
|
||||
}
|
||||
rr.Algorithm = uint8(i)
|
||||
i, e := strconv.ParseUint(l.token, 10, 8)
|
||||
rr.Algorithm = uint8(i) // if 0 we'll check the mnemonic in the if
|
||||
if e != nil {
|
||||
v, ok := StringToAlgorithm[l.token]
|
||||
if !ok {
|
||||
return &ParseError{"", "bad RRSIG Algorithm", l}
|
||||
}
|
||||
rr.Algorithm = v
|
||||
}
|
||||
|
||||
c.Next() // zBlank
|
||||
l, _ = c.Next()
|
||||
|
@ -1216,6 +1223,117 @@ func (rr *DS) parse(c *zlexer, o string) *ParseError { return rr.parseDS(c,
|
|||
func (rr *DLV) parse(c *zlexer, o string) *ParseError { return rr.parseDS(c, o, "DLV") }
|
||||
func (rr *CDS) parse(c *zlexer, o string) *ParseError { return rr.parseDS(c, o, "CDS") }
|
||||
|
||||
func (rr *IPSECKEY) parse(c *zlexer, o string) *ParseError {
|
||||
l, _ := c.Next()
|
||||
num, err := strconv.ParseUint(l.token, 10, 8)
|
||||
if err != nil || l.err {
|
||||
return &ParseError{"", "bad IPSECKEY value", l}
|
||||
}
|
||||
rr.Precedence = uint8(num)
|
||||
c.Next() // zBlank
|
||||
|
||||
l, _ = c.Next()
|
||||
num, err = strconv.ParseUint(l.token, 10, 8)
|
||||
if err != nil || l.err {
|
||||
return &ParseError{"", "bad IPSECKEY value", l}
|
||||
}
|
||||
rr.GatewayType = uint8(num)
|
||||
c.Next() // zBlank
|
||||
|
||||
l, _ = c.Next()
|
||||
num, err = strconv.ParseUint(l.token, 10, 8)
|
||||
if err != nil || l.err {
|
||||
return &ParseError{"", "bad IPSECKEY value", l}
|
||||
}
|
||||
rr.Algorithm = uint8(num)
|
||||
c.Next() // zBlank
|
||||
|
||||
l, _ = c.Next()
|
||||
if l.err {
|
||||
return &ParseError{"", "bad IPSECKEY gateway", l}
|
||||
}
|
||||
|
||||
rr.GatewayAddr, rr.GatewayHost, err = parseAddrHostUnion(l.token, o, rr.GatewayType)
|
||||
if err != nil {
|
||||
return &ParseError{"", "IPSECKEY " + err.Error(), l}
|
||||
}
|
||||
|
||||
c.Next() // zBlank
|
||||
|
||||
s, pErr := endingToString(c, "bad IPSECKEY PublicKey")
|
||||
if pErr != nil {
|
||||
return pErr
|
||||
}
|
||||
rr.PublicKey = s
|
||||
return slurpRemainder(c)
|
||||
}
|
||||
|
||||
func (rr *AMTRELAY) parse(c *zlexer, o string) *ParseError {
|
||||
l, _ := c.Next()
|
||||
num, err := strconv.ParseUint(l.token, 10, 8)
|
||||
if err != nil || l.err {
|
||||
return &ParseError{"", "bad AMTRELAY value", l}
|
||||
}
|
||||
rr.Precedence = uint8(num)
|
||||
c.Next() // zBlank
|
||||
|
||||
l, _ = c.Next()
|
||||
if l.err || !(l.token == "0" || l.token == "1") {
|
||||
return &ParseError{"", "bad discovery value", l}
|
||||
}
|
||||
if l.token == "1" {
|
||||
rr.GatewayType = 0x80
|
||||
}
|
||||
|
||||
c.Next() // zBlank
|
||||
|
||||
l, _ = c.Next()
|
||||
num, err = strconv.ParseUint(l.token, 10, 8)
|
||||
if err != nil || l.err {
|
||||
return &ParseError{"", "bad AMTRELAY value", l}
|
||||
}
|
||||
rr.GatewayType |= uint8(num)
|
||||
c.Next() // zBlank
|
||||
|
||||
l, _ = c.Next()
|
||||
if l.err {
|
||||
return &ParseError{"", "bad AMTRELAY gateway", l}
|
||||
}
|
||||
|
||||
rr.GatewayAddr, rr.GatewayHost, err = parseAddrHostUnion(l.token, o, rr.GatewayType&0x7f)
|
||||
if err != nil {
|
||||
return &ParseError{"", "AMTRELAY " + err.Error(), l}
|
||||
}
|
||||
|
||||
return slurpRemainder(c)
|
||||
}
|
||||
|
||||
// same constants and parsing between IPSECKEY and AMTRELAY
|
||||
func parseAddrHostUnion(token, o string, gatewayType uint8) (addr net.IP, host string, err error) {
|
||||
switch gatewayType {
|
||||
case IPSECGatewayNone:
|
||||
if token != "." {
|
||||
return addr, host, errors.New("gateway type none with gateway set")
|
||||
}
|
||||
case IPSECGatewayIPv4, IPSECGatewayIPv6:
|
||||
addr = net.ParseIP(token)
|
||||
if addr == nil {
|
||||
return addr, host, errors.New("gateway IP invalid")
|
||||
}
|
||||
if (addr.To4() == nil) == (gatewayType == IPSECGatewayIPv4) {
|
||||
return addr, host, errors.New("gateway IP family mismatch")
|
||||
}
|
||||
case IPSECGatewayHost:
|
||||
var ok bool
|
||||
host, ok = toAbsoluteName(token, o)
|
||||
if !ok {
|
||||
return addr, host, errors.New("invalid gateway host")
|
||||
}
|
||||
}
|
||||
|
||||
return addr, host, nil
|
||||
}
|
||||
|
||||
func (rr *RKEY) parse(c *zlexer, o string) *ParseError {
|
||||
l, _ := c.Next()
|
||||
i, e := strconv.ParseUint(l.token, 10, 16)
|
||||
|
|
56
vendor/github.com/miekg/dns/server.go
generated
vendored
56
vendor/github.com/miekg/dns/server.go
generated
vendored
|
@ -18,7 +18,7 @@ import (
|
|||
const maxTCPQueries = 128
|
||||
|
||||
// aLongTimeAgo is a non-zero time, far in the past, used for
|
||||
// immediate cancelation of network operations.
|
||||
// immediate cancellation of network operations.
|
||||
var aLongTimeAgo = time.Unix(1, 0)
|
||||
|
||||
// Handler is implemented by any value that implements ServeDNS.
|
||||
|
@ -71,12 +71,12 @@ type response struct {
|
|||
tsigTimersOnly bool
|
||||
tsigStatus error
|
||||
tsigRequestMAC string
|
||||
tsigSecret map[string]string // the tsig secrets
|
||||
udp net.PacketConn // i/o connection if UDP was used
|
||||
tcp net.Conn // i/o connection if TCP was used
|
||||
udpSession *SessionUDP // oob data to get egress interface right
|
||||
pcSession net.Addr // address to use when writing to a generic net.PacketConn
|
||||
writer Writer // writer to output the raw DNS bits
|
||||
tsigProvider TsigProvider
|
||||
udp net.PacketConn // i/o connection if UDP was used
|
||||
tcp net.Conn // i/o connection if TCP was used
|
||||
udpSession *SessionUDP // oob data to get egress interface right
|
||||
pcSession net.Addr // address to use when writing to a generic net.PacketConn
|
||||
writer Writer // writer to output the raw DNS bits
|
||||
}
|
||||
|
||||
// handleRefused returns a HandlerFunc that returns REFUSED for every request it gets.
|
||||
|
@ -211,6 +211,8 @@ type Server struct {
|
|||
WriteTimeout time.Duration
|
||||
// TCP idle timeout for multiple queries, if nil, defaults to 8 * time.Second (RFC 5966).
|
||||
IdleTimeout func() time.Duration
|
||||
// An implementation of the TsigProvider interface. If defined it replaces TsigSecret and is used for all TSIG operations.
|
||||
TsigProvider TsigProvider
|
||||
// Secret(s) for Tsig map[<zonename>]<base64 secret>. The zonename must be in canonical form (lowercase, fqdn, see RFC 4034 Section 6.2).
|
||||
TsigSecret map[string]string
|
||||
// If NotifyStartedFunc is set it is called once the server has started listening.
|
||||
|
@ -222,8 +224,12 @@ type Server struct {
|
|||
// Maximum number of TCP queries before we close the socket. Default is maxTCPQueries (unlimited if -1).
|
||||
MaxTCPQueries int
|
||||
// Whether to set the SO_REUSEPORT socket option, allowing multiple listeners to be bound to a single address.
|
||||
// It is only supported on go1.11+ and when using ListenAndServe.
|
||||
// It is only supported on certain GOOSes and when using ListenAndServe.
|
||||
ReusePort bool
|
||||
// Whether to set the SO_REUSEADDR socket option, allowing multiple listeners to be bound to a single address.
|
||||
// Crucially this allows binding when an existing server is listening on `0.0.0.0` or `::`.
|
||||
// It is only supported on certain GOOSes and when using ListenAndServe.
|
||||
ReuseAddr bool
|
||||
// AcceptMsgFunc will check the incoming message and will reject it early in the process.
|
||||
// By default DefaultMsgAcceptFunc will be used.
|
||||
MsgAcceptFunc MsgAcceptFunc
|
||||
|
@ -238,6 +244,16 @@ type Server struct {
|
|||
udpPool sync.Pool
|
||||
}
|
||||
|
||||
func (srv *Server) tsigProvider() TsigProvider {
|
||||
if srv.TsigProvider != nil {
|
||||
return srv.TsigProvider
|
||||
}
|
||||
if srv.TsigSecret != nil {
|
||||
return tsigSecretProvider(srv.TsigSecret)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (srv *Server) isStarted() bool {
|
||||
srv.lock.RLock()
|
||||
started := srv.started
|
||||
|
@ -292,7 +308,7 @@ func (srv *Server) ListenAndServe() error {
|
|||
|
||||
switch srv.Net {
|
||||
case "tcp", "tcp4", "tcp6":
|
||||
l, err := listenTCP(srv.Net, addr, srv.ReusePort)
|
||||
l, err := listenTCP(srv.Net, addr, srv.ReusePort, srv.ReuseAddr)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -305,7 +321,7 @@ func (srv *Server) ListenAndServe() error {
|
|||
return errors.New("dns: neither Certificates nor GetCertificate set in Config")
|
||||
}
|
||||
network := strings.TrimSuffix(srv.Net, "-tls")
|
||||
l, err := listenTCP(network, addr, srv.ReusePort)
|
||||
l, err := listenTCP(network, addr, srv.ReusePort, srv.ReuseAddr)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -315,7 +331,7 @@ func (srv *Server) ListenAndServe() error {
|
|||
unlock()
|
||||
return srv.serveTCP(l)
|
||||
case "udp", "udp4", "udp6":
|
||||
l, err := listenUDP(srv.Net, addr, srv.ReusePort)
|
||||
l, err := listenUDP(srv.Net, addr, srv.ReusePort, srv.ReuseAddr)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -526,7 +542,7 @@ func (srv *Server) serveUDP(l net.PacketConn) error {
|
|||
|
||||
// Serve a new TCP connection.
|
||||
func (srv *Server) serveTCPConn(wg *sync.WaitGroup, rw net.Conn) {
|
||||
w := &response{tsigSecret: srv.TsigSecret, tcp: rw}
|
||||
w := &response{tsigProvider: srv.tsigProvider(), tcp: rw}
|
||||
if srv.DecorateWriter != nil {
|
||||
w.writer = srv.DecorateWriter(w)
|
||||
} else {
|
||||
|
@ -581,7 +597,7 @@ func (srv *Server) serveTCPConn(wg *sync.WaitGroup, rw net.Conn) {
|
|||
|
||||
// Serve a new UDP request.
|
||||
func (srv *Server) serveUDPPacket(wg *sync.WaitGroup, m []byte, u net.PacketConn, udpSession *SessionUDP, pcSession net.Addr) {
|
||||
w := &response{tsigSecret: srv.TsigSecret, udp: u, udpSession: udpSession, pcSession: pcSession}
|
||||
w := &response{tsigProvider: srv.tsigProvider(), udp: u, udpSession: udpSession, pcSession: pcSession}
|
||||
if srv.DecorateWriter != nil {
|
||||
w.writer = srv.DecorateWriter(w)
|
||||
} else {
|
||||
|
@ -632,15 +648,11 @@ func (srv *Server) serveDNS(m []byte, w *response) {
|
|||
}
|
||||
|
||||
w.tsigStatus = nil
|
||||
if w.tsigSecret != nil {
|
||||
if w.tsigProvider != nil {
|
||||
if t := req.IsTsig(); t != nil {
|
||||
if secret, ok := w.tsigSecret[t.Hdr.Name]; ok {
|
||||
w.tsigStatus = TsigVerify(m, secret, "", false)
|
||||
} else {
|
||||
w.tsigStatus = ErrSecret
|
||||
}
|
||||
w.tsigStatus = TsigVerifyWithProvider(m, w.tsigProvider, "", false)
|
||||
w.tsigTimersOnly = false
|
||||
w.tsigRequestMAC = req.Extra[len(req.Extra)-1].(*TSIG).MAC
|
||||
w.tsigRequestMAC = t.MAC
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -718,9 +730,9 @@ func (w *response) WriteMsg(m *Msg) (err error) {
|
|||
}
|
||||
|
||||
var data []byte
|
||||
if w.tsigSecret != nil { // if no secrets, dont check for the tsig (which is a longer check)
|
||||
if w.tsigProvider != nil { // if no provider, dont check for the tsig (which is a longer check)
|
||||
if t := m.IsTsig(); t != nil {
|
||||
data, w.tsigRequestMAC, err = TsigGenerate(m, w.tsigSecret[t.Hdr.Name], w.tsigRequestMAC, w.tsigTimersOnly)
|
||||
data, w.tsigRequestMAC, err = TsigGenerateWithProvider(m, w.tsigProvider, w.tsigRequestMAC, w.tsigTimersOnly)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
51
vendor/github.com/miekg/dns/sig0.go
generated
vendored
51
vendor/github.com/miekg/dns/sig0.go
generated
vendored
|
@ -3,6 +3,7 @@ package dns
|
|||
import (
|
||||
"crypto"
|
||||
"crypto/ecdsa"
|
||||
"crypto/ed25519"
|
||||
"crypto/rsa"
|
||||
"encoding/binary"
|
||||
"math/big"
|
||||
|
@ -38,18 +39,17 @@ func (rr *SIG) Sign(k crypto.Signer, m *Msg) ([]byte, error) {
|
|||
}
|
||||
buf = buf[:off:cap(buf)]
|
||||
|
||||
hash, ok := AlgorithmToHash[rr.Algorithm]
|
||||
if !ok {
|
||||
return nil, ErrAlg
|
||||
h, cryptohash, err := hashFromAlgorithm(rr.Algorithm)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
hasher := hash.New()
|
||||
// Write SIG rdata
|
||||
hasher.Write(buf[len(mbuf)+1+2+2+4+2:])
|
||||
h.Write(buf[len(mbuf)+1+2+2+4+2:])
|
||||
// Write message
|
||||
hasher.Write(buf[:len(mbuf)])
|
||||
h.Write(buf[:len(mbuf)])
|
||||
|
||||
signature, err := sign(k, hasher.Sum(nil), hash, rr.Algorithm)
|
||||
signature, err := sign(k, h.Sum(nil), cryptohash, rr.Algorithm)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
@ -82,20 +82,10 @@ func (rr *SIG) Verify(k *KEY, buf []byte) error {
|
|||
return ErrKey
|
||||
}
|
||||
|
||||
var hash crypto.Hash
|
||||
switch rr.Algorithm {
|
||||
case RSASHA1:
|
||||
hash = crypto.SHA1
|
||||
case RSASHA256, ECDSAP256SHA256:
|
||||
hash = crypto.SHA256
|
||||
case ECDSAP384SHA384:
|
||||
hash = crypto.SHA384
|
||||
case RSASHA512:
|
||||
hash = crypto.SHA512
|
||||
default:
|
||||
return ErrAlg
|
||||
h, cryptohash, err := hashFromAlgorithm(rr.Algorithm)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
hasher := hash.New()
|
||||
|
||||
buflen := len(buf)
|
||||
qdc := binary.BigEndian.Uint16(buf[4:])
|
||||
|
@ -103,7 +93,6 @@ func (rr *SIG) Verify(k *KEY, buf []byte) error {
|
|||
auc := binary.BigEndian.Uint16(buf[8:])
|
||||
adc := binary.BigEndian.Uint16(buf[10:])
|
||||
offset := headerSize
|
||||
var err error
|
||||
for i := uint16(0); i < qdc && offset < buflen; i++ {
|
||||
_, offset, err = UnpackDomainName(buf, offset)
|
||||
if err != nil {
|
||||
|
@ -166,21 +155,21 @@ func (rr *SIG) Verify(k *KEY, buf []byte) error {
|
|||
return &Error{err: "signer name doesn't match key name"}
|
||||
}
|
||||
sigend := offset
|
||||
hasher.Write(buf[sigstart:sigend])
|
||||
hasher.Write(buf[:10])
|
||||
hasher.Write([]byte{
|
||||
h.Write(buf[sigstart:sigend])
|
||||
h.Write(buf[:10])
|
||||
h.Write([]byte{
|
||||
byte((adc - 1) << 8),
|
||||
byte(adc - 1),
|
||||
})
|
||||
hasher.Write(buf[12:bodyend])
|
||||
h.Write(buf[12:bodyend])
|
||||
|
||||
hashed := hasher.Sum(nil)
|
||||
hashed := h.Sum(nil)
|
||||
sig := buf[sigend:]
|
||||
switch k.Algorithm {
|
||||
case RSASHA1, RSASHA256, RSASHA512:
|
||||
pk := k.publicKeyRSA()
|
||||
if pk != nil {
|
||||
return rsa.VerifyPKCS1v15(pk, hash, hashed, sig)
|
||||
return rsa.VerifyPKCS1v15(pk, cryptohash, hashed, sig)
|
||||
}
|
||||
case ECDSAP256SHA256, ECDSAP384SHA384:
|
||||
pk := k.publicKeyECDSA()
|
||||
|
@ -192,6 +181,14 @@ func (rr *SIG) Verify(k *KEY, buf []byte) error {
|
|||
}
|
||||
return ErrSig
|
||||
}
|
||||
case ED25519:
|
||||
pk := k.publicKeyED25519()
|
||||
if pk != nil {
|
||||
if ed25519.Verify(pk, hashed, sig) {
|
||||
return nil
|
||||
}
|
||||
return ErrSig
|
||||
}
|
||||
}
|
||||
return ErrKeyAlg
|
||||
}
|
||||
|
|
61
vendor/github.com/miekg/dns/singleinflight.go
generated
vendored
61
vendor/github.com/miekg/dns/singleinflight.go
generated
vendored
|
@ -1,61 +0,0 @@
|
|||
// Copyright 2013 The Go Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
// Adapted for dns package usage by Miek Gieben.
|
||||
|
||||
package dns
|
||||
|
||||
import "sync"
|
||||
import "time"
|
||||
|
||||
// call is an in-flight or completed singleflight.Do call
|
||||
type call struct {
|
||||
wg sync.WaitGroup
|
||||
val *Msg
|
||||
rtt time.Duration
|
||||
err error
|
||||
dups int
|
||||
}
|
||||
|
||||
// singleflight represents a class of work and forms a namespace in
|
||||
// which units of work can be executed with duplicate suppression.
|
||||
type singleflight struct {
|
||||
sync.Mutex // protects m
|
||||
m map[string]*call // lazily initialized
|
||||
|
||||
dontDeleteForTesting bool // this is only to be used by TestConcurrentExchanges
|
||||
}
|
||||
|
||||
// Do executes and returns the results of the given function, making
|
||||
// sure that only one execution is in-flight for a given key at a
|
||||
// time. If a duplicate comes in, the duplicate caller waits for the
|
||||
// original to complete and receives the same results.
|
||||
// The return value shared indicates whether v was given to multiple callers.
|
||||
func (g *singleflight) Do(key string, fn func() (*Msg, time.Duration, error)) (v *Msg, rtt time.Duration, err error, shared bool) {
|
||||
g.Lock()
|
||||
if g.m == nil {
|
||||
g.m = make(map[string]*call)
|
||||
}
|
||||
if c, ok := g.m[key]; ok {
|
||||
c.dups++
|
||||
g.Unlock()
|
||||
c.wg.Wait()
|
||||
return c.val, c.rtt, c.err, true
|
||||
}
|
||||
c := new(call)
|
||||
c.wg.Add(1)
|
||||
g.m[key] = c
|
||||
g.Unlock()
|
||||
|
||||
c.val, c.rtt, c.err = fn()
|
||||
c.wg.Done()
|
||||
|
||||
if !g.dontDeleteForTesting {
|
||||
g.Lock()
|
||||
delete(g.m, key)
|
||||
g.Unlock()
|
||||
}
|
||||
|
||||
return c.val, c.rtt, c.err, c.dups > 0
|
||||
}
|
424
vendor/github.com/miekg/dns/svcb.go
generated
vendored
424
vendor/github.com/miekg/dns/svcb.go
generated
vendored
|
@ -4,6 +4,7 @@ import (
|
|||
"bytes"
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"fmt"
|
||||
"net"
|
||||
"sort"
|
||||
"strconv"
|
||||
|
@ -13,16 +14,18 @@ import (
|
|||
// SVCBKey is the type of the keys used in the SVCB RR.
|
||||
type SVCBKey uint16
|
||||
|
||||
// Keys defined in draft-ietf-dnsop-svcb-https-01 Section 12.3.2.
|
||||
// Keys defined in draft-ietf-dnsop-svcb-https-08 Section 14.3.2.
|
||||
const (
|
||||
SVCB_MANDATORY SVCBKey = 0
|
||||
SVCB_ALPN SVCBKey = 1
|
||||
SVCB_NO_DEFAULT_ALPN SVCBKey = 2
|
||||
SVCB_PORT SVCBKey = 3
|
||||
SVCB_IPV4HINT SVCBKey = 4
|
||||
SVCB_ECHCONFIG SVCBKey = 5
|
||||
SVCB_IPV6HINT SVCBKey = 6
|
||||
svcb_RESERVED SVCBKey = 65535
|
||||
SVCB_MANDATORY SVCBKey = iota
|
||||
SVCB_ALPN
|
||||
SVCB_NO_DEFAULT_ALPN
|
||||
SVCB_PORT
|
||||
SVCB_IPV4HINT
|
||||
SVCB_ECHCONFIG
|
||||
SVCB_IPV6HINT
|
||||
SVCB_DOHPATH // draft-ietf-add-svcb-dns-02 Section 9
|
||||
|
||||
svcb_RESERVED SVCBKey = 65535
|
||||
)
|
||||
|
||||
var svcbKeyToStringMap = map[SVCBKey]string{
|
||||
|
@ -31,8 +34,9 @@ var svcbKeyToStringMap = map[SVCBKey]string{
|
|||
SVCB_NO_DEFAULT_ALPN: "no-default-alpn",
|
||||
SVCB_PORT: "port",
|
||||
SVCB_IPV4HINT: "ipv4hint",
|
||||
SVCB_ECHCONFIG: "echconfig",
|
||||
SVCB_ECHCONFIG: "ech",
|
||||
SVCB_IPV6HINT: "ipv6hint",
|
||||
SVCB_DOHPATH: "dohpath",
|
||||
}
|
||||
|
||||
var svcbStringToKeyMap = reverseSVCBKeyMap(svcbKeyToStringMap)
|
||||
|
@ -167,10 +171,14 @@ func (rr *SVCB) parse(c *zlexer, o string) *ParseError {
|
|||
}
|
||||
l, _ = c.Next()
|
||||
}
|
||||
|
||||
// "In AliasMode, records SHOULD NOT include any SvcParams, and recipients MUST
|
||||
// ignore any SvcParams that are present."
|
||||
// However, we don't check rr.Priority == 0 && len(xs) > 0 here
|
||||
// It is the responsibility of the user of the library to check this.
|
||||
// This is to encourage the fixing of the source of this error.
|
||||
|
||||
rr.Value = xs
|
||||
if rr.Priority == 0 && len(xs) > 0 {
|
||||
return &ParseError{l.token, "SVCB aliasform can't have values", l}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
|
@ -191,6 +199,8 @@ func makeSVCBKeyValue(key SVCBKey) SVCBKeyValue {
|
|||
return new(SVCBECHConfig)
|
||||
case SVCB_IPV6HINT:
|
||||
return new(SVCBIPv6Hint)
|
||||
case SVCB_DOHPATH:
|
||||
return new(SVCBDoHPath)
|
||||
case svcb_RESERVED:
|
||||
return nil
|
||||
default:
|
||||
|
@ -200,16 +210,24 @@ func makeSVCBKeyValue(key SVCBKey) SVCBKeyValue {
|
|||
}
|
||||
}
|
||||
|
||||
// SVCB RR. See RFC xxxx (https://tools.ietf.org/html/draft-ietf-dnsop-svcb-https-01).
|
||||
// SVCB RR. See RFC xxxx (https://tools.ietf.org/html/draft-ietf-dnsop-svcb-https-08).
|
||||
//
|
||||
// NOTE: The HTTPS/SVCB RFCs are in the draft stage.
|
||||
// The API, including constants and types related to SVCBKeyValues, may
|
||||
// change in future versions in accordance with the latest drafts.
|
||||
type SVCB struct {
|
||||
Hdr RR_Header
|
||||
Priority uint16
|
||||
Priority uint16 // If zero, Value must be empty or discarded by the user of this library
|
||||
Target string `dns:"domain-name"`
|
||||
Value []SVCBKeyValue `dns:"pairs"` // Value must be empty if Priority is zero.
|
||||
Value []SVCBKeyValue `dns:"pairs"`
|
||||
}
|
||||
|
||||
// HTTPS RR. Everything valid for SVCB applies to HTTPS as well.
|
||||
// Except that the HTTPS record is intended for use with the HTTP and HTTPS protocols.
|
||||
//
|
||||
// NOTE: The HTTPS/SVCB RFCs are in the draft stage.
|
||||
// The API, including constants and types related to SVCBKeyValues, may
|
||||
// change in future versions in accordance with the latest drafts.
|
||||
type HTTPS struct {
|
||||
SVCB
|
||||
}
|
||||
|
@ -235,15 +253,29 @@ type SVCBKeyValue interface {
|
|||
}
|
||||
|
||||
// SVCBMandatory pair adds to required keys that must be interpreted for the RR
|
||||
// to be functional.
|
||||
// to be functional. If ignored, the whole RRSet must be ignored.
|
||||
// "port" and "no-default-alpn" are mandatory by default if present,
|
||||
// so they shouldn't be included here.
|
||||
//
|
||||
// It is incumbent upon the user of this library to reject the RRSet if
|
||||
// or avoid constructing such an RRSet that:
|
||||
// - "mandatory" is included as one of the keys of mandatory
|
||||
// - no key is listed multiple times in mandatory
|
||||
// - all keys listed in mandatory are present
|
||||
// - escape sequences are not used in mandatory
|
||||
// - mandatory, when present, lists at least one key
|
||||
//
|
||||
// Basic use pattern for creating a mandatory option:
|
||||
//
|
||||
// s := &dns.SVCB{Hdr: dns.RR_Header{Name: ".", Rrtype: dns.TypeSVCB, Class: dns.ClassINET}}
|
||||
// e := new(dns.SVCBMandatory)
|
||||
// e.Code = []uint16{65403}
|
||||
// e.Code = []uint16{dns.SVCB_ALPN}
|
||||
// s.Value = append(s.Value, e)
|
||||
// t := new(dns.SVCBAlpn)
|
||||
// t.Alpn = []string{"xmpp-client"}
|
||||
// s.Value = append(s.Value, t)
|
||||
type SVCBMandatory struct {
|
||||
Code []SVCBKey // Must not include mandatory
|
||||
Code []SVCBKey
|
||||
}
|
||||
|
||||
func (*SVCBMandatory) Key() SVCBKey { return SVCB_MANDATORY }
|
||||
|
@ -257,7 +289,7 @@ func (s *SVCBMandatory) String() string {
|
|||
}
|
||||
|
||||
func (s *SVCBMandatory) pack() ([]byte, error) {
|
||||
codes := append([]SVCBKey(nil), s.Code...)
|
||||
codes := cloneSlice(s.Code)
|
||||
sort.Slice(codes, func(i, j int) bool {
|
||||
return codes[i] < codes[j]
|
||||
})
|
||||
|
@ -282,10 +314,11 @@ func (s *SVCBMandatory) unpack(b []byte) error {
|
|||
}
|
||||
|
||||
func (s *SVCBMandatory) parse(b string) error {
|
||||
str := strings.Split(b, ",")
|
||||
codes := make([]SVCBKey, 0, len(str))
|
||||
for _, e := range str {
|
||||
codes = append(codes, svcbStringToKey(e))
|
||||
codes := make([]SVCBKey, 0, strings.Count(b, ",")+1)
|
||||
for len(b) > 0 {
|
||||
var key string
|
||||
key, b, _ = strings.Cut(b, ",")
|
||||
codes = append(codes, svcbStringToKey(key))
|
||||
}
|
||||
s.Code = codes
|
||||
return nil
|
||||
|
@ -296,13 +329,12 @@ func (s *SVCBMandatory) len() int {
|
|||
}
|
||||
|
||||
func (s *SVCBMandatory) copy() SVCBKeyValue {
|
||||
return &SVCBMandatory{
|
||||
append([]SVCBKey(nil), s.Code...),
|
||||
}
|
||||
return &SVCBMandatory{cloneSlice(s.Code)}
|
||||
}
|
||||
|
||||
// SVCBAlpn pair is used to list supported connection protocols.
|
||||
// Protocol ids can be found at:
|
||||
// The user of this library must ensure that at least one protocol is listed when alpn is present.
|
||||
// Protocol IDs can be found at:
|
||||
// https://www.iana.org/assignments/tls-extensiontype-values/tls-extensiontype-values.xhtml#alpn-protocol-ids
|
||||
// Basic use pattern for creating an alpn option:
|
||||
//
|
||||
|
@ -310,13 +342,57 @@ func (s *SVCBMandatory) copy() SVCBKeyValue {
|
|||
// h.Hdr = dns.RR_Header{Name: ".", Rrtype: dns.TypeHTTPS, Class: dns.ClassINET}
|
||||
// e := new(dns.SVCBAlpn)
|
||||
// e.Alpn = []string{"h2", "http/1.1"}
|
||||
// h.Value = append(o.Value, e)
|
||||
// h.Value = append(h.Value, e)
|
||||
type SVCBAlpn struct {
|
||||
Alpn []string
|
||||
}
|
||||
|
||||
func (*SVCBAlpn) Key() SVCBKey { return SVCB_ALPN }
|
||||
func (s *SVCBAlpn) String() string { return strings.Join(s.Alpn, ",") }
|
||||
func (*SVCBAlpn) Key() SVCBKey { return SVCB_ALPN }
|
||||
|
||||
func (s *SVCBAlpn) String() string {
|
||||
// An ALPN value is a comma-separated list of values, each of which can be
|
||||
// an arbitrary binary value. In order to allow parsing, the comma and
|
||||
// backslash characters are themselves escaped.
|
||||
//
|
||||
// However, this escaping is done in addition to the normal escaping which
|
||||
// happens in zone files, meaning that these values must be
|
||||
// double-escaped. This looks terrible, so if you see a never-ending
|
||||
// sequence of backslash in a zone file this may be why.
|
||||
//
|
||||
// https://datatracker.ietf.org/doc/html/draft-ietf-dnsop-svcb-https-08#appendix-A.1
|
||||
var str strings.Builder
|
||||
for i, alpn := range s.Alpn {
|
||||
// 4*len(alpn) is the worst case where we escape every character in the alpn as \123, plus 1 byte for the ',' separating the alpn from others
|
||||
str.Grow(4*len(alpn) + 1)
|
||||
if i > 0 {
|
||||
str.WriteByte(',')
|
||||
}
|
||||
for j := 0; j < len(alpn); j++ {
|
||||
e := alpn[j]
|
||||
if ' ' > e || e > '~' {
|
||||
str.WriteString(escapeByte(e))
|
||||
continue
|
||||
}
|
||||
switch e {
|
||||
// We escape a few characters which may confuse humans or parsers.
|
||||
case '"', ';', ' ':
|
||||
str.WriteByte('\\')
|
||||
str.WriteByte(e)
|
||||
// The comma and backslash characters themselves must be
|
||||
// doubly-escaped. We use `\\` for the first backslash and
|
||||
// the escaped numeric value for the other value. We especially
|
||||
// don't want a comma in the output.
|
||||
case ',':
|
||||
str.WriteString(`\\\044`)
|
||||
case '\\':
|
||||
str.WriteString(`\\\092`)
|
||||
default:
|
||||
str.WriteByte(e)
|
||||
}
|
||||
}
|
||||
}
|
||||
return str.String()
|
||||
}
|
||||
|
||||
func (s *SVCBAlpn) pack() ([]byte, error) {
|
||||
// Liberally estimate the size of an alpn as 10 octets
|
||||
|
@ -351,7 +427,47 @@ func (s *SVCBAlpn) unpack(b []byte) error {
|
|||
}
|
||||
|
||||
func (s *SVCBAlpn) parse(b string) error {
|
||||
s.Alpn = strings.Split(b, ",")
|
||||
if len(b) == 0 {
|
||||
s.Alpn = []string{}
|
||||
return nil
|
||||
}
|
||||
|
||||
alpn := []string{}
|
||||
a := []byte{}
|
||||
for p := 0; p < len(b); {
|
||||
c, q := nextByte(b, p)
|
||||
if q == 0 {
|
||||
return errors.New("dns: svcbalpn: unterminated escape")
|
||||
}
|
||||
p += q
|
||||
// If we find a comma, we have finished reading an alpn.
|
||||
if c == ',' {
|
||||
if len(a) == 0 {
|
||||
return errors.New("dns: svcbalpn: empty protocol identifier")
|
||||
}
|
||||
alpn = append(alpn, string(a))
|
||||
a = []byte{}
|
||||
continue
|
||||
}
|
||||
// If it's a backslash, we need to handle a comma-separated list.
|
||||
if c == '\\' {
|
||||
dc, dq := nextByte(b, p)
|
||||
if dq == 0 {
|
||||
return errors.New("dns: svcbalpn: unterminated escape decoding comma-separated list")
|
||||
}
|
||||
if dc != '\\' && dc != ',' {
|
||||
return errors.New("dns: svcbalpn: bad escaped character decoding comma-separated list")
|
||||
}
|
||||
p += dq
|
||||
c = dc
|
||||
}
|
||||
a = append(a, c)
|
||||
}
|
||||
// Add the final alpn.
|
||||
if len(a) == 0 {
|
||||
return errors.New("dns: svcbalpn: last protocol identifier empty")
|
||||
}
|
||||
s.Alpn = append(alpn, string(a))
|
||||
return nil
|
||||
}
|
||||
|
||||
|
@ -364,15 +480,17 @@ func (s *SVCBAlpn) len() int {
|
|||
}
|
||||
|
||||
func (s *SVCBAlpn) copy() SVCBKeyValue {
|
||||
return &SVCBAlpn{
|
||||
append([]string(nil), s.Alpn...),
|
||||
}
|
||||
return &SVCBAlpn{cloneSlice(s.Alpn)}
|
||||
}
|
||||
|
||||
// SVCBNoDefaultAlpn pair signifies no support for default connection protocols.
|
||||
// Should be used in conjunction with alpn.
|
||||
// Basic use pattern for creating a no-default-alpn option:
|
||||
//
|
||||
// s := &dns.SVCB{Hdr: dns.RR_Header{Name: ".", Rrtype: dns.TypeSVCB, Class: dns.ClassINET}}
|
||||
// t := new(dns.SVCBAlpn)
|
||||
// t.Alpn = []string{"xmpp-client"}
|
||||
// s.Value = append(s.Value, t)
|
||||
// e := new(dns.SVCBNoDefaultAlpn)
|
||||
// s.Value = append(s.Value, e)
|
||||
type SVCBNoDefaultAlpn struct{}
|
||||
|
@ -385,14 +503,14 @@ func (*SVCBNoDefaultAlpn) len() int { return 0 }
|
|||
|
||||
func (*SVCBNoDefaultAlpn) unpack(b []byte) error {
|
||||
if len(b) != 0 {
|
||||
return errors.New("dns: svcbnodefaultalpn: no_default_alpn must have no value")
|
||||
return errors.New("dns: svcbnodefaultalpn: no-default-alpn must have no value")
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (*SVCBNoDefaultAlpn) parse(b string) error {
|
||||
if b != "" {
|
||||
return errors.New("dns: svcbnodefaultalpn: no_default_alpn must have no value")
|
||||
return errors.New("dns: svcbnodefaultalpn: no-default-alpn must have no value")
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
@ -442,15 +560,15 @@ func (s *SVCBPort) parse(b string) error {
|
|||
// to the hinted IP address may be terminated and a new connection may be opened.
|
||||
// Basic use pattern for creating an ipv4hint option:
|
||||
//
|
||||
// h := new(dns.HTTPS)
|
||||
// h.Hdr = dns.RR_Header{Name: ".", Rrtype: dns.TypeHTTPS, Class: dns.ClassINET}
|
||||
// e := new(dns.SVCBIPv4Hint)
|
||||
// e.Hint = []net.IP{net.IPv4(1,1,1,1).To4()}
|
||||
// h := new(dns.HTTPS)
|
||||
// h.Hdr = dns.RR_Header{Name: ".", Rrtype: dns.TypeHTTPS, Class: dns.ClassINET}
|
||||
// e := new(dns.SVCBIPv4Hint)
|
||||
// e.Hint = []net.IP{net.IPv4(1,1,1,1).To4()}
|
||||
//
|
||||
// Or
|
||||
// Or
|
||||
//
|
||||
// e.Hint = []net.IP{net.ParseIP("1.1.1.1").To4()}
|
||||
// h.Value = append(h.Value, e)
|
||||
// e.Hint = []net.IP{net.ParseIP("1.1.1.1").To4()}
|
||||
// h.Value = append(h.Value, e)
|
||||
type SVCBIPv4Hint struct {
|
||||
Hint []net.IP
|
||||
}
|
||||
|
@ -474,6 +592,7 @@ func (s *SVCBIPv4Hint) unpack(b []byte) error {
|
|||
if len(b) == 0 || len(b)%4 != 0 {
|
||||
return errors.New("dns: svcbipv4hint: ipv4 address byte array length is not a multiple of 4")
|
||||
}
|
||||
b = cloneSlice(b)
|
||||
x := make([]net.IP, 0, len(b)/4)
|
||||
for i := 0; i < len(b); i += 4 {
|
||||
x = append(x, net.IP(b[i:i+4]))
|
||||
|
@ -495,35 +614,37 @@ func (s *SVCBIPv4Hint) String() string {
|
|||
}
|
||||
|
||||
func (s *SVCBIPv4Hint) parse(b string) error {
|
||||
if b == "" {
|
||||
return errors.New("dns: svcbipv4hint: empty hint")
|
||||
}
|
||||
if strings.Contains(b, ":") {
|
||||
return errors.New("dns: svcbipv4hint: expected ipv4, got ipv6")
|
||||
}
|
||||
str := strings.Split(b, ",")
|
||||
dst := make([]net.IP, len(str))
|
||||
for i, e := range str {
|
||||
|
||||
hint := make([]net.IP, 0, strings.Count(b, ",")+1)
|
||||
for len(b) > 0 {
|
||||
var e string
|
||||
e, b, _ = strings.Cut(b, ",")
|
||||
ip := net.ParseIP(e).To4()
|
||||
if ip == nil {
|
||||
return errors.New("dns: svcbipv4hint: bad ip")
|
||||
}
|
||||
dst[i] = ip
|
||||
hint = append(hint, ip)
|
||||
}
|
||||
s.Hint = dst
|
||||
s.Hint = hint
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SVCBIPv4Hint) copy() SVCBKeyValue {
|
||||
hint := make([]net.IP, len(s.Hint))
|
||||
for i, ip := range s.Hint {
|
||||
hint[i] = copyIP(ip)
|
||||
}
|
||||
|
||||
return &SVCBIPv4Hint{
|
||||
Hint: hint,
|
||||
hint[i] = cloneSlice(ip)
|
||||
}
|
||||
return &SVCBIPv4Hint{Hint: hint}
|
||||
}
|
||||
|
||||
// SVCBECHConfig pair contains the ECHConfig structure defined in draft-ietf-tls-esni [RFC xxxx].
|
||||
// Basic use pattern for creating an echconfig option:
|
||||
// Basic use pattern for creating an ech option:
|
||||
//
|
||||
// h := new(dns.HTTPS)
|
||||
// h.Hdr = dns.RR_Header{Name: ".", Rrtype: dns.TypeHTTPS, Class: dns.ClassINET}
|
||||
|
@ -531,7 +652,7 @@ func (s *SVCBIPv4Hint) copy() SVCBKeyValue {
|
|||
// e.ECH = []byte{0xfe, 0x08, ...}
|
||||
// h.Value = append(h.Value, e)
|
||||
type SVCBECHConfig struct {
|
||||
ECH []byte
|
||||
ECH []byte // Specifically ECHConfigList including the redundant length prefix
|
||||
}
|
||||
|
||||
func (*SVCBECHConfig) Key() SVCBKey { return SVCB_ECHCONFIG }
|
||||
|
@ -539,23 +660,22 @@ func (s *SVCBECHConfig) String() string { return toBase64(s.ECH) }
|
|||
func (s *SVCBECHConfig) len() int { return len(s.ECH) }
|
||||
|
||||
func (s *SVCBECHConfig) pack() ([]byte, error) {
|
||||
return append([]byte(nil), s.ECH...), nil
|
||||
return cloneSlice(s.ECH), nil
|
||||
}
|
||||
|
||||
func (s *SVCBECHConfig) copy() SVCBKeyValue {
|
||||
return &SVCBECHConfig{
|
||||
append([]byte(nil), s.ECH...),
|
||||
}
|
||||
return &SVCBECHConfig{cloneSlice(s.ECH)}
|
||||
}
|
||||
|
||||
func (s *SVCBECHConfig) unpack(b []byte) error {
|
||||
s.ECH = append([]byte(nil), b...)
|
||||
s.ECH = cloneSlice(b)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SVCBECHConfig) parse(b string) error {
|
||||
x, err := fromBase64([]byte(b))
|
||||
if err != nil {
|
||||
return errors.New("dns: svcbechconfig: bad base64 echconfig")
|
||||
return errors.New("dns: svcbech: bad base64 ech")
|
||||
}
|
||||
s.ECH = x
|
||||
return nil
|
||||
|
@ -594,6 +714,7 @@ func (s *SVCBIPv6Hint) unpack(b []byte) error {
|
|||
if len(b) == 0 || len(b)%16 != 0 {
|
||||
return errors.New("dns: svcbipv6hint: ipv6 address byte array length not a multiple of 16")
|
||||
}
|
||||
b = cloneSlice(b)
|
||||
x := make([]net.IP, 0, len(b)/16)
|
||||
for i := 0; i < len(b); i += 16 {
|
||||
ip := net.IP(b[i : i+16])
|
||||
|
@ -618,30 +739,80 @@ func (s *SVCBIPv6Hint) String() string {
|
|||
}
|
||||
|
||||
func (s *SVCBIPv6Hint) parse(b string) error {
|
||||
if strings.Contains(b, ".") {
|
||||
return errors.New("dns: svcbipv6hint: expected ipv6, got ipv4")
|
||||
if b == "" {
|
||||
return errors.New("dns: svcbipv6hint: empty hint")
|
||||
}
|
||||
str := strings.Split(b, ",")
|
||||
dst := make([]net.IP, len(str))
|
||||
for i, e := range str {
|
||||
|
||||
hint := make([]net.IP, 0, strings.Count(b, ",")+1)
|
||||
for len(b) > 0 {
|
||||
var e string
|
||||
e, b, _ = strings.Cut(b, ",")
|
||||
ip := net.ParseIP(e)
|
||||
if ip == nil {
|
||||
return errors.New("dns: svcbipv6hint: bad ip")
|
||||
}
|
||||
dst[i] = ip
|
||||
if ip.To4() != nil {
|
||||
return errors.New("dns: svcbipv6hint: expected ipv6, got ipv4-mapped-ipv6")
|
||||
}
|
||||
hint = append(hint, ip)
|
||||
}
|
||||
s.Hint = dst
|
||||
s.Hint = hint
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SVCBIPv6Hint) copy() SVCBKeyValue {
|
||||
hint := make([]net.IP, len(s.Hint))
|
||||
for i, ip := range s.Hint {
|
||||
hint[i] = copyIP(ip)
|
||||
hint[i] = cloneSlice(ip)
|
||||
}
|
||||
return &SVCBIPv6Hint{Hint: hint}
|
||||
}
|
||||
|
||||
return &SVCBIPv6Hint{
|
||||
Hint: hint,
|
||||
// SVCBDoHPath pair is used to indicate the URI template that the
|
||||
// clients may use to construct a DNS over HTTPS URI.
|
||||
//
|
||||
// See RFC xxxx (https://datatracker.ietf.org/doc/html/draft-ietf-add-svcb-dns-02)
|
||||
// and RFC yyyy (https://datatracker.ietf.org/doc/html/draft-ietf-add-ddr-06).
|
||||
//
|
||||
// A basic example of using the dohpath option together with the alpn
|
||||
// option to indicate support for DNS over HTTPS on a certain path:
|
||||
//
|
||||
// s := new(dns.SVCB)
|
||||
// s.Hdr = dns.RR_Header{Name: ".", Rrtype: dns.TypeSVCB, Class: dns.ClassINET}
|
||||
// e := new(dns.SVCBAlpn)
|
||||
// e.Alpn = []string{"h2", "h3"}
|
||||
// p := new(dns.SVCBDoHPath)
|
||||
// p.Template = "/dns-query{?dns}"
|
||||
// s.Value = append(s.Value, e, p)
|
||||
//
|
||||
// The parsing currently doesn't validate that Template is a valid
|
||||
// RFC 6570 URI template.
|
||||
type SVCBDoHPath struct {
|
||||
Template string
|
||||
}
|
||||
|
||||
func (*SVCBDoHPath) Key() SVCBKey { return SVCB_DOHPATH }
|
||||
func (s *SVCBDoHPath) String() string { return svcbParamToStr([]byte(s.Template)) }
|
||||
func (s *SVCBDoHPath) len() int { return len(s.Template) }
|
||||
func (s *SVCBDoHPath) pack() ([]byte, error) { return []byte(s.Template), nil }
|
||||
|
||||
func (s *SVCBDoHPath) unpack(b []byte) error {
|
||||
s.Template = string(b)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SVCBDoHPath) parse(b string) error {
|
||||
template, err := svcbParseParam(b)
|
||||
if err != nil {
|
||||
return fmt.Errorf("dns: svcbdohpath: %w", err)
|
||||
}
|
||||
s.Template = string(template)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SVCBDoHPath) copy() SVCBKeyValue {
|
||||
return &SVCBDoHPath{
|
||||
Template: s.Template,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -661,67 +832,26 @@ type SVCBLocal struct {
|
|||
}
|
||||
|
||||
func (s *SVCBLocal) Key() SVCBKey { return s.KeyCode }
|
||||
func (s *SVCBLocal) pack() ([]byte, error) { return append([]byte(nil), s.Data...), nil }
|
||||
func (s *SVCBLocal) String() string { return svcbParamToStr(s.Data) }
|
||||
func (s *SVCBLocal) pack() ([]byte, error) { return cloneSlice(s.Data), nil }
|
||||
func (s *SVCBLocal) len() int { return len(s.Data) }
|
||||
|
||||
func (s *SVCBLocal) unpack(b []byte) error {
|
||||
s.Data = append([]byte(nil), b...)
|
||||
s.Data = cloneSlice(b)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SVCBLocal) String() string {
|
||||
var str strings.Builder
|
||||
str.Grow(4 * len(s.Data))
|
||||
for _, e := range s.Data {
|
||||
if ' ' <= e && e <= '~' {
|
||||
switch e {
|
||||
case '"', ';', ' ', '\\':
|
||||
str.WriteByte('\\')
|
||||
str.WriteByte(e)
|
||||
default:
|
||||
str.WriteByte(e)
|
||||
}
|
||||
} else {
|
||||
str.WriteString(escapeByte(e))
|
||||
}
|
||||
}
|
||||
return str.String()
|
||||
}
|
||||
|
||||
func (s *SVCBLocal) parse(b string) error {
|
||||
data := make([]byte, 0, len(b))
|
||||
for i := 0; i < len(b); {
|
||||
if b[i] != '\\' {
|
||||
data = append(data, b[i])
|
||||
i++
|
||||
continue
|
||||
}
|
||||
if i+1 == len(b) {
|
||||
return errors.New("dns: svcblocal: svcb private/experimental key escape unterminated")
|
||||
}
|
||||
if isDigit(b[i+1]) {
|
||||
if i+3 < len(b) && isDigit(b[i+2]) && isDigit(b[i+3]) {
|
||||
a, err := strconv.ParseUint(b[i+1:i+4], 10, 8)
|
||||
if err == nil {
|
||||
i += 4
|
||||
data = append(data, byte(a))
|
||||
continue
|
||||
}
|
||||
}
|
||||
return errors.New("dns: svcblocal: svcb private/experimental key bad escaped octet")
|
||||
} else {
|
||||
data = append(data, b[i+1])
|
||||
i += 2
|
||||
}
|
||||
data, err := svcbParseParam(b)
|
||||
if err != nil {
|
||||
return fmt.Errorf("dns: svcblocal: svcb private/experimental key %w", err)
|
||||
}
|
||||
s.Data = data
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SVCBLocal) copy() SVCBKeyValue {
|
||||
return &SVCBLocal{s.KeyCode,
|
||||
append([]byte(nil), s.Data...),
|
||||
}
|
||||
return &SVCBLocal{s.KeyCode, cloneSlice(s.Data)}
|
||||
}
|
||||
|
||||
func (rr *SVCB) String() string {
|
||||
|
@ -737,8 +867,8 @@ func (rr *SVCB) String() string {
|
|||
// areSVCBPairArraysEqual checks if SVCBKeyValue arrays are equal after sorting their
|
||||
// copies. arrA and arrB have equal lengths, otherwise zduplicate.go wouldn't call this function.
|
||||
func areSVCBPairArraysEqual(a []SVCBKeyValue, b []SVCBKeyValue) bool {
|
||||
a = append([]SVCBKeyValue(nil), a...)
|
||||
b = append([]SVCBKeyValue(nil), b...)
|
||||
a = cloneSlice(a)
|
||||
b = cloneSlice(b)
|
||||
sort.Slice(a, func(i, j int) bool { return a[i].Key() < a[j].Key() })
|
||||
sort.Slice(b, func(i, j int) bool { return b[i].Key() < b[j].Key() })
|
||||
for i, e := range a {
|
||||
|
@ -753,3 +883,53 @@ func areSVCBPairArraysEqual(a []SVCBKeyValue, b []SVCBKeyValue) bool {
|
|||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// svcbParamStr converts the value of an SVCB parameter into a DNS presentation-format string.
|
||||
func svcbParamToStr(s []byte) string {
|
||||
var str strings.Builder
|
||||
str.Grow(4 * len(s))
|
||||
for _, e := range s {
|
||||
if ' ' <= e && e <= '~' {
|
||||
switch e {
|
||||
case '"', ';', ' ', '\\':
|
||||
str.WriteByte('\\')
|
||||
str.WriteByte(e)
|
||||
default:
|
||||
str.WriteByte(e)
|
||||
}
|
||||
} else {
|
||||
str.WriteString(escapeByte(e))
|
||||
}
|
||||
}
|
||||
return str.String()
|
||||
}
|
||||
|
||||
// svcbParseParam parses a DNS presentation-format string into an SVCB parameter value.
|
||||
func svcbParseParam(b string) ([]byte, error) {
|
||||
data := make([]byte, 0, len(b))
|
||||
for i := 0; i < len(b); {
|
||||
if b[i] != '\\' {
|
||||
data = append(data, b[i])
|
||||
i++
|
||||
continue
|
||||
}
|
||||
if i+1 == len(b) {
|
||||
return nil, errors.New("escape unterminated")
|
||||
}
|
||||
if isDigit(b[i+1]) {
|
||||
if i+3 < len(b) && isDigit(b[i+2]) && isDigit(b[i+3]) {
|
||||
a, err := strconv.ParseUint(b[i+1:i+4], 10, 8)
|
||||
if err == nil {
|
||||
i += 4
|
||||
data = append(data, byte(a))
|
||||
continue
|
||||
}
|
||||
}
|
||||
return nil, errors.New("bad escaped octet")
|
||||
} else {
|
||||
data = append(data, b[i+1])
|
||||
i += 2
|
||||
}
|
||||
}
|
||||
return data, nil
|
||||
}
|
||||
|
|
10
vendor/github.com/miekg/dns/tools.go
generated
vendored
Normal file
10
vendor/github.com/miekg/dns/tools.go
generated
vendored
Normal file
|
@ -0,0 +1,10 @@
|
|||
//go:build tools
|
||||
// +build tools
|
||||
|
||||
// We include our tool dependencies for `go generate` here to ensure they're
|
||||
// properly tracked by the go tool. See the Go Wiki for the rationale behind this:
|
||||
// https://github.com/golang/go/wiki/Modules#how-can-i-track-tool-dependencies-for-a-module.
|
||||
|
||||
package dns
|
||||
|
||||
import _ "golang.org/x/tools/go/packages"
|
65
vendor/github.com/miekg/dns/tsig.go
generated
vendored
65
vendor/github.com/miekg/dns/tsig.go
generated
vendored
|
@ -74,6 +74,24 @@ func (key tsigHMACProvider) Verify(msg []byte, t *TSIG) error {
|
|||
return nil
|
||||
}
|
||||
|
||||
type tsigSecretProvider map[string]string
|
||||
|
||||
func (ts tsigSecretProvider) Generate(msg []byte, t *TSIG) ([]byte, error) {
|
||||
key, ok := ts[t.Hdr.Name]
|
||||
if !ok {
|
||||
return nil, ErrSecret
|
||||
}
|
||||
return tsigHMACProvider(key).Generate(msg, t)
|
||||
}
|
||||
|
||||
func (ts tsigSecretProvider) Verify(msg []byte, t *TSIG) error {
|
||||
key, ok := ts[t.Hdr.Name]
|
||||
if !ok {
|
||||
return ErrSecret
|
||||
}
|
||||
return tsigHMACProvider(key).Verify(msg, t)
|
||||
}
|
||||
|
||||
// TSIG is the RR the holds the transaction signature of a message.
|
||||
// See RFC 2845 and RFC 4635.
|
||||
type TSIG struct {
|
||||
|
@ -140,18 +158,17 @@ type timerWireFmt struct {
|
|||
}
|
||||
|
||||
// TsigGenerate fills out the TSIG record attached to the message.
|
||||
// The message should contain
|
||||
// a "stub" TSIG RR with the algorithm, key name (owner name of the RR),
|
||||
// time fudge (defaults to 300 seconds) and the current time
|
||||
// The TSIG MAC is saved in that Tsig RR.
|
||||
// When TsigGenerate is called for the first time requestMAC is set to the empty string and
|
||||
// timersOnly is false.
|
||||
// If something goes wrong an error is returned, otherwise it is nil.
|
||||
// The message should contain a "stub" TSIG RR with the algorithm, key name
|
||||
// (owner name of the RR), time fudge (defaults to 300 seconds) and the current
|
||||
// time The TSIG MAC is saved in that Tsig RR. When TsigGenerate is called for
|
||||
// the first time requestMAC should be set to the empty string and timersOnly to
|
||||
// false.
|
||||
func TsigGenerate(m *Msg, secret, requestMAC string, timersOnly bool) ([]byte, string, error) {
|
||||
return tsigGenerateProvider(m, tsigHMACProvider(secret), requestMAC, timersOnly)
|
||||
return TsigGenerateWithProvider(m, tsigHMACProvider(secret), requestMAC, timersOnly)
|
||||
}
|
||||
|
||||
func tsigGenerateProvider(m *Msg, provider TsigProvider, requestMAC string, timersOnly bool) ([]byte, string, error) {
|
||||
// TsigGenerateWithProvider is similar to TsigGenerate, but allows for a custom TsigProvider.
|
||||
func TsigGenerateWithProvider(m *Msg, provider TsigProvider, requestMAC string, timersOnly bool) ([]byte, string, error) {
|
||||
if m.IsTsig() == nil {
|
||||
panic("dns: TSIG not last RR in additional")
|
||||
}
|
||||
|
@ -162,20 +179,29 @@ func tsigGenerateProvider(m *Msg, provider TsigProvider, requestMAC string, time
|
|||
if err != nil {
|
||||
return nil, "", err
|
||||
}
|
||||
|
||||
buf, err := tsigBuffer(mbuf, rr, requestMAC, timersOnly)
|
||||
if err != nil {
|
||||
return nil, "", err
|
||||
}
|
||||
|
||||
t := new(TSIG)
|
||||
// Copy all TSIG fields except MAC and its size, which are filled using the computed digest.
|
||||
// Copy all TSIG fields except MAC, its size, and time signed which are filled when signing.
|
||||
*t = *rr
|
||||
mac, err := provider.Generate(buf, rr)
|
||||
if err != nil {
|
||||
return nil, "", err
|
||||
t.TimeSigned = 0
|
||||
t.MAC = ""
|
||||
t.MACSize = 0
|
||||
|
||||
// Sign unless there is a key or MAC validation error (RFC 8945 5.3.2)
|
||||
if rr.Error != RcodeBadKey && rr.Error != RcodeBadSig {
|
||||
mac, err := provider.Generate(buf, rr)
|
||||
if err != nil {
|
||||
return nil, "", err
|
||||
}
|
||||
t.TimeSigned = rr.TimeSigned
|
||||
t.MAC = hex.EncodeToString(mac)
|
||||
t.MACSize = uint16(len(t.MAC) / 2) // Size is half!
|
||||
}
|
||||
t.MAC = hex.EncodeToString(mac)
|
||||
t.MACSize = uint16(len(t.MAC) / 2) // Size is half!
|
||||
|
||||
tbuf := make([]byte, Len(t))
|
||||
off, err := PackRR(t, tbuf, 0, nil, false)
|
||||
|
@ -189,14 +215,15 @@ func tsigGenerateProvider(m *Msg, provider TsigProvider, requestMAC string, time
|
|||
return mbuf, t.MAC, nil
|
||||
}
|
||||
|
||||
// TsigVerify verifies the TSIG on a message.
|
||||
// If the signature does not validate err contains the
|
||||
// error, otherwise it is nil.
|
||||
// TsigVerify verifies the TSIG on a message. If the signature does not
|
||||
// validate the returned error contains the cause. If the signature is OK, the
|
||||
// error is nil.
|
||||
func TsigVerify(msg []byte, secret, requestMAC string, timersOnly bool) error {
|
||||
return tsigVerify(msg, tsigHMACProvider(secret), requestMAC, timersOnly, uint64(time.Now().Unix()))
|
||||
}
|
||||
|
||||
func tsigVerifyProvider(msg []byte, provider TsigProvider, requestMAC string, timersOnly bool) error {
|
||||
// TsigVerifyWithProvider is similar to TsigVerify, but allows for a custom TsigProvider.
|
||||
func TsigVerifyWithProvider(msg []byte, provider TsigProvider, requestMAC string, timersOnly bool) error {
|
||||
return tsigVerify(msg, provider, requestMAC, timersOnly, uint64(time.Now().Unix()))
|
||||
}
|
||||
|
||||
|
|
129
vendor/github.com/miekg/dns/types.go
generated
vendored
129
vendor/github.com/miekg/dns/types.go
generated
vendored
|
@ -65,6 +65,7 @@ const (
|
|||
TypeAPL uint16 = 42
|
||||
TypeDS uint16 = 43
|
||||
TypeSSHFP uint16 = 44
|
||||
TypeIPSECKEY uint16 = 45
|
||||
TypeRRSIG uint16 = 46
|
||||
TypeNSEC uint16 = 47
|
||||
TypeDNSKEY uint16 = 48
|
||||
|
@ -98,6 +99,7 @@ const (
|
|||
TypeURI uint16 = 256
|
||||
TypeCAA uint16 = 257
|
||||
TypeAVC uint16 = 258
|
||||
TypeAMTRELAY uint16 = 260
|
||||
|
||||
TypeTKEY uint16 = 249
|
||||
TypeTSIG uint16 = 250
|
||||
|
@ -159,6 +161,22 @@ const (
|
|||
ZoneMDHashAlgSHA512 = 2
|
||||
)
|
||||
|
||||
// Used in IPSEC https://datatracker.ietf.org/doc/html/rfc4025#section-2.3
|
||||
const (
|
||||
IPSECGatewayNone uint8 = iota
|
||||
IPSECGatewayIPv4
|
||||
IPSECGatewayIPv6
|
||||
IPSECGatewayHost
|
||||
)
|
||||
|
||||
// Used in AMTRELAY https://datatracker.ietf.org/doc/html/rfc8777#section-4.2.3
|
||||
const (
|
||||
AMTRELAYNone = IPSECGatewayNone
|
||||
AMTRELAYIPv4 = IPSECGatewayIPv4
|
||||
AMTRELAYIPv6 = IPSECGatewayIPv6
|
||||
AMTRELAYHost = IPSECGatewayHost
|
||||
)
|
||||
|
||||
// Header is the wire format for the DNS packet header.
|
||||
type Header struct {
|
||||
Id uint16
|
||||
|
@ -180,7 +198,7 @@ const (
|
|||
_CD = 1 << 4 // checking disabled
|
||||
)
|
||||
|
||||
// Various constants used in the LOC RR. See RFC 1887.
|
||||
// Various constants used in the LOC RR. See RFC 1876.
|
||||
const (
|
||||
LOC_EQUATOR = 1 << 31 // RFC 1876, Section 2.
|
||||
LOC_PRIMEMERIDIAN = 1 << 31 // RFC 1876, Section 2.
|
||||
|
@ -218,6 +236,9 @@ var CertTypeToString = map[uint16]string{
|
|||
CertOID: "OID",
|
||||
}
|
||||
|
||||
// Prefix for IPv4 encoded as IPv6 address
|
||||
const ipv4InIPv6Prefix = "::ffff:"
|
||||
|
||||
//go:generate go run types_generate.go
|
||||
|
||||
// Question holds a DNS question. Usually there is just one. While the
|
||||
|
@ -613,8 +634,8 @@ func nextByte(s string, offset int) (byte, int) {
|
|||
return 0, 0
|
||||
case 2, 3: // too short to be \ddd
|
||||
default: // maybe \ddd
|
||||
if isDigit(s[offset+1]) && isDigit(s[offset+2]) && isDigit(s[offset+3]) {
|
||||
return dddStringToByte(s[offset+1:]), 4
|
||||
if isDDD(s[offset+1:]) {
|
||||
return dddToByte(s[offset+1:]), 4
|
||||
}
|
||||
}
|
||||
// not \ddd, just an RFC 1035 "quoted" character
|
||||
|
@ -733,6 +754,11 @@ func (rr *AAAA) String() string {
|
|||
if rr.AAAA == nil {
|
||||
return rr.Hdr.String()
|
||||
}
|
||||
|
||||
if rr.AAAA.To4() != nil {
|
||||
return rr.Hdr.String() + ipv4InIPv6Prefix + rr.AAAA.String()
|
||||
}
|
||||
|
||||
return rr.Hdr.String() + rr.AAAA.String()
|
||||
}
|
||||
|
||||
|
@ -774,7 +800,10 @@ type LOC struct {
|
|||
|
||||
// cmToM takes a cm value expressed in RFC 1876 SIZE mantissa/exponent
|
||||
// format and returns a string in m (two decimals for the cm).
|
||||
func cmToM(m, e uint8) string {
|
||||
func cmToM(x uint8) string {
|
||||
m := x & 0xf0 >> 4
|
||||
e := x & 0x0f
|
||||
|
||||
if e < 2 {
|
||||
if e == 1 {
|
||||
m *= 10
|
||||
|
@ -830,10 +859,9 @@ func (rr *LOC) String() string {
|
|||
s += fmt.Sprintf("%.0fm ", alt)
|
||||
}
|
||||
|
||||
s += cmToM(rr.Size&0xf0>>4, rr.Size&0x0f) + "m "
|
||||
s += cmToM(rr.HorizPre&0xf0>>4, rr.HorizPre&0x0f) + "m "
|
||||
s += cmToM(rr.VertPre&0xf0>>4, rr.VertPre&0x0f) + "m"
|
||||
|
||||
s += cmToM(rr.Size) + "m "
|
||||
s += cmToM(rr.HorizPre) + "m "
|
||||
s += cmToM(rr.VertPre) + "m"
|
||||
return s
|
||||
}
|
||||
|
||||
|
@ -994,6 +1022,69 @@ func (rr *DNSKEY) String() string {
|
|||
" " + rr.PublicKey
|
||||
}
|
||||
|
||||
// IPSECKEY RR. See RFC 4025.
|
||||
type IPSECKEY struct {
|
||||
Hdr RR_Header
|
||||
Precedence uint8
|
||||
GatewayType uint8
|
||||
Algorithm uint8
|
||||
GatewayAddr net.IP `dns:"-"` // packing/unpacking/parsing/etc handled together with GatewayHost
|
||||
GatewayHost string `dns:"ipsechost"`
|
||||
PublicKey string `dns:"base64"`
|
||||
}
|
||||
|
||||
func (rr *IPSECKEY) String() string {
|
||||
var gateway string
|
||||
switch rr.GatewayType {
|
||||
case IPSECGatewayIPv4, IPSECGatewayIPv6:
|
||||
gateway = rr.GatewayAddr.String()
|
||||
case IPSECGatewayHost:
|
||||
gateway = rr.GatewayHost
|
||||
case IPSECGatewayNone:
|
||||
fallthrough
|
||||
default:
|
||||
gateway = "."
|
||||
}
|
||||
|
||||
return rr.Hdr.String() + strconv.Itoa(int(rr.Precedence)) +
|
||||
" " + strconv.Itoa(int(rr.GatewayType)) +
|
||||
" " + strconv.Itoa(int(rr.Algorithm)) +
|
||||
" " + gateway +
|
||||
" " + rr.PublicKey
|
||||
}
|
||||
|
||||
// AMTRELAY RR. See RFC 8777.
|
||||
type AMTRELAY struct {
|
||||
Hdr RR_Header
|
||||
Precedence uint8
|
||||
GatewayType uint8 // discovery is packed in here at bit 0x80
|
||||
GatewayAddr net.IP `dns:"-"` // packing/unpacking/parsing/etc handled together with GatewayHost
|
||||
GatewayHost string `dns:"amtrelayhost"`
|
||||
}
|
||||
|
||||
func (rr *AMTRELAY) String() string {
|
||||
var gateway string
|
||||
switch rr.GatewayType & 0x7f {
|
||||
case AMTRELAYIPv4, AMTRELAYIPv6:
|
||||
gateway = rr.GatewayAddr.String()
|
||||
case AMTRELAYHost:
|
||||
gateway = rr.GatewayHost
|
||||
case AMTRELAYNone:
|
||||
fallthrough
|
||||
default:
|
||||
gateway = "."
|
||||
}
|
||||
boolS := "0"
|
||||
if rr.GatewayType&0x80 == 0x80 {
|
||||
boolS = "1"
|
||||
}
|
||||
|
||||
return rr.Hdr.String() + strconv.Itoa(int(rr.Precedence)) +
|
||||
" " + boolS +
|
||||
" " + strconv.Itoa(int(rr.GatewayType&0x7f)) +
|
||||
" " + gateway
|
||||
}
|
||||
|
||||
// RKEY RR. See https://www.iana.org/assignments/dns-parameters/RKEY/rkey-completed-template.
|
||||
type RKEY struct {
|
||||
Hdr RR_Header
|
||||
|
@ -1434,7 +1525,7 @@ func (a *APLPrefix) str() string {
|
|||
case net.IPv6len:
|
||||
// add prefix for IPv4-mapped IPv6
|
||||
if v4 := a.Network.IP.To4(); v4 != nil {
|
||||
sb.WriteString("::ffff:")
|
||||
sb.WriteString(ipv4InIPv6Prefix)
|
||||
}
|
||||
sb.WriteString(a.Network.IP.String())
|
||||
}
|
||||
|
@ -1450,7 +1541,7 @@ func (a *APLPrefix) str() string {
|
|||
// equals reports whether two APL prefixes are identical.
|
||||
func (a *APLPrefix) equals(b *APLPrefix) bool {
|
||||
return a.Negation == b.Negation &&
|
||||
bytes.Equal(a.Network.IP, b.Network.IP) &&
|
||||
a.Network.IP.Equal(b.Network.IP) &&
|
||||
bytes.Equal(a.Network.Mask, b.Network.Mask)
|
||||
}
|
||||
|
||||
|
@ -1518,21 +1609,19 @@ func euiToString(eui uint64, bits int) (hex string) {
|
|||
return
|
||||
}
|
||||
|
||||
// copyIP returns a copy of ip.
|
||||
func copyIP(ip net.IP) net.IP {
|
||||
p := make(net.IP, len(ip))
|
||||
copy(p, ip)
|
||||
return p
|
||||
// cloneSlice returns a shallow copy of s.
|
||||
func cloneSlice[E any, S ~[]E](s S) S {
|
||||
if s == nil {
|
||||
return nil
|
||||
}
|
||||
return append(S(nil), s...)
|
||||
}
|
||||
|
||||
// copyNet returns a copy of a subnet.
|
||||
func copyNet(n net.IPNet) net.IPNet {
|
||||
m := make(net.IPMask, len(n.Mask))
|
||||
copy(m, n.Mask)
|
||||
|
||||
return net.IPNet{
|
||||
IP: copyIP(n.IP),
|
||||
Mask: m,
|
||||
IP: cloneSlice(n.IP),
|
||||
Mask: cloneSlice(n.Mask),
|
||||
}
|
||||
}
|
||||
|
||||
|
|
1
vendor/github.com/miekg/dns/udp.go
generated
vendored
1
vendor/github.com/miekg/dns/udp.go
generated
vendored
|
@ -1,3 +1,4 @@
|
|||
//go:build !windows
|
||||
// +build !windows
|
||||
|
||||
package dns
|
||||
|
|
8
vendor/github.com/miekg/dns/udp_windows.go
generated
vendored
8
vendor/github.com/miekg/dns/udp_windows.go
generated
vendored
|
@ -1,5 +1,9 @@
|
|||
//go:build windows
|
||||
// +build windows
|
||||
|
||||
// TODO(tmthrgd): Remove this Windows-specific code if go.dev/issue/7175 and
|
||||
// go.dev/issue/7174 are ever fixed.
|
||||
|
||||
package dns
|
||||
|
||||
import "net"
|
||||
|
@ -14,7 +18,6 @@ func (s *SessionUDP) RemoteAddr() net.Addr { return s.raddr }
|
|||
|
||||
// ReadFromSessionUDP acts just like net.UDPConn.ReadFrom(), but returns a session object instead of a
|
||||
// net.UDPAddr.
|
||||
// TODO(fastest963): Once go1.10 is released, use ReadMsgUDP.
|
||||
func ReadFromSessionUDP(conn *net.UDPConn, b []byte) (int, *SessionUDP, error) {
|
||||
n, raddr, err := conn.ReadFrom(b)
|
||||
if err != nil {
|
||||
|
@ -24,12 +27,9 @@ func ReadFromSessionUDP(conn *net.UDPConn, b []byte) (int, *SessionUDP, error) {
|
|||
}
|
||||
|
||||
// WriteToSessionUDP acts just like net.UDPConn.WriteTo(), but uses a *SessionUDP instead of a net.Addr.
|
||||
// TODO(fastest963): Once go1.10 is released, use WriteMsgUDP.
|
||||
func WriteToSessionUDP(conn *net.UDPConn, b []byte, session *SessionUDP) (int, error) {
|
||||
return conn.WriteTo(b, session.raddr)
|
||||
}
|
||||
|
||||
// TODO(fastest963): Once go1.10 is released and we can use *MsgUDP methods
|
||||
// use the standard method in udp.go for these.
|
||||
func setUDPSocketOptions(*net.UDPConn) error { return nil }
|
||||
func parseDstFromOOB([]byte, net.IP) net.IP { return nil }
|
||||
|
|
4
vendor/github.com/miekg/dns/update.go
generated
vendored
4
vendor/github.com/miekg/dns/update.go
generated
vendored
|
@ -32,7 +32,9 @@ func (u *Msg) Used(rr []RR) {
|
|||
u.Answer = make([]RR, 0, len(rr))
|
||||
}
|
||||
for _, r := range rr {
|
||||
r.Header().Class = u.Question[0].Qclass
|
||||
hdr := r.Header()
|
||||
hdr.Class = u.Question[0].Qclass
|
||||
hdr.Ttl = 0
|
||||
u.Answer = append(u.Answer, r)
|
||||
}
|
||||
}
|
||||
|
|
2
vendor/github.com/miekg/dns/version.go
generated
vendored
2
vendor/github.com/miekg/dns/version.go
generated
vendored
|
@ -3,7 +3,7 @@ package dns
|
|||
import "fmt"
|
||||
|
||||
// Version is current version of this library.
|
||||
var Version = v{1, 1, 43}
|
||||
var Version = v{1, 1, 57}
|
||||
|
||||
// v holds the version of this library.
|
||||
type v struct {
|
||||
|
|
46
vendor/github.com/miekg/dns/xfr.go
generated
vendored
46
vendor/github.com/miekg/dns/xfr.go
generated
vendored
|
@ -17,11 +17,22 @@ type Transfer struct {
|
|||
DialTimeout time.Duration // net.DialTimeout, defaults to 2 seconds
|
||||
ReadTimeout time.Duration // net.Conn.SetReadTimeout value for connections, defaults to 2 seconds
|
||||
WriteTimeout time.Duration // net.Conn.SetWriteTimeout value for connections, defaults to 2 seconds
|
||||
TsigProvider TsigProvider // An implementation of the TsigProvider interface. If defined it replaces TsigSecret and is used for all TSIG operations.
|
||||
TsigSecret map[string]string // Secret(s) for Tsig map[<zonename>]<base64 secret>, zonename must be in canonical form (lowercase, fqdn, see RFC 4034 Section 6.2)
|
||||
tsigTimersOnly bool
|
||||
}
|
||||
|
||||
// Think we need to away to stop the transfer
|
||||
func (t *Transfer) tsigProvider() TsigProvider {
|
||||
if t.TsigProvider != nil {
|
||||
return t.TsigProvider
|
||||
}
|
||||
if t.TsigSecret != nil {
|
||||
return tsigSecretProvider(t.TsigSecret)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// TODO: Think we need to away to stop the transfer
|
||||
|
||||
// In performs an incoming transfer with the server in a.
|
||||
// If you would like to set the source IP, or some other attribute
|
||||
|
@ -33,7 +44,6 @@ type Transfer struct {
|
|||
// dnscon := &dns.Conn{Conn:con}
|
||||
// transfer = &dns.Transfer{Conn: dnscon}
|
||||
// channel, err := transfer.In(message, master)
|
||||
//
|
||||
func (t *Transfer) In(q *Msg, a string) (env chan *Envelope, err error) {
|
||||
switch q.Question[0].Qtype {
|
||||
case TypeAXFR, TypeIXFR:
|
||||
|
@ -70,8 +80,13 @@ func (t *Transfer) In(q *Msg, a string) (env chan *Envelope, err error) {
|
|||
|
||||
func (t *Transfer) inAxfr(q *Msg, c chan *Envelope) {
|
||||
first := true
|
||||
defer t.Close()
|
||||
defer close(c)
|
||||
defer func() {
|
||||
// First close the connection, then the channel. This allows functions blocked on
|
||||
// the channel to assume that the connection is closed and no further operations are
|
||||
// pending when they resume.
|
||||
t.Close()
|
||||
close(c)
|
||||
}()
|
||||
timeout := dnsTimeout
|
||||
if t.ReadTimeout != 0 {
|
||||
timeout = t.ReadTimeout
|
||||
|
@ -121,8 +136,13 @@ func (t *Transfer) inIxfr(q *Msg, c chan *Envelope) {
|
|||
axfr := true
|
||||
n := 0
|
||||
qser := q.Ns[0].(*SOA).Serial
|
||||
defer t.Close()
|
||||
defer close(c)
|
||||
defer func() {
|
||||
// First close the connection, then the channel. This allows functions blocked on
|
||||
// the channel to assume that the connection is closed and no further operations are
|
||||
// pending when they resume.
|
||||
t.Close()
|
||||
close(c)
|
||||
}()
|
||||
timeout := dnsTimeout
|
||||
if t.ReadTimeout != 0 {
|
||||
timeout = t.ReadTimeout
|
||||
|
@ -224,12 +244,9 @@ func (t *Transfer) ReadMsg() (*Msg, error) {
|
|||
if err := m.Unpack(p); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if ts := m.IsTsig(); ts != nil && t.TsigSecret != nil {
|
||||
if _, ok := t.TsigSecret[ts.Hdr.Name]; !ok {
|
||||
return m, ErrSecret
|
||||
}
|
||||
if ts, tp := m.IsTsig(), t.tsigProvider(); ts != nil && tp != nil {
|
||||
// Need to work on the original message p, as that was used to calculate the tsig.
|
||||
err = TsigVerify(p, t.TsigSecret[ts.Hdr.Name], t.tsigRequestMAC, t.tsigTimersOnly)
|
||||
err = TsigVerifyWithProvider(p, tp, t.tsigRequestMAC, t.tsigTimersOnly)
|
||||
t.tsigRequestMAC = ts.MAC
|
||||
}
|
||||
return m, err
|
||||
|
@ -238,11 +255,8 @@ func (t *Transfer) ReadMsg() (*Msg, error) {
|
|||
// WriteMsg writes a message through the transfer connection t.
|
||||
func (t *Transfer) WriteMsg(m *Msg) (err error) {
|
||||
var out []byte
|
||||
if ts := m.IsTsig(); ts != nil && t.TsigSecret != nil {
|
||||
if _, ok := t.TsigSecret[ts.Hdr.Name]; !ok {
|
||||
return ErrSecret
|
||||
}
|
||||
out, t.tsigRequestMAC, err = TsigGenerate(m, t.TsigSecret[ts.Hdr.Name], t.tsigRequestMAC, t.tsigTimersOnly)
|
||||
if ts, tp := m.IsTsig(), t.tsigProvider(); ts != nil && tp != nil {
|
||||
out, t.tsigRequestMAC, err = TsigGenerateWithProvider(m, tp, t.tsigRequestMAC, t.tsigTimersOnly)
|
||||
} else {
|
||||
out, err = m.Pack()
|
||||
}
|
||||
|
|
58
vendor/github.com/miekg/dns/zduplicate.go
generated
vendored
58
vendor/github.com/miekg/dns/zduplicate.go
generated
vendored
|
@ -43,6 +43,32 @@ func (r1 *AFSDB) isDuplicate(_r2 RR) bool {
|
|||
return true
|
||||
}
|
||||
|
||||
func (r1 *AMTRELAY) isDuplicate(_r2 RR) bool {
|
||||
r2, ok := _r2.(*AMTRELAY)
|
||||
if !ok {
|
||||
return false
|
||||
}
|
||||
_ = r2
|
||||
if r1.Precedence != r2.Precedence {
|
||||
return false
|
||||
}
|
||||
if r1.GatewayType != r2.GatewayType {
|
||||
return false
|
||||
}
|
||||
switch r1.GatewayType {
|
||||
case IPSECGatewayIPv4, IPSECGatewayIPv6:
|
||||
if !r1.GatewayAddr.Equal(r2.GatewayAddr) {
|
||||
return false
|
||||
}
|
||||
case IPSECGatewayHost:
|
||||
if !isDuplicateName(r1.GatewayHost, r2.GatewayHost) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
func (r1 *ANY) isDuplicate(_r2 RR) bool {
|
||||
r2, ok := _r2.(*ANY)
|
||||
if !ok {
|
||||
|
@ -423,6 +449,38 @@ func (r1 *HTTPS) isDuplicate(_r2 RR) bool {
|
|||
return true
|
||||
}
|
||||
|
||||
func (r1 *IPSECKEY) isDuplicate(_r2 RR) bool {
|
||||
r2, ok := _r2.(*IPSECKEY)
|
||||
if !ok {
|
||||
return false
|
||||
}
|
||||
_ = r2
|
||||
if r1.Precedence != r2.Precedence {
|
||||
return false
|
||||
}
|
||||
if r1.GatewayType != r2.GatewayType {
|
||||
return false
|
||||
}
|
||||
if r1.Algorithm != r2.Algorithm {
|
||||
return false
|
||||
}
|
||||
switch r1.GatewayType {
|
||||
case IPSECGatewayIPv4, IPSECGatewayIPv6:
|
||||
if !r1.GatewayAddr.Equal(r2.GatewayAddr) {
|
||||
return false
|
||||
}
|
||||
case IPSECGatewayHost:
|
||||
if !isDuplicateName(r1.GatewayHost, r2.GatewayHost) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
if r1.PublicKey != r2.PublicKey {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (r1 *KEY) isDuplicate(_r2 RR) bool {
|
||||
r2, ok := _r2.(*KEY)
|
||||
if !ok {
|
||||
|
|
110
vendor/github.com/miekg/dns/zmsg.go
generated
vendored
110
vendor/github.com/miekg/dns/zmsg.go
generated
vendored
|
@ -32,6 +32,22 @@ func (rr *AFSDB) pack(msg []byte, off int, compression compressionMap, compress
|
|||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *AMTRELAY) pack(msg []byte, off int, compression compressionMap, compress bool) (off1 int, err error) {
|
||||
off, err = packUint8(rr.Precedence, msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
off, err = packUint8(rr.GatewayType, msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
off, err = packIPSECGateway(rr.GatewayAddr, rr.GatewayHost, msg, off, rr.GatewayType, compression, false)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *ANY) pack(msg []byte, off int, compression compressionMap, compress bool) (off1 int, err error) {
|
||||
return off, nil
|
||||
}
|
||||
|
@ -332,6 +348,30 @@ func (rr *HTTPS) pack(msg []byte, off int, compression compressionMap, compress
|
|||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *IPSECKEY) pack(msg []byte, off int, compression compressionMap, compress bool) (off1 int, err error) {
|
||||
off, err = packUint8(rr.Precedence, msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
off, err = packUint8(rr.GatewayType, msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
off, err = packUint8(rr.Algorithm, msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
off, err = packIPSECGateway(rr.GatewayAddr, rr.GatewayHost, msg, off, rr.GatewayType, compression, false)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
off, err = packStringBase64(rr.PublicKey, msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *KEY) pack(msg []byte, off int, compression compressionMap, compress bool) (off1 int, err error) {
|
||||
off, err = packUint16(rr.Flags, msg, off)
|
||||
if err != nil {
|
||||
|
@ -1180,6 +1220,34 @@ func (rr *AFSDB) unpack(msg []byte, off int) (off1 int, err error) {
|
|||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *AMTRELAY) unpack(msg []byte, off int) (off1 int, err error) {
|
||||
rdStart := off
|
||||
_ = rdStart
|
||||
|
||||
rr.Precedence, off, err = unpackUint8(msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
rr.GatewayType, off, err = unpackUint8(msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
rr.GatewayAddr, rr.GatewayHost, off, err = unpackIPSECGateway(msg, off, rr.GatewayType)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *ANY) unpack(msg []byte, off int) (off1 int, err error) {
|
||||
rdStart := off
|
||||
_ = rdStart
|
||||
|
@ -1636,6 +1704,48 @@ func (rr *HTTPS) unpack(msg []byte, off int) (off1 int, err error) {
|
|||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *IPSECKEY) unpack(msg []byte, off int) (off1 int, err error) {
|
||||
rdStart := off
|
||||
_ = rdStart
|
||||
|
||||
rr.Precedence, off, err = unpackUint8(msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
rr.GatewayType, off, err = unpackUint8(msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
rr.Algorithm, off, err = unpackUint8(msg, off)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
rr.GatewayAddr, rr.GatewayHost, off, err = unpackIPSECGateway(msg, off, rr.GatewayType)
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
if off == len(msg) {
|
||||
return off, nil
|
||||
}
|
||||
rr.PublicKey, off, err = unpackStringBase64(msg, off, rdStart+int(rr.Hdr.Rdlength))
|
||||
if err != nil {
|
||||
return off, err
|
||||
}
|
||||
return off, nil
|
||||
}
|
||||
|
||||
func (rr *KEY) unpack(msg []byte, off int) (off1 int, err error) {
|
||||
rdStart := off
|
||||
_ = rdStart
|
||||
|
|
453
vendor/github.com/miekg/dns/ztypes.go
generated
vendored
453
vendor/github.com/miekg/dns/ztypes.go
generated
vendored
File diff suppressed because it is too large
Load diff
4
vendor/modules.txt
vendored
4
vendor/modules.txt
vendored
|
@ -687,8 +687,8 @@ github.com/klauspost/compress/zstd/internal/xxhash
|
|||
# github.com/matttproud/golang_protobuf_extensions v1.0.4
|
||||
## explicit; go 1.9
|
||||
github.com/matttproud/golang_protobuf_extensions/pbutil
|
||||
# github.com/miekg/dns v1.1.43
|
||||
## explicit; go 1.14
|
||||
# github.com/miekg/dns v1.1.57
|
||||
## explicit; go 1.19
|
||||
github.com/miekg/dns
|
||||
# github.com/mistifyio/go-zfs/v3 v3.0.1
|
||||
## explicit; go 1.14
|
||||
|
|
Loading…
Reference in a new issue