mirror of
https://github.com/coredns/coredns.git
synced 2026-10-26 12:15:50 -04:00
46 lines
1.4 KiB
Go
46 lines
1.4 KiB
Go
|
|
//go:build aix || darwin || dragonfly || freebsd || linux || netbsd || openbsd || solaris
|
||
|
|
|
||
|
|
package dnsserver
|
||
|
|
|
||
|
|
import (
|
||
|
|
"net"
|
||
|
|
|
||
|
|
"golang.org/x/net/ipv4"
|
||
|
|
"golang.org/x/net/ipv6"
|
||
|
|
"golang.org/x/sys/unix"
|
||
|
|
)
|
||
|
|
|
||
|
|
var udpOOBSize = len(ipv4.NewControlMessage(ipv4.FlagDst|ipv4.FlagInterface)) +
|
||
|
|
len(ipv6.NewControlMessage(ipv6.FlagDst|ipv6.FlagInterface))
|
||
|
|
|
||
|
|
func enableUDPPacketInfo(conn *net.UDPConn) bool {
|
||
|
|
err4 := ipv4.NewPacketConn(conn).SetControlMessage(ipv4.FlagDst|ipv4.FlagInterface, true)
|
||
|
|
err6 := ipv6.NewPacketConn(conn).SetControlMessage(ipv6.FlagDst|ipv6.FlagInterface, true)
|
||
|
|
return err4 == nil || err6 == nil
|
||
|
|
}
|
||
|
|
|
||
|
|
func parseUDPPacketInfo(oob []byte, flags int) udpPacketInfo {
|
||
|
|
if flags&unix.MSG_CTRUNC != 0 {
|
||
|
|
return udpPacketInfo{}
|
||
|
|
}
|
||
|
|
cm6 := new(ipv6.ControlMessage)
|
||
|
|
if cm6.Parse(oob) == nil && cm6.Dst != nil {
|
||
|
|
return udpPacketInfo{dst: cm6.Dst, ifIndex: cm6.IfIndex}
|
||
|
|
}
|
||
|
|
cm4 := new(ipv4.ControlMessage)
|
||
|
|
if cm4.Parse(oob) == nil && cm4.Dst != nil {
|
||
|
|
return udpPacketInfo{dst: cm4.Dst, ifIndex: cm4.IfIndex}
|
||
|
|
}
|
||
|
|
return udpPacketInfo{}
|
||
|
|
}
|
||
|
|
|
||
|
|
func udpSourceControl(info udpPacketInfo) []byte {
|
||
|
|
if info.dst == nil || info.dst.IsUnspecified() || info.dst.IsMulticast() {
|
||
|
|
return nil
|
||
|
|
}
|
||
|
|
if ip4 := info.dst.To4(); ip4 != nil {
|
||
|
|
return (&ipv4.ControlMessage{Src: ip4, IfIndex: info.replyInterface()}).Marshal()
|
||
|
|
}
|
||
|
|
return (&ipv6.ControlMessage{Src: info.dst, IfIndex: info.replyInterface()}).Marshal()
|
||
|
|
}
|