vtorri
vtorri

Reputation: 325

Is my loop wrong ? Do I misuse ReadFile() and I/O completion port ?

I want to implement a server/client using named pipes (for IPC).I'm using async (overlapped) connections and I/O completion port (I searched a lot and it seems that it is the most efficient way to do that).

First here are the codes:

server: http://pastebin.com/XxeXdunC

and client: http://pastebin.com/fbCH2By8

The problem is in the server (i can improve the client but i will do that when the server works).

I use I/O completion port like that : basically, I run a thread in which I call ReadFile(). If it returns TRUE, I get all the data, if it returns FALSE, and the error is ERROR_IO_PENDING, I wait with GetQueuedCompletionStatus().

What is strange is that, even if I read all the data, the last ReadFile() call fails and the error is ERROR_IO_PENDING

The thread in which I call ReadFile() is beginning line 64 of the server code.

The client sends 24 bytes (the string "salut, c'est le client !") and the ReadFile() buffer is of length 5 bytes (to check how my server deals data that is larger than the Readfile() buffer)

The output is:

waiting for client...
WaitForMultipleObjects : 0
client connected (1)
ReadFile 1 msg (5 -> 05) : salut
ReadFile 2 msg (5 -> 10) : salut, c'e
ReadFile 2 msg (5 -> 15) : salut, c'est le
ReadFile 2 msg (5 -> 20) : salut, c'est le clie
ReadFile 2 msg (4 -> 24) : salut, c'est le client !
ReadFile2: ERROR_IO_PENDING
GQCIOS 0 255 003D3A18
ReadFile3: ERROR_IO_PENDING
ReadFile1: ERROR_IO_PENDING
GQCIOS 5 255 003D3A2C
ReadFile3: ERROR_IO_PENDING
ReadFile1: ERROR_IO_PENDING
GQCIOS 5 255 003D3A2C
ReadFile3: ERROR_IO_PENDING
ReadFile1: ERROR_IO_PENDING
GQCIOS 5 255 003D3A2C
ReadFile3: ERROR_IO_PENDING
ReadFile1: ERROR_IO_PENDING
GQCIOS 5 255 003D3A2C
ReadFile3: ERROR_IO_PENDING
ReadFile1: ERROR_IO_PENDING
GQCIOS 4 255 003D3A2C
ReadFile3: ERROR_IO_PENDING
ReadFile1: ERROR_IO_PENDING

What I do not understand is that even if I read all the data, ReadFile() still returns a pending operation (it's the "ReadFile2: ERROR_IO_PENDING" error message after the last "msg" output)

Is my loop wrong ? Do I misuse ReadFile() / GetQueuedCompletionStatus() ?

thank you

Upvotes: 1

Views: 1162

Answers (1)

JosephH
JosephH

Reputation: 8815

Where is your write related function? it seems that your code is in wrong order. In the _read_data_cb routine, GetQueuedCompletionStatus should be called first, then depending on the lpOverlapped parameter, the received data should be ready in the buffer that you specified in the ReadFile function. Since you're calling Readfile without checking whether OVERLAPPED is a overlapped structure for the send context or recv context, you're not getting the expected output. The following code should clear things up:

while(TRUE)
{
    bReturnValue=GetQueuedCompletionStatus(pIOCPServer->m_pIOCP, &dwBytesTransferred,(DWORD *)pClient,reinterpret_cast<LPOVERLAPPED*>(&pOverlapped),INFINITE);
    if(!bReturnValue)
    {
        if(NULL==pOverlapped)
            continue;
        else
            break;
    }
    else
    {
        if(pOverlapped==NULL)
            continue;
    }
    if(dwBytesTransferred==0)
        break;
    if(lpOverlapped==&(pClient->m_pRecvContext->overlapped))
        pClient->handleRecvEvent(dwBytesTransferred)
    else if(lpOverlapped==&(pClient->m_pSendContext->overlapped))
        pClient->handleSendEvent(dwBytesTransferred)
}
...

Upvotes: 1

Related Questions