2012-08-06 33 views
1

我的主线程创建多个I/O工作线程。然后我做启动从我的主线程的I/O请求:在我的I/O工作线程将调用线程置于可警告等待状态

{ 
    ... 
    IoRequest *pIoRequest = new IoRequest(m_socket); 
    pIoRequest->SetBuffer(vecCommandData); // vector of BYTEs 
    pIoRequest->SetOperationType(OP_TYPE_SEND); 
    WSASend(m_socket, pIoRequest->GetWsaBuffer(), 1, NULL, 0, pIoRequest, NULL); 
    ... 
} 

在某一点上,该请求已完成,我IoRequest对象的缓冲区充满了有效的响应数据。

DWORD WINAPI WorkerThreadProc(LPVOID lpParameter) 
{ 
    IoCompletionPort *pIocp = reinterpret_cast<IoCompletionPort*>(lpParameter);  
    ... 
    while (true) 
    { 
     BOOL bReturn = pIocp->GetStatus(&ulCompletionKey, &dwNumberOfBytesTransferred, (LPOVERLAPPED*)&pIoRequest); 
     ... 
     switch (pIoRequest->GetOperationType()) 
     { 
     ... 
     case OP_TYPE_RECEIVE_DATA: 
      { 
       ... 
       // the requested I/O operation has completed and pIoRequest's buffer now contains valid response data! 
       break; 
      } 
     ... 
     } 
    } 

    return 0; 
} 

我怎样才能把我的主线程处于警惕性的等待状态调用WSASend(后),并使其接收响应数据时,它准备好了?

+0

您的主线程还存在其他什么限制(例如,您是否需要在等待时泵送消息,是否可以阻止,直到工人准备就绪等)? – 2012-08-06 12:07:30

+0

@Nate Kohl-这是我希望我的主线程工作的方式;如果已经有一个I/O请求正在处理,那么我的主线程只是将任何进一步的请求放入一个队列(而不是被阻塞)。无论何时当前的请求正在完成,我的主线程将一个挂起的请求出队并使用WSASend()发送它。作为测试,我打电话while(1){Sleep(1000); }现在WSASend()立即返回。 – jpen 2012-08-06 13:37:21

回答

2

在IOCP服务器中,通常是GetQueuedCompletionStatus()。

+1

如果您不使用IOCP,请使用[SleepEx](http://msdn.microsoft.com/en-us/library/windows/desktop/ms686307%28v=vs.85%29.aspx)。 – 2012-08-06 12:24:54

+0

@Martin James - 我正在创建一个使用IOCP的客户端应用程序。我的GetStatus()函数内部调用GetQueuedCompletionStatus()。我所有的工作线程都通过调用这个函数来等待完成端口。我所追求的是一种机制,它允许我的主线程在I/O工作线程完成请求时得到通知。也许像在我的主线程中实现的回调函数(OnResponseDataReceived()或其他)在每个I/O请求完成时被调用? ...但我不知道该怎么做。 – jpen 2012-08-06 13:17:08

+0

@jpen - 为下一次数据加载发出另一个WSArecv(),然后向主线程发送PostMessage()RxBuffer(或任何您称之为表示WSArecv()调用及其数据的实例)实例。如果RxBuffer类包含对套接字对象的引用(它肯定必须这样做),那么当IOCP工作线程使用主线程消息处理程序时,如果要访问套接字数据,则必须采取通常的预防措施。 – 2012-08-06 13:58:25

相关问题