Во-первых, я знаю, что UDP - ненадежный транспортный механизм на сетевом уровне, и нет, я не могу переключить свое приложение на TCP.Теперь, когда у нас это не так, как надо ...
У меня возникла проблема, когда я не могу прочитать данные из моего UDP-клиента в свое приложение так, чтобы я мог видеть все полученные пакеты,Я могу убедиться, что пакеты поступают на машину с Wireshark, что устраняет проблему надежности сети.Я удалил почти все из своего кода и буквально все, что он делает, это подсчитывает пакеты, и я до сих пор не могу привести количество пакетов из Wireshark в соответствие с количеством пакетов, которое я считаю в своем приложении.Я перепробовал все, что я могу найти в Интернете, включая увеличение размера буфера, чтобы избежать заполнения буфера ядра (который, казалось, не имел никакого эффекта).Клиенты Udp должны быть способны отправлять как широковещательные, так и одноадресные пакеты, но должны обрабатывать только одноадресные ответы.
Эта проблема проявляется при обработке большого количества одноадресных ответов от разных конечных точек в течение короткого периода времени.(~ 200 в 1 секунду).Если ответы распределены больше, тогда проблем нет, но я не могу контролировать получателей.
Я прошу прощения за то, что код немного неаккуратный, поскольку я пробовал разные вещи, чтобырешить проблему и не удалось (очевидно).
Код для создания клиента:
UdpClient Udp = new UdpClient();
Udp.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReceiveBuffer, 0x4000);
Udp.ExclusiveAddressUse = false;
Udp.EnableBroadcast = true;
Udp.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
Udp.Client.Bind(new IPEndPoint(A, 12345));
ReceiveDataAsync(Udp, ReceiveDataCallback);
Код для обработки данных (опять же, просто подсчет пакетов):
private static void ReceiveDataAsync(UdpClient Client, Action<UdpClient, UdpReceiveResult> Callback)
{
Thread T = new Thread(() =>
{
try
{
while (true)
{
try
{
IPEndPoint E = new IPEndPoint(IPAddress.Any, 12345);
byte[] Data = Client.Receive(ref E);
PacketsFound += 1;
}
catch (SocketException)
{
// Do nothing, triggered when we get ICMP unreachable.
}
}
}
catch (ObjectDisposedException)
{
// Do nothing
}
catch (NullReferenceException)
{
// Also do nothing. Seems to fire when disposed and callback is still waiting.
}
catch (Exception ex)
{
MessageBox.Show(ex.Message + "\r\n\r\n" + ex.StackTrace, ex.GetType().ToString());
}
});
T.IsBackground = true;
T.Priority = ThreadPriority.Highest;
T.Start();
}
Заранее благодарим за помощь.