Вход/Регистрация
UNIX: разработка сетевых приложений
вернуться

Стивенс Уильям Ричард

Шрифт:

int execle(const char * pathname, const char * arg0... /* (char*)0,

char *const envp[] */ );

int execve(const char * pathname, char *const argv[], char *const envp[]);

int execlp(const char * filename, const char * arg0, .... /* (char*)0 */ );

int execvp(const char * filename, char *const argv[]);

Все шесть функций возвращают: -1 в случае ошибки, если же функция выполнена успешно, то ничего не возвращается

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

main
.

Отношения между этими шестью функциями показаны на рис. 4.4. Обычно только функция

execve
является системным вызовом внутри ядра, а остальные представляют собой библиотечные функции, вызывающие
execve
.

Рис. 4.4. Отношения между шестью функциями exec

Отметим различия между этими функциями:

1. Три верхних функции (см. рис. 4.4) принимают каждую строку как отдельный аргумент, причем перечень аргументов завершается пустым указателем (так как их количество может быть различным). У трех нижних функций имеется массив

argv
, содержащий указатели на строки. Этот массив должен содержать пустой указатель, определяющий конец массива, поскольку размер массива не задается.

2. Две функции в левой колонке получают аргумент

filename
. Он преобразуется в
pathname
с использованием текущей переменной окружения
PATH
. Если аргумент
filename
функций
execlp
или
execvp
содержит косую черту (
/
) в любом месте строки, переменная
PATH
не используется. Четыре функции в двух правых колонках получают полностью определенный аргумент
pathname
.

3. Четыре функции в двух левых колонках не получают явного списка переменных окружения. Вместо этого с помощью текущего значения внешней переменной

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

Дескрипторы, открытые в процессе перед вызовом функции

exec
, обычно остаются открытыми во время ее выполнения. Мы говорим «обычно», поскольку это свойство может быть отключено при использовании функции
fcntl
для установки флага дескриптора
FD_CLOEXEC
. Это нужно серверу
inetd
, о котором пойдет речь в разделе 13.5.

4.8. Параллельные серверы

Сервер, представленный в листинге 4.2, является последовательным (итеративным) сервером. Для такого простого сервера, как сервер времени и даты, это допустимо. Но когда обработка запроса клиента занимает больше времени, мы не можем связывать один сервер с одним клиентом, поскольку нам хотелось бы обрабатывать множество клиентов одновременно. Простейшим способом написать параллельный сервер под Unix является вызов функции

fork
, порождающей дочерний процесс для каждого клиента. В листинге 4.3 представлена общая схема типичного параллельного сервера.

Листинг 4.3. Типичный параллельный сервер

pid_t pid;

int listenfd, connfd;

listenfd = Socket( ... );

/* записываем в sockaddr_in{} параметры заранее известного порта сервера */

Bind(listenfd, ... );

Listen(listenfd, LISTENQ);

for (;;) {

connfd = Accept(listenfd, ...); /* вероятно, блокировка */

if ((pid = Fork == 0) {

Close(listenfd); /* дочерний процесс закрывает

прослушиваемый сокет */

doit(connfd); /* обработка запроса */

Close(connfd); /* с этим клиентом закончено */

exit(0); /* дочерний процесс завершен */

}

Close(connfd); /* родительский процесс закрывает

присоединенный сокет */

}

Когда соединение установлено, функция

accept
возвращает управление, сервер вызывает функцию
fork
и затем дочерний процесс занимается обслуживанием клиента (по присоединенному сокету
connfd
), а родительский процесс ждет другого соединения (на прослушиваемом сокете
listenfd
). Родительский процесс закрывает присоединенный сокет, поскольку новый клиент обрабатывается дочерним процессом.

  • Читать дальше
  • 1
  • ...
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • ...

Ебукер (ebooker) – онлайн-библиотека на русском языке. Книги доступны онлайн, без утомительной регистрации. Огромный выбор и удобный дизайн, позволяющий читать без проблем. Добавляйте сайт в закладки! Все произведения загружаются пользователями: если считаете, что ваши авторские права нарушены – используйте форму обратной связи.

Полезные ссылки

  • Моя полка

Контакты

  • chitat.ebooker@gmail.com

Подпишитесь на рассылку: