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

Тут можно читать онлайн Уильям Стивенс - UNIX: разработка сетевых приложений - бесплатно ознакомительный отрывок. Жанр: comp-osnet, издательство Питер, год 2007. Здесь Вы можете читать ознакомительный отрывок из книги онлайн без регистрации и SMS на сайте лучшей интернет библиотеки ЛибКинг или прочесть краткое содержание (суть), предисловие и аннотацию. Так же сможете купить и скачать торрент в электронном формате fb2, найти и слушать аудиокнигу на русском языке или узнать сколько частей в серии и всего страниц в публикации. Читателям доступно смотреть обложку, картинки, описание и отзывы (комментарии) о произведении.
  • Название:
    UNIX: разработка сетевых приложений
  • Автор:
  • Жанр:
  • Издательство:
    Питер
  • Год:
    2007
  • Город:
    Санкт-Петербург
  • ISBN:
    5-94723-991-4
  • Рейтинг:
    4.33/5. Голосов: 91
  • Избранное:
    Добавить в избранное
  • Отзывы:
  • Ваша оценка:
    • 80
    • 1
    • 2
    • 3
    • 4
    • 5

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

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

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

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

UNIX: разработка сетевых приложений - читать книгу онлайн бесплатно (ознакомительный отрывок), автор Уильям Стивенс
Тёмная тема
Сбросить

Интервал:

Закладка:

Сделать
Инициализация указателей буфера

16-19 Инициализируются указатели в двух буферах и вычисляется максимальный дескриптор. Это значение, увеличенное на единицу, будет использоваться в качестве первого аргумента функции select.

Основной цикл: подготовка к вызову функции select

20 Как и в случае первой версии этой функции, показанной в листинге 6.2, основной цикл функции содержит вызов функции select, за которой следуют отдельные проверки различных интересующих нас условий.

Подготовка интересующих нас дескрипторов

21-30 Оба набора дескрипторов обнуляются и затем в каждом наборе включается не более двух битов. Если мы еще не прочитали конец файла из стандартного потока ввода и есть место как минимум для 1 байта данных в буфере to, то в наборе флагов чтения включается бит, соответствующий стандартному потоку ввода. Если есть место как минимум для 1 байта данных в буфере fr, то в наборе флагов чтения включается бит, соответствующий сокету. Если есть данные для записи в сокет в буфере to, то в наборе флагов записи включается бит, соответствующий сокету. Наконец если в буфере frесть данные для отправки в стандартный поток вывода, то в наборе флагов записи включается бит, соответствующий этому стандартному потоку.

Вызов функции select

31 Вызывается функция select, ожидающая, когда одно из четырех условий станет истинным. Для этой функции мы не задаем тайм-аута.

Следующая часть нашей функции показана в листинге 16.2. Этот код содержит первые две проверки (из четырех возможных), выполняемые после завершения функции select.

Листинг 16.2. Функция str_cli: вторая часть, чтение из стандартного потока ввода или сокета

//nonblock/strclinonb.c

32 if (FD_ISSET(STDIN_FILENO, &rset)) {

33 if ((n = read(STDIN_FILENO, toiptr, &to[MAXLINE] - toiptr)) < 0) {

34 if (errno != EWOULDBLOCK)

35 err_sys("read error on stdin");

36 } else if (n == 0) {

37 fprintf(stderr, "%s: EOF on stdin\n", gf_time());

38 stdineof = 1; /* с stdin все сделано */

39 if (tooptr == toiptr)

40 Shutdown(sockfd, SHUT_WR); /* отсылаем FIN */

41 } else {

42 fprintf(stderr, "%s: read %d bytes from stdin\n", gf_time(),

43 n);

44 toiptr += n; /* только что полученное из функции read число */

45 FD_SET(sockfd, &wset); /* включаем бит в наборе чтения */

46 }

47 }

48 if (FD_ISSET(sockfd, &rset)) {

49 if ((n = read(sockfd, friptr, &fr[MAXLINE] - friptr)) < 0) {

50 if (errno != EWOULDBLOCK)

51 err_sys("read error on socket");

52 } else if (n == 0) {

53 fprintf(stderr, "%s: EOF on socket\n", gf_time());

54 if (stdineof)

55 return; /* нормальное завершение */

56 else

57 err_quit("str_cli: server terminated prematurely");

58 } else {

59 fprintf(stderr, "%s: read %d bytes from socket\n",

60 gf_time(), n);

61 friptr += n; /* только что полученное из функции read число */

62 FD_SЕТ(STDOUT_FILЕNO, &wset); /* включаем бит в наборе

чтения */

63 }

64 }

