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

32   if (FD_ISSET(listenfd, rset))

33    if (readable_listen = 0)

34     continue;

35   if (FD_ISSET(fd4, rset))

36    if (readable_v4 = 0)

37     continue;

38 #ifdef IPV6

39   if (FD_ISSET(fd6, rset))

40    if (readable_v6 = 0)

41     continue;

42 #endif

43   for (i = 0; i = maxi; i++) { /* проверка всех клиентов */

44    if ( (sockfd = client[i].connfd) 0)

45     continue;

46    if (FD_ISSET(sockfd, rset))

47     if (readable_conn(i) = 0)

48      break; /* готовых дескрипторов больше нет */

49   }

50  }

51  exit(0);

52 }

Проверка прослушиваемого доменного сокета Unix

32-34 Прослушиваемый доменный сокет Unix проверяется в первую очередь, и если он готов, запускается функция readable_listen. Переменная nready— количество дескрипторов, которое функция select возвращает как готовые к чтению — является глобальной. Каждая из наших функций readablе_XXXуменьшает ее значение на 1, и новое значение этой переменной является возвращаемым значением функции. Когда ее значение достигает нуля, это говорит о том, что все готовые к чтению дескрипторы обработаны, и поэтому функция selectвызывается снова.

Проверка символьных сокетов ICMP

35-42 Проверяется символьный сокет ICMPv4, а затем символьный сокет ICMPv6.

Проверка присоединенных доменных сокетов Unix

43-49 Затем проверяется, готов ли для чтения какой-нибудь из присоединенных доменных сокетов Unix. Готовность для чтения какого-либо из таких сокетов обозначает, что клиент отослал дескриптор или завершился.

В листинге 28.26 приведена функция readable_listen, вызываемая, когда прослушиваемый сокет готов для чтения. Это указывает на новое клиентское соединение.

Листинг 28.26. Обработка нового соединения клиента

//icmpd/readablе_listen.c

 1 #include "icmpd.h"

 2 int

 3 readable_listen(void)

 4 {

 5  int i, connfd;

 6  socklen_t clilen;

 7  clilen = sizeof(cliaddr);

 8  connfd = Accept(listenfd, (SA*)cliaddr, clilen);

 9  /* поиск первой свободной структуры в массиве client[] */

10  for (i = 0; i FD_SETSIZE; i++)

11   if (client[i].connfd 0) {

12    client[i].connfd = connfd; /* сохранение дескриптора */

13    break;

14   }

15  if (i == FD_SETSIZE) {

16   close(connfd); /* невозможно обработать новый клиент */

17   return(--nready); /* грубое закрытие нового соединения */

18  }

19  printf("new connection, i = %d, connfd = %d\n", i, connfd);

20  FD_SET(connfd, allset); /* добавление нового дескриптора в набор */

21  if (connfd maxfd)

22   maxfd = connfd; /* для select */

23  if (i maxi)

24   maxi = i; /* максимальный индекс в массиве client[] */

25  return(--nready);

26 }

7-25 Принимается соединение и используется первый свободный элемент массива client. Код данной функции скопирован из начала кода, приведенного в листинге 6.4. Если свободных элементов в массиве нет, мы закрываем новое соединение и занимаемся обслуживанием уже имеющихся клиентов.

Когда присоединенный сокет готов для чтения, вызывается функция readablе_conn(листинг 28.27), а ее аргументом является индекс данного клиента в массиве client.

Листинг 28.27. Считывание данных и, возможно, дескриптора от клиента

//icmpd/readable_conn.c

 1 #include "icmpd.h"

 2 int

 3 readable_conn(int I)

 4 {

 5  int unixfd, recvfd;

 6  char c;

 7  ssize_t n;

 8  socklen_t len;

 9  struct sockaddr_storage ss;

10  unixfd = client[i].connfd;

11  recvfd = -1;

12  if ((n = Read_fd(unixfd, c, 1, recvfd)) == 0) {

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

Похожие книги

Основы программирования в Linux
Основы программирования в Linux

В четвертом издании популярного руководства даны основы программирования в операционной системе Linux. Рассмотрены: использование библиотек C/C++ и стан­дартных средств разработки, организация системных вызовов, файловый ввод/вывод, взаимодействие процессов, программирование средствами командной оболочки, создание графических пользовательских интерфейсов с помощью инструментальных средств GTK+ или Qt, применение сокетов и др. Описана компиляция программ, их компоновка c библиотеками и работа с терминальным вводом/выводом. Даны приемы написания приложений в средах GNOME® и KDE®, хранения данных с использованием СУБД MySQL® и отладки программ. Книга хорошо структурирована, что делает обучение легким и быстрым. Для начинающих Linux-программистов

Нейл Мэтью , Ричард Стоунс , Татьяна Коротяева

ОС и Сети / Программирование / Книги по IT
1001 совет по обустройству компьютера
1001 совет по обустройству компьютера

В книге собраны и обобщены советы по решению различных проблем, которые рано или поздно возникают при эксплуатации как экономичных нетбуков, так и современных настольных моделей. Все приведенные рецепты опробованы на практике и разбиты по темам: аппаратные средства персональных компьютеров, компьютерные сети и подключение к Интернету, установка, настройка и ремонт ОС Windows, работа в Интернете, защита от вирусов. Рассмотрены не только готовые решения внезапно возникающих проблем, но и ответы на многие вопросы, которые возникают еще до покупки компьютера. Приведен необходимый минимум технических сведений, позволяющий принять осознанное решение.Компакт-диск прилагается только к печатному изданию книги.

Юрий Всеволодович Ревич

Программирование, программы, базы данных / Интернет / Компьютерное «железо» / ОС и Сети / Программное обеспечение / Книги по IT