无名管道半双工,读写方向是固定的吗?

_xixihaha_ 2018-01-11 09:13:32
各位大神好,小白从工控转过来,对于半双工,有点疑问;
在工控中,比如PLC和仪表之间通信,基于485的差分信号,是半双工的,即:在同一时刻,只能有一端发,一端收,不能同时收发。
但是关键在于,可以分时收发,例如:A----->485------->B,A发信号给B,当A发完后,A变为接收端,A<-----485<-------B,接受B发过来的报文。
我的尝试如下:
思路是,首先建立一个缓存数组,子进程从父进程中集成了缓存数组;
然后在父进程中修改缓存,write,之后子进程打印缓存,即会发现在父进程中修改的缓存内容,同时在子进程中也被修改了;
之后,如果按照工控的半双工思路,两端都停止发送,子进程先写入,父进程再读取,即可;
实测不行,看到很多教程中说道,读写是固定的,是否意思为,初始为父写入子,那么这个管道永远都是父写入子?

#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
short ReadFromPipe(int *fd,char *buf);
short WriteToPipe(int *fd,char *buf);
int main()
{

printf("hello test\n");
int fd[2]={0,0};
char buff[100]={1,2,3,4,5,6,7,8};
pid_t pid;
int No=0;
No = pipe(fd);
printf("NO.=%d\n",No);
pid=fork();
switch (pid)
{
case -1:
printf("fork error\n");break;
case 0: //子进程起始为接收端
printf("son proccess\n");
ReadFromPipe(fd,buff);
printf("pipe=%d\n",*(buff+2));

sleep(3); //尝试转为发送端
*(buff+1)=97;
WriteToPipe(fd,buff);
break;
default: //父进程起始为发送端
printf("father\n");
*(buff+2)=99;
WriteToPipe(fd,buff);

sleep(5); //尝试转为接收端送端
ReadFromPipe(fd,buff);
printf("pipe2=%d\n",*(buff+1));
}
return 0;
}
short ReadFromPipe(int *fd,char *buf)
{
short re; //return value
close(*(fd+1));
re=read(*fd,buf,100); //fd+0 for reading
return re;
}
short WriteToPipe(int *fd,char *buf)
{
short re;
close(*fd); //fd+1 for writing
re=write(*(fd+1),buf,100);
return re;
}
...全文
701 2 打赏 收藏 转发到动态 举报
写回复
用AI写文章
2 条回复
切换为时间正序
请发表友善的回复…
发表回复
双林子木 2018-01-20
  • 打赏
  • 举报
回复
半双工的理解就像你说的那样,你的理解一点问题都没有,但为什么你的测试程序与预期不符呢?那是因为你的程序设计有问题,子进程在消息还未写入管道的另一端的内核缓冲时就已经终止,因此发送的消息随着进程的终止而被丢弃。你的程序稍作修改就可以,可以参考如下例子: #include <stdio.h> #include <string.h> #include <errno.h> #include <unistd.h> #include <limits.h> int sendinfo(int fd[2], char *buffer, size_t size) { int bytes = -1; if ( (bytes = write(fd[1], buffer, size)) == -1) { perror("write error!"); } sync(); return bytes; } int recvinfo(int fd[2], char *buffer, size_t size) { int bytes = -1; if ((bytes = read(fd[0], buffer, size)) == -1) { perror("read error!"); } return bytes; } int main() { int fd[2]; int ret; pid_t pid; char buffer[PIPE_BUF]; ret = pipe(fd); if (ret == -1) { perror("Create pipe failed!"); return -1; } pid = fork(); switch (pid) { case 0: recvinfo(fd, buffer, PIPE_BUF) != -1 ? printf("%s\n", buffer):printf("son process recvfailed\n"); ret = sprintf(buffer, "father i received your message!"); sendinfo(fd, buffer, ret); break; case -1: perror("fork failed"); break; default: ret = sprintf(buffer, "son process pid is : %d", pid); sendinfo(fd, buffer, ret); recvinfo(fd, buffer, PIPE_BUF); printf("%s\n", buffer); break; } return 0; }
cocoabird 2018-01-17
  • 打赏
  • 举报
回复
半双工是固定的

23,117

社区成员

发帖
与我相关
我的任务
社区描述
Linux/Unix社区 应用程序开发区
社区管理员
  • 应用程序开发区社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