Π§ΠΈΡ‚Π°ΠΉΡ‚Π΅ ΠΊΠ½ΠΈΠ³ΠΈ ΠΎΠ½Π»Π°ΠΉΠ½ Π½Π° Bookidrom.ru! БСсплатныС ΠΊΠ½ΠΈΠ³ΠΈ Π² ΠΎΠ΄Π½ΠΎΠΌ ΠΊΠ»ΠΈΠΊΠ΅

Π§ΠΈΡ‚Π°Ρ‚ΡŒ ΠΎΠ½Π»Π°ΠΉΠ½ Β«UNIX: взаимодСйствиС процСссов». Π‘Ρ‚Ρ€Π°Π½ΠΈΡ†Π° 16

Автор Уильям БтивСнс

Π—Π΄Π΅ΡΡŒ pathname β€” ΠΎΠ±Ρ‹Ρ‡Π½ΠΎΠ΅ для Unix ΠΏΠΎΠ»Π½ΠΎΠ΅ имя Ρ„Π°ΠΉΠ»Π°, ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠ΅ ΠΈ Π±ΡƒΠ΄Π΅Ρ‚ ΠΈΠΌΠ΅Π½Π΅ΠΌ FIFO.

АргумСнт mode ΡƒΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ Π±ΠΈΡ‚ΠΎΠ²ΡƒΡŽ маску Ρ€Π°Π·Ρ€Π΅ΡˆΠ΅Π½ΠΈΠΉ доступа ΠΊ Ρ„Π°ΠΉΠ»Ρƒ, Π°Π½Π°Π»ΠΎΠ³ΠΈΡ‡Π½ΠΎ Π²Ρ‚ΠΎΡ€ΠΎΠΌΡƒ Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚Ρƒ ΠΊΠΎΠΌΠ°Π½Π΄Ρ‹ open. Π’ Ρ‚Π°Π±Π». 2.3 ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½Ρ‹ ΡˆΠ΅ΡΡ‚ΡŒ констант, ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½Π½Ρ‹Ρ… Π² Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΊΠ΅ <sys/stat.h>. Π­Ρ‚ΠΈ константы ΠΌΠΎΠ³ΡƒΡ‚ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒΡΡ для задания Ρ€Π°Π·Ρ€Π΅ΡˆΠ΅Π½ΠΈΠΉ доступа ΠΈ ΠΊ FIFO.

Ѐункция mkfifo дСйствуСт ΠΊΠ°ΠΊ open, вызванная с Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚ΠΎΠΌ O_CREAT | O_EXCL. Π­Ρ‚ΠΎ ΠΎΠ·Π½Π°Ρ‡Π°Π΅Ρ‚, Ρ‡Ρ‚ΠΎ создаСтся Π½ΠΎΠ²Ρ‹ΠΉ ΠΊΠ°Π½Π°Π» FIFO ΠΈΠ»ΠΈ возвращаСтся ошибка EEXIST, Π² случаС Ссли ΠΊΠ°Π½Π°Π» с Π·Π°Π΄Π°Π½Π½Ρ‹ΠΌ ΠΏΠΎΠ»Π½Ρ‹ΠΌ ΠΈΠΌΠ΅Π½Π΅ΠΌ ΡƒΠΆΠ΅ сущСствуСт. Если Π½Π΅ трСбуСтся ΡΠΎΠ·Π΄Π°Π²Π°Ρ‚ΡŒ Π½ΠΎΠ²Ρ‹ΠΉ ΠΊΠ°Π½Π°Π», Π²Ρ‹Π·Ρ‹Π²Π°ΠΉΡ‚Π΅ open вмСсто mkfifo. Для открытия ΡΡƒΡ‰Π΅ΡΡ‚Π²ΡƒΡŽΡ‰Π΅Π³ΠΎ ΠΊΠ°Π½Π°Π»Π° ΠΈΠ»ΠΈ создания Π½ΠΎΠ²ΠΎΠ³ΠΎ Π² Ρ‚ΠΎΠΌ случаС, Ссли Π΅Π³ΠΎ Π΅Ρ‰Π΅ Π½Π΅ сущСствуСт, Π²Ρ‹Π·ΠΎΠ²ΠΈΡ‚Π΅ mkfifo, ΠΏΡ€ΠΎΠ²Π΅Ρ€ΡŒΡ‚Π΅, Π½Π΅ Π²ΠΎΠ·Π²Ρ€Π°Ρ‰Π΅Π½Π° Π»ΠΈ ошибка EEXIST, ΠΈ Ссли Ρ‚Π°ΠΊΠΎΠ΅ случится, Π²Ρ‹Π·ΠΎΠ²ΠΈΡ‚Π΅ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΡŽ open.

