Главная страница  Взаимодействие нетривиальных процессов 

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 [ 160 ] 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186

35 KilKchildpid. SIGTERM);

36 exitCO):

37 }

Функция doit

2-9 Эта функция запускается родительским процессом. Мы измеряем время ее работы. Она помещает 1 байт в канал, из которого читает дочерний процесс, и считывает 1 байт из другого канала, в который сообщение помещается дочерним процессом. При этом измеряется именно то, что мы назвали задержкой, - время передачи небольшого сообщения туда и обратно.

Создание каналов

19-20 Создаются два канала, после чего вызов fork порождает дочерний процесс. При этом образуется схема, изображенная на рис. 4.6 (но без закрытия неиспользуемых дескрипторов каналов). Для этого теста требуются два канала, поскольку каналы являются односторонними, а мы хотим передавать сообщение в обе стороны.

Дочерний процесс отсылает обратно сообщение

22-27 Дочерний процесс представляет собой бесконечный цикл, в котором однобайтовое сообщение считывается и отсылается обратно.

Измерение времени работы родительского процесса

29-34 Родительский процесс вызывает функцию doit для отправки однобайтового сообщения дочернему процессу и получения ответа. После этого мы имеем гарантию, что оба процесса выполняются. Затем функция doit вызывается в цикле с измерением времени задержки.

На компьютере Sparc под управлением Solaris 2.6 при запуске программы пять раз подряд мы получим вот что:

Solaris % lat pipe 10000 latency: 278.633 usee Solaris % lat pipe 10000 latency: 397.810 usee Solaris % lat pipe 10000 latency: 392.567 usee Solaris % lat pipe 10000 latency: 266.572 usee Solaris % lat pipe 10000 latency: 284.559 usee

Среднее для пяти попыток составляет 324 микросекунды, и именно это значение приведено в табл. А.1. Это время учитывает два переключения контекста (от родительского процесса к дочернему и обратно), четыре системных вызова (wri te, read, write, read) и затраты на передачу 1 байта данных по каналу.

Программа измерения задержки очередей сообщений Posix

Программа измерения задержки для очередей сообщений Posix приведена в листинге А. 15.



Листинг А.15. Программа измерения задержки для очереди сообщений Posix

bench/lat pxmsg.c

1 #include unpipc.h

2 #define NAMEl lat pxmsgr

3 #define NAME2 lat pxmsg2

4 #define MAXMSG 4 /* место для 4096 байт в очереди */

5 #define MSGSIZE 1024

6 void

7 doit(mqd t mqsend. mqd t mqrecv)

9 char buff[MSGSIZE]:

10 Mq send(mqsend, buff, 1, 0):

11 if (Mq receive(mqrecv, buff, MSGSIZE, NULL) != 1)

12 err quit( mq receive error ):

13 }

14 int

15 mainCint argc, char **argv)

16 {

17 int i, nloop:

18 mqd t mql, mq2:

19 char buff[MSGSIZE]:

20 pid t childpid:

21 struct mq attr attr:

22 if (argc != 2)

23 err quit( usage: lat pxmsg <#loops> ):

24 nloop = atoi(argv[l]):

25 attr.mq maxmsg = MAXMSG:

26 attr.mq msgs i ze = MSGSIZ E:

27 mql = Mq open(Px ipc name(NAMEl), 0 RDWR 0 CREAT, FILE MODE, Sattr):

28 mq2 = Mq open(Px ipc name(NAME2), 0 RDWR 0 CREAT, FILE MODE, Sattr):

29 if ( (childpid =- ForkO) == 0) {

30 for ( : : ) { /* дочерний процесс */

31 if (Mq receive(mql, buff, MSGSIZE, NULL) != 1)

32 err quit( mq receive error ):

33 Mq send(mq2, buff, 1, 0):

34 }

35 exit(O):

36 }

37 /* родительский процесс */

38 doitCmql, mq2):

39 Start time():

40 for (i = 0; i < nloop: i++)

41 doitCmql, mq2);

42 printf( latency: %.3f usec\n , Stop time() / nloop):

43 KilKchildpid, SIGTERM):

44 Mq close(mql);

45 Mq close(mq2):

46 Mq unl ink (Px ipc name( NAMED):



47 Mq unlink(PxJpc name(NAME2)):

48 exit(O);

49 }

25-28 Создаются две очереди сообщений, каждая из которых используется для передачи данных в одну сторону. Хотя для очередей Posix можно указывать приоритет сообщений, функция mq receive всегда возвращает сообщение с наивысшим приоритетом, поэтому мы не можем использовать лишь одну очередь для данного приложения.

Измерение задержки очередей сообщений System V

в листинге А. 16 приведен текст программы измерения времени задержки для очередей сообщений System V.

Листинг А. 16. Программа измерения времени задержки для очередей сообщений System V

bench/lat svmsg.c

1 #include unpipc.h

2 struct msgbuf p2child = { 1. { 0 } }: /* type = 1 */

3 struct msgbuf child2p = { 2. { 0 } }; /* type = 2 */

4 struct msgbuf inbuf:

5 void

6 doitCint msgid) 1 {

8 MsgsndCmsgid, &p2child. 0. 0):

9 if (Msgrcv(msgid. Sinbuf. sizeof(inbuf.mtext). 2. 0) != 0)

10 err quit( msgrcv error ):

11 }

12 int

13 mainCint argc. char **argv)

14 {

15 int i, nloop. msgid:

16 pid t childpid:

17 if (argc != 2)

18 err quit( usage; lat svmsg <#loops> ):

19 nloop = atoi(argv[l]);

20 msgid = Msgget(IPC PRIVATE. IPC CREAT SVMSG MODE);

21 if ( (childpid = ForkO) == 0) {

22 for ( ; ; ) { /* дочерний процесс */

23 if (Msgrcv(msgid. Sinbuf. sizeof(inbuf.mtext). 1. 0) != 0)

24 err quit( msgrcv error );

25 Msgsnd(msgid, &child2p. 0. 0);

26 }

27 exit(O):

28 }

29 /* родительский процесс */

30 doit(msgid); продолжение



1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 [ 160 ] 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186

© 2000 - 2024 ULTRASONEX-AMFODENT.RU.
Копирование материалов разрешено исключительно при условии цититирования.