Search code examples
c#tcpudpicmptraceroute

How do I implement Traceroute using UDP?


Apparently ICMP isn't the only way to create a Traceroute. This and this answer indicates it's possible to send a UDP packet (or any other) with a low TTL and wait for the ICMP message.

How would I go about implementing this in C#? System.IO.Sockets? The TCP objects? Anyone know of an easy/best way?

Update 1:

The following code seems to correctly throw an exception when the TTL is hit. How do I extract information from the returned UDP Packet?

How do I know that the UDP packet I'm receiving is intended for me (and not some other application on my host?)

   public  void PingUDPAsync(IPAddress _destination, short ttl)
    {
        // This constructor arbitrarily assigns the local port number.
        UdpClient udpClient = new UdpClient(21000);
        udpClient.Ttl = ttl;
       // udpClient.DontFragment = true;

        try
        {
            udpClient.Connect(_destination, 21000);

            // Sends a message to the host to which you have connected.
            Byte[] sendBytes = Encoding.ASCII.GetBytes("Is anybody there?");

            udpClient.Send(sendBytes, sendBytes.Length);


            //IPEndPoint object will allow us to read datagrams sent from any source.
            IPEndPoint RemoteIpEndPoint = new IPEndPoint(IPAddress.Any, 0);

            // Blocks until a message returns on this socket from a remote host.
            Byte[] receiveBytes = udpClient.Receive(ref RemoteIpEndPoint);
            string returnData = Encoding.ASCII.GetString(receiveBytes);

            // Uses the IPEndPoint object to determine which of these two hosts responded.
            Console.WriteLine("This is the message you received " +
                                         returnData.ToString());
            Console.WriteLine("This message was sent from " +
                                        RemoteIpEndPoint.Address.ToString() +
                                        " on their port number " +
                                        RemoteIpEndPoint.Port.ToString());

            udpClient.Close();
        }
        catch (SocketException socketException)
        {
            Console.WriteLine(socketException.ToString());
        }
        catch (Exception e)
        {
            Console.WriteLine(e.ToString());
        }

    }

Solution

  • Yes, System.Net.Sockets should provide you all the primitive objects you would need to send/receive UDP/TCP packets. Plenty of documentation and samples online, the two articles you included in your question are very interesting and a good starting point :)