神奇的ConnectNamedPipe,哪位高手能告诉小弟我它的异步模式的大致实现

神奇的ConnectNamedPipe,谁能告诉我它的异步模式的大致实现?
本帖最后由 tzleo 于 2012-09-14 10:15:53 编辑
在使用ConnectNamePipe异步模式的时候,发现一件很神奇的事情,我调试了微软MSDN的代码例子:http://msdn.microsoft.com/EN-US/library/windows/desktop/aa365601(v=vs.85).aspx

明明这个函数调用的时候已经立即返回了,但是在读写回调(CompletedReadRoutine和CompletedWriteRoutine)的时候堆栈却是从这个函数发出的,而且位于主线程当中!而这个时候主线程按道理还在WaitForSingleObjectEx中阻塞着,这到底是什么情况,我凌乱了。。。求高手来给解释。

附完整代码:

// NamedPipTest.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include <windows.h> 
#include <stdio.h>
#include <tchar.h>
#include <strsafe.h>

#define PIPE_TIMEOUT 5000
#define BUFSIZE 4096

typedef struct 

OVERLAPPED oOverlap; 
HANDLE hPipeInst; 
TCHAR chRequest[BUFSIZE]; 
DWORD cbRead;
TCHAR chReply[BUFSIZE]; 
DWORD cbToWrite; 
} PIPEINST, *LPPIPEINST; 

VOID DisconnectAndClose(LPPIPEINST); 
BOOL CreateAndConnectInstance(LPOVERLAPPED); 
BOOL ConnectToNewClient(HANDLE, LPOVERLAPPED); 
VOID GetAnswerToRequest(LPPIPEINST); 

VOID WINAPI CompletedWriteRoutine(DWORD, DWORD, LPOVERLAPPED); 
VOID WINAPI CompletedReadRoutine(DWORD, DWORD, LPOVERLAPPED); 

HANDLE hPipe; 

int _tmain(VOID) 

HANDLE hConnectEvent; 
OVERLAPPED oConnect; 
LPPIPEINST lpPipeInst; 
DWORD dwWait, cbRet; 
BOOL fSuccess, fPendingIO; 

// Create one event object for the connect operation. 

hConnectEvent = CreateEvent( 
NULL,    // default security attribute
TRUE,    // manual reset event 
TRUE,    // initial state = signaled 
NULL);   // unnamed event object 

if (hConnectEvent == NULL) 
{
printf("CreateEvent failed with %d.\n", GetLastError()); 
return 0;
}

oConnect.hEvent = hConnectEvent; 

// Call a subroutine to create one instance, and wait for 
// the client to connect. 

fPendingIO = CreateAndConnectInstance(&oConnect); 

while (1) 

// Wait for a client to connect, or for a read or write 
// operation to be completed, which causes a completion 
// routine to be queued for execution. 

dwWait = WaitForSingleObjectEx( 
hConnectEvent,  // event object to wait for 
INFINITE,       // waits indefinitely 
TRUE);          // alertable wait enabled 

switch (dwWait) 

// The wait conditions are satisfied by a completed connect 
// operation. 
case 0: 
// If an operation is pending, get the result of the