Тип net.IPNet

Тип net.IPNet представляет собой структуру, содержащую IP-адрес сети и маску подсети. Он используется в сетевом программировании для работы с подсетями, проверки вхождения IP-адреса в сеть, получения сетевого адреса и других операций, связанных с маскированием и маршрутизацией. Структура имеет два поля: IP — сетевой адрес, и Mask — маска подсети в формате net.IPMask.

Создание IPNet

Для создания net.IPNet можно использовать функцию net.ParseCIDR, которая принимает строку с CIDR-нотацией и возвращает IP-адрес и сеть. Либо можно создать структуру вручную, задав поля IP и Mask.

gopackage main

import (
  "fmt"
  "net"
)

func main() {
  // Creating IPNet using ParseCIDR
  ip, ipnet, err := net.ParseCIDR("192.168.1.0/24")
  if err != nil {
    fmt.Println("Error:", err)
    return
  }
  fmt.Println("IP:", ip)
  fmt.Println("IPNet:", ipnet)
  fmt.Println("Network:", ipnet.IP)
  fmt.Println("Mask:", ipnet.Mask)

  // Manual creation
  manualIP := net.IP{192, 168, 1, 0}
  manualMask := net.IPMask{255, 255, 255, 0}
  manualIPNet := &net.IPNet{
    IP:   manualIP,
    Mask: manualMask,
  }
  fmt.Println("Manual IPNet:", manualIPNet)
}

Результат выполнения кода:

go"IP: 192.168.1.0"
"IPNet: 192.168.1.0/24"
"Network: 192.168.1.0"
"Mask: ffffff00"
"Manual IPNet: 192.168.1.0/24"

Проверка принадлежности IP-адреса сети

С помощью метода Contains можно проверить, входит ли IP-адрес в подсеть. Метод принимает net.IP и возвращает true, если адрес принадлежит сети.

gopackage main

import (
  "fmt"
  "net"
)

func main() {
  _, ipnet, err := net.ParseCIDR("192.168.1.0/24")
  if err != nil {
    fmt.Println("Error:", err)
    return
  }

  testIP1 := net.ParseIP("192.168.1.10")
  testIP2 := net.ParseIP("192.168.2.10")

  fmt.Println("192.168.1.10 in network:", ipnet.Contains(testIP1))
  fmt.Println("192.168.2.10 in network:", ipnet.Contains(testIP2))
}

Результат выполнения кода:

go"192.168.1.10 in network: true"
"192.168.2.10 in network: false"

Получение сетевого адреса

Структура IPNet содержит поле IP, которое представляет сетевой адрес. Однако при использовании ParseCIDR этот адрес автоматически нормализуется (маскируется) до сетевого адреса. Метод String возвращает строковое представление сети в CIDR-нотации.

gopackage main

import (
  "fmt"
  "net"
)

func main() {
  _, ipnet, err := net.ParseCIDR("10.0.0.1/8")
  if err != nil {
    fmt.Println("Error:", err)
    return
  }

  fmt.Println("Network address:", ipnet.IP)
  fmt.Println("String representation:", ipnet.String())
}

Результат выполнения кода:

go"Network address: 10.0.0.0"
"String representation: 10.0.0.0/8"

Работа с маской подсети

Поле Mask содержит маску подсети. С помощью метода Size можно получить размер сети в битах (количество единичных бит в маске). Для преобразования маски в длину префикса используется функция net.IPMask.Size.

gopackage main

import (
  "fmt"
  "net"
)

func main() {
  _, ipnet, err := net.ParseCIDR("192.168.0.0/16")
  if err != nil {
    fmt.Println("Error:", err)
    return
  }

  ones, bits := ipnet.Mask.Size()
  fmt.Printf("Mask: %v\n", ipnet.Mask)
  fmt.Printf("Ones: %d, Total bits: %d\n", ones, bits)
  fmt.Printf("CIDR prefix length: /%d\n", ones)
}

Результат выполнения кода:

go"Mask: ffff0000"
"Ones: 16, Total bits: 32"
"CIDR prefix length: /16"

Смотрите также

  • функцию net.ParseCIDR,
    которая создает IPNet из CIDR-нотации
  • функцию net.ParseIP,
    которая преобразует строку в IP-адрес
  • тип net.IP,
    который представляет IP-адрес
  • тип net.IPMask,
    который представляет маску подсети