UNIX: разработка сетевых приложений
UNIX: разработка сетевых приложений читать книгу онлайн
Новое издание книги, посвященной созданию веб-серверов, клиент-серверных приложений или любого другого сетевого программного обеспечения в операционной системе UNIX, — классическое руководство по сетевым программным интерфейсам, в частности сокетам. Оно основано на трудах Уильяма Стивенса и полностью переработано и обновлено двумя ведущими экспертами по сетевому программированию. В книгу включено описание ключевых современных стандартов, реализаций и методов, она содержит большое количество иллюстрирующих примеров и может использоваться как учебник по программированию в сетях, так и в качестве справочника для опытных программистов.
Внимание! Книга может содержать контент только для совершеннолетних. Для несовершеннолетних чтение данного контента СТРОГО ЗАПРЕЩЕНО! Если в книге присутствует наличие пропаганды ЛГБТ и другого, запрещенного контента - просьба написать на почту [email protected] для удаления материала
26.2. Основные функции для работы с потоками: создание и завершение потоков
В этом разделе мы рассматриваем пять основных функций для работы с потоками, а в следующих двух разделах мы используем эти функции для написания потоковой модификации клиента и сервера TCP.
Функция pthread_create
Когда программа запускается с помощью функции
exec
pthread_create
#include <pthread.h>
int pthread_create(pthread_t* <i>tid</i>, const pthread_attr_t *<i>attr</i>,
void *(*<i>func</i>)(void*), void *<i>arg</i>);
<i>Возвращает: 0 в случае успешного выполнения, положительное значение Exxx в случае ошибки</i>
Каждый поток процесса обладает собственным идентификатором потока (thread ID), относящимся к типу данных
pthread_t
unsigned int
tid
У каждого потока имеется несколько атрибутов: его приоритет, исходный размер стека, указание на то, должен ли этот поток являться демоном или нет, и т.д. При создании потока мы можем задать эти атрибуты, инициализируя переменную типа
pthread_attr_t
attr
Наконец, при создании потока мы должны указать, какую функцию будет выполнять этот поток. Выполнение потока начинается с вызова заданной функции, а завершается либо явно (вызовом
pthread_exit
func
arg
Обратите внимание на объявления
func
arg
void*
Возвращаемое значение функций Pthreads — это обычно 0 в случае успешного выполнения или ненулевая величина в случае ошибки. Но в отличие от функций сокетов и большинства системных вызовов, для которых в случае ошибки возвращается -1 и переменной
errno
pthread_create
EAGAIN
errno
Exxx
<sys/errno.h>
Функция pthread_join
Мы можем приостановить выполнение текущего потока и ждать завершения выполнения какого-либо другого потока, используя функцию
pthread_join
pthread_create
fork
pthread_join
waitpid
#include <pthread.h>
int pthread_join(pthread_t <i>tid</i>, void **<i>status</i>);
<i>Возвращает: 0 в случае успешного выполнения, положительное значение Exxx в случае ошибки</i>
Следует указать идентификатор
tid
waitpid
Если указатель
status
status
Функция pthread_self
Каждый поток снабжен идентификатором, уникальным в пределах данного процесса. Идентификатор потока возвращается функцией
pthread_create
pthread_join
pthread_self
#include <pthread.h>
pthread_t pthread_self(void);
<i>Возвращает: идентификатор вызывающего потока</i>
Сравнивая потоки и процессы Unix, можно отметить, что функция
pthread_self
getpid
Функция pthread_detach
Поток может быть либо присоединяемым (joinable), каким он является по умолчанию, либо отсоединенным (detached). Когда присоединяемый поток завершает свое выполнение, его статус завершения и идентификатор сохраняются, пока другой поток данного процесса не вызовет функцию
pthread_join
Функция
pthread_detach
#include <pthread.h>
int pthread_detach(pthread_t <i>tid</i>);