1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798 |
- package sockaddr
- import "bytes"
- type IPAddrs []IPAddr
- func (s IPAddrs) Len() int { return len(s) }
- func (s IPAddrs) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
- // // SortIPAddrsByCmp is a type that satisfies sort.Interface and can be used
- // // by the routines in this package. The SortIPAddrsByCmp type is used to
- // // sort IPAddrs by Cmp()
- // type SortIPAddrsByCmp struct{ IPAddrs }
- // // Less reports whether the element with index i should sort before the
- // // element with index j.
- // func (s SortIPAddrsByCmp) Less(i, j int) bool {
- // // Sort by Type, then address, then port number.
- // return Less(s.IPAddrs[i], s.IPAddrs[j])
- // }
- // SortIPAddrsBySpecificMaskLen is a type that satisfies sort.Interface and
- // can be used by the routines in this package. The
- // SortIPAddrsBySpecificMaskLen type is used to sort IPAddrs by smallest
- // network (most specific to largest network).
- type SortIPAddrsByNetworkSize struct{ IPAddrs }
- // Less reports whether the element with index i should sort before the
- // element with index j.
- func (s SortIPAddrsByNetworkSize) Less(i, j int) bool {
- // Sort masks with a larger binary value (i.e. fewer hosts per network
- // prefix) after masks with a smaller value (larger number of hosts per
- // prefix).
- switch bytes.Compare([]byte(*s.IPAddrs[i].NetIPMask()), []byte(*s.IPAddrs[j].NetIPMask())) {
- case 0:
- // Fall through to the second test if the net.IPMasks are the
- // same.
- break
- case 1:
- return true
- case -1:
- return false
- default:
- panic("bad, m'kay?")
- }
- // Sort IPs based on the length (i.e. prefer IPv4 over IPv6).
- iLen := len(*s.IPAddrs[i].NetIP())
- jLen := len(*s.IPAddrs[j].NetIP())
- if iLen != jLen {
- return iLen > jLen
- }
- // Sort IPs based on their network address from lowest to highest.
- switch bytes.Compare(s.IPAddrs[i].NetIPNet().IP, s.IPAddrs[j].NetIPNet().IP) {
- case 0:
- break
- case 1:
- return false
- case -1:
- return true
- default:
- panic("lol wut?")
- }
- // If a host does not have a port set, it always sorts after hosts
- // that have a port (e.g. a host with a /32 and port number is more
- // specific and should sort first over a host with a /32 but no port
- // set).
- if s.IPAddrs[i].IPPort() == 0 || s.IPAddrs[j].IPPort() == 0 {
- return false
- }
- return s.IPAddrs[i].IPPort() < s.IPAddrs[j].IPPort()
- }
- // SortIPAddrsBySpecificMaskLen is a type that satisfies sort.Interface and
- // can be used by the routines in this package. The
- // SortIPAddrsBySpecificMaskLen type is used to sort IPAddrs by smallest
- // network (most specific to largest network).
- type SortIPAddrsBySpecificMaskLen struct{ IPAddrs }
- // Less reports whether the element with index i should sort before the
- // element with index j.
- func (s SortIPAddrsBySpecificMaskLen) Less(i, j int) bool {
- return s.IPAddrs[i].Maskbits() > s.IPAddrs[j].Maskbits()
- }
- // SortIPAddrsByBroadMaskLen is a type that satisfies sort.Interface and can
- // be used by the routines in this package. The SortIPAddrsByBroadMaskLen
- // type is used to sort IPAddrs by largest network (i.e. largest subnets
- // first).
- type SortIPAddrsByBroadMaskLen struct{ IPAddrs }
- // Less reports whether the element with index i should sort before the
- // element with index j.
- func (s SortIPAddrsByBroadMaskLen) Less(i, j int) bool {
- return s.IPAddrs[i].Maskbits() < s.IPAddrs[j].Maskbits()
- }
|