c-在FIFO上读取()时如何检查EOF
在客户机-服务器程序中,需要检查c-在FIFO上读取()时如何检查EOF,c,linux,ipc,eof,fifo,C,Linux,Ipc,Eof,Fifo,在客户机-服务器程序中,需要检查FIFO上的read()的EOF 问题: // fifo header #ifndef _CS_FIFO #define _CS_FIFO #define CLIENT_DATA_SIZE 2 #define SERVER_DATA_SIZE 10 #define SERVER_FIFO_PATH "/tmp/server_fifo" #define CLIENT_COUNT 3 #endif // client - server fifo, serve
FIFO上的read()
的EOF
问题:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
- FIFO中的EOF是否返回
0
,或-1
且未设置错误
- 该规则是否也适用于其他IPC设施
@更新
我仍然发现结果有用,所以需要继续询问
以下是源代码:
cs\u fifo.h:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
fifo\u服务器c:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
//客户端-服务器fifo,服务器部分,
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括“cs_fifo.h”
int fifo_服务器(){
int标志;
int-fd;
char buf[客户机数据大小];
//在创建之前删除fifo
移除(服务器\先进先出\路径);
//创建fifo
模式=0644;
如果((标志=mkfifo(服务器FIFO路径,模式))=-1){
printf(“mkfifo()时出错:%s\n”,strerror(errno));
返回-1;
}
printf(“已创建服务器fifo,路径:%s\n”,服务器fifo\u路径);
//开放阅读
如果((fd=打开(服务器的FIFO路径,仅O_RDONLY))=-1){
printf(“打开时出错():%s\n”,strerror(errno));
出口(-1);
}
//循环以从客户端接收数据,
而(1){
//从fifo读取
如果((标志=读取(fd、buf、客户端数据大小))=-1){
printf(“读取时出错():%s\n”,strerror(errno));
出口(0);
}如果(标志==0){//无数据,则为else
printf(“无数据”);
睡眠(1);
继续;
}
//收到的数据,
printf(“接收数据:%s\n”,buf);
//将数据发送回客户的fifo,
//待办事项
}
//完成使用后,移除fifo,
移除(服务器\先进先出\路径);
返回0;
}
int main(int argc,char*argv[]){
返回fifo_服务器();
}
fifo\u客户端c:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
//客户端-服务器fifo,客户端池部分,
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括“cs_fifo.h”
int fifo_客户端_池(){
int标志;
int server_fd;
字符数据[客户端数据大小];
int i=0;
pid_t cpid;
字符标识;
//开放供写
如果((服务器\u fd=打开(服务器\u FIFO\u路径,O\u WRONLY))=-1){
printf(“打开时出错():%s\n”,strerror(errno));
出口(-1);
}
//创建子进程作为客户端,
而(i<客户数量){
开关(cpid=fork()){
案例-1://失败
printf(“fork()时出错:%s\n”,strerror(errno));
出口(errno);
案例0://成功,子进程在此进行
printf(“已创建子进程,pid[%d],父pid[%d]\n”,(int)getpid(),(int)getppid());
identity=i+65;//从“A”开始
//准备数据
数据[0]=标识;
数据[1]='\0';
//写入fifo
if((标志=写入(服务器\u fd、数据、客户端\u数据\u大小))=-1){
printf(“[%c]写入时出错():%s\n”,标识,strerror(errno));
_出口(-1);
}
printf(“[%c]向服务器发送数据\n”,标识);
_出口(0);
打破
默认值://success,父进程位于此处
//睡一会儿,
睡眠(1);
打破
}
i++;
}
如果((flag=close(server_fd))!=0){
printf(“关闭时出错():%s\n”,strerror(errno));
}
返回0;
}
int main(int argc,char*argv[]){
返回fifo_客户端_池();
}
编译:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
服务器:gcc-Wall-fifo_服务器.c-o服务器
客户端:gcc-Wall-fifo\u Client\u pool.c-o Client\u pool
执行:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
第一个启动服务器:/server
然后启动客户端池:/client\u pool
结果:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
- 服务器启动,并在客户端启动前阻塞
- 然后客户端启动,服务器从3个客户端中的每一个接收1个请求,总共3个
- 然后所有客户端进程终止,然后服务器的read()continue返回
0
而不阻塞
未来的问题是:
// fifo header
#ifndef _CS_FIFO
#define _CS_FIFO
#define CLIENT_DATA_SIZE 2
#define SERVER_DATA_SIZE 10
#define SERVER_FIFO_PATH "/tmp/server_fifo"
#define CLIENT_COUNT 3
#endif
// client - server fifo, server part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_server() {
int flag;
int fd;
char buf[CLIENT_DATA_SIZE];
// remove fifo, before create
remove(SERVER_FIFO_PATH);
// create fifo
mode_t mode = 0644;
if((flag = mkfifo(SERVER_FIFO_PATH, mode)) == -1) {
printf("error while mkfifo(): %s\n", strerror(errno));
return -1;
}
printf("server fifo created, path: %s\n", SERVER_FIFO_PATH);
// open for read
if((fd = open(SERVER_FIFO_PATH, O_RDONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// loop to receive data from client,
while(1) {
// read from fifo
if((flag = read(fd, buf, CLIENT_DATA_SIZE)) == -1) {
printf("error while read(): %s\n", strerror(errno));
exit(0);
} else if(flag == 0) { // no data
printf("no data\n");
sleep(1);
continue;
}
// data received,
printf("receive data: %s\n", buf);
// send data back to client's fifo,
// TODO
}
// remove fifo, after finish using,
remove(SERVER_FIFO_PATH);
return 0;
}
int main(int argc, char * argv[]) {
return fifo_server();
}
// client - server fifo, client pool part,
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "cs_fifo.h"
int fifo_client_pool() {
int flag;
int server_fd;
char data[CLIENT_DATA_SIZE];
int i = 0;
pid_t cpid;
char identity;
// open for write
if((server_fd= open(SERVER_FIFO_PATH, O_WRONLY)) == -1) {
printf("error while open(): %s\n", strerror(errno));
exit(-1);
}
// create child processes as clients,
while(i < CLIENT_COUNT) {
switch(cpid=fork()) {
case -1: // failed
printf("error while fork(): %s\n", strerror(errno));
exit(errno);
case 0: // success, child process goes here
printf("child process created, pid [%d], parent pid [%d]\n",(int)getpid(), (int)getppid());
identity = i + 65; // start from 'A'
// prepare data
data[0] = identity;
data[1] = '\0';
// write to fifo
if((flag = write(server_fd, data, CLIENT_DATA_SIZE)) == -1) {
printf("[%c] error while write(): %s\n", identity, strerror(errno));
_exit(-1);
}
printf("[%c] send data to server\n", identity);
_exit(0);
break;
default: // success, parent process goes here
// sleep a while,
sleep(1);
break;
}
i++;
}
if((flag = close(server_fd)) != 0) {
printf("error while close(): %s\n", strerror(errno));
}
return 0;
}
int main(int argc, char * argv[]) {
return fifo_client_pool();
}
- 所有客户端终止后,服务器的
read()
是否应该阻止?因为它处于阻塞模式
所有从描述符读取的数据,其中read
返回零表示“关闭”或“结束”
如果您有一个阻塞描述符(默认值),那么如果当前没有可读取的内容,read
将阻塞。如果描述符是非阻塞的,则read
返回-1
,并将errno
设置为EAGAIN
或ewoodblock
,如果没有可读取的内容。在我的程序中,read()
返回0
,它处于阻塞模式,读卡器仍然打开,但所有写卡器都关闭,这是正常的还是挥舞的?@EricWang当管道(FIFO)从另一端关闭时,当没有更多的内容可读取时,read
将返回零,您应该关闭一端。对于阻塞描述符,read
只会阻塞(不返回),直到有东西要读取。@EricWang如果read
返回零,则表示您已完成接收,您将不会再接收任何内容。因此,您应该关闭描述符并退出您所处的循环,而不是继续希望会有更多,因为它不会继续。当read
返回零时,它并不意味着“没有数据”,它意味着“文件结束”或“连接关闭”或“管道中没有更多数据”,它不是暂时缺少数据,而是数据流的永久结束。是的。如果管道的另一端已关闭,则管道已关闭,不再有数据。所以read()取消阻止,并返回0,这样您就可以对该事实采取行动。是的,我会的