Команда mkfifΠΎ Ρ‚Π°ΠΊΠΆΠ΅ создаСт ΠΊΠ°Π½Π°Π» FIFO. Π•ΡŽ ΠΌΠΎΠΆΠ½ΠΎ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒΡΡ Π² сцСнариях ΠΈΠ½Ρ‚Π΅Ρ€ΠΏΡ€Π΅Ρ‚Π°Ρ‚ΠΎΡ€Π° ΠΈΠ»ΠΈ ΠΈΠ· ΠΊΠΎΠΌΠ°Π½Π΄Π½ΠΎΠΉ строки.

ПослС создания ΠΊΠ°Π½Π°Π» FIFO Π΄ΠΎΠ»ΠΆΠ΅Π½ Π±Ρ‹Ρ‚ΡŒ ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚ Π½Π° Ρ‡Ρ‚Π΅Π½ΠΈΠ΅ ΠΈΠ»ΠΈ запись с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Π»ΠΈΠ±ΠΎ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ open, Π»ΠΈΠ±ΠΎ ΠΎΠ΄Π½ΠΎΠΉ ΠΈΠ· стандартных Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΉ открытия Ρ„Π°ΠΉΠ»ΠΎΠ² ΠΈΠ· Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΠΈ Π²Π²ΠΎΠ΄Π°-Π²Ρ‹Π²ΠΎΠ΄Π° (Π½Π°ΠΏΡ€ΠΈΠΌΠ΅Ρ€, fopen). FIFO ΠΌΠΎΠΆΠ΅Ρ‚ Π±Ρ‹Ρ‚ΡŒ ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚ Π»ΠΈΠ±ΠΎ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Π½Π° Ρ‡Ρ‚Π΅Π½ΠΈΠ΅, Π»ΠΈΠ±ΠΎ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Π½Π° запись. НСльзя ΠΎΡ‚ΠΊΡ€Ρ‹Π²Π°Ρ‚ΡŒ ΠΊΠ°Π½Π°Π» Π½Π° Ρ‡Ρ‚Π΅Π½ΠΈΠ΅ ΠΈ запись, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ ΠΈΠΌΠ΅Π½ΠΎΠ²Π°Π½Π½Ρ‹Π΅ ΠΊΠ°Π½Π°Π»Ρ‹ ΠΌΠΎΠ³ΡƒΡ‚ Π±Ρ‹Ρ‚ΡŒ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ односторонними. 

ΠŸΡ€ΠΈ записи Π² ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠ°Π½Π°Π» ΠΈΠ»ΠΈ ΠΊΠ°Π½Π°Π» FIFO Π²Ρ‹Π·ΠΎΠ²ΠΎΠΌ write Π΄Π°Π½Π½Ρ‹Π΅ всСгда Π΄ΠΎΠ±Π°Π²Π»ΡΡŽΡ‚ΡΡ ΠΊ ΡƒΠΆΠ΅ ΠΈΠΌΠ΅ΡŽΡ‰ΠΈΠΌΡΡ, Π° Π²Ρ‹Π·ΠΎΠ² read считываСт Π΄Π°Π½Π½Ρ‹Π΅, ΠΏΠΎΠΌΠ΅Ρ‰Π΅Π½Π½Ρ‹Π΅ Π² ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠ°Π½Π°Π» ΠΈΠ»ΠΈ FIFO ΠΏΠ΅Ρ€Π²Ρ‹ΠΌΠΈ. ΠŸΡ€ΠΈ Π²Ρ‹Π·ΠΎΠ²Π΅ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ lseek для ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½ΠΎΠ³ΠΎ ΠΊΠ°Π½Π°Π»Π° ΠΈΠ»ΠΈ FIFO Π±ΡƒΠ΄Π΅Ρ‚ Π²ΠΎΠ·Π²Ρ€Π°Ρ‰Π΅Π½Π° ошибка ESPIPE.

