2013-01-13 4 views
5

나는 명명 된 파이프로 시작하고 두 개의 로컬 프로세스 사이에서 IPC를 위해 사용해야합니다. 나는 nonblocking overlapped 모드에서 파이프를 사용하는 서버와 클라이언트 프로세스를 가지고있다.논 블로킹 ConnectNamedPipe 이벤트가 신호를 보내지 않음

OVERLAPPED 구조체를 통해 ConnectNamedPipe()로 전달 된 이벤트가 예상대로 신호를 보내지 않는다는 점을 제외하면 모든 것이 잘 작동합니다 (클라이언트가 보낸 문자열을 클라이언트가 성공적으로 수신함).

서버가 WaitForSingleObject() 호출에서 차단되는 동안 클라이언트 프로세스가 파이프에 연결되어 데이터를 보내고 이벤트가 신호를받지 못하고 종료됩니다. 내가 뭘 놓치고 있니?

서버 코드 : (사용되지 않음) 당신은 사용하지 말아야합니다

HANDLE hPipe = ::CreateNamedPipeW(
    L"\\\\.\\pipe\\ThePipe", 
    PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED, 
    PIPE_TYPE_MESSAGE | PIPE_READMODE_MESSAGE | PIPE_NOWAIT, 
    1, 
    4096, 
    4096, 
    100, 
    nullptr); 

OVERLAPPED ov = {0}; 
ov.hEvent = ::CreateEventW(nullptr, TRUE, FALSE, nullptr); 

BOOL retVal = ::ConnectNamedPipe(hPipe, &ov); 

if (retVal == 0) 
{ 
    DWORD err = ::GetLastError(); 
    if (err == ERROR_IO_PENDING) 
    { 
     ::WaitForSingleObject(ov.hEvent, 30000); 
    } 
    if (err == ERROR_PIPE_LISTENING) 
    { 
     ::WaitForSingleObject(ov.hEvent, 30000); // this blocks until time-out??? 
    } 
} 
+0

ERROR_IO_PENDING을 받나요? (당신은이 케이스를 구별하기 쉽도록 만들거나, 프로세스에 첨부하여 기다리는 곳을보아야합니다.) –

답변

10

PIPE_NOWAIT 함께 중복 모드. PIPE_NOWAIT은 클라이언트가 연결되어 있지 않은 경우 ERROR_PIPE_LISTENING을 바로 반환합니다. ConnectNamedPipe을 반환합니다. 중첩 된 I/O는 발생하지 않으며 이벤트를 기다리는 것은 쓸모가 없습니다.

PIPE_NOWAIT을 설정하고 파이프가 성공할 때까지 주기적으로 폴링하거나 FILE_FLAG_OVERLAPPED을 설정하고 이벤트를 사용하여 완료를 확인/대기하십시오.

+1

내 문제가 해결되었습니다. 정말 고맙습니다! Microsoft는이 문서를 실제로 업데이트해야합니다. – links77

+0

CreateNamedPipe의 MSDN 페이지에서 "비 차단 모드는 Microsoft LAN Manager 버전 2.0과의 호환성을 위해 지원되므로 명명 된 파이프와 비동기 I/O를 수행하는 데 사용해서는 안됩니다." –

+0

비동기 모드에서 ConnectNamedPipe를 사용하지 않는다는 경고가 표시됩니다. 대신'OVERLAPPED' 구조체가'ReadFile'에 전달되어 읽기를 기다릴 수 있습니다. – Steve

관련 문제