-->

UNIX: разработка сетевых приложений

На нашем литературном портале можно бесплатно читать книгу UNIX: разработка сетевых приложений, Стивенс Уильям Ричард-- . Жанр: ОС и Сети. Онлайн библиотека дает возможность прочитать весь текст и даже без регистрации и СМС подтверждения на нашем литературном портале bazaknig.info.
UNIX: разработка сетевых приложений
Название: UNIX: разработка сетевых приложений
Дата добавления: 16 январь 2020
Количество просмотров: 381
Читать онлайн

UNIX: разработка сетевых приложений читать книгу онлайн

UNIX: разработка сетевых приложений - читать бесплатно онлайн , автор Стивенс Уильям Ричард

Новое издание книги, посвященной созданию веб-серверов, клиент-серверных приложений или любого другого сетевого программного обеспечения в операционной системе UNIX, — классическое руководство по сетевым программным интерфейсам, в частности сокетам. Оно основано на трудах Уильяма Стивенса и полностью переработано и обновлено двумя ведущими экспертами по сетевому программированию. В книгу включено описание ключевых современных стандартов, реализаций и методов, она содержит большое количество иллюстрирующих примеров и может использоваться как учебник по программированию в сетях, так и в качестве справочника для опытных программистов.

Внимание! Книга может содержать контент только для совершеннолетних. Для несовершеннолетних чтение данного контента СТРОГО ЗАПРЕЩЕНО! Если в книге присутствует наличие пропаганды ЛГБТ и другого, запрещенного контента - просьба написать на почту [email protected] для удаления материала

Перейти на страницу:

2-7
 Определяется структура
proto
для IPv4 и IPv6. Указатели структуры адреса сокета инициализируются как нулевые, поскольку еще не известно, какая из версий будет использоваться — IPv4 или IPv6.

Длина дополнительных данных

8
 Устанавливается количество дополнительных данных (56 байт), которые будут посылаться с эхо-запросом ICMP. При этом полная IPv4-дейтаграмма будет иметь размер 84 байта (20 байт на IPv4-заголовок и 8 байт на ICMP-заголовок), а IPv6-дейтаграмма будет иметь длину 104 байта. Все данные, посылаемые с эхо- запросом, должны быть возвращены в эхо-ответе. Время отправки эхо-запроса будет сохраняться в первых 8 байтах области данных, а затем, при получении эхо- ответа, будет использоваться для вычисления и вывода времени RTT.

Обработка параметров командной строки

15-24
 Единственный параметр командной строки, поддерживаемый в нашей версии, это параметр
-v
, в результате использования которого большинство ICMP-сообщений будут выводиться на консоль. (Мы не выводим эхо-ответы, принадлежащие другой запущенной копии программы
ping
.) Для сигнала
SIGALRM
устанавливается обработчик, и мы увидим, что этот сигнал генерируется один раз в секунду и вызывает отправку эхо-запросов ICMP.

Обработка аргумента, содержащего имя узла

31-48
 Строка, содержащая имя узла или IP-адрес, является обязательным аргументом и обрабатывается функцией
host_serv
. Возвращаемая структура
addrinfo
содержит семейство протоколов — либо
AF_INET
, либо
AF_INET6
. Глобальный указатель pr устанавливается на требуемую в конкретной ситуации структуру
proto
. Также с помощью вызова функции
IN6_IS_ADDR_V4MAPPED
мы убеждаемся, что адрес IPv6 на самом деле не является адресом IPv4, преобразованным к виду IPv6, поскольку даже если возвращаемый адрес является адресом IPv6, узлу будет отправлен пакет IPv4. (Если такая ситуация возникнет, можно переключиться и использовать IPv4.) Структура адреса сокета, уже размещенная в памяти с помощью функции
getaddrinfo
, используется для отправки, а другая структура адреса сокета того же размера размещается в памяти для получения.

Обработка ответов осуществляется функцией

readlоор
, представленной в листинге 28.4.

Листинг 28.4. Функция readloop

//ping/readlоор.c

 1 #include "ping.h"

 2 void

 3 readloop(void)

 4 {

 5  int size;

 6  char recvbuf[BUFSIZE];

 7  char controlbuf[BUFSIZE];

 8  struct msghdr msg;

 9  struct iovec iov;

10  ssize_t n;

11  struct timeval tval;

12  sockfd = Socket(pr->sasend->sa_family, SOCK_RAW, pr->icmpproto);

13  setuid(getuid()); /* права привилегированного пользователя

                         больше не нужны */

14  if (pr->finit)

15   (*pr->finit)();

16  size = 60 * 1024; /* setsockopt может завершиться с ошибкой */

17  setsockopt(sockfd, SOL_SOCKET, SO_RCVBUF, &size, sizeof(size));

18  sig_alrm(SIGALRM); /* отправка первого пакета */

19  iov.iov_base = recvbuf;

20  iov.iov_len = sizeof(recvbuf);

21  msg.msg_name = pr->sarecv;

22  msg.msg_iov = &iov;

23  msg.msg_iovlen = 1;

24  msg.msg_control = controlbuf;

25  for (;;) {

26   msg.msg_namelen = pr->salen;

27   msg.msg_controllen = sizeof(controlbuf);

28   n = recvmsg(sockfd, &msg, 0);

29   if (n < 0) {

30    if (errno == EINTR)

31     continue;

32    else

33     err_sys("recvmsg error");

24   }

35   Gettimeofday(&tval, NULL);

36   (*pr->fproc)(recvbuf, n, &msg, &tval);

37  }

38 }

Создание сокета

12-13
 Создается символьный сокет, соответствующий выбранному протоколу. В вызове функции
setuid
нашему эффективному идентификатору пользователя присваивается фактический идентификатор пользователя. Для создания символьных сокетов программа должна иметь права привилегированного пользователя, но когда символьный сокет уже создан, от этих прав можно отказаться. Всегда разумнее отказаться от лишних прав, если в них нет необходимости, например на тот случай, если в программе есть скрытая ошибка, которой кто-либо может воспользоваться.

Выполнение инициализации для протокола

14-15
 Мы выполняем функцию инициализации для выбранного протокола. Для IPv6 такая функция представлена в листинге 28.7.

Установка размера приемного буфера сокета

16-17
 Пытаемся установить размер приемного буфера сокета, равный 61 440 байт (60×1024) — этот размер больше задаваемого по умолчанию. Это делается в расчете на случай, когда пользователь проверяет качество связи с помощью программы
ping
, обращаясь либо к широковещательному адресу IPv4, либо к групповому адресу. В обоих случаях может быть получено большое количество ответов. Увеличивая размер буфера, мы уменьшаем вероятность того, что приемный буфер переполнится.

Отправка первого пакета

18
 Запускаем обработчик сигнала, который, как мы увидим, посылает пакет и создает сигнал
SIGALRM
один раз в секунду. Обычно обработчик сигналов не запускается напрямую, как у нас, но это можно делать. Обработчик сигналов является обычной функцией языка С, просто в нормальных условиях он асинхронно запускается ядром.

Перейти на страницу:
Комментариев (0)
название