ΠŸΡ€ΠΈΠΌΠ΅Ρ€

ΠŸΠ΅Ρ€Π΅Π΄Π΅Π»Π°Π΅ΠΌ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡƒ, ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½Π½ΡƒΡŽ Π² листингС 4.1, Ρ‚Π°ΠΊΠΈΠΌ ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ Π΄Π²Π° ΠΊΠ°Π½Π°Π»Π° FIFO вмСсто Π΄Π²ΡƒΡ… ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹Ρ… ΠΊΠ°Π½Π°Π»ΠΎΠ². Π€ΡƒΠ½ΠΊΡ†ΠΈΠΈ client ΠΈ server останутся ΠΏΡ€Π΅ΠΆΠ½ΠΈΠΌΠΈ; отличия появятся Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Π² Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ main, Π½ΠΎΠ²Ρ‹ΠΉ тСкст ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΉ ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½ Π² листингС 4.6.

Листинг 4.6. Ѐункция main прилоТСния ΠΊΠ»ΠΈΠ΅Π½Ρ‚-сСрвСр, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡŽΡ‰Π΅Π³ΠΎ Π΄Π²Π΅ ΠΎΡ‡Π΅Ρ€Π΅Π΄ΠΈ

//pipe/mainfifo.c

1  #include "unpipc.h"

2  #define FIFO1 "/tmp/fifo.1"

3  #define FIFO2 "/tmp/fifo.2"

4  void client(int, int), server(int. int);

5  int

6  main(int argc, char **argv)

7  {

8   int readfd, writefd;

9   pid_t childpid;

10  /* созданиС Π΄Π²ΡƒΡ… FIFO, Ссли ΡΡƒΡ‰Π΅ΡΡ‚Π²ΡƒΡŽΡ‚ – OK */

11  if ((mkfifo(FIF01, FILE_MODE) < 0) && (errno != EEXIST))

12   err_sys("can't create %s", FIF01);

13  if ((mkfifo(FIF02, FILE_MODE) < 0) && (errno != EEXIST)) {

14   unlink(FIF01);

15   err_sys("can't create %s", FIF02);

16  }

17  if ((childpid = Fork()) == 0) { /* child */

18   readfd = Open(FIF01, O_RDONLY, 0);

19   writefd = Open(FIF02, O_WRONLY, 0);

20   server(readfd, writefd);

21   exit(0);

22  }

23  /* Ρ€ΠΎΠ΄ΠΈΡ‚Π΅Π»ΡŒΡΠΊΠΈΠΉ процСсс */

24  writefd = Open(FIF01, O_WRONLY, 0);

25  readfd = Open(FIF02, O_RDONLY, 0);

26  client(readfd, writefd);

27  waitpid(childpid, NULL, 0); /* ΠΎΠΆΠΈΠ΄Π°Π½ΠΈΠ΅ Π·Π°Π²Π΅Ρ€ΡˆΠ΅Π½ΠΈΡ Π΄ΠΎΡ‡Π΅Ρ€Π½Π΅Π³ΠΎ процСсса */

28  Close(readfd):

29  Close(writefd);

30  Unlink(FIF01);

31  Unlink(FIF02);

32  exit(0);

33 }

Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ Π΄Π²ΡƒΡ… FIFO

10-16 Π’ Ρ„Π°ΠΉΠ»ΠΎΠ²ΠΎΠΉ систСмС Π² ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³Π΅ /tmp создаСтся Π΄Π²Π° ΠΊΠ°Π½Π°Π»Π°. Если ΠΊΠ°ΠΊΠΎΠΉ-Π»ΠΈΠ±ΠΎ ΠΈΠ· Π½ΠΈΡ… ΡƒΠΆΠ΅ сущСствуСт β€” Π½ΠΈΡ‡Π΅Π³ΠΎ ΡΡ‚Ρ€Π°ΡˆΠ½ΠΎΠ³ΠΎ. ΠšΠΎΠ½ΡΡ‚Π°Π½Ρ‚Π° FILE_MODE ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½Π° Π² нашСм Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΊΠ΅ unpiрс.h (листинг Π’.1) ΠΊΠ°ΠΊ

#define FILEMODE(S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)

