在线咨询
eetop公众号 创芯大讲堂 创芯人才网
切换到宽版

EETOP 创芯网论坛 (原名:电子顶级开发网)

手机号码,快捷登录

手机号码,快捷登录

找回密码

  登录   注册  

快捷导航
搜帖子
查看: 4684|回复: 0

以命名管道方式实现网络进程间通信的一个实例[转帖]

[复制链接]
发表于 2003-8-4 17:18:59 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?注册

x
Win32位API集支持的命名管道(named pipe)是实现网络进程间通信的一种有效手段。命名管道的接口比较简单,在程序中实现比较方便,由其开发的应用程序也很容易使用,只要知道机器及管道的名称即可连接两台机器上的两个进程。
  命名管道首先由一进程调用CreateNamedPipe函数创建,这一创建命名管道的进程称为Server进程,然后Server进程通过调用ConnectNamedPipe函数等待一客户相连。在管道的另一段,Client进程用CreateFile函数或CallNamedPipe函数打开管道句柄,若无可用的管道实例,Client进程可调用WaitNamedPipe函数等待。一旦连接成功,Client进程和Server进程可调用函数ReadFile、WriteFile或ReadFileEx、WriteileEx传输信息。
  笔者在应用程序开发过程中,曾用命名管道方法做了实现网络两进程间通信的一个小例子。这一例子实现了网络两进程间文本的实时互编辑操作,即在任一台机器上对文本的修改可实时反映到另一台机器上,就好像这一修改是在另一台机器上进行的一样。下面就对这一实验程序作一介绍。
  程序分两部分:Server部分和Client部分。文中只介绍与命名管道实现有关的内容。
