ОПИСАНИЕ
В Linux
    реализован
    протокол
    Интернета
    (Internet Protocol, IP) версии 4,
    описанный
    в RFC 791 и RFC 1122. В
    модуле ip
    содержится
    реализация
    второго
    уровня
    групповых
    многоадресных
    сообщений,
    которая
    соответствует
    RFC 1112. Кроме
    того, в нём
    имеется
    маршрутизатор
    IP с
    фильтрацией
    пакетов.
Программный
    интерфейс
    совместим
    с
    интерфейсом
    сокетов BSD.
    Более
    подробную
    информацию
    смотрите в
    socket(7).
Сокет IP
    создаётся
    с помощью
    socket(2):
  
   socket(AF_INET, socket_type, protocol);
Возможные
    типы
    сокета (socket_type):
    SOCK_STREAM (для
    открытия
    сокета tcp(7)),
    SOCK_DGRAM (для
    открытия
    сокета udp(7)),
    SOCK_RAW (для
    открытия
    сокета raw(7) с
    прямым
    доступом к
    протоколу
    IP). В protocol
    задаётся
    протокол IP,
    который
    указывается
    в
    IP-заголовке
    принимаемых
    или
    отправляемых
    пакетов.
    Допустимые
    значения
    для
    параметра
    protocol: 0 и IPPROTO_TCP —
    для
    сокетов TCP, 0 и
    IPPROTO_UDP — для
    сокетов UDP.
    Для SOCK_RAW
    можно
    указать
    любой из
    IP-протоколов,
    описанных
    в RFC 1700 и
    зарегистрированных
    в IANA.
Если
    процесс
    хочет
    принимать
    новые
    входящие
    пакеты или
    соединения,
    то он
    должен
    связать
    сокет с
    адресом
    локального
    интерфейса
    с помощью
    bind(2). Каждый
    IP-сокет
    может быть
    связан
    только с
    одной
    задаваемой
    локальной
    парой
    (адрес,
    порт). Если в
    вызове bind(2)
    указать INADDR_ANY,
    то сокет
    будет
    связан со
    всеми
    локальными
    интерфейсами.
    При вызове
    listen(2) для
    несвязанного
    сокета
    происходит
    автоматическая
    привязка к
    произвольно
    выбранному
    свободному
    порту с
    локальным
    адресом INADDR_ANY.
    При вызове
    connect(2) для
    несвязанного
    сокета
    происходит
    автоматическая
    привязка к
    произвольно
    выбранному
    свободному
    порту или
    используемому
    общему
    порту с
    локальным
    адресом
  INADDR_ANY.
После
    закрытия
    связанного
    локального
    TCP-сокета
    его адрес
    будет
    недоступен
    в течение
    некоторого
    времени,
    если
    только не
    был
    установлен
    флаг SO_REUSEADDR.
    Следует
    проявлять
    осторожность
    при
    использовании
    этого
    флага,
    поскольку
    это делает
    TCP менее
    надежным.
Формат
  адреса
Адрес
    IP-сокета
    определяется
    как
    комбинация
    IP-адреса
    интерфейса
    и номера
    порта. В
    самом
    протоколе IP
    нет
    номеров
    портов, они
    реализуются
    протоколами
    более
    высокого
    уровня,
    например
    udp(7) и tcp(7). У
    неструктурированных
    (raw) сокетов
    номер
    протокола IP
    указывается
    в sin_port.
  
struct sockaddr_in {
    sa_family_t    sin_family; /* семейство адресов: AF_INET */
    in_port_t      sin_port;   /* порт сокета в сетевом порядке
                                  байт */
    struct in_addr sin_addr;   /* Интернет-адрес */
};
/* Интернет-адрес */
struct in_addr {
    uint32_t       s_addr;     /* адрес в сетевом порядке байт */
};
Значение
    sin_family всегда
    устанавливается
    в AF_INET. Это
    обязательно;
    в Linux 2.2 большая
    часть
    сетевых
    функций
    возвращает
    код ошибки
    EINVAL, если это
    условие не
    выполняется.
    В sin_port
    указывается
    номер
    порта в
    сетевом
    порядке
    байт. Порты,
    номера
    которых
    меньше 1024,
    называются
    привилегированными
    портами
    (или, иногда,
    зарезервированными
    портами).
    Только
    привилегированные
    процессы (в
    Linux: процессы
    с мандатом
    CAP_NET_BIND_SERVICE в
    пользовательском
    пространстве
    имён,
    управляющим
    его
    сетевым
    пространством
    имён) могут
    быть
    связаны с
    этими
    сокетами с
    помощью bind(2).
    Заметим,
    что у
    неструктурированного
    протокола
    IPv4 нет
    понятия
    портов как
    таковых,
    они
    реализуются
    только
    протоколами
    более
    высокого
    уровня,
    типа tcp(7) и udp(7).
В sin_addr
    указывается
    IP-адрес
    узла. В поле
    s_addr
    структуры
    struct in_addr
    содержится
    адрес
    интерфейса
    узла в
    сетевом
    порядке
    байт.
    Значение
    in_addr должно
    быть одним
    из INADDR_*
    (например,
    INADDR_LOOPBACK)
    установленное
    htonl(3), или с
    помощью
    библиотечных
    функций
    inet_aton(3), inet_addr(3), inet_makeaddr(3)
    или
    напрямую с
    помощью
    преобразователя
    имён
    (смотрите
    gethostbyname(3)).
Адреса IPv4
    делятся на
    однозначные
    (unicast),
    широковещательные
    (broadcast) и
    многоадресные
    (multicast).
    Однозначный
    адрес
    указывает
    на один
    интерфейс
    узла,
    широковещательный
    адрес
    указывает
    на все узлы
    в сети, а
    многоадресный
    указывает
    на все узлы
    многоадресной
    (multicast group).
    Дейтаграммы
    могут
    посылаться
    или
    приниматься
    по
    широковещательным
    адресам
    только,
    если для
    сокета
    установлен
    флаг SO_BROADCAST. В
    текущей
    реализации
    сокетам,
    ориентированным
    на
    соединения,
    разрешено
    иметь
    только
    однозначные
    адреса.