/* Ρ€Π°Π·Ρ€Π΅ΡˆΠ΅Π½ΠΈΡ ΠΏΠΎ ΡƒΠΌΠΎΠ»Ρ‡Π°Π½ΠΈΡŽ для вновь создаваСмых Ρ„Π°ΠΉΠ»ΠΎΠ² */

ΠŸΡ€ΠΈ этом Π²Π»Π°Π΄Π΅Π»ΡŒΡ†Ρƒ Ρ„Π°ΠΉΠ»Π° Ρ€Π°Π·Ρ€Π΅ΡˆΠ°Π΅Ρ‚ΡΡ Ρ‡Ρ‚Π΅Π½ΠΈΠ΅ ΠΈ запись Π² Π½Π΅Π³ΠΎ, Π° Π³Ρ€ΡƒΠΏΠΏΠ΅ ΠΈ ΠΏΡ€ΠΎΡ‡ΠΈΠΌ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»ΡΠΌ β€” Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Ρ‡Ρ‚Π΅Π½ΠΈΠ΅. Π­Ρ‚ΠΈ Π±ΠΈΡ‚Ρ‹ Ρ€Π°Π·Ρ€Π΅ΡˆΠ΅Π½ΠΈΠΉ Π½Π°ΠΊΠ»Π°Π΄Ρ‹Π²Π°ΡŽΡ‚ΡΡ Π½Π° маску Ρ€Π΅ΠΆΠΈΠΌΠ° доступа создаваСмых Ρ„Π°ΠΉΠ»ΠΎΠ² (file mode creation mask) процСсса.

17-27 Π”Π°Π»Π΅Π΅ происходит Π²Ρ‹Π·ΠΎΠ² fork, Π΄ΠΎΡ‡Π΅Ρ€Π½ΠΈΠΉ процСсс Π²Ρ‹Π·Ρ‹Π²Π°Π΅Ρ‚ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΡŽ server (листинг 4.3), Π° Ρ€ΠΎΠ΄ΠΈΡ‚Π΅Π»ΡŒΡΠΊΠΈΠΉ процСсс Π²Ρ‹Π·Ρ‹Π²Π°Π΅Ρ‚ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΡŽ client (листинг 4.2). ΠŸΠ΅Ρ€Π΅Π΄ Π²Ρ‹Π·ΠΎΠ²ΠΎΠΌ этих Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΉ Ρ€ΠΎΠ΄ΠΈΡ‚Π΅Π»ΡŒΡΠΊΠΈΠΉ процСсс ΠΎΡ‚ΠΊΡ€Ρ‹Π²Π°Π΅Ρ‚ ΠΏΠ΅Ρ€Π²Ρ‹ΠΉ ΠΊΠ°Π½Π°Π» Π½Π° запись, Π° Π²Ρ‚ΠΎΡ€ΠΎΠΉ Π½Π° Ρ‡Ρ‚Π΅Π½ΠΈΠ΅, Π² Ρ‚ΠΎ врСмя ΠΊΠ°ΠΊ Π΄ΠΎΡ‡Π΅Ρ€Π½ΠΈΠΉ процСсс ΠΎΡ‚ΠΊΡ€Ρ‹Π²Π°Π΅Ρ‚ ΠΏΠ΅Ρ€Π²Ρ‹ΠΉ ΠΊΠ°Π½Π°Π» Π½Π° Ρ‡Ρ‚Π΅Π½ΠΈΠ΅, Π° Π²Ρ‚ΠΎΡ€ΠΎΠΉ β€” Π½Π° запись. ΠšΠ°Ρ€Ρ‚ΠΈΠ½Π° Π°Π½Π°Π»ΠΎΠ³ΠΈΡ‡Π½Π° ΠΏΡ€ΠΈΠΌΠ΅Ρ€Ρƒ с ΠΊΠ°Π½Π°Π»Π°ΠΌΠΈ ΠΈ ΠΈΠ»Π»ΡŽΡΡ‚Ρ€ΠΈΡ€ΡƒΠ΅Ρ‚ΡΡ рис. 4.11. 

Рис. 4.11. ΠŸΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠ΅ ΠΊΠ»ΠΈΠ΅Π½Ρ‚-сСрвСр, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡŽΡ‰Π΅Π΅ Π΄Π²Π΅ ΠΎΡ‡Π΅Ρ€Π΅Π΄ΠΈ


