2016-09-20 10 views
1

今日、私はCreateIoCompletionPort()を呼び出してから、WaitForSingleObject()に戻っHANDLEを渡すことができることを学びました:完了ポートのWaitForSingleObject()?

#include <Windows.h> 

int main() 
{ 
    HANDLE h = CreateIoCompletionPort(INVALID_HANDLE_VALUE, nullptr, 0, 0); 
    auto bRes = PostQueuedCompletionStatus(h, 1, 2, 0); 
    if (!bRes) { 
     abort(); 
    } 

    auto dwRes = WaitForSingleObject(h, INFINITE); 
    if (dwRes != WAIT_OBJECT_0){ 
     abort(); 
    } 

    LPOVERLAPPED pOvr; 
    DWORD cb; 
    ULONG_PTR key; 
    bRes = GetQueuedCompletionStatus(
     h, &cb, &key, &pOvr, INFINITE); // <-- returns 1, 2, nullptr 

    if (!bRes) { 
     abort(); 
    } 

    dwRes = WaitForSingleObject(h, INFINITE); // <-- blocks here 
    return 0; 
} 

私のWindows 10のボックスに期待どおりに働いています。

このような行為は知られているか、法的に文書化されていますか?私はそれについて何かを見つけることができませんでした。

+0

'dwRes = WaitForSingleObject(h、INFINITE); // < - ブロックここに ' - 本当にブロック?確信してるの ?ちょうど不思議だ – RbMm

+0

はい。待機状態でのクラッシュダンプとソースコードはここにあります:https://1drv.ms/f/s!AtyOp6RRifUTuC2CAVzWdFrvZu6w –

+0

はい、win10では実際にKQUEUEディスパッチャーヘッダーで待機します。 win8.1で言う - いいえ。 – RbMm

答えて

3

あなたがWaitForSingleObject() documentationを読めば、I/O完了ポートがではありません許さハンドルタイプ:

WaitForSingleObject機能は、以下のオブジェクトを待つことができます。

  • 変更通知
  • コンソール入力
  • イベント
  • メモリリソース通知
  • ミューテックス
  • プロセス
  • セマフォ
  • ポートに到着するために完了イベントを待機するスレッド
  • 待機可能タイマー

、あなたはハンドルを渡す必要がありますGetQueuedCompletionStatus()に送信し、イベントが到着するかタイムアウトが発生するまでブロックします。

#include <Windows.h> 

int main() 
{ 
    HANDLE h = CreateIoCompletionPort(INVALID_HANDLE_VALUE, nullptr, 0, 0); 
    auto bRes = PostQueuedCompletionStatus(h, 1, 2, 0); 
    if (!bRes) { 
     abort(); 
    } 

    LPOVERLAPPED pOvr; 
    DWORD cb; 
    ULONG_PTR key; 
    bRes = GetQueuedCompletionStatus(
     h, &cb, &key, &pOvr, INFINITE); // <-- returns 1, 2, nullptr 

    if (!bRes) { 
     abort(); 
    } 

    bRes = GetQueuedCompletionStatus(
     h, &cb, &key, &pOvr, INFINITE); // <-- blocks here 

    return 0; 
} 
+1

WaitForSingleObject()はWaitForSingleObject()のドキュメントで明示的に言及されていませんが、ファイルハンドルを待つこともできます(https://blogs.msdn.microsoft.com/oldnewthing/20121012-00/?p=6343、ファイルハンドルは待機可能なオブジェクトです ")。 私は完了ポートの適切な使用について十分に認識しています。私は完了ポートが待ち受け可能なオブジェクトであるかどうか疑問に思います。 –

+0

['GetOverlappedResult()'](https://msdn.microsoft.com/en-us/library/windows/desktop/ms683209.aspx)のドキュメントでは、ファイル、名前付きパイプ、および通信デバイスのハンドルも待つことができるハンドルを持っていますが、それらを直接待つことは避けてください。しかし、[I/O Completion Portsのドキュメント](https://msdn.microsoft.com/en-us/library/windows/desktop/aa365198.aspx)には、I/O完了ポートハンドルが直接待つことはないと言われています。何かが文書化されていない場合は、それに頼らないでください。 –

1

概要:

  • それをしません。完了ポートを正しく使用する方法については、Remy Lebeauの答えとMSDNを参照してください。
  • このような完了ポートの乱用は、文書化されていないだけでなく、信頼性もありません。動作はWindows 10のビルドによって異なります。
  • 完了ポートは、完了ポートをバックアップするKQUEUEがDISPATCHER_HEADERを持っているため、おそらくカーネルの待機のための正当なオブジェクトです。