は、私は、次のスタックトレースが含まれているサーバー上のイベントビューアのエントリを取得しています:.NETでNullReferenceExceptionが発生する理由は何ですか?TCP接続を受け入れる/受け入れますか?私自身のウェブサーバソフトウェアで
Framework Version: v4.0.30319
Description: The process was terminated due to an unhandled exception.
Exception Info: System.ArgumentNullException
Stack:
at System.Net.FixedSizeReader.ReadCallback(System.IAsyncResult)
at System.Net.LazyAsyncResult.Complete(IntPtr)
at System.Threading.ExecutionContext.RunInternal(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object, Boolean)
at System.Threading.ExecutionContext.Run(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object, Boolean)
at System.Threading.ExecutionContext.Run(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object)
at System.Net.ContextAwareResult.Complete(IntPtr)
at System.Net.Sockets.BaseOverlappedAsyncResult.CompletionPortCallback(UInt32, UInt32, System.Threading.NativeOverlapped*)
at System.Threading._IOCompletionCallback.PerformIOCompletionCallback(UInt32, UInt32, System.Threading.NativeOverlapped*)
言うまでもないが言って、これは、サーバーがダウンしたことのプロセスを、クラッシュします。
stacktraceには自分のコードが記述されていないので、私は非常に困惑しています。これは.NETのバグですか?その場合は、既知の回避策がありますか?または、この特定の例外には既知の原因がありますか?
stacktraceに記載されているCompletionPortCallback
という名前は、サーバーが受信TCP接続を受け入れるときに発生すると考えているため、以下では関連するコードを含めます。もちろん、問題が他の場所にあると思うなら、他のコードも含めることができます。
ここで、_listeningSocket
はタイプSystem.Net.Sockets.Socket
は次のとおりです。
BeginAccept
への呼び出しは次のようになります。
acceptSocket
の方法を以下に示します。コメントがコードを十分に説明していると仮定します。もしそうでなければ、私はコメントで明確にすることができてうれしいです。このコードはライブサーバーでRELEASEモードで実行されるため、#if DEBUG
は当然間違いです。
private void acceptSocket(IAsyncResult result)
{
#if DEBUG
// Workaround for bug in .NET 4.0 and 4.5:
// https://connect.microsoft.com/VisualStudio/feedback/details/535917
new Thread(() =>
#endif
{
// Ensure that this callback is really due to a new connection (might be due to listening socket closure)
if (!IsListening)
return;
// Get the socket
Socket socket = null;
try { socket = _listeningSocket.EndAccept(result); }
catch (SocketException) { } // can happen if the remote party has closed the socket while it was waiting for us to accept
catch (ObjectDisposedException) { }
catch (NullReferenceException) { if (_listeningSocket != null) throw; } // can happen if StopListening is called at precisely the "wrong" time
// Schedule the next socket accept
if (_listeningSocket != null)
try { _listeningSocket.BeginAccept(acceptSocket, null); }
catch (NullReferenceException) { if (_listeningSocket != null) throw; } // can happen if StopListening is called at precisely the "wrong" time
// Handle this connection
if (socket != null)
HandleConnection(socket);
}
#if DEBUG
).Start();
#endif
}
私の知る限り、nullの代わりに 'BeginAccept()'呼び出しで '_listeningSocket'を渡すべきです。' _listeningSocket.BeginAccept(acceptSocket、_listeningSocket); 'ドキュメントと例を参照してください。そのため、あなたはArgumentNull例外を受け取りました。 –
これは明らかに.NETフレームワークのバグです。 APIをmsiusしていた場合は、IOコールバックのBCLの奥深くではなく、エラーが発生したはずです。問題は、これを回避する方法です。 – usr