Заметим,
    что
    значение
    адреса и
    порта
    всегда
    хранится в
    сетевом
    порядке
    байт. В
    частности,
    это
    означает,
    что
    требуется
    вызывать
    htons(3) для
    числа,
    обозначающего
    порт. Все
    функции из
    стандартной
    библиотеки,
    используемые
    для работы
    с
    адресами/портами,
    используют
    сетевой
    порядок
    байт.
Есть
    несколько
    специальных
    адресов:
    INADDR_LOOPBACK (127.0.0.1)
    всегда
    ссылается
    на
    локальный
    узел через
    интерфейс
    обратной
    петли; INADDR_ANY (0.0.0.0)
    означает
    любой
    адрес для
    связывания;
    INADDR_BROADCAST (255.255.255.255)
    означает
    любой узел
    и, по
    историческим
    причинам,
    при
    связывании
    подобен
  INADDR_ANY.
Параметры
  сокета
IP
    поддерживает
    некоторые
    параметры
    сокета,
    относящиеся
    к
    протоколу,
    которые
    могут быть
    установлены
    с помощью
    setsockopt(2) и
    прочитаны
    с помощью
    getsockopt(2).
    Значением
    уровня (level)
    параметров
    сокета для IP
    является
    IPPROTO_IP.
    Логический
    флаг в виде
    целого
    числа со
    значением
    ноль
    означает
    «ложь»,
    другие
    значения —
    «истина».
Если
    сокету
    передается
    неправильный
    параметр,
    то getsockopt(2) и setsockopt(2)
    завершаются
    с ошибкой
    ENOPROTOOPT.
  - IP_ADD_MEMBERSHIP
    (начиная с Linux
    1.2)
- Присоединиться
      к
      многоадресной
      группе. В
      аргументе
      указывается
      структура
      ip_mreqn.
  
struct ip_mreqn {
    struct in_addr imr_multiaddr; /* IP-адрес группы */
    struct in_addr imr_address;   /* IP локального
                                     интерфейса */
    int            imr_ifindex;   /* индекс интерфейса */
};
В imr_multiaddr
    содержится
    адрес
    многоадресной
    группы, в
    которую
    приложение
    хочет
    войти или
    выйти. Это
    должен
    быть
    правильный
    адрес
    многоадресной
    рассылки
    (иначе setsockopt(2)
    завершится
    с ошибкой
    EINVAL). В imr_address
    указывается
    адрес
    локального
    интерфейса,
    через
    который
    система
    должна
    войти в
    многоадресную
    группу;
    если
    указано
    значение
    INADDR_ANY, то
    нужный
    интерфейс
    выбирается
    системой
    самостоятельно.
    В imr_ifindex
    указывается
    индекс
    интерфейса,
    через
    который
    нужно
    войти/выйти
    в группу
    imr_multiaddr, или 0,
    если
    интерфейс
    может быть
    любым.
  
  - Структура
      ip_mreqn
      доступна
      только
      начиная с Linux
      2.2. Для
      совместимости,
      старая
      структура
      ip_mreq
      (существует
      с Linux 1.2)
      по-прежнему
      поддерживается;
      она
      отличается
      от ip_mreqn
      только
      отсутствием
      поля imr_ifindex
      (при
      передаче
      ядро
      определяет
      нужную
      структуру
      исходя из
      размера,
      переданного
      в optlen).
- IP_ADD_MEMBERSHIP
      допустим
      только для
      setsockopt(2).
  - IP_ADD_SOURCE_MEMBERSHIP
    (начиная с Linux
    2.4.22 / 2.5.68)
- Присоединиться
      к
      многоадресной
      группе и
      разрешить
      принимать
      данные
      только из
      указанного
      источника.
      Аргументом
      является
      структура
      ip_mreq_source.
  
struct ip_mreq_source {
    struct in_addr imr_multiaddr;  /* IP многоадресной
                                      группы */
    struct in_addr imr_interface;  /* IP-адрес локального
                                      интерфейса */
    struct in_addr imr_sourceaddr; /* IP-адрес многоадресного
                                      источника */
};
Структура
    ip_mreq_source похожа
    на ip_mreqn,
    которая
    описана в
    разделе о
    IP_ADD_MEMBERSIP. Поле
    imr_multiaddr
    содержит
    адрес
    многоадресной
    группы, к
    которой
    приложение
    хочет
    подключиться
    или выйти.
    Поле imr_interface
    содержит
    адрес
    локального
    интерфейса,
    с которого
    система
    должна
    подключаться
    к
    многоадресной
    группе. В
    поле imr_sourceaddr
    содержится
    адрес
    источника,
    из
    которого
    приложение
    хочет
    получать
    данные.
  
  - Для приёма
      данных из
      нескольких
      источников
      этот
      параметр
      можно
      использовать
      несколько
      раз.
  - IP_BIND_ADDRESS_NO_PORT
    (начиная с Linux
    4.2)
- Информирует
      ядро, что
      не
      требуется
      резервировать
      эфемерный
      порт при
      использовании
      bind(2) с
      номером
      порта 0.
      Позднее,
      порт будет
      автоматически
      выбран при
      connect(2); это
      позволяет
      использовать
      общий
      исходящий
      порт пока
      уникальна
      связка 4-х
      значений.
- IP_BLOCK_SOURCE
    (начиная с Linux
    2.4.22 / 2.5.68)
- Прекратить
      приём
      многоадресных
      данных из
      указанного
      источника
      заданной
      группы. Это
      допустимо,
      если
      приложение
      подписывалось
      на
      многоадресную
      группу с
      помощью
      IP_ADD_MEMBERSHIP или
      IP_ADD_SOURCE_MEMBERSHIP.
  
  - Аргументом
      является
      структура
      ip_mreq_source,
      описанная
      в разделе о
      IP_ADD_SOURCE_MEMBERSHIP.
  - IP_DROP_MEMBERSHIP
    (начиная с Linux
    1.2)
