5

1 つの TCP サーバーと複数の UDP サーバー/リスナーを持つアプリを開発しています。各サーバーは個別のスレッドであり、確立された TCP 接続のワーカー スレッドと同じです。各スレッドで WSAStartup() を呼び出しています。

時々、WSAStartup() の呼び出しがハングします (デッドロックのように見えます)。スタック トレースは次のとおりです。

  ntdll.dll!_KiFastSystemCallRet@0()  
  ntdll.dll!_ZwWaitForSingleObject@12()  + 0xc bytes 
  ntdll.dll!_RtlpWaitForCriticalSection@4()  + 0x8c bytes 
  ntdll.dll!_RtlEnterCriticalSection@4()  + 0x46 bytes 
  ntdll.dll!_LdrpGetProcedureAddress@20()  + 0x17d bytes 
  ntdll.dll!_LdrGetProcedureAddress@16()  + 0x18 bytes 
  kernel32.dll!_GetProcAddress@8()  + 0x3e bytes 
  vld.dll!03203723()  
  [Frames below may be incorrect and/or missing, no symbols loaded for vld.dll] 
  ws2_32.dll!CheckForHookersOrChainers()  + 0x22 bytes 
  ws2_32.dll!_WSAStartup@8()  + 0xa7 bytes 

このデッドロックは、初期化フェイズ中に発生します。TCP サーバーが開始され、TCP 接続が 1 つ確立されていることがわかりますが、UDP サーバーは 1 つしか開始されていません。スタック トレースは、残りの UDP サーバーを開始する関数からのものです。私の推測では、UDP サーバーを初期化して WSACStartup() を呼び出している間に、別のトレッドが別のソケット操作 (新しい TCP 接続など) を処理しており、WSAStartup() も呼び出しているのではないでしょうか?

私の質問は、複数のスレッドから WSAStartup() を呼び出すと、このデッドロックが発生する可能性があるかどうかです。また、デッドロックの前に呼び出された WSACleanup() を確認しましたが、そうではありません。実行は WSACleanup() のいずれにも到達しません。

WSAStartup を 1 回呼び出すだけで十分であることは承知していますが、WSAStartup() を数回呼び出すことは問題にならないはずです (MSDN] 1 ):「アプリケーションは、WSADATA 構造情報を取得する必要がある場合、WSAStartup を複数回呼び出すことができます。一回以上。" したがって、このデッドロックが WSAStartup() によって引き起こされているのか、それとも他の何かによって引き起こされているのかを確認したいと思います。

4

4 に答える 4

3

何度も電話する必要はありませんWSAStartup()。プログラムごとに 1 回で問題ありません。

于 2010-08-05T18:41:40.577 に答える
1

私はルークが正しいと思います。DllMain() またはグローバル/静的変数の初期化子で WSAStartup() を呼び出すことはできません。それが起こらないようにコードを変更してください。

于 2010-08-05T19:10:18.097 に答える
0

WSAStartupは、実際にはどのような種類のLoadLibraryにもつながりません。そのため、そうではないと思いloader lockます。

代わりに、Windows APIがあなたのケースに閉じ込められていることは明らかです(Windowsでは他の意味がtrapあるため、ここでは用語の方が適しています)。hook

したがって、問題はWSAStartupの同時使用ではなく、プロセス内の元のWindowsAPI関数に対するサードパーティのトラップの副作用にあると思います。私は、外部の影響(あなたの側からの、またはアンチウイルスソフトウェアからのAPIトラップなど)から環境をクリーンアップする必要があると思います。

ちなみに、あなたのスレッドの各スレッドがWSAStartupにWSADATA出力パラメーターの独自の個別のコピーを提供していることを確認してください

于 2010-08-05T21:19:26.170 に答える