0

我有以下问题:

我必须从各种终端启动一个进程,但我只能在启动一定数量的进程后才能开始运行该程序。换句话说,我必须以某种方式阻止进程,直到获得正确数量的进程。

我正在尝试通过使用称为“服务器”的第一个进程来使用 FIFO 来做到这一点。问题继续作为门票入口问题:“服务器”进程始终写入 FIFO,该 FIFO 将是下一个进程的编号。下一个过程获取它的“票”并将他的号码发送到“服务器”++。我基本上是这样编码的:

服务器:

count = 0;
fd_w = open ("client", O_WRONLY);
fd_r = open ("server", O_RDONLY);
do {
    write (fd_w, &count, sizeof(int)); //Write on client's reading FIFO
    read (fd_r, &count, sizeof(int));  //Read what clients wrote
    printf ("Msg read: %d\n", count);
} while (count != 4);

printf ("Starting...\n");

客户:

fd_r = open ("client", O_RDONLY);
fd_w = open ("server", O_WRONLY);

read (fd_r, &count, sizeof(int)); // Read the ticket from server

count++;

write (fd_w, &count, sizeof(int)); // Write what should be the next ticket

//Wait until we have 4 processes

发生的情况是服务器等待第一个调用,但是当第一个进程到达时,它会正确读取服务器消息,将消息正确放回服务器,但服务器以某种方式在循环中交互 1 或 2(它似乎有点随机)和简单地结束。甚至没有打印“开始...”。任何想法为什么会发生这种情况?另外,我应该如何通知其他流程他们可以继续?

如果重要的话,我实际上对服务器和客户端使用相同的代码,我通过测试是否已经创建了“服务器”FIFO来检查哪个是哪个。但我想这并不重要。

4

1 回答 1

1

您的程序中存在多个问题。首先请注意,FIFO 语义与常规文件的语义不同。

如果您以只读 ( O_RDONLY) 或只写 ( O_WRONLY) 模式打开 FIFO,则这些打开的调用将阻塞,直到 FIFO 也分别以只写/读写 ( O_WRONLY/O_RDWR) 或只读 (O_RDONLY) 模式打开。如果您希望您的打开调用立即返回而不管上述情况,那么您必须以非阻塞和只读 ( O_RDONLY | O_NONBLOCK) 模式或读写模式 ( O_RDWR) 打开 FIFO。

如果您使用 ( O_RDONLY | O_NONBLOCK) 标志打开,那么您将立即收到一个EAGAIN错误,read()除非 FIFO 也未打开以进行写入。但是,如果您为读取和写入(O_RDWR)打开它,那么您的读取将阻塞,直到 FIFO 中的数据可用。这是有道理的,因为它确保了这个 FIFO 上至少有一个写入器和一个读取器。

此外,您还没有在代码中进行错误检查,这会混淆编码错误并使调试更加困难。

我已经修复了SERVER代码,使其按预期工作。

#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <fcntl.h>

int main(int argc, char *argv[]) {
        int count = 0;
    int fd_w = open ("client-fifo", O_RDWR);
    if (fd_w < 0) {
            perror("open");
            exit(-1);
        }
    int fd_r = open ("server-fifo", O_RDWR);
    if (fd_r < 0) {
            perror("open");
            exit(-1);
        }   
    do {
        if (write (fd_w, &count, sizeof(int)) < 0) { //Write
                perror("write");
                exit(-1);
        }
        if (read (fd_r, &count, sizeof(int)) < 0) {  //Read
                perror("read");
                exit(-1);
        }

    } while (count != 4);

    printf ("Starting...\n");
    return 0;
}
于 2013-08-12T03:10:21.610 回答