- Выйти из
      многоадресной
      группы.
      Аргументом
      является
      структура
      ip_mreqn или ip_mreq,
      описана в
      IP_ADD_MEMBERSHIP.
- IP_DROP_SOURCE_MEMBERSHIP
    (начиная с Linux
    2.4.22 / 2.5.68)
- Выйти из
      указанной
      группы — то
      есть
      прекратить
      приём
      данных
      указанной
      многоадресной
      группы,
      которые
      поступают
      из
      указанного
      источника.
      Если
      приложение
      подписано
      на
      несколько
      источников
      одной
      группы, то
      данные из
      оставшихся
      источников
      продолжат
      поступать.
      Чтобы
      прекратить
      приём
      данных из
      всех
      источников
      сразу,
      используйте
      IP_DROP_MEMBERSHIP.
  
  - Аргументом
      является
      структура
      ip_mreq_source,
      описанная
      в разделе о
      IP_ADD_SOURCE_MEMBERSHIP.
  - IP_FREEBIND
    (начиная с Linux
    2.4)
- Этот
      логический
      параметр
      позволяет
      привязаться
      (если
      значение
      равно
      «истина») к
      IP-адресу,
      который не
      является
      локальным
      или (пока)
      не
      существует.
      Это
      позволяет
      прослушивать
      сокет, не
      имея
      нижележащего
      сетевого
      интерфейса
      или
      назначенного
      динамического
      IP-адреса,
      которых
      может ещё
      не быть,
      когда
      приложение
      пытается
      связаться
      с ним. Этот
      параметр
      имеет
      эквивалентный
      интерфейс
      ip_nonlocal_bind (описан
      далее) в /proc
      на каждый
      сокет.
- IP_HDRINCL
    (начиная с Linux
    2.0)
- Если
      значение
      равно
      «истина»,
      то это
      означает,
      что
      пользователь
      добавил
      заголовок
      IP в начало
      своих
      данных.
      Допустим
      только для
      сокетов SOCK_RAW;
      более
      подробную
      информацию
      смотрите в
      raw(7). Если
      этот флаг
      установлен,
      то
      значения,
      заданные
      параметрами
      IP_OPTIONS, IP_TTL и IP_TOS,
      игнорируются.
- IP_MSFILTER
    (начиная с Linux
    2.4.22 / 2.5.68)
- Этот
      параметр
      предоставляет
      доступ к
      расширенному
      программному
      интерфейсу
      фильтрации.
      Аргументом
      является
      структура
      ip_msfilter.
  
struct ip_msfilter {
    struct in_addr imsf_multiaddr; /* IP-адрес
                                      многоадресной группы */
    struct in_addr imsf_interface; /* IP-адрес локального
                                      интерфейса */
    uint32_t       imsf_fmode;     /* Режим фильтрации */
    uint32_t       imsf_numsrc;    /* Количество источников в
                                      следующем массиве */
    struct in_addr imsf_slist[1];  /* Массив адресов
                                      источников */
};
Для
    задания
    режима
    фильтрации
    существует
    два
    макроса —
    MCAST_INCLUDE и MCAST_EXCLUDE.
    Также,
    существует
    макрос IP_MSFILTER_SIZE(n),
    которым
    можно
    определить
    количество
    памяти,
    требуемой
    для
    хранения
    структуры
    ip_msfilter с n
    источниками
    в списке
    источников.
  
  - Полное
      описание
      фильтрации
      многоадресных
      источников
      групп
      смотрите в
      RFC 3376.
  - IP_MTU
    (начиная с Linux
    2.2)
- Возвращает
      известное
      в данный
      момент
      значение MTU
      маршрута
      текущего
      сокета.
      Возвращается
      целое
      число.
  
  - Параметр
      IP_MTU
      допускается
      только для
      getsockopt(2) и может
      использоваться
      только для
      подключённого
      сокета.
  - IP_MTU_DISCOVER
    (начиная с Linux
    2.2)
- Устанавливает
      или
      возвращает
      значение Path MTU
      Discovery
      (обнаружение
      значения MTU
      маршрута)
      для сокета.
      Если он
      установлен,
      то Linux будет
      производить
      обнаружение
      значения MTU
      маршрута
      для
      сокетов
      SOCK_STREAM
      согласно
      RFC 1191. Для
      сокетов не
      SOCK_STREAM при
      значении
      IP_PMTUDISC_DO у всех
      исходящих
      пакетов
      будет
      устанавливаться
      флаг
      запрета
      фрагментации.
      Ответственность
      за
      разбивку
      данных на
      пакеты
      согласно
      размеру MTU, и
      за
      выполнение,
      при
      необходимости,
      повторной
      передачи
      данных,
      лежит на
      пользователе.
      Ядро будет
      отвергать
      пакеты (с
      ошибкой EMSGSIZE),
      размер
      которых
      больше
      текущего
      значения MTU
      у маршрута.
      При
      значении
      IP_PMTUDISC_WANT
      дейтаграмма
      будет
      фрагментироваться
      по размеру
      MTU, если
      требуется,
      иначе
      устанавливается
      флаг
      запрета
      фрагментации.
  
  - Системное
      значение
      по
      умолчанию
      можно
      переключать
      между IP_PMTUDISC_WANT и
      IP_PMTUDISC_DONT,
      записывая,
      соответственно,
      нулевое и
      ненулевое
      значение в
      файл
      /proc/sys/net/ipv4/ip_no_pmtu_disc.
    
      
        | Значение
          определения
          маршрута
          MTU | Значение |  
        | IP_PMTUDISC_WANT | Использовать
          для
          каждого
          маршрута
          своё
          значение. |  
        | IP_PMTUDISC_DONT | Никогда
          не
          выполнять
          обнаружение
          значения MTU
          маршрута. |  
        | IP_PMTUDISC_DO | Всегда
          выполнять
          обнаружение
          значения MTU
          маршрута. |  
        | IP_PMTUDISC_PROBE | Установить
          DF, но
          игнорировать
          маршрут MTU. |  
 Если
        значение Path
        MTU Discovery задано,
        то ядро
        автоматически
        следит за MTU
        маршрута
        для
        каждого
        удалённого
        узла.
        Когда с
        некоторым
        узлом
        установлено
        соединение
        с помощью
        connect(2),
        текущее
        значение MTU
        маршрута
        можно
        легко
        получить
        через
        параметр
        сокета IP_MTU
        (например,
        после
        возникновения
        ошибки EMSGSIZE).
        Значение MTU
        может со
        временем
        меняться.
        Для
        сокетов
        без
        установления
        соединения,
        которые
        имеют
        несколько
        узлов-получателей,
        новое
        значение MTU
        для
        заданного
        узла
        назначения
        может
        быть
        получено
        с помощью
        очереди
        ошибок
        (смотрите
        IP_RECVERR). При
        каждом
        входящем
        сообщении
        об
        обновлении
        MTU в очередь
        будет
        добавляться
        новая
        ошибка. 
- Во время
      процесса
      обнаружения
      MTU
      начальные
      пакеты от
      дейтаграмных
      сокетов
      могут быть
      отброшены.
      Приложения,
      использующие
      UDP, должны
      учитывать
      это и не
      думать, что
      эти пакеты
      будут
      переданы
      повторно.
- Чтобы
      запустить
      процесс
      обнаружения
      MTU маршрута
      для
      сокетов
      без
      установления
      соединения
      сначала
      можно
      установить
      большой
      размер
      дейтаграммы
      (с размером
      заголовка
      до 64
      килобайт) и
      сокращать
      его при
      изменении
      MTU маршрута.
- Чтобы
      получить
      начальную
      оценку MTU
      маршрута,
      соедините
      дейтаграмный
      сокет с
      адресом
      назначения,
      используя
      connect(2), и
      узнайте
      значение MTU
      путем
      вызова getsockopt(2)
      с
      параметром
      IP_MTU.
- Возможно
      реализовать
      обнаружение
      MTU согласно RFC
      4821 с помощью
      сокетов
      типа SOCK_DGRAM
      или SOCK_RAW,
      установив
      значение
      IP_PMTUDISC_PROBE
      (доступно,
      начиная с Linux
      2.6.22). В
      частности,
      это также
      полезно
      для
      инструментов
      диагностики,
      таких как
      tracepath(8),
      которым
      нужно
      умышленно
      посылать
      проверочные
      пакеты
      большего
      размера,
      чем
      исследуемый
      Path MTU.
  - IP_MULTICAST_ALL
    (since Linux 2.6.31)
- Может
      использоваться
      для
      изменения
      политики
      доставки
      многоадресных
      сообщений
      в сокеты,
      подсоединённые
      к
      шаблонному
      (wildcard) адресу
      INADDR_ANY.
      Аргументом
      является
      логическое
      целое (по
      умолчанию
      1). Если
      значение
      равно 1, то
      сокет
      будет
      принимать
      сообщения
      от всех
      групп, к
      которым
      было
      выполнено
      присоединение
      глобально
      всей
      системы. В
      противном
      случае
      будут
      доставляться
      сообщения
      от групп, к
      которым
      было
      выполнено
      присоединение
      явным
      образом(например,
      с помощью
      IP_ADD_MEMBERSHIP) на
      этом
      сокете.
- IP_MULTICAST_IF
    (начиная с Linux
    1.2)
- Назначает
      локальное
      устройство
      для
      многоадресного
      группового
      сокета (multicast socket).
      Аргументом
      для setsockopt(2)
      является
      структура
      ip_mreqn или ip_mreq
      (начиная с Linux
      3.5), подобная
      IP_ADD_MEMBERSHIP или
      структуре
      in_addr (при
      передаче
      ядро
      определяет
      нужную
      структуру
      исходя из
      размера,
      переданного
      в optlen). Для getsockopt(2)
      аргументом
      является
      структура
      in_addr.
- IP_MULTICAST_LOOP
    (начиная с Linux
    1.2)
- Устанавливает
      или
      возвращает
      логический
      флаг в виде
      целого
      числа, в
      зависимости
      от того,
      будут ли
      пакеты,
      использующие
      многоадресную
      адресацию,
      закольцовываться
      на
      локальные
      сокеты.
- IP_MULTICAST_TTL
    (начиная с Linux
    1.2)
- Устанавливает
      или
      возвращает
      значение
      времени
      существования
      (time-to-live) для
      многоадресных
      исходящих
      из этого
      сокета
      пакетов,
      использующих
      многоадресную
      адресацию.
      Для
      подобных
      пакетов
      очень
      важно
      установить
      наименьшее
      возможное
      значение TTL.
      По
      умолчанию
      оно равно 1,
      это значит,
      что
      многоадресные
      пакеты не
      выйдут за
      пределы
      локальной
      сети, если
      только
      пользовательская
      программа
      явно не
      попросит
      этого.
      Значением
      аргумента
      является
      целое
      число.
- IP_NODEFRAG
    (начиная с Linux
    2.6.36)
- Если
      установлен
      (аргумент
      не равен
      нулю), то на
      уровне netfilter
      запрещается
      выполнять
      переборку
      (reassembly)
      исходящих
      пакетов.
      Значением
      аргумента
      является
      целое
      число.
  
  - Этот
      параметр
      допускается
      только для
      сокетов с
      типом SOCK_RAW.
  - IP_OPTIONS
    (начиная с Linux
    2.0)
