You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
85 lines
1.6 KiB
85 lines
1.6 KiB
package nets |
|
|
|
import ( |
|
"errors" |
|
"fmt" |
|
"math" |
|
"math/big" |
|
"net" |
|
"strconv" |
|
"strings" |
|
) |
|
|
|
// GetHostIpv4 获取本地内网IP |
|
func GetHostIpv4() (string, error) { |
|
privates, err := getAllIPV4(func(ip net.IP) bool { |
|
return ip.IsPrivate() |
|
}) |
|
if err != nil { |
|
return "", err |
|
} |
|
if len(privates) == 0 { |
|
return "", errors.New("no private ip") |
|
} |
|
return privates[0], nil |
|
} |
|
|
|
func getAllIPV4(filter func(net.IP) bool) (ips []string, err error) { |
|
// 获取所有网卡 |
|
addrs, err := net.InterfaceAddrs() |
|
if err != nil { |
|
return |
|
} |
|
|
|
for _, addr := range addrs { |
|
// 这个网络地址是IP地址: ipv4, ipv6 |
|
ipNet, isIpNet := addr.(*net.IPNet) |
|
if isIpNet && !ipNet.IP.IsLoopback() { |
|
// 跳过IPV6 |
|
if ipNet.IP.To4() != nil { |
|
if filter(ipNet.IP) { |
|
ips = append(ips, ipNet.IP.String()) |
|
} |
|
} |
|
} |
|
} |
|
return |
|
} |
|
|
|
func Address2i64(addr string) (int64, error) { |
|
idx := strings.Index(addr, ":") |
|
if idx < 0 { |
|
return 0, fmt.Errorf("invalid addr %s", addr) |
|
} |
|
ip, port := addr[0:idx], addr[idx+1:] |
|
portI, err := strconv.Atoi(port) |
|
if err != nil { |
|
return 0, err |
|
} |
|
ipI, err := Ip2i64(ip) |
|
if err != nil { |
|
return 0, err |
|
} |
|
return (int64(portI) << 32) | ipI, nil |
|
} |
|
|
|
func I642Address(addr int64) string { |
|
port := addr >> 32 |
|
ip := addr & math.MaxUint32 |
|
return fmt.Sprintf("%s:%d", I642Ip(ip), port) |
|
} |
|
|
|
func Ip2i64(ip string) (int64, error) { |
|
ip4 := net.ParseIP(ip).To4() |
|
if ip4 == nil { |
|
return 0, fmt.Errorf("invalid ip %s", ip) |
|
} |
|
ret := big.NewInt(0) |
|
ret.SetBytes(ip4) |
|
return ret.Int64(), nil |
|
} |
|
|
|
func I642Ip(ip int64) string { |
|
return fmt.Sprintf("%d.%d.%d.%d", |
|
byte(ip>>24), byte(ip>>16), byte(ip>>8), byte(ip)) |
|
}
|
|
|