How to work with named pipes (C++ server , C# client)
I am trying to get started with working with named pipes as I will need to use them for a project of mine in the future.
At the moment I have a C++ server which waits until a client connects and sends over a test message. I roughly followed this tutorial to get started. The relevant code is below:
#define MESSAGE L"TestMessage"
HANDLE hnamedPipe = INVALID_HANDLE_VALUE;
hnamedPipe = CreateNamedPipe(
L"\.pipetestpipe",
PIPE_ACCESS_DUPLEX,
PIPE_TYPE_MESSAGE|
PIPE_READMODE_MESSAGE|
PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES,
1024,
1024,
NMPWAIT_USE_DEFAULT_WAIT,
NULL);
if(hnamedPipe == INVALID_HANDLE_VALUE)
{
cout << "Failed" << endl;
}
while(true)
{
cout<< "Waiting for client"<< endl;
if(!ConnectNamedPipe(hnamedPipe,NULL))
{
if(ERROR_PIPE_CONNECTED != GetLastError())
{
cout << "FAIL"<< endl;
}
}
cout<<"Connected!"<<endl;
//Send over the message
wchar_t chResponse[] = MESSAGE;
DWORD cbResponse,cbWritten;
cbResponse = sizeof(chResponse);
if(!WriteFile(
hnamedPipe,
chResponse,
cbResponse,
&cbWritten,
NULL))
{
wprintf(L"failiure w/err 0x%08lxn",GetLastError);
}
cout<<"Sent bytes :)" << endl;
}
The client code (C#) is below:
using (NamedPipeClientStream pipeClient = new NamedPipeClientStream(".", "testpipe", PipeDirection.InOut))
{
while (true)
{
Console.WriteLine("Connecting to server...");
pipeClient.Connect();
Console.WriteLine("Connected :)");
Console.WriteLine(pipeClient.ReadByte());
pipeClient.Close();
Console.WriteLine("Closed");
}
}
At the moment I have got the client to connect successfully to the server and it prints out the first byte. I want to know how to do 2 things:
Read the entire message - I tried using StreamReader over the pipeClient to read the message but it hangs on ReadLine() indefinitely.
Continuously send over messages - I want the server to send message after message to the client which will read them in one at a time and print them out. I am a bit clueless about IPC so at first I tried to make the client disconnect and reconnect to the server in the while(true) loop whilst the server is in a while true loop which at the top always waits for a new client connection before sending another message. My attempt at this is in the code above.
Any help with this would be greatly appreciated. Eventually the aim is to be sending over images from the server to the client. The client would then print them out to the screen in real-time. I wanted to get this working with simple string messages before I tried the image data.
EDIT:
Eventually I want to be able to send a message from the client to the server indicating it wants to get the latest image frame, the server will then send over the latest frame which the client will then display on screen. So the flow is:
ReadLine
hangs because it is waiting for a newline, which your test message doesn't include.
If you want the server to send messages continuously just put a loop round the WriteFile
call. You don't need to connect more than once. Similarly in the client, put the loop around ReadLine
.
If each message consists of text terminated by a newline then that should suffice, but if you really want the pipe client to work in message mode you need to call:
pipeClient.ReadMode = PipeTransmissionMode.Message;
However, I doubt this would interact well with a StreamReader
. Instead, you should read single messages using pipeClient.Read
.
Update
To answer your new question:
On the server, once the client has connected enter a loop in which:
On the client, once it has connected to the server enter a loop in which:
I wouldn't use a message mode pipe. If the frames are fixed in size then the client knows how much data to read from the server. Otherwise, precede the frame with a uint containing its length.
链接地址: http://www.djcxy.com/p/48282.html上一篇: 命名管道示例