简体   繁体   中英

C# UdpClient - Listener not receiving all packets sent

I want to create a simple UdpClient listener process and a UdpClient publisher process as a proof of concept for a larger scale project. I created a simple UdpClient listener that listens for messages that are sent on a local port. The code for this listener is below.

// UdpMessageReceiver
class Program
    {
        static async Task Main(string[] args)
        {
            const int Port = 5001;
            await UdpListener(Port);
        }

        public static async Task UdpListener(int port)
        {
            var client = new UdpClient(port, AddressFamily.InterNetwork);
            var receivedCount = 0;
            while (true)
            {
                var receivedResult = await client.ReceiveAsync();
                var resultString = Encoding.ASCII.GetString(receivedResult.Buffer);
                receivedCount++;
                Console.WriteLine("Message: " + resultString);
                Console.WriteLine("Current Message Total: " + receivedCount);
            }
        }
    }

I also created a message publisher that creates and sends a messages to the same local port that my listener is listening on, in this case port 5001. The code for the message publisher is below.

class Runner
    {
        public static string Host = "127.0.0.1";
        public static int Port = 5001;

        // The Message class contains an id prop of type int and a packet prop of type byte[]
        public static async Task<ConcurrentBag<Task>> BuildAndExecuteTasksAsync(ConcurrentBag<Message> messages)
        {
            var tasks = new ConcurrentBag<Task>();

            Parallel.ForEach(messages, message =>
            {
                var sendTask = SendUdpMessageAsync(message);
                tasks.Add(sendTask);
            });

            await Task.WhenAll(tasks);

            return tasks;
        }

        public static async Task SendUdpMessageAsync(Message message)
        {
            var client = new UdpClient(Host, Port);
            await client.SendAsync(message._packet, message._packet.Length);
        }
    }

This snippet is how I generate the list of messages to be sent.

const int NUMBER_OF_MESSAGES = 5000;
var messages = new ConcurrentBag<Message>();

for (int i = 0; i < NUMBER_OF_MESSAGES; i++)
{
     var messageToSend = "Hello World from Id: " + i;
     var packetToSend = Encoding.ASCII.GetBytes(messageToSend);
     messages.Add(new Message(i, packetToSend));
}

The code above does work. I start the listener and then I run the publisher and the listener receives and prints out all of the messages to the console. The issue comes when I try to send a large number of packets at once. The listener only receives and processes the first 2,700 packets or so. All other packets that were sent from the publisher were not received. Is there something I can do to ensure that all of the packets are received by my listener or do I need to change the way that my messages are sent in the publisher?

It is normal for UDP messages to get lost. This happens not only with UDP but TCP as well. The difference when a packet loss happens with TCP, it will notify the sender the packet is lost and should be resent.

That is why UDP is faster, but less accurate.

If you truly want all messages to come through then use TCP.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM