fifo实现单服务器多客户端
程序员文章站
2024-03-22 16:44:05
...
费劲的折腾,好几次小细节没处理好,真是醉了,不说了
代码记录下
服务端:
//fifo(first in, first out)
//有名管道
#include <iostream>
#include <unistd.h>
#include <cstdio>
#include <sys/wait.h>
#include <signal.h>
#include <cstring>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <errno.h>
#include <cstdlib>
using namespace std;
#define FILE_MODE (S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)
#define FIFO_0 "/tmp/fifo0"
const int size=256;
struct DATA
{
int nLen; //sBuf+pid的有效长度
pid_t pid;
char sBuf[size];
};
int server(int &readfd,int &writefd);
//server
//作用:多个客户端通过FIFO向server传来文件路径名,server返回路径名的反序
int main()
{
//start();
int readfd,writefd;
cout << FILE_MODE << endl;
unlink(FIFO_0);
if( (mkfifo(FIFO_0,FILE_MODE) < 0 ) )
{
if(errno = EEXIST)
cout << "fifo is exist!" << endl;
else
perror("server create FIFO_0");
}
readfd=open(FIFO_0,O_RDONLY,0);
writefd=open(FIFO_0,O_WRONLY,0);
cout << "readfd=" << readfd << endl;
cout << "writefd=" << writefd << endl;
server(readfd,writefd);
return 0;
}
int fifo_ret(DATA & data);
int server(int & readfd,int & writefd)
{
struct DATA data={0};
size_t n=0;
size_t len=0;
char sBuf[256]= {0};
while(true)
{
//迭代式,一个个处理
memset(&data,0x00,sizeof(data));
n = read(readfd,&data,sizeof(data.nLen));
if(n <= 0)
break;
else if(n != sizeof(data.nLen))
{
perror("readfifo");
break;
}
len = data.nLen;
if(read(readfd,&data.pid,sizeof(pid_t)) == sizeof(pid_t) && \
len == read(readfd,data.sBuf,len))
{
cout << "server:" << data.nLen << data.pid << data.sBuf << endl;
fifo_ret(data);
}
}
}
void reverse(char * from, char * to)
{
int n=strlen(from);
int m=n;
for(int i=0;i < n;i++)
{
to[i] = from[--m];
}
}
int fifo_ret(DATA & data)
{
//cout << "come" << endl;
char pathname[size]="/tmp/fifo";
int pid=(int)data.pid;
//strcat(pathname,itoa(pid)); ubuntu,下没有itoa
char sBuf[256];
memset(sBuf,0x00,sizeof(sBuf));
sprintf(sBuf,"%d",pid);
strcat(pathname,sBuf);
//cout <<"pathname"<< pathname << endl;
if(mkfifo(pathname,FILE_MODE) < 0)
{
if(errno == EEXIST)
cout << pathname << "exist" << endl;
else
{
perror("mkfifo pathname");
return -1;
}
}
int writefd;
sleep(3);
if( (writefd=open(pathname,O_WRONLY,0)) < 0)
perror("open fifo");
char sTmp[256]={0};
reverse(data.sBuf,sTmp);
cout << sTmp << endl;
write(writefd,sTmp,strlen(sTmp));
close(writefd);
}
客户端:
#include <iostream>
#include <unistd.h>
#include <cstdio>
#include <sys/wait.h>
#include <signal.h>
#include <cstring>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <errno.h>
#include <cstdlib>
using namespace std;
#define FILE_MODE (S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)
#define FIFO_0 "/tmp/fifo0"
const int size=256;
struct DATA
{
int nLen; //sBuf+pid的有效长度
pid_t pid;
char sBuf[size];
};
int main()
{
if( (mkfifo(FIFO_0,FILE_MODE) < 0 ) )
{
if(errno = EEXIST)
cout << "fifo is exist!" << endl;
else
perror("server create FIFO_0");
}
int readfd,writefd;
char pathname[size]="/tmp/fifo";
int pid=(int)getpid();
char sBuf[256]={0};
memset(sBuf,0x00,sizeof(sBuf));
sprintf(sBuf,"%d",pid);
strcat(pathname,sBuf);
if(mkfifo(pathname,FILE_MODE) < 0)
{
if(errno == EEXIST)
cout << pathname << "exist" << endl;
else
{
perror("mkfifo pathname");
return -1;
}
}
//多客户端向服务端发送字符串,服务器返回反序
writefd=open(FIFO_0,O_WRONLY,0);
sprintf(sBuf,"%d",pid);
char sTmp[256]={0};
DATA data;
while(1) //与服务器通讯
{
memset(sBuf,0x00,sizeof(sBuf));
memset(sTmp,0x00,sizeof(sTmp));
memset(&data,0x00,sizeof(data));
cout << "input:[# quit]" << endl;
cin >> data.sBuf;
if(data.sBuf[0] == '#')
break;
data.pid=pid;
data.nLen=strlen(data.sBuf);
write(writefd,&data,data.nLen+sizeof(data.nLen)+sizeof(data.pid));
readfd=open(pathname,O_RDONLY,0);
read(readfd,sTmp,sizeof(sTmp));
cout << "recv:" <<sTmp << endl;
}
close(writefd);
close(readfd);
unlink(pathname);
exit(0);
}
推荐阅读
-
Linux C语言实现TCP客户端与服务器
-
fifo实现单服务器多客户端
-
使用TCP协议实现客户端和服务器数据传输
-
生命周期组件框架:带有多状态机的单实现类 博客分类: 软件设计 JavaLifecycleStateMachine状态机生命周期
-
生命周期组件框架:带有多状态机的单实现类 博客分类: 软件设计 JavaLifecycleStateMachine状态机生命周期
-
类之间的单继承,接口之间多继承,类与接口之间多实现,单继承多实现
-
Java的单继承多实现问题
-
【TCP/IP网络编程实验】之【python实现客户端给服务器发送小写字母,服务器返回大写字母(UDP)】
-
【TCP/IP网络编程实验】之【python实现客户端给服务器发送小写字母,服务器返回大写字母(TCP)】
-
vue实现单页面多标签页