Чтение из стандартного потока ввода с помощью функции read

32-33 Если стандартный поток ввода готов для чтения, мы вызываем функцию read. Третий ее аргумент — это количество свободного места в буфере to.

Обработка ошибки

34-35 Если происходит ошибка EWOULDBLOCK, мы ничего не предпринимаем. Обычно эта ситуация — когда функция selectсообщает нам о том, что дескриптор готов для чтения, а функция read возвращает ошибку EWOULDBLOCK— не должна возникать, но тем не менее мы ее обрабатываем.

Возвращение конца файла функцией read

36-40 Если функция readвозвращает нуль, мы закончили со стандартным потоком ввода. Флаг stdineofустановлен. Если в буфере to больше нет данных для отправки ( tooptrравно toiptr), функция shutdownотправляет серверу сегмент FIN. Если в буфере toеще есть данные для отправки, сегмент FIN не может быть отправлен до тех пор, пока содержимое буфера не будет записано в сокет.

ПРИМЕЧАНИЕ

Мы выводим в стандартный поток сообщений об ошибках строку, отмечающую конец файла, вместе с текущим временем. Мы покажем, как мы используем этот вывод, после описания функции. Аналогичные вызовы функции fprintf выполняются неоднократно в процессе выполнения нашей функции.

Возвращение данных функцией read

41-45 Когда функция read возвращает данные, мы увеличиваем на единицу toiptr. Мы также включаем бит, соответствующий сокету, в наборе флагов записи, чтобы позже при проверке этого бита в цикле он был включен и тем самым инициировалась бы попытка записи в сокет с помощью функции write.

ПРИМЕЧАНИЕ

Это одно из непростых конструктивных решений, которые приходится принимать при написании кода. У нас есть несколько альтернатив. Вместо установки бита в наборе записи мы можем ничего не делать, и в этом случае функция select будет проверять возможность записи в сокет, когда она будет вызвана в следующий раз. Но это требует дополнительного прохода цикла и вызова функции select, когда мы уже знаем, что у нас есть данные для записи в сокет. Другой вариант — дублировать код, который записывает в сокет, но это кажется расточительным, к тому же это возможный источник ошибки (в случае, если в этой части дублируемого кода есть ошибка и мы обнаруживаем и устраняем ее только в одном месте). Наконец, мы можем создать функцию, записывающую в сокет, и вызывать эту функцию вместо дублирования кода, но эта функция должна использовать три локальные переменные совместно с функцией str_cli, что может привести к необходимости сделать эти переменные глобальными. Выбор, сделанный в нашем случае, — это результат субъективного мнения автора относительно того, какой из описанных трех вариантов предпочтительнее.

Чтение из сокета с помощью функции read

48-64Эти строки кода аналогичны выражению if, только что описанному для случая, когда стандартный поток ввода готов для чтения. Если функция readвозвращает ошибку EWOULDBLOCK, ничего не происходит. Если мы встречаем признак конца файла, присланный сервером, это нормально, когда мы уже получили признак конца файла в стандартном потоке ввода. Но иначе это будет ошибкой, означающей преждевременное завершение работы сервера ( Server terminated prematurely). Если функция readвозвращает некоторые данные, friptrувеличивается на единицу и в наборе флагов записи включается бит для стандартного потока вывода, с тем чтобы попытаться записать туда данные в следующей части функции.

В листинге 16.3 показана последняя часть нашей функции.

Листинг 16.3. Функция str_cli: третья часть, запись в стандартный поток вывода или сокет

//nonblock/strclinonb.c

65 if (FD_ISSET(STDOUT_FILENO, &wset) && ((n = friptr - froptr) > 0)) {

Читать дальше
Тёмная тема
Сбросить

Интервал:

Закладка:

Сделать


Уильям Стивенс читать все книги автора по порядку

Уильям Стивенс - все книги автора в одном месте читать по порядку полные версии на сайте онлайн библиотеки LibKing.




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


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


Понравилась книга? Поделитесь впечатлениями - оставьте Ваш отзыв или расскажите друзьям

Напишите свой комментарий
x