- Устанавливает
      или
      возвращает
      параметры
      IP, которые
      посылаются
      с каждым
      пакетом из
      данного
      сокета.
      Аргументами
      являются
      указатель
      на буфер
      памяти с
      этими
      параметрами
      и размер
      параметра.
      Системный
      вызов setsockopt(2)
      устанавливает
      параметры
      IP,
      связанные
      с сокетом.
      Для IPv4
      максимальный
      размер
      параметра
      IPv4 равен 40
      байтам. Все
      возможные
      параметры
      перечислены
      в RFC 791. Если
      пакет,
      устанавливающий
      соединение
      с сокетом
      типа SOCK_STREAM,
      содержит
      параметры
      IP, то эти
      параметры
      IP (с
      инвертированными
      заголовками
      маршрутизации)
      будут
      использоваться
      в этом
      сокете.
      После
      установления
      соединения
      изменять
      параметры
      входящими
      пакетами
      запрещено.
      По
      умолчанию,
      обработка
      всех
      параметров,
      связанных
      с
      маршрутизацией
      от
      источника,
      отключена,
      но её можно
      включить
      через
      интерфейс
      accept_source_route в /proc.
      Другие
      параметры,
      например
      связанные
      с
      временными
      отметками
      (timestamp),
      продолжают
      обрабатываться.
      Для
      дейтаграмных
      сокетов
      параметры
      IP могут
      быть
      установлены
      только
      локальным
      пользователем.
      Вызов getsockopt(2) с
      параметром
      IP_OPTIONS
      помещает в
      указанный
      буфер
      текущие
      параметры
      IP,
      используемые
      при
      отправке.
- IP_PKTINFO
    (начиная с Linux
    2.2)
- Передает
      вспомогательное
      (ancillary)
      сообщение
      IP_PKTINFO с
      структурой
      pktinfo, которая
      содержит
      некоторую
      информацию
      о входящем
      пакете.
      Допускается
      только для
      сокетов,
      ориентированных
      на посылку
      дейтаграмм.
      Аргументом
      является
      флаг,
      который
      сообщает
      сокету,
      нужно ли
      посылать
      сообщение
      IP_PKTINFO или нет.
      Само
      сообщение
      может быть
      послано/получено
      только в
      виде
      управляющего
      сообщения
      с пакетом,
      используя
      recvmsg(2) или sendmsg(2).
  
  - 
    
    struct in_pktinfo {
    unsigned int   ipi_ifindex;  /* индекс интерфейса */
    struct in_addr ipi_spec_dst; /* локальный адрес */
    struct in_addr ipi_addr;     /* заголовок адреса
                                    назначения */
};
- ipi_ifindex это
      уникальный
      индекс
      интерфейса,
      из
      которого
      был
      получен
      этот пакет.
      ipi_spec_dst это
      локальный
      адрес
      пакета, а ipi_addr
      это адрес
      назначения,
      указанный
      в
      заголовке
      пакета.
      Если
      параметр
      IP_PKTINFO
      передаётся
      в sendmsg(2) и ipi_spec_dst не
      равно нулю,
      то ipi_spec_dst
      будет
      использован
      как
      локальный
      адрес
      источника
      при
      просмотре
      таблицы
      маршрутизации
      и для
      установки
      IP-параметров
      маршрутизации
      от
      источника.
      Если
      значение
      ipi_ifindex не
      равно нулю,
      то при
      поиске в
      таблице
      маршрутизации
      вместо
      значения
      ipi_spec_dst
      используется
      первичный
      локальный
      адрес
      интерфейса
      с
      указанным
      индексом.
  - IP_RECVERR
    (начиная с Linux
    2.2)
- Делает
      передачу
      сообщений
      об ошибках
      более
      надёжной.
      Если этот
      параметр
      установлен
      для
      дейтаграмного
      сокета, то
      все
      возникающие
      ошибки
      будут
      поставлены
      в очередь
      ошибок,
      свою для
      каждого
      сокета. Для
      получения
      ошибки при
      операции с
      сокетом
      пользователь
      может
      воспользоваться
      вызовом recvmsg(2)
      с
      установленным
      флагом MSG_ERRQUEUE.
      Структура
      sock_extended_err,
      описывающая
      ошибку,
      будет
      передана в
      вспомогательном
      сообщении
      с типом IP_RECVERR
      и уровнем
      IPPROTO_IP. Этот
      параметр
      полезен
      для
      надежной
      обработки
      ошибок для
      сокетов
      без
      установления
      соединения.
      В пакете с
      ошибкой из
      очереди
      ошибок,
      также
      содержится
      порция
      полученных
      данных.
  
  - Вспомогательное
      сообщение
      IP_RECVERR
      содержит
      структуру
      sock_extended_err:
- 
    
    #define SO_EE_ORIGIN_NONE    0
#define SO_EE_ORIGIN_LOCAL   1
#define SO_EE_ORIGIN_ICMP    2
#define SO_EE_ORIGIN_ICMP6   3
struct sock_extended_err {
    uint32_t ee_errno;   /* номер ошибки */
    uint8_t  ee_origin;  /* где возникла ошибка */
    uint8_t  ee_type;    /* тип */
    uint8_t  ee_code;    /* код */
    uint8_t  ee_pad;
    uint32_t ee_info;    /* дополнительная информация */
    uint32_t ee_data;    /* другие данные */
    /* Дальше могут следовать данные */
};
struct sockaddr *SO_EE_OFFENDER(struct sock_extended_err *);
- В ee_errno
      содержится
      номер
      ошибки в
      очереди. В
      ee_origin
      содержится
      код
      источника
      ошибки.
      Значение
      остальных
      полей
      зависит от
      протокола.
      Макрос SO_EE_OFFENDER
      возвращает
      указатель
      на адрес
      сетевого
      объекта, в
      котором
      возникла
      ошибка,
      согласно
      указанному
      указателю
      на
      вспомогательное
      сообщение.
      Если адрес
      неизвестен,
      то поле sa_family
      структуры
      sockaddr
      содержит
      AF_UNSPEC, и
      остальные
      поля sockaddr не
      определены.
