邮槽是Windows系统提供的一种单向通信的机制。即进程中的一方只能写入或读取数据,而另一方则只能读取或写入数据。通过邮槽,用户可以实现一对多或跨网络的进程之间的通信。但是,邮槽能传输的数据非常小,一般在400KB左右。如果用户操作的数据过大,可能会导致邮槽不能正常工作。
用户在实际编程时,可以使用Windows邮槽实现进程间通信。但是用户必须首先创建邮槽。在Windows系统中,用户可以通过函数CreateMailslot函数创建邮槽。函数原型如下:
HANDLE CreateMailslotW(
LPCWSTR lpName,
DWORD nMaxMessageSize,
DWORD lReadTimeout,
LPSECURITY_ATTRIBUTES lpSecurityAttributes
);
该函数的作用是创建邮槽并返回该邮槽的句柄。如果函数调用成功,将返回创建邮槽的句柄。否则,函数将返回INVALID_HANDLE_VALUE,表示邮槽创建失败,参数说明如下:
参数lpName表示邮槽的名称。邮槽名称的格式为“\\.\mailslot\name”。其中,name表示邮槽的名称。用户在c++开发环境中,应该将其指定为“\\\\.\\mailslot\\name”。如果用户在不同的主机上运行程序,则需要把名称字符串中的“.”换成对方主机名称。
参数nMaxMessageSize 指定将通过邮槽发送或接收的消息的最大值,在实际编程中,一般将其设置为0,表示消息的大小为任意值。
参数lReadTimeout表示程序读取操作的超时时间。如果该参数值为0,则当邮槽中没有任何消息时,该函数将立即返回。如果该函数值为MAILSLOT_WAIT_FOREVER,则表示该函数将等待,直到邮槽中有消息函数才返回。
参数lpSecurityAttributes是指向结构体LPSECURITY_ATTRIBUTES的指针,表示邮槽的安全属性,一般情况下,将其设置为NULL,表示默认安全属性。
一般情况下,函数CreateMailslot常被用于进程通信的服务方,客户端方使用CreateFile函数打开指定的邮槽,再进行相关操作。
用户对邮槽进行操作包括将数据写入邮槽和从邮槽中读取数据等。在实际编程时,操作邮槽和操作文件一样,都是通过调用函数ReadFile()和WriteFile()进行读写操作。函数原型如下:
BOOL ReadFile(
HANDLE hFile,
LPVOID lpBuffer,
nNumberOfBytesToRead,
LPDWORD lpNumberOfBytesRead,
LPOVERLAPPED lpOverlapped
);
BOOL WriteFile(
HANDLE hFile,
LPCVOID lpBuffer,
DWORD nNumberOfBytesToWrite,
LPDWORD lpNumberOfBytesWritten,
LPOVERLAPPED lpOverlapped
);
服务端:
#include "stdafx.h"
#include
#include
using namespace std;
int _tmain(int argc, _TCHAR* argv[])
{
HANDLE mail; //定义邮槽句柄
//创建邮槽
mail=CreateMailslot("\\\\.\\mailslot\\my",0,MAILSLOT_WAIT_FOREVER,NULL);
if(mail==INVALID_HANDLE_VALUE) //判断邮槽句柄
{
cout<<"创建邮槽失败!\r\n"; //提示信息
return 0;
}
else
{
cout<<"创建邮槽成功,正在读取数据……!\r\n";
char text[200]; //定义字符数组
DWORD readtext; //获取实际读取值
while(1)
{
if(ReadFile(mail,text,200,&readtext,NULL)) //读取数据
{
cout<
客户端:
#include "stdafx.h"
#include
#include
using namespace std;
int _tmain(int argc, _TCHAR* argv[])
{
HANDLE mail2; //定义邮槽句柄
char text[]="您好,this is a message"; //初始化消息
DWORD writetext; //获取实际发送值
mail2=CreateFile("\\\\.\\mailslot\\my",GENERIC_WRITE,FILE_SHARE_READ,
NULL, OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
//打开文件
if(INVALID_HANDLE_VALUE==mail2)
{
cout<<"邮槽打开失败!\r\n";
}
else
{
if(WriteFile(mail2,text,sizeof(text),&writetext,NULL)) //写入数据
{
Sleep(1000);
cout<<"数据写入成功\r\n"; //数据写入成功
}
else
{
cout<<"数据写入失败\r\n";
}
CloseHandle(mail2); //关闭句柄
}
Sleep(10000);
return 0;
}