Note
この記事は .NET Framework に固有のものです。 .NET 6 以降のバージョンを含む、.NET の新しい実装には適用されません。
ガベージ コレクション ヒープで作成されなかった重なり合ったポインターが特定の Win32 関数に渡されると、 invalidOverlappedToPinvoke マネージド デバッグ アシスタント (MDA) がアクティブになります。
Note
既定では、この MDA は、プラットフォーム呼び出し呼び出しがコードで定義され、デバッガーが各メソッドの JustMyCode 状態を報告する場合にのみアクティブ化されます。 JustMyCode を理解していないデバッガー (拡張機能のない MDbg.exe など) では、この MDA はアクティブになりません。 構成ファイルを使用し、.mda.config ファイル (<invalidOverlappedToPinvoke enable="true" justMyCode="false"/>) にjustMyCode="false"を明示的に設定することで、これらのデバッガーに対してこの MDA を有効にすることができます。
Symptoms
クラッシュまたは原因不明のヒープの破損。
原因
ガベージ コレクション ヒープで作成されなかった重なり合ったポインターは、特定のオペレーティング システム関数に渡されます。
次の表に、この MDA が追跡する関数を示します。
| モジュール | Function |
|---|---|
| HttpApi.dll | HttpReceiveHttpRequest |
| IpHlpApi.dll | NotifyAddrChange |
| kernel32.dll | ReadFile |
| kernel32.dll | ReadFileEx |
| kernel32.dll | WriteFile |
| kernel32.dll | WriteFileEx |
| kernel32.dll | ReadDirectoryChangesW |
| kernel32.dll | PostQueuedCompletionStatus |
| MSWSock.dll | ConnectEx |
| WS2_32.dll | WSASend |
| WS2_32.dll | WSASendTo |
| WS2_32.dll | WSARecv |
| WS2_32.dll | WSARecvFrom |
| MQRT.dll | MQReceiveMessage |
呼び出しを行う AppDomain がアンロードされる可能性があるため、この状態ではヒープ破損の可能性が高くなります。 AppDomainがアンロードされると、アプリケーション コードは重なっているポインターのメモリを解放し、操作の終了時に破損を引き起こすか、コードによってメモリがリークされ、後で問題が発生します。
Resolution
Overlapped オブジェクトを使用し、Pack メソッドを呼び出して、関数に渡すことができるNativeOverlapped構造体を取得します。 AppDomainがアンロードされた場合、CLR は非同期操作が完了するまで待機してからポインターを解放します。
ランタイムへの影響
この MDA は CLR に影響を与えなくなりました。
アウトプット
この MDA からの出力の例を次に示します。
An overlapped pointer (0x00ea3430) that was not allocated on the GC heap was passed via Pinvoke to the Win32 function 'WriteFile' in module 'KERNEL32.DLL'. If the AppDomain is shut down, this can cause heap corruption when the async I/O completes. The best solution is to pass a NativeOverlapped structure retrieved from a call to System.Threading.Overlapped.Pack(). If the AppDomain exits, the CLR will keep this structure alive and pinned until the I/O completes.
コンフィギュレーション
<mdaConfig>
<assistants>
<invalidOverlappedToPinvoke/>
</assistants>
</mdaConfig>
こちらも参照ください
.NET