写入FIFO文件/从中读取-Linux [英] Write/Read to/from FIFO files - linux

查看:832
本文介绍了写入FIFO文件/从中读取-Linux的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直试图把头放在FIFO上,并想出了一个简单的服务器和客户端程序.
我并不是想做任何花哨的事情,只是让一个进程扮演服务器"的角色,这个进程将监听"另一进程传递的任何消息;客户.
这是我写的:

I've been trying to wrap my head around FIFO, and came up with a simple program of server and client.
I'm not trying to do anything fancy, just to have one process that will play a role of 'server', this process will 'listen' to any messages delivered by another process; the client.
Here's what I wrote:

server.c

#include<stdio.h>
#include <fcntl.h>
#include <stdlib.h>


#define INGOING "clientToServer.fifo"

#define BUFFER 200

int main(int argc, char *argv[]) {

    char in[BUFFER];

    mkfifo(INGOING, 0666);

    printf("Welcome to server.\n");
    printf("channel for sending messages to server is %s\n", INGOING);

    int in_fd=open(INGOING, O_RDONLY);

    if (in_fd==-1) {
        perror("open error");
        exit(-1);
    }

    while (read(in_fd, in, BUFFER)>0) {
        printf("You sent %s to server.\n", in);
    }

    return 2;
}

如您所见,这很简单,当我在后台使用./server.out&运行此代码时,它在read调用中被阻止,并等待任何人写入clientToServer.fifo.到目前为止一切都很好.

As you can see, this is pretty straight forward, when I ran this at background with ./server.out& it's blocked at the read call and waiting for anyone to write to clientToServer.fifo. so far so good.

现在,考虑客户端:
client.c

Now, consider the client end:
client.c

#include<stdio.h>
#include<fcntl.h>
#include<string.h>


#define BUFFER 200

int main(int argc, char *argv[]) {

    char input[BUFFER]={0};
    int out_fd=open("clientToServer.fifo", O_WRONLY);

    if (out_fd==-1) {
        perror("open error");
    }

    while (1) {

        printf("What would you like to send to server? (send Quit to quit)\n");
        fgets(input, BUFFER, stdin);
        if (input[strlen(input)-1]=='\n') {
            input[strlen(input)-1]='\0';
        }

        if (strcmp(input, "Quit")==0) {
            printf("Bye!");
            break;
        }

        if (write(out_fd, input, strlen(input))==-1) {
            perror("write error");
        }
    }

    return 1;
}

这是客户.也很简单的代码.当我从外壳使用./a.out运行它时,它可以工作-它发送消息,并且server.out进程打印You sent %s to server.
问题是,当我通过客户端将Quit发送到服务器时,尽管a.out进程按需要终止了,但server.out中的while循环也中断了.这意味着read不再阻止server.out进程并等待其他客户端,而是服务器程序与客户端一起结束.
为什么会这样呢?即使在a.out进程结束后,read是否也不应再次暂停server.out ?

This is the client. also pretty simple code. when I run it with ./a.out from shell, it works - it sends the message, and the server.out process prints You sent %s to server.
Problem is, when I send Quit through the client to the server, although the a.out process terminates as desired, the while loop in the server.out breaks as well. meaning, the read no longer blocks the server.out process and awaits other clients, instead, the server program ends, along with the client.
Why is this happening? shouldn't the read suspend the server.out again, even after the a.out process ends?

推荐答案

当我使用./server.out&在后台运行此文件时它在读取调用时被阻止,并等待任何人写入clientToServer.fifo

when I ran this at background with ./server.out& it's blocked at the read call and waiting for anyone to write to clientToServer.fifo

实际上,它在open处阻塞.这就是FIFO的工作方式. open(处于阻塞模式)将阻塞,直到有另一端打开另一端的FIFO.

Actually it blocks at the open. This is the way FIFOs work. The open (in blocking mode) is going to block until something opens the FIFO on the other end.

server.out中的while循环也会中断.意思是,读取不再阻止server.out进程并等待其他客户端,而是服务器程序结束

the while loop in the server.out breaks as well. meaning, the read no longer blocks the server.out process and awaits other clients, instead, the server program ends

再次,这是正常现象.只有一个客户端进程连接到FIFO,因此当它关闭其末端时,将发送EOF并退出服务器.如果将多个客户端同时连接到FIFO,则只有最后一个客户端关闭后,您才能看到EOF.如果要使一台运行时间较长的服务器连续为多个客户端提供服务,最简单的方法是打开服务器的FIFO作为读/写功能.这样,总会有一个读写器-服务器本身-即使最后一个客户端退出,您也不会看到EOF.是时候关闭服务器了,然后关闭服务器中相应的一端,然后自然而然地退出真正的客户端.

Again, this is normal behavior. Only one client process is connected to the FIFO so when it closes its end then EOF is sent and the server quits. If multiple clients are attached to the FIFO at the same time you won't see EOF until the last client closes it. If you want a long running server to serve multiple clients continuously the easiest way to accomplish it is to open the server's FIFO as read/write. This way there is always a reader/writer - the server itself - and you won't see EOF when even the last client exits. When it is time to shut down the server then close the appropriate end in the server and let nature take its course as the real clients quit.

这篇关于写入FIFO文件/从中读取-Linux的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