- Для IP
      структура
      sock_extended_err
      используется
      следующим
      образом:
      значение
      поля ee_origin
      устанавливается
      в SO_EE_ORIGIN_ICMP, если
      ошибка
      получена
      из пакета ICMP,
      или в SO_EE_ORIGIN_LOCAL,
      если
      возникла
      локальная
      ошибка.
      Неизвестные
      значения
      следует
      игнорировать.
      Значения
      полей ee_type и
      ee_code
      устанавливаются
      исходя из
      значений
      полей типа
      и кода
      заголовка
      ICMP. При
      ошибках EMSGSIZE
      поле ee_info
      содержит
      обнаруженную
      величину MTU.
      Сообщение
      также
      содержит
      структуру
      sockaddr_in узла,
      вызвавшего
      ошибку,
      которая
      доступна
      через
      макрос SO_EE_OFFENDER.
      Если
      источник
      неизвестен,
      то поле sin_family
      адреса,
      возвращённого
      макросом
      SO_EE_OFFENDER,
      содержит
      значение
      AF_UNSPEC. Если
      ошибка
      возникла в
      сети, то
      все
      параметры
      IP (IP_OPTIONS, IP_TTL и т.д.),
      которые
      используются
      сокетом и
      содержатся
      в пакете с
      описанием
      ошибки,
      передаются
      в
      управляющих
      сообщениях.
      Данные
      пакета,
      вызвавшего
      ошибку,
      возвращаются
      как
      нормальные
      данные.
      Заметьте,
      что у TCP нет
      очереди
      ошибок;
      флаг MSG_ERRQUEUE
      нельзя
      использовать
      для
      сокетов
      типа SOCK_STREAM.
      Параметр
      IP_RECVERR
      допустим
      для TCP, но все
      ошибки
      возвращаются
      только
      через
      функцию
      сокета или
      через
      параметр
      SO_ERROR.
- Для
      неструктурированных
      сокетов,
      параметром
      IP_RECVERR
      включается
      передача в
      приложение
      всех
      получаемых
      ошибок ICMP,
      иначе
      сообщается
      только об
      ошибках в
      сокетах,
      ориентированных
      на
      соединение.
- Этот
      параметр
      устанавливается
      или
      возвращается
      как
      логический
      флаг в виде
      целого
      числа. По
      умолчанию,
      параметр
      IP_RECVERR
      выключен.
  - IP_RECVOPTS
    (начиная с Linux
    2.2)
- Передает
      пользователю
      все
      входящие
      параметры
      IP с помощью
      управляющего
      сообщения
      IP_OPTIONS. Для
      локального
      узла
      заполняется
      заголовок
      маршрутизации
      и другие
      параметры.
      Не
      поддерживается
      сокетами
      типа SOCK_STREAM.
- IP_RECVORIGDSTADDR
    (начиная с Linux
    2.6.29)
- Данный
      логический
      параметр
      включает
      вспомогательное
      сообщение
      IP_ORIGDSTADDR в recvmsg(2), в
      котором
      ядро
      возвращает
      первоначальный
      адрес
      назначения
      полученной
      дейтаграммы.
      Вспомогательное
      сообщение
      содержит
      структуру
      struct sockaddr_in.
- IP_RECVTOS
    (начиная с Linux
    2.2)
- Если
      включён, то
      вместе с
      входящими
      пакетами
      передаётся
      вспомогательное
      сообщение
      IP_TOS. В нём
      содержится
      байт, в
      котором
      указано
      поле типа
      сервиса/приоритета
      из
      заголовка
      пакета.
      Ожидается
      логическое
      значение в
      виде
      целого
      числа.
- IP_RECVTTL
    (начиная с Linux
    2.2)
- Если
      указан
      этот флаг,
      то
      передаётся
      управляющее
      сообщение
      IP_TTL с байтом
      значения
      поля
      времени
      существования
      из
      полученного
      пакета в
      виде
      32-битного
      целого. Не
      поддерживается
      сокетами
      типа SOCK_STREAM.
- IP_RETOPTS
    (начиная с Linux
    2.2)
- Идентичен
      параметру
      IP_RECVOPTS, но
      возвращает
      необработанные
      параметры,
      причём без
      заполненных
      временных
      меток и
      записи о
      маршрутизации
      до этой
      точки (hop).
- IP_ROUTER_ALERT
    (начиная с Linux
    2.2)
- Передаёт
      этому
      сокету все
      пересылаемые
      (forwarded) пакеты с
      установленным
      параметром
      IP Router Alert. Этот
      параметр
      используется
      для
      «сырых»
      сокетов. Он
      может быть
      полезен,
      например,
      для служб RSVP,
      запущенных
      в
      пространстве
      пользователя.
      Перехваченные
      пакеты
      дальше
      ядром не
      пересылаются:
      ответственность
      за их
      отсылку
      лежит на
      пользователе.
      Связывание
      сокета
      игнорируется,
      так как
      пакеты
      фильтруются
      по
      протоколу.
      Ожидается
      логическое
      значение в
      виде
      целого
      числа.
- IP_TOS
    (начиная с Linux
    1.0)
- Устанавливает
      или
      получает
      значение
      поля Type-Of-Service (TOS,
      тип
      сервиса)
      каждого
      IP-пакета,
      который
      отсылается
      с этого
      сокета. Это
      поле
      используется
      для
      указания
      приоритета
      пакета в
      сети.
      Значение TOS
      хранится в
      одном
      байте.
      Существует
      несколько
      стандартных
      флагов TOS:
      IPTOS_LOWDELAY — для
      минимизации
      задержки
      передаваемого
      трафика,
      IPTOS_THROUGHPUT — для
      оптимизации
      пропускной
      способности,
      IPTOS_RELIABILITY — для
      увеличения
      надёжности,
      IPTOS_MINCOST — при
      пересылки
      данных, для
      которых
      неважна
      скорость
      передачи.
      Может быть
      указано не
      более
      одного из
      этих
      значений TOS.
      Все другие
      биты
      являются
      недействительными
      и должны
      быть
      обнулены.
      По
      умолчанию,
      Linux посылает
      дейтаграммы
      с IPTOS_LOWDELAY
      первыми, но
      точное
      поведение
      зависит от
      настроенного
      порядка
      очередности
      (queueing discipline). Для
      установки
      некоторых
      высокоприоритетных
      типов
      сервиса
      могут
      потребоваться
      права
      суперпользователя
      (мандат
    CAP_NET_ADMIN).
- IP_TRANSPARENT
    (начиная с Linux
    2.6.24)