ИзмСнСния ΠΏΠΎ ΡΡ€Π°Π²Π½Π΅Π½ΠΈΡŽ с ΠΏΡ€ΠΈΠΌΠ΅Ρ€ΠΎΠΌ, Π² ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΌ использовались ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹Π΅ ΠΊΠ°Π½Π°Π»Ρ‹, ΡΠ»Π΅Π΄ΡƒΡŽΡ‰ΠΈΠ΅:

β–  Для создания ΠΈ открытия ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½ΠΎΠ³ΠΎ ΠΊΠ°Π½Π°Π»Π° трСбуСтся Ρ‚ΠΎΠ»ΡŒΠΊΠΎ ΠΎΠ΄ΠΈΠ½ Π²Ρ‹Π·ΠΎΠ² β€” pipe. Для создания ΠΈ открытия FIFO трСбуСтся Π²Ρ‹Π·ΠΎΠ² mkfifo ΠΈ ΠΏΠΎΡΠ»Π΅Π΄ΡƒΡŽΡ‰ΠΈΠΉ Π²Ρ‹Π·ΠΎΠ² open.

β–  ΠŸΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠ°Π½Π°Π» автоматичСски исчСзаСт послС Ρ‚ΠΎΠ³ΠΎ, ΠΊΠ°ΠΊ Π±ΡƒΠ΄Π΅Ρ‚ Π·Π°ΠΊΡ€Ρ‹Ρ‚ послСдним ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡŽΡ‰ΠΈΠΌ Π΅Π³ΠΎ процСссом. Канал FIFO удаляСтся ΠΈΠ· Ρ„Π°ΠΉΠ»ΠΎΠ²ΠΎΠΉ систСмы Ρ‚ΠΎΠ»ΡŒΠΊΠΎ послС Π²Ρ‹Π·ΠΎΠ²Π° unlink. Польза ΠΎΡ‚ лишнСго Π²Ρ‹Π·ΠΎΠ²Π°, Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΠΎΠ³ΠΎ для создания FIFO, ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π°Ρ: ΠΊΠ°Π½Π°Π» FIFO ΠΏΠΎΠ»ΡƒΡ‡Π°Π΅Ρ‚ имя Π² Ρ„Π°ΠΉΠ»ΠΎΠ²ΠΎΠΉ систСмС, Ρ‡Ρ‚ΠΎ позволяСт ΠΎΠ΄Π½ΠΎΠΌΡƒ процСссу ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ Ρ‚Π°ΠΊΠΎΠΉ ΠΊΠ°Π½Π°Π», Π° Π΄Ρ€ΡƒΠ³ΠΎΠΌΡƒ ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚ΡŒ Π΅Π³ΠΎ, Π΄Π°ΠΆΠ΅ Ссли послСдний Π½Π΅ являСтся родствСнным ΠΏΠ΅Ρ€Π²ΠΎΠΌΡƒ. Π‘ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΌΠΈ ΠΊΠ°Π½Π°Π»Π°ΠΌΠΈ это нСосущСствимо.

Π’ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ°Ρ…, Π½Π΅ΠΊΠΎΡ€Ρ€Π΅ΠΊΡ‚Π½ΠΎ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡŽΡ‰ΠΈΡ… ΠΊΠ°Π½Π°Π»Ρ‹ FIFO, ΠΌΠΎΠ³ΡƒΡ‚ Π²ΠΎΠ·Π½ΠΈΠΊΠ°Ρ‚ΡŒ Π½Π΅ΠΎΡ‡Π΅Π²ΠΈΠ΄Π½Ρ‹Π΅ ΠΏΡ€ΠΎΠ±Π»Π΅ΠΌΡ‹. Рассмотрим, Π½Π°ΠΏΡ€ΠΈΠΌΠ΅Ρ€, листинг 4.6: Ссли ΠΏΠΎΠΌΠ΅Π½ΡΡ‚ΡŒ порядок Π΄Π²ΡƒΡ… Π²Ρ‹Π·ΠΎΠ²ΠΎΠ² Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ open Π² ΠΏΠΎΡ€ΠΎΠ΄ΠΈΠ²ΡˆΠ΅ΠΌ процСссС, ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ° пСрСстанСт Ρ€Π°Π±ΠΎΡ‚Π°Ρ‚ΡŒ. ΠŸΡ€ΠΈΡ‡ΠΈΠ½Π° Π² Ρ‚ΠΎΠΌ, Ρ‡Ρ‚ΠΎ Ρ‡Ρ‚Π΅Π½ΠΈΠ΅ ΠΈΠ· FIFO Π±Π»ΠΎΠΊΠΈΡ€ΡƒΠ΅Ρ‚ процСсс, Ссли ΠΊΠ°Π½Π°Π» Π΅Ρ‰Π΅ Π½Π΅ ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚ Π½Π° запись ΠΊΠ°ΠΊΠΈΠΌ-Π»ΠΈΠ±ΠΎ Π΄Ρ€ΡƒΠ³ΠΈΠΌ процСссом. Π”Π΅ΠΉΡΡ‚Π²ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎ, Ссли ΠΌΡ‹ мСняСм порядок Π²Ρ‹Π·ΠΎΠ²ΠΎΠ² open Π² ΠΏΠΎΡ€ΠΎΠ΄ΠΈΠ²ΡˆΠ΅ΠΌ процСссС, ΠΈ ΠΏΠΎΡ€ΠΎΠ΄ΠΈΠ²ΡˆΠΈΠΉ, ΠΈ ΠΏΠΎΡ€ΠΎΠΆΠ΄Π΅Π½Π½Ρ‹ΠΉ процСссы ΠΎΡ‚ΠΊΡ€Ρ‹Π²Π°ΡŽΡ‚ ΠΊΠ°Π½Π°Π» Π½Π° Ρ‡Ρ‚Π΅Π½ΠΈΠ΅, ΠΏΡ€ΠΈΡ‚ΠΎΠΌ Ρ‡Ρ‚ΠΎ Π½Π° запись ΠΎΠ½ Π΅Ρ‰Π΅ Π½Π΅ ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚, Ρ‚Π°ΠΊ Ρ‡Ρ‚ΠΎ ΠΎΠ±Π° процСсса Π±Π»ΠΎΠΊΠΈΡ€ΡƒΡŽΡ‚ΡΡ. Вакая ситуация называСтся Π±Π»ΠΎΠΊΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ΠΌ, ΠΈΠ»ΠΈ зависаниСм (deadlock). Она Π±ΡƒΠ΄Π΅Ρ‚ рассмотрСна ΠΏΠΎΠ΄Ρ€ΠΎΠ±Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ Ρ€Π°Π·Π΄Π΅Π»Π΅.

ΠŸΡ€ΠΈΠΌΠ΅Ρ€: нСродствСнныС ΠΊΠ»ΠΈΠ΅Π½Ρ‚ ΠΈ сСрвСр

Π’ листингС 4.6 ΠΊΠ»ΠΈΠ΅Π½Ρ‚ ΠΈ сСрвСр всС Π΅Ρ‰Π΅ являлись родствСнными процСссами. ΠŸΠ΅Ρ€Π΅Π΄Π΅Π»Π°Π΅ΠΌ этот ΠΏΡ€ΠΈΠΌΠ΅Ρ€ Ρ‚Π°ΠΊ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ родство ΠΌΠ΅ΠΆΠ΄Ρƒ Π½ΠΈΠΌΠΈ отсутствовало. Π’ листингС 4.7 ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½ тСкст ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹-сСрвСра. ВСкст практичСски ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ‡Π΅Π½ Ρ‚ΠΎΠΉ части ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹ ΠΈΠ· листинга 4.6, которая ΠΎΡ‚Π½ΠΎΡΠΈΠ»Π°ΡΡŒ ΠΊ сСрвСру.

Π‘ΠΎΠ΄Π΅Ρ€ΠΆΠΈΠΌΠΎΠ΅ Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΊΠ° fifΠΎ.h ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½ΠΎ Π² листингС 4.8. Π­Ρ‚ΠΎΡ‚ Ρ„Π°ΠΉΠ» опрСдСляСт ΠΈΠΌΠ΅Π½Π° Π΄Π²ΡƒΡ… FIFO, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π΄ΠΎΠ»ΠΆΠ½Ρ‹ Π±Ρ‹Ρ‚ΡŒ извСстны ΠΊΠ°ΠΊ ΠΊΠ»ΠΈΠ΅Π½Ρ‚Ρƒ, Ρ‚Π°ΠΊ ΠΈ сСрвСру.

