接続しているクライアントに送信する必要のあるデータを格納するためにキュー(C#)を使用しています。
私のロックステートメントはプライベート読み取り専用です:
private readonly object completedATEQueueSynched = new object();
エンキューしているメソッドは2つだけです。
1)mainform-threadによって実行される、mouse-movementによって開始されます。
public void handleEddingToolMouseMove(MouseEventArgs e)
{
AbstractTrafficElement de = new...
sendElementToAllPlayers(de)
lock (completedATEQueueSynched)
{
completedATEQueue.Enqueue(de);
}
}
2)mainform-threadによっても実行されるbutton-eventで開始されます(ここでは重要ではありませんが、申し訳ありませんが安全です):
public void handleBLC(EventArgs e)
{
AbstractTrafficElement de = new...
sendElementToAllPlayers(de);
lock (completedATEQueueSynched)
{
completedATEQueue.Enqueue(de);
}
}
このメソッドは、接続されている特定のクライアントを担当するスレッドによって呼び出されます。ここにあります:
private void sendSetData(TcpClient c)
{
NetworkStream clientStream = c.GetStream();
lock (completedATEQueueSynched)
{
foreach (AbstractTrafficElement ate in MainForm.completedATEQueue)
{
binaryF.Serialize(clientStream, ate);
}
}
}
クライアントが接続し、同時にマウスを動かしている場合、デッドロックが発生します。反復のみをロックすると、キューが変更されたため、InvalidOperationexectionがスローされます。
同期されたQueue-Wrapperも試しましたが、反復処理では機能しません。(ロックと組み合わせても)何かアイデアはありますか?間違えない