github.com/sealerio/sealer@v0.11.1-0.20240507115618-f4f89c5853ae/utils/net/iputils.go (about)

     1  // Copyright © 2021 Alibaba Group Holding Ltd.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package net
    16  
    17  import (
    18  	"bytes"
    19  	"fmt"
    20  	"math/big"
    21  	"net"
    22  	"sort"
    23  	"strings"
    24  
    25  	k8snet "k8s.io/apimachinery/pkg/util/net"
    26  )
    27  
    28  func GetHostNetInterface(host net.IP) (string, error) {
    29  	netInterfaces, err := net.Interfaces()
    30  	if err != nil {
    31  		return "", err
    32  	}
    33  	for i := 0; i < len(netInterfaces); i++ {
    34  		if (netInterfaces[i].Flags & net.FlagUp) == 0 {
    35  			continue
    36  		}
    37  		addrs, err := netInterfaces[i].Addrs()
    38  		if err != nil {
    39  			return "", fmt.Errorf("failed to get Addrs: %v", err)
    40  		}
    41  		if IsLocalIP(host, addrs) {
    42  			return netInterfaces[i].Name, nil
    43  		}
    44  	}
    45  	return "", nil
    46  }
    47  
    48  func GetLocalHostAddresses() ([]net.Addr, error) {
    49  	netInterfaces, err := net.Interfaces()
    50  	if err != nil {
    51  		return nil, fmt.Errorf("failed to get net.Interfaces: %v", err)
    52  	}
    53  
    54  	var allAddrs []net.Addr
    55  	for i := 0; i < len(netInterfaces); i++ {
    56  		if (netInterfaces[i].Flags & net.FlagUp) == 0 {
    57  			continue
    58  		}
    59  		addrs, err := netInterfaces[i].Addrs()
    60  		if err != nil {
    61  			return nil, fmt.Errorf("failed to get Addrs: %v", err)
    62  		}
    63  		for j := 0; j < len(addrs); j++ {
    64  			allAddrs = append(allAddrs, addrs[j])
    65  		}
    66  	}
    67  	return allAddrs, nil
    68  }
    69  
    70  func IsLocalIP(ip net.IP, addrs []net.Addr) bool {
    71  	if len(addrs) == 0 {
    72  		addrs, _ = GetLocalHostAddresses()
    73  	}
    74  
    75  	for _, address := range addrs {
    76  		if ipnet, ok := address.(*net.IPNet); ok && !ipnet.IP.IsLoopback() && ipnet.IP.Equal(ip) {
    77  			return true
    78  		}
    79  	}
    80  	return false
    81  }
    82  
    83  func GetLocalDefaultIP() (string, error) {
    84  	netIP, err := k8snet.ChooseHostInterface()
    85  	if err != nil {
    86  		return "", fmt.Errorf("failed to get default route ip, err: %v", err)
    87  	}
    88  	return netIP.String(), nil
    89  }
    90  
    91  func GetLocalIP(master0IPPort string) (net.IP, error) {
    92  	conn, err := net.Dial("udp", master0IPPort)
    93  	if err != nil {
    94  		return nil, err
    95  	}
    96  	localAddr := conn.LocalAddr().String()
    97  	return net.ParseIP(strings.Split(localAddr, ":")[0]), err
    98  }
    99  
   100  // TransferToIPList transfer network segment string to ip list string
   101  func TransferToIPList(ipStr string) (string, error) {
   102  	var result []string
   103  	var ips = strings.Split(ipStr, "-")
   104  	if ipStr == "" || !strings.Contains(ipStr, "-") {
   105  		return ipStr, nil
   106  	}
   107  	if len(ips) != 2 {
   108  		return "", fmt.Errorf("input IP(%s) is invalid, IP range format must be xxx.xxx.xxx.1-xxx.xxx.xxx.2", ipStr)
   109  	}
   110  	if returnedIP := net.ParseIP(ips[0]); returnedIP == nil {
   111  		return "", fmt.Errorf("failed tp parse IP(%s)", ips[0])
   112  	}
   113  	if returnedIP := net.ParseIP(ips[1]); returnedIP == nil {
   114  		return "", fmt.Errorf("failed tp parse IP(%s)", ips[1])
   115  	}
   116  
   117  	//ips[0],ips[1] = 192.168.56.3, 192.168.56.7;  result = [192.168.56.3, 192.168.56.4, 192.168.56.5, 192.168.56.6, 192.168.56.7]
   118  	for res := CompareIP(ips[0], ips[1]); res <= 0; {
   119  		result = append(result, ips[0])
   120  		ips[0] = NextIP(ips[0]).String()
   121  		res = CompareIP(ips[0], ips[1])
   122  	}
   123  	if len(result) == 0 {
   124  		return "", fmt.Errorf("input IP(%s) is invalid", ipStr)
   125  	}
   126  	return strings.Join(result, ","), nil
   127  }
   128  
   129  func IPToInt(v string) *big.Int {
   130  	ip := net.ParseIP(v).To4()
   131  	if val := ip.To4(); val != nil {
   132  		return big.NewInt(0).SetBytes(val)
   133  	}
   134  	return big.NewInt(0).SetBytes(ip.To16())
   135  }
   136  
   137  func CompareIP(v1, v2 string) int {
   138  	i := IPToInt(v1)
   139  	j := IPToInt(v2)
   140  
   141  	if i == nil {
   142  		return 2
   143  	}
   144  	if j == nil {
   145  		return 2
   146  	}
   147  
   148  	return i.Cmp(j)
   149  }
   150  
   151  func NextIP(ip string) net.IP {
   152  	i := IPToInt(ip)
   153  	return i.Add(i, big.NewInt(1)).Bytes()
   154  }
   155  
   156  func SortIPList(iplist []string) {
   157  	realIPs := make([]net.IP, 0, len(iplist))
   158  	for _, ip := range iplist {
   159  		realIPs = append(realIPs, net.ParseIP(ip))
   160  	}
   161  
   162  	sort.Slice(realIPs, func(i, j int) bool {
   163  		return bytes.Compare(realIPs[i], realIPs[j]) < 0
   164  	})
   165  
   166  	for i := range realIPs {
   167  		iplist[i] = realIPs[i].String()
   168  	}
   169  }
   170  
   171  func IsInIPList(key net.IP, slice []net.IP) bool {
   172  	for _, s := range slice {
   173  		if s.Equal(key) {
   174  			return true
   175  		}
   176  	}
   177  	return false
   178  }
   179  
   180  func IPStrsToIPs(ipStrs []string) []net.IP {
   181  	if ipStrs == nil {
   182  		return nil
   183  	}
   184  
   185  	var result []net.IP
   186  	for _, ipStr := range ipStrs {
   187  		if ipStr == "" {
   188  			continue
   189  		}
   190  		result = append(result, net.ParseIP(ipStr))
   191  	}
   192  	return result
   193  }
   194  
   195  func IPsToIPStrs(ips []net.IP) []string {
   196  	if ips == nil {
   197  		return nil
   198  	}
   199  
   200  	var result []string
   201  	for _, ip := range ips {
   202  		result = append(result, ip.String())
   203  	}
   204  	return result
   205  }
   206  
   207  func RemoveIPs(clusterIPList []net.IP, toBeDeletedIPList []net.IP) (res []net.IP) {
   208  	for _, ip := range clusterIPList {
   209  		if !IsInIPList(ip, toBeDeletedIPList) {
   210  			res = append(res, ip)
   211  		}
   212  	}
   213  	return
   214  }
   215  
   216  func GetIndexIP(subnet *net.IPNet, index int) (string, error) {
   217  	bip := big.NewInt(0).SetBytes(subnet.IP.To4())
   218  	if subnet.IP.To4() == nil {
   219  		bip = big.NewInt(0).SetBytes(subnet.IP.To16())
   220  	}
   221  	ip := net.IP(big.NewInt(0).Add(bip, big.NewInt(int64(index))).Bytes())
   222  	if subnet.Contains(ip) {
   223  		return ip.String(), nil
   224  	}
   225  
   226  	return "", fmt.Errorf("can't generate IP with index %d from subnet. subnet too small. subnet: %q", index, subnet)
   227  }