Π’ листингС 4.9 ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½ тСкст ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹-ΠΊΠ»ΠΈΠ΅Π½Ρ‚Π°, которая Π½Π΅ слишком отличаСтся ΠΎΡ‚ части ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹ ΠΈΠ· листинга 4.6, относящСйся ΠΊ ΠΊΠ»ΠΈΠ΅Π½Ρ‚Ρƒ. ΠžΠ±Ρ€Π°Ρ‚ΠΈΡ‚Π΅ Π²Π½ΠΈΠΌΠ°Π½ΠΈΠ΅, Ρ‡Ρ‚ΠΎ ΠΈΠΌΠ΅Π½Π½ΠΎ ΠΊΠ»ΠΈΠ΅Π½Ρ‚, Π° Π½Π΅ сСрвСр удаляСт ΠΊΠ°Π½Π°Π» FIFO ΠΏΠΎ Π·Π°Π²Π΅Ρ€ΡˆΠ΅Π½ΠΈΠΈ Ρ€Π°Π±ΠΎΡ‚Ρ‹, ΠΏΠΎΡ‚ΠΎΠΌΡƒ Ρ‡Ρ‚ΠΎ послСдниС ΠΎΠΏΠ΅Ρ€Π°Ρ†ΠΈΠΈ с этим ΠΊΠ°Π½Π°Π»ΠΎΠΌ Π²Ρ‹ΠΏΠΎΠ»Π½ΡΡŽΡ‚ΡΡ ΠΈΠΌ.

Листинг 4.7. Ѐункция main нСзависимого сСрвСра

//pipe/server_main.c

1  #include "fifo.h"

2  void server(int, int);

3  int

4  main(int argc, char **argv)

5  {

6   int readfd, writefd;

7   /* созданиС Π΄Π²ΡƒΡ… FIFO. OK, Ссли ΠΎΠ½ΠΈ ΡΡƒΡ‰Π΅ΡΡ‚Π²ΡƒΡŽΡ‚ */

8   if ((mkfifo(FIF01, FILE_MODE) < 0) && (errno != EEXIST))

9    err_sys("can't create %s", FIF01);

10  if ((mkfifo(FIF02, FILE MODE) < 0) && (errno != EEXIST)) {

11   unlink(FIF01);

12   err_sys("can't create %s", FIF02);

13  }

14  readfd = Open(FIF01, O_RDONLY, 0);

15  writefd = Open(FIFO2, O_WRONLY, 0);

16  server(readfd, writefd);

17  exit(0);

18 } 

Листинг 4.8. Π—Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΉ Ρ„Π°ΠΉΠ» fifo.h, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌΡ‹ΠΉ ΠΈ ΠΊΠ»ΠΈΠ΅Π½Ρ‚ΠΎΠΌ, ΠΈ сСрвСром

//pipe/fifo.h

1 #include "unpipc.h"

2 #define FIFO1 "/tmp/fifo.1"

3 #define FIFO2 "/tmp/fifo.2"

Листинг 4.9. Ѐункция main нСзависимого ΠΊΠ»ΠΈΠ΅Π½Ρ‚Π°

//pipe/client_main.c

1  #include "fifo.h"

2  void client(int, int);

3  int

4  main(int argc, char **argv)

5  {

6   int readfd, writefd;

7   writefd = Open(FIFO1, O_WRONLY, 0);

8   readfd = Open(FIFO2, O_RDONLY, 0);

9   client(readfd, writefd);

10  Close(readfd);

11  Close(writefd);

12  Unlink(FIFO1);

13  UnLink(FIFO2);

14  exit(0);

15 }

ΠŸΠ Π˜ΠœΠ•Π§ΠΠΠ˜Π•