1.Server部分
#define BUFSIZE 1280
HANDLE hPipe; ∥管道句柄
BOOL FConnected;
int Success=0;
typedef struct Infor{DWORD Type;char Text[BUFSIZE-64];};∥信息传输结构
struct infor Info;
∥包含编辑控制的对话框
BOOL FAR PASCAL _export PipeServerDlg(HWND hDlg UINT message,WPARAM wParam,LPARAM IParam)
{
UINT IdTimer,DWORD ret,dwMode;
switch(message){
case WM_INITDIALOG;
IdTimer=SetTimer(hDlg,IdTimer,50,(TIMERPROC)NULL);
∥Server创建命名管道
hPipe=CreateNamedPipe("\\ \\.\\pipe\\buf",∥管道名
PIPE_ACCESS_DUPLEX, ∥双向传输
PIPE_WAIT|PIPE_TYPE_MESSAGE, ∥阻塞模式,消息流管道
PIPE_UNLIMITED_INSTANCES,, ∥可以创建数目不限的管道实例
BUFSIZE,BUFSIZE,1000,NULL);
if(hPipe!=INVALID_HANDLE_VALUE){ ∥管道句柄有效
FConnected=ConnectNamedPipe(hPipe,NULL);∥等待连接
if(FConected)Succes=1;∥连接成功
else{CloseHandle(hipe);Succes=0;}
}
if(Succes==1){∥若连接成功,将阻塞模式变为非阻塞模式;设置读模式为消息模式
dwMode=PIPE_READMODE_MESSAGE|PIPE_NOWAIT;
SetNamedPipeHandleState(hPipe,&dwMode,NULL,NULL);
}
return(TRUE);
case WM_TIMER;
if(Succes==1){∥若连接成功,定时读管道数据
Info.Type=-1;∥设初始值
if(ReadFile(hPipe,(char*)&Info,sizeof(Infor),&ret,NULL)==TRUE){∥读管道数据
if(Info.Type==-2){∥收到对方结束对话框信号,与对方同时结束对话框
KillTimer(hDig,IdTimer); CloseHandle(hPipe); Succes=0;
EndDialog(hDlg,TRUE); return(TRUE);
}
if(Info.Type==1)SetDlgItemText(hDlg,IDC_EDIT1,Info.Text);
∥根据对方的变化修改编辑控制内容
} }
break;
case WM_COMMAND;
if(GET_WM_COMMAND_ID(wParam,lParam)==IDOK){∥结束对话框
KillTimer(hDlg.IdTimer);
if(Succes==1){
Info.Type=-2;∥置结束对话框信号
WriteFile(hPipe,(char*)&Info,sizeof(Infor),&ret,NULL;
∥写数据到管道
CloseHandle(hPipe);
}
Succes=0;EndDialog(hDlg,TRUE);return(TRUE);
}
if(Succes==1&&LOWORD(wParam)==IDC_EDIT1&&HIWORD(wParam)==
EN_UPDATE){∥得到已修改的编辑控制中的内容,并写入管道
GetDlgItemText(hDlg,IDC_EDIT1,(LPSTR)(Info.Text),BUFSIZE-64);
Info.Type=1;∥Info.Type=1:修改
WriteFile(hPipe,(char*)&Info,sizeof(Infor),&ret,NULL);
}
break;
}
return(FALSE);
}
2.Client部分
#define BUFSIZE 1280
HANDLE hPipe∥管道句柄
BOOL FConnected;
int Succes=0,Flag=0;
typedef struct Infor{DWORD Type;char Text[BUFSIZE-64];};∥信息传输结构
struct Infor Info;
∥包含编辑控制的对话框
BOOL FAR PASCAL —export PipeClientDlg(HWND hDlg,UINT message,WPARAM wParam, LPARAM lParam)
{
UINT IdTimer;
DWORD ret,dwMode;
switch(message){
case WM_INITDIALOG:
IdTimer=SetTimer(hDlg,IdTimer,50,(TIMERPROC)NULL);
return(TRUE);
case WM_TIMER;
if(Succes==0&&Flag==0){ ∥若未打开管道句柄,定时作打开操作
∥Client打开管道句柄
hPipe=CreateFile("\\\\ServerName\\pipe\\buf", ∥管道名
∥ServerName为运行服务器进程的机器名称
GENERIC_READ|GENERIC_WRITE, ∥读/写模式
0,∥文件非共享
NULL,OPEN_EXISTING,0,NULL);
if(hPipe!=INVALID_HANDLE_VALUE){∥句柄有效
Succes=1;Flag=1;
}
else{
Flag=1;
if(!WaitNamedPipe("\\\\ServerName\\pipe\\buf",20000)Flag=0;∥等待
clse Succes=1;
}
if(Succes==1){
∥若连接成功,将阻塞模式变为非阻塞模式;设置读模式为消息模式
dwMode=PIPE_READMODE_MESSAGE|PIPE_NOWAIT;
SetNamedPipeHandleState(hPipe,&dwMode,NULL,NULL);
}
}
if(Succes==1){ ∥若连接成功,定时读管道数据
Info.Type=-1;∥设置初值
if(ReadFile(hPipe,(char*)&Info,sizeof(Infor),&ret,NULL)==TRUE){
if(Info1.Type==-2){∥收到对方结束对话框信号,与对方同时结束对话框
KillTimer(hDlg,IdTimer);CloseHandle(hPipe);Succes=0;Flag=0;
EndDialog(hDlg,TRUE);return(TRUE);
}
if(Info.Type==1)SetDlgItemText(hDlg.IDC_EDIT1,Info.Text);
}
}
break;
case WM_COMMAND;
if(GET_WM_COMMAND_ID(wParam,1Param)==IDOK){∥结束对话框
KillTimer(hDlg,IdTimer);
if(Succes==1{
Info.Type=-2;WriteFile(hPipe,(char*)&Info,sizeof(Infor),&ret,NULL);
CloseHandle(hPipe);
}
Succes=0;Flag=0;EndDialog(hDlg,TRUE);return(TRUE);
}
if(Succes==1&&LOWORD(wParam)==IDC_EDIT1&&
HIWORD(wParam)==EN_UPDATE){
GetDlgItemText(hDlg,IDC_ENIT1,(LPSTR)(Info.Text),BUFSIZE-64);
Info.Type=1;WriteFile(hPipe,(char*)&Info,sizeof(Infor),&ret,NULL);
}
break;
}
return(FALSE);
}
您需要登录后才可以回帖 登录 | 注册

本版积分规则

关闭

站长推荐 上一条 /1 下一条

小黑屋| 手机版| 关于我们| 联系我们| 在线咨询| 隐私声明| EETOP 创芯网
( 京ICP备:10050787号 京公网安备:11010502037710 )

GMT+8, 2024-11-16 17:56 , Processed in 0.022777 second(s), 9 queries , Gzip On, Redis On.

eetop公众号 创芯大讲堂 创芯人才网
快速回复 返回顶部 返回列表