Автоматическое управление потоками сервера: несколько процедур

Автоматическое управление потоками сервера: несколько процедур

В предыдущем примере процесс-сервер содержал лишь одну процедуру сервера. Вопрос, которым мы займемся теперь, звучит так: могут ли несколько процедур одного процесса использовать один и тот же пул потоков сервера? Чтобы узнать ответ, добавим к нашему серверу еще одну процедуру, а заодно перепишем наши программы заново, чтобы продемонстрировать более приличный стиль передачи аргументов и результатов между процессами.

Первый файл в этом примере называется squareproc.h. В нем определен один тип данных для входных аргументов функции, возводящей в квадрат, и еще один — для возвращаемых ею результатов. В этом заголовочном файле также определяется полное имя двери для данной процедуры. Его текст его приведен в листинге 15.8.

Листинг 15.8. Заголовочный файл squareproc.h

//doors/squareproc.h

1 #define PATH_SQUARE_DOOR "/tmp/squareproc_door"

2 typedef struct { /* аргументы squareproc() */

3  long arg1;

4 } squareproc_in_t;

5 typedef struct { /* возврат squareproc() */

6  long res1;

7 } squareproc_out_t;

Наша новая процедура будет принимать длинное целое и возвращать квадратный корень из него (типа double). Мы определяем полное имя двери этой процедуры, структуры аргументов и результатов в заголовочном файле sqrtproc.h в листинге 15.9.

Листинг 15.9. Заголовочный файл sqrtproc.h

//doors/sqrtproc.h

1 #define PATH_SQRT_DOOR "/tmp/sqrtproc_door"

2 typedef struct { /* входные данные sqrtproc() */

3  long arg1;

4 } sqrtproc_in_t;

5 typedef struct { /* возвращаемые sqrtproc() данные */

6  double res1;

7 } sqrtproc_out_t;

Программа-клиент приведена в листинге 15.10. Она последовательно вызывает две процедуры сервера и выводит возвращаемые ими результаты. Эта программа устроена аналогично другим клиентским программам, приведенным в этой главе.

Листинг 15.10. Клиент, вызывающий две процедуры

//doors/client7.c

1  #include "unpipc.h"

2  #include "squareproc.h"

3  #include "sqrtproc.h"

4  int

5  main(int argc, char **argv)

6  {

7   int fdsquare, fdsqrt;

8   door_arg_t arg;

9   squareproc_in_t square_in;

10  squareproc_out_t square_out;

11  sqrtproc_in_t sqrt_in;

12  sqrtproc_out_t sqrt_out;

13  if (argc != 2)

14   err_quit("usage: client7 <integer-value>");

15  fdsquare = Open(PATH_SQUARE_DOOR, O_ROWR);

16  fdsqrt = Open(PATH_SQRT_DOOR, O_RDWR);

17  /* подготовка аргументов и вызов squareproc() */

18  square_in.arg1 = atol(argv[1]);

19  arg.data_ptr = (char*)&square_in;

20  arg.data_size = sizeof(square_in);

21  arg.desc_ptr = NULL;

22  arg.desc_num = 0;

23  arg.rbuf = (char*)&square_out;

24  arg.rsize = sizeof(square_out);

25  Door_call(fdsquare, &arg);

26  /* подготовка аргументов и вызов sqrtproc() */

27  sqrt_in.arg1 = atol(argv[1]);

28  arg.data_ptr = (char*)&sqrt_in;

29  arg.data_size = sizeof(sqrt_in);

30  arg.desc_ptr = NULL;

31  arg.desc_num = 0;

32  arg.rbuf = (char*)&sqrt_out;

33  arg.rsize = sizeof(sqrt_out);

34  Door_call(fdsqrt, &arg);

35  printf("result: %ld %g ", square_out.res1, sqrt_out.res1);

36  exit(0);

37 }

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

Листинг 15.11. Две процедуры сервера

//doors/server7.c

1  #include "unpipc.h"

2  #include <math.h>

3  #include "squareproc.h"

4  #include "sqrtproc.h"

5  void

6  squareproc(void *cookie, char *dataptr, size_t datasize,

7   door_desc_t *descptr, size_t ndesc)

8  {

9   squareproc_in_t in;

10  squareproc_out_t out;

11  memcpy(&in, dataptr, min(sizeof(in), datasize));

12  printf("squareproc: thread id %ld, arg = %ld ",

13   pr_thread_id(NULL), in.arg1);

14  sleep(5);

15  out.res1 = in.arg1 * in.arg1;

16  Door_return((char *) &out, sizeof(out), NULL, 0);

17 }

18 void

19 sqrtproc(void *cookie, char *dataptr, size_t datasize,

20  door_desc_t *descptr, size_t ndesc)

21 {

22  sqrtproc_in_t in;

23  sqrtproc_out_t out;

24  memcpy(&in, dataptr, min(sizeof(in), datasize));

25  printf("sqrtproc: thread id %ld, arg = %ld ",

26   pr_thread_id(NULL), in.arg1);

27  sleep(5);

28  out.res1 = sqrt((double)in.arg1);

29  Door_return((char *) &out, sizeof(out), NULL, 0);

30 }

Функция main сервера, текст которой приведен в листинге 15.12, открывает дескрипторы дверей и связывает каждый из них с одной из процедур сервера.

Листинг 15.12. Функция main сервера

//doors/server7.c

31 int

32 main(int argc, char **argv)

33 {

34  int fd;

35  if (argc != 1)

36   err_quit("usage: server7");

37  fd = Door_create(squareproc, NULL, 0);

38  unlink(PATH_SQUARE_DOOR);

39  Close(Open(PATH_SQUARE_DOOR, O_CREAT | O_RDWR, FILE_MODE));

40  Fattach(fd, PATH_SQUARE_DOOR);

41  fd = Door_create(sqrtproc, NULL, 0);

42  unlink(PATH_SQRT_DOOR);

43  Close(Open(PATH_SQRT_DOOR, O_CREAT | O_RDWR, FILE_MODE));

44  Fattach(fd, PATH_SQRT_DOOR);

45  for (;;)

46   pause();

47 }

Запустим программу-клиент и подождем 10 секунд до вывода результатов (как мы и ожидали):

solaris % client7 77

result: 5929 8.77496

Посмотрев на выводимый сервером текст, мы увидим, что один и тот же поток этого процесса использовался для обработки обоих запросов клиента:

solaris % server7

squareproc: thread id 4, arg = 77

sqrtproc: thread id 4, arg = 77

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

Поделитесь на страничке

Следующая глава >

Похожие главы из других книг

Автоматическое обновление

Из книги Windows Vista без напряга автора Жвалевский Андрей Валентинович

Автоматическое обновление Купив последнюю версию Windows, вы покупаете не совсем последнюю версию. Пройдет совсем немного времени, и программисты компании Microsoft (или просто доброхоты-любители) обнаружат, что в системе есть уязвимость, через которую можно проникнуть на


Автоматическое управление памятью

Из книги Основы объектно-ориентированного программирования автора Мейер Бертран

Автоматическое управление памятью Ни один из рассмотренных подходов не является полностью удовлетворительным. Общее решение проблемы управления памятью предполагает серьезную работу на уровне реализации


10.10. Несколько производителей, несколько потребителей

Из книги UNIX: взаимодействие процессов автора Стивенс Уильям Ричард

10.10. Несколько производителей, несколько потребителей Следующее изменение, которое мы внесем в нашу пpoгрaммy, будет заключаться в добавлении возможности одновременной работы нескольких потребителей вместе с несколькими производителями. Есть ли смысл в наличии


Автоматическое управление потоками сервера

Из книги Системное программирование в среде Windows автора Харт Джонсон М

Автоматическое управление потоками сервера Чтобы посмотреть, как осуществляется управление потоками сервера, добавим в процедуру сервера команду выдачи ее идентификатора потока. Добавим в нее также пятисекундную паузу, чтобы имитировать длительное выполнение. За это


Б.2. Основные функции для работы с потоками: создание и завершение

Из книги Scrum и XP: заметки с передовой автора Книберг Хенрик

Б.2. Основные функции для работы с потоками: создание и завершение В этом разделе мы опишем пять основных функций для работы с потоками.Функция pthread_createПри запуске пpoгрaммы вызовом exec создается единственный поток, называемый начальным потоком, или главным (initial thread).


Управление потоками

Из книги XSLT автора Хольцнер Стивен

Управление потоками Вероятно, вы не будете удивлены, узнав о том, что у потоков, как и у любого другого объекта Windows, имеются дескрипторы и что для создания потоков, выполняющихся в адресном пространстве вызывающего процесса, предусмотрен системный вызов CreateThread. Как и в


Дополнительные функции управления потоками

Из книги Интернет на 100%. Подробный самоучитель: от «чайника» – до профессионала автора Гладкий Алексей Анатольевич

Дополнительные функции управления потоками Несмотря на то что функций управления потоками, которые мы выше обсуждали, вполне достаточно для большинства случаев, в том числе и для примеров, приведенных в этой книге, в Windows XP и Windows Server 2003 были введены две дополнительные


Дросселирование семафора для уменьшения состязательности между потоками

Из книги VBA для чайников автора Каммингс Стив

Дросселирование семафора для уменьшения состязательности между потоками Слишком большое количество потоков, соревнующихся между собой за право владения единственным ресурсом, например, мьютексом или объектом CS, могут стать причиной снижения производительности как в


Подход третий: Несколько product owner’ов - несколько backlog’ов

Из книги Недокументированные и малоизвестные возможности Windows XP автора Клименко Роман Александрович

Подход третий: Несколько product owner’ов - несколько backlog’ов Похоже на второй вариант, по отдельному product backlog на команду, только ещё и с отдельным product owner’ом на каждую команду. Мы не пробовали так делать, и, скорее всего, пробовать не будем.Если два product backlog’а касаются одного и


Автоматическое выравнивание

Из книги Программирование для Linux. Профессиональный подход автора Митчелл Марк

Автоматическое выравнивание Элемент <xsl:output> поддерживает атрибут indent который устанавливается в «yes» или «no», и указывает процессору XSLT, нужно ли выравнивать результирующий документ. Как правило, выравнивание результирующего документа не имеет большого значения,


Автоматическое обновление

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

Автоматическое обновление Любой программный продукт постоянно дорабатывается и совершенствуется (если, конечно, он не снят с обслуживания и поддержки ввиду появления новых версий или по иным причинам). Это касается и операционной системы Windows 7: разработчики постоянно


Отличия процедур типа Function от процедур типа Sub

Из книги автора

Отличия процедур типа Function от процедур типа Sub Между процедурами типа Function и типа Sub есть одно существенное отличие: в процедуре типа Function обязательно где-то должен присутствовать по крайней мере один оператор, задающий значение этой функции. При этом используется имя


Автоматическое обновление

Из книги автора

Автоматическое обновление Служба предназначена для автоматического скачивания из Интернета и установки обновлений операционной системы и стандартных компонентов Windows XP. При этом сведения об уже установленных обновлениях берутся из реестра. Для этого предназначены


4.1.3. Значения, возвращаемые потоками

Из книги автора

4.1.3. Значения, возвращаемые потоками Если второй аргумент функции pthread_join() не равен NULL, то в него помещается значение, возвращаемое потоком. Как и потоковый аргумент, это значение имеет тип void*. Если поток возвращает обычное число типа int, его можно свободно привести к типу


26.2. Основные функции для работы с потоками: создание и завершение потоков

Из книги автора

26.2. Основные функции для работы с потоками: создание и завершение потоков В этом разделе мы рассматриваем пять основных функций для работы с потоками, а в следующих двух разделах мы используем эти функции для написания потоковой модификации клиента и сервера