Для ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹Ρ… ΠΊΠ°Π½Π°Π»ΠΎΠ² ΠΈ ΠΊΠ°Π½Π°Π»ΠΎΠ² FIFO ядро Π²Π΅Π΄Π΅Ρ‚ подсчСт числа ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚Ρ‹Ρ… дСскрипторов, относящихся ΠΊ Π½ΠΈΠΌ, поэтому Π±Π΅Π·Ρ€Π°Π·Π»ΠΈΡ‡Π½ΠΎ, ΠΊΡ‚ΠΎ ΠΈΠΌΠ΅Π½Π½ΠΎ Π²Ρ‹Π·ΠΎΠ²Π΅Ρ‚ unlink β€” ΠΊΠ»ΠΈΠ΅Π½Ρ‚ ΠΈΠ»ΠΈ сСрвСр. Π₯отя эта функция ΠΈ удаляСт Ρ„Π°ΠΉΠ» ΠΈΠ· Ρ„Π°ΠΉΠ»ΠΎΠ²ΠΎΠΉ систСмы, ΠΎΠ½Π° Π½Π΅ влияСт Π½Π° ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚Ρ‹Π΅ Π² ΠΌΠΎΠΌΠ΅Π½Ρ‚ Π΅Π΅ выполнСния дСскрипторы. Однако для Π΄Ρ€ΡƒΠ³ΠΈΡ… Ρ„ΠΎΡ€ΠΌ IPC, Ρ‚Π°ΠΊΠΈΡ… ΠΊΠ°ΠΊ ΠΎΡ‡Π΅Ρ€Π΅Π΄ΠΈ сообщСний стандарта System V, счСтчик отсутствуСт, ΠΈ Ссли сСрвСр ΡƒΠ΄Π°Π»ΠΈΡ‚ ΠΎΡ‡Π΅Ρ€Π΅Π΄ΡŒ послС записи Π² Π½Π΅Π΅ послСднСго сообщСния, ΠΎΠ½Π° ΠΌΠΎΠΆΠ΅Ρ‚ Π±Ρ‹Ρ‚ΡŒ ΡƒΠ΄Π°Π»Π΅Π½Π° Π΅Ρ‰Π΅ Π΄ΠΎ Ρ‚ΠΎΠ³ΠΎ, ΠΊΠ°ΠΊ ΠΊΠ»ΠΈΠ΅Π½Ρ‚ это сообщСниС считаСт.

Для запуска ΠΊΠ»ΠΈΠ΅Π½Ρ‚Π° ΠΈ сСрвСра запуститС сСрвСр Π² Ρ„ΠΎΠ½ΠΎΠ²ΠΎΠΌ Ρ€Π΅ΠΆΠΈΠΌΠ΅:

% server_fifo &

Π° Π·Π°Ρ‚Π΅ΠΌ запуститС ΠΊΠ»ΠΈΠ΅Π½Ρ‚. МоТно Π±Ρ‹Π»ΠΎ ΡΠ΄Π΅Π»Π°Ρ‚ΡŒ ΠΈ ΠΏΠΎ-Π΄Ρ€ΡƒΠ³ΠΎΠΌΡƒ: Π·Π°ΠΏΡƒΡΠΊΠ°Ρ‚ΡŒ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡƒ-ΠΊΠ»ΠΈΠ΅Π½Ρ‚, которая запускала Π±Ρ‹ сСрвСр с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ fork ΠΈ exec. ΠšΠ»ΠΈΠ΅Π½Ρ‚ ΠΌΠΎΠ³ Π±Ρ‹ ΠΏΠ΅Ρ€Π΅Π΄Π°Π²Π°Ρ‚ΡŒ сСрвСру ΠΈΠΌΠ΅Π½Π° FIFO Π² качСствС Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚ΠΎΠ² ΠΊΠΎΠΌΠ°Π½Π΄Π½ΠΎΠΉ строки Π² ΠΊΠΎΠΌΠ°Π½Π΄Π΅ exec, вмСсто Ρ‚ΠΎΠ³ΠΎ Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΠΎΠ±Π΅ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹ считывали ΠΈΡ… ΠΈΠ· Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΊΠ°. Но Π² этом случаС сСрвСр являлся Π±Ρ‹ Π΄ΠΎΡ‡Π΅Ρ€Π½ΠΈΠΌ процСссом ΠΈ ΠΏΡ€ΠΎΡ‰Π΅ Π±Ρ‹Π»ΠΎ Π±Ρ‹ ΠΎΠ±ΠΎΠΉΡ‚ΠΈΡΡŒ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΌ ΠΊΠ°Π½Π°Π»ΠΎΠΌ.