- Установка
      этого
      логического
      параметра
      включает
      прозрачное
      проксирование
      на
      заданный
      сокет.
      Данный
      параметр
      сокета
      позволяет
      вызвавшему
      приложению
      привязаться
      к
      нелокальному
      IP-адресу и
      работать
      клиентом и
      сервером с
      внешним
      адресом
      как с
      локальной
      конечной
      точкой.
      ЗАМЕЧАНИЕ:
      требуется
      настройка
      маршрутизации
      пакетов
      для
      внешнего
      адреса
      через TProxy (то
      есть,
      системы, на
      которой
      находится
      приложение,
      применяющее
      параметр
      сокета IP_TRANSPARENT).
      Для
      установки
      данного
      параметра
      сокета
      требуются
      права
      суперпользователя
      (мандат
    CAP_NET_ADMIN).
  
  - Также, для
      установки
      данного
      параметра
      на
      перенаправляемый
      сокет
      требуется
      перенаправление
      TProxy с помощью
      цели TPROXY в iptables.
  - IP_TTL
    (начиная с Linux
    1.0)
- Устанавливает
      или
      получает
      текущее
      значение
      поля
      времени
      существования
      (time to live), которое
      указывается
      в каждом
      пакете,
      отсылаемом
      с этого
      сокета.
- IP_UNBLOCK_SOURCE
    (начиная с Linux
    2.4.22 / 2.5.68)
- Разблокировать
      ранее
      заблокированный
      многоадресный
      источник.
      Возвращает
      EADDRNOTAVAIL, если
      указанный
      источник
      не
      заблокирован.
  
  - Аргументом
      является
      структура
      ip_mreq_source,
      описанная
      в разделе о
      IP_ADD_SOURCE_MEMBERSHIP.
Интерфейсы
  в /proc
Настройку
    глобальных
    параметров
    протокола IP
    можно
    осуществлять
    через
    интерфейс
    /proc. Все
    параметры
    доступны
    посредством
    чтения или
    записи
    файлов из
    каталога
    /proc/sys/net/ipv4/. Для
    логических
    (Boolean)
    параметров
    значения
    указываются
    в виде
    целых
    чисел:
    ненулевое
    значение
    («истина»)
    означает
    включает
    параметра,
    а нулевое
    значение
    («ложь») —
    выключение.
  - ip_always_defrag
    (Boolean; начиная с
    Linux 2.2.13)
- [Появился в
      ядре
      версии 2.2.13; в
      ранних
      версиях
      это
      свойство
      контролировалось
      с помощью
      флага CONFIG_IP_ALWAYS_DEFRAG
      времени
      компиляции;
      данный
      параметр
      убран в 2.4.x]
  
  - Если этот
      флаг
      включён (не
      равен 0), то
      входящие
      фрагменты
      (части
      IP-пакетов,
      которые
      образуются,
      если
      некоторый
      узел,
      находящийся
      между
      отправителем
      и
      получателем,
      решает, что
      пакеты
      слишком
      велики и
      разделяет
      их на
      кусочки)
      будут
      снова
      собраны
      (дефрагментированны)
      перед
      дальнейшей
      обработкой,
      даже если
      они должны
      быть
      пересланы
      дальше.
- Включайте
      этот
      параметр
      только на
      межсетевом
      экране,
      который
      является
      единственной
      связью с
      вашей
      сетью, или
      на
      прозрачном
      прокси;
      никогда не
      включайте
      его на
      обычном
      маршрутизаторе
      или узле. В
      противном
      случае,
      соединение
      может быть
      нарушено,
      если
      фрагменты
      передаются
      по
      различным
      линиям.
      Дефрагментация
      также
      требует
      много
      памяти и
      процессорного
      времени.
- Этот
      параметр
      включается
      автоматически
      при
      настройке
      маскарадинга
      или
      прозрачного
      проксирования.
  - ip_autoconfig
    (в Linux 2.2 по 2.6.17)
- Не описан.
- ip_default_ttl
    (integer; по
    умолчанию:
    64; начиная с Linux
    2.2)
- Устанавливает
      значение
      time-to-live по
      умолчанию
      для
      исходящих
      пакетов.
      Это
      значение
      может быть
      изменено
      для
      каждого
      отдельного
      сокета с
      помощью
      параметра
      IP_TTL.
- ip_dynaddr
    (Boolean; по
    умолчанию:
    выключен;
    начиная с Linux
    2.0.31)
- Включает
      динамическую
      адресацию
      сокета и
      подмену (masquerading)
      при
      изменении
      адреса
      интерфейса.
      Это
      полезно
      для
      интерфейсов
      коммутируемых
      соединений
      (dialup) с
      изменяющимися
      IP-адресами.
      Значение 0
      означает
      не
      подменять,
      1 включает
      подмену и 2
      включает
      режим
      подробностей
      работы.
- ip_forward
    (Boolean; по
    умолчанию:
    выключен;
    начиная с Linux
    1.2)
- Включает/выключает
      пересылку
      (forwarding) IP-пакетов.
      Пересылка
      IP также
      может быть
      включена
      для
      каждого
      интерфейса
      в
      отдельности.
- ip_local_port_range
    (начиная с Linux
    2.2)
- В этом
      файле
      содержатся
      два целых
      числа,
      определяющие
      диапазон
      локальных
      портов по
      умолчанию,
      выделенных
      для
      сокетов, у
      которые
      нет явно
      привязанного
      номера
      порта — то
      есть
      диапазон
      эфемерных
      портов.
      Эфемерный
      порт
      выделяется
      сокету в
      следующих
      случаях:
  - при вызове
      bind(2) в номере
      порта
      адреса
      сокета
      указан 0;
- Вызов listen(2)
      вызван для
      потокового
      сокета,
      который
      ещё не
      привязан;
- Вызов connect(2)
      вызван для
      сокета,
      который
      ещё не
      привязан;
- Вызов sendto(2)
      вызван для
      дейтаграмного
      сокета,
      который
      ещё не
      привязан.
 
  
  - Выделение
      эфемерных
      портов
      начинается
      с первого
      числа в
      ip_local_port_range и
      заканчивается
      вторым
      числом.
      Если
      диапазон
      эфемерных
      портов
      закончился,
      то
      соответствующий
      системный
      вызов
      вернёт
      ошибку (но
      смотрите
      ДЕФЕКТЫ).
- Заметим,
      что
      диапазон
      портов в
      ip_local_port_range не
      должен
      конфликтовать
      с портами,
      используемыми
      для
      маскарадинг
      (хотя это
      проверяется).
      Также,
      произвольные
      значения
      могут
      вызвать
      проблемы с
      некоторыми
      пакетными
      фильтрами
      межсетевых
      экранов,
      которые
      делают
      предположения
      об
      используемых
      локальных
      портах.
      Первое
      число
      должно
      быть не
      менее 1024, или
      лучше
      более 4096,
      чтобы не
      пересекаться
      с всем
      известными
      портами и
      минимизировать
      проблемы с
      межсетевыми
      экранами.
  - ip_no_pmtu_disc
    (Boolean; по
    умолчанию:
    выключен;
    начиная с Linux
    2.2)
- Если
      включён,
      то, по
      умолчанию,
      не
      производится
      обнаружение
      значения MTU
      у маршрута
      для TCP
      сокетов.
      Обнаружение
      MTU маршрута
      может
      завершиться
      с ошибкой
      из-за
      встретившихся
      на пути
      неверно
      настроенных
      межсетевых
      экранов
      (которые
      отбрасывают
      все пакеты
      ICMP) или из-за
      неверно
      настроенных
      интерфейсов
      (например,
      соединение
      точка-точка,
      у которого
      оба конца
      не
      договорились
      о MTU). Лучше
      исправить
      встреченные
      на пути
      неисправные
      маршрутизаторы,
      чем
      глобально
      отключать
      обнаружение
      MTU маршрута,
      потому что
      это
      отключение
      приведёт к
      высокой
      нагрузке
      на сеть.
- ip_nonlocal_bind
    (Boolean; по
    умолчанию:
    выключен;
    начиная с Linux
    2.4)
- Если
      установлен,
      то это
      позволяет
      процессам
      привязываться
      (bind(2)) к
      нелокальным
      IP-адресам,
      что
      полезно, но
      может
      привести к
      неработоспособности
      некоторых
      приложений.
- ip6frag_time
    (integer; по
    умолчанию:
    30)
- Время в
      секундах,
      на которое
      фрагмент IPv6
      остаётся в
      памяти.
- ip6frag_secret_interval
    (integer; по
    умолчанию:
    600)
- Интервал
      регенерации
      (в
      секундах)
      контрольной
      суммы
      секрета (hash secret)
      (или время
      существования
      контрольной
      суммы
      секрета)
      фрагментов
      IPv6.
- ipfrag_high_thresh
    (integer), ipfrag_low_thresh (integer)
- Если
      количество
      фрагментов
      IP, стоящих в
      очереди,
      достигает
      значения
      ipfrag_high_thresh, то
      очередь
      укорачивается
      до
      значения
      ipfrag_low_thresh.
      Содержит
      целое
      число,
      означающее
      количество
      байт.
- neigh/*
- Смотрите в
      arp(7).
Вызовы ioctl
Все
    вызовы ioctl,
    описанные
    в socket(7),
    применимы
    к ip.
Вызовы ioctl
    для
    настройки
    общих
    параметров
    устройств
    описаны в
    netdevice(7).
ЗАМЕЧАНИЯ
Значения
    IP_FREEBIND, IP_MSFILTER, IP_MTU,
    IP_MTU_DISCOVER, IP_RECVORIGDSTADDR, IP_PKTINFO,
    IP_RECVERR, IP_ROUTER_ALERT и IP_TRANSPARENT
    есть
    только в Linux.
Будьте
    осторожны
    при
    использовании
    параметра
    SO_BROADCAST — в Linux он
    не
    является
    привилегированным.
    Если
    небрежно
    относиться
    к
    широковещательным
    сообщениям,
    то можно
    легко
    перегрузить
    сеть. В
    новых
    протоколах
    для
    приложений
    лучше
    использовать
    многоадресные
    рассылки
    вместо
    широковещательных.
    Не
    используйте
    широковещание.
Для
    определения
    адреса
    назначения
    и
    интерфейса
    полученных
    дейтаграмм
    в
    некоторые
    реализациях
    сокетов BSD
    введены
    параметры
    сокетов
    IP_RCVDSTADDR и IP_RECVIF. В Linux
    для этой
    цели есть
    общий
    параметр
    IP_PKTINFO.
В
    некоторых
    реализациях
    сокетов BSD
    также есть
    параметр
    IP_RECVTTL, но
    вспомогательное
    сообщение
    с типом IP_RECVTTL
    передаётся
    с входным
    пакетом. В
    этом
    отличие от
    параметра
    IP_TTL,
    используемого
    в Linux.
Использование
    уровня
    параметров
    сокета SOL_IP
    непереносимо
    — в BSD-стеках
    используется
    уровень
  IPPROTO_IP.
Значение
    INADDR_ANY (0.0.0.0) и INADDR_BROADCAST
    (255.255.255.255)
    указываются
    с
    нейтральным
    порядком
    байт. Это
    означает,
    что htonl(3) на
    них не
    действует.
Совместимость
Для
    совместимости
    с Linux 2.0
    устаревший
    синтаксис
    socket(AF_INET, SOCK_PACKET, protocol)
    всё ещё
    поддерживается
    для
    открытия
    сокетов
    типа packet(7).
    Такое
    использование
    не
    поощряется
    и должно
    быть
    заменено
    на socket(AF_PACKET, SOCK_RAW, protocol).
    Основное
    различие
    между ними
    в новой
    адресной
    структуре
    sockaddr_ll (вместо
    старой
    структуры
    sockaddr_pkt),
    хранящей
    информацию
    обобщённого
    уровня
    соединения.