Click here to Skip to main content
65,938 articles
CodeProject is changing. Read more.
Articles / Languages / C#

How to easily exchange data among .NET applications

4.22/5 (8 votes)
28 Jul 2010CPOL3 min read 47.8K  
A simple way of connectionless communication through the UDP protocol is described here.

Introduction

There are many solutions we can choose to exchange data between two (or more) different applications: Remoting, named pipes, TCP client-server etc. However, in all these technologies, the communicating applications must be connected when exchanging data, and your programs must always be prepared for a sudden connection break. It's too complicated for simple purposes.

After a few days of searching, I found the simplest way for data exchange. This solution uses the UdpClient class to send and receive data.

Background

UdpClient is defined in the System.Net.Sockets namespace. It allows to send data to any host and any port and receive data from any other host. When an application sends data, it send to the HOST and PORT instead of sending it to the second application. Moreover, the second application might not even be working! There is no connection between these two applications, and this is the best feature of thise solution.

Let's see how this works.

First of all, you need to initialize a UdpClient object in your program. There are many constructors of the UdpClient class. All of these need to "know" what network protocol you choose and what port will be used to receive data from.

C#
int port=65000
UdpClient u=new UdpClient(port, AddressFamily.InterNetwork);

As you can see in the listing above, I initialize the object u with an arbitrary port number 65000, and the second parameter points to a suitable network protocol.

The application can now read all the data coming to port 65000 from other programs working on the same or even remote machines in the network.

To read (recieve data), you can use this chunk of code:

C#
if (u.Available > 0)
{ 
    IPEndPoint e = new IPEndPoint(IPAddress.Any, 0);
    byte[] b = u.Receive(ref e);
    string readData = ASCIIEncoding.UTF32.GetString(b);
}

First, I check how many bytes are ready to read at the port. This value you can get from the Available property of UdpCleint. So, if the quantity of "available" bytes is greater then zero, read these bytes with the Receive method. The method Receive requires a reference to the IPEndPoint object that points to the IP of the host which sent the data. It also requires a port where data is sent from. As you can see, I use IpAdress.Any to create IPEndPoint. This means that I want to read data sent by any host. I also use 0 as the second parameter - it means I want to read data sent from any port. The Receive method has a "blocking" behavoiur; this means that it waits until data will be available on the port. That's why I check the u.Available>0 condition before calling the Receive method.

As for sending data, it is even easier than reading. Take a look at the following example:

C#
int port=65001
string host="localhost";
UdpClient u1 = new UdpClient();
u1.Connect(host, p);
u1.Send(ASCIIEncoding.UTF32.GetBytes(s), ASCIIEncoding.UTF32.GetByteCount(s));
u1.Close(); // release all recources allocated by UdpClient

I create a new UdpClient using the parameterless constructor. Next, I try to connect to another host and port. In my example, the host is "localhost"; this means that the application that I want to send data to works on the same machine. I repeat once again: when I use the method Connect, it doesn't mean that I connect with a second application, but only with a host and port.

Note that in the example, I use port 65001, so I don't send data to myself (i.e., to 65000) but to another application which can read at this port.

Now we can read and write. Let's suppose we have two applications: App1 and App2, both working on the same machine (localhost).

The first contains a UdpClient object initialized as below:

C#
UdpClient u=new UdpClient(65000, AddressFamily.InterNetwork); // App1

and the second one:

C#
UdpClient u=new UdpClient(65001, AddressFamily.InterNetwork); // App2

Now App1 sends data to App2 using the following code:

C#
string s = "This is app1 is anybody there?"; // data to send
UdpClient u1 = new UdpClient();
u1.Connect("localhost", 65001);
u1.Send(ASCIIEncoding.UTF32.GetBytes(s), ASCIIEncoding.UTF32.GetByteCount(s));

App2 receives data:

C#
if (u.Available > 0) // default port for u is 65001
{ 
    IPEndPoint e = new IPEndPoint(IPAddress.Any, 0);
    byte[] b = u.Receive(ref e);
    string readData = ASCIIEncoding.UTF32.GetString(b);
}

and answers (sending a message to App1):

C#
string s = "App2 here howdy"; // data to send
UdpClient u1 = new UdpClient();
u1.Connect("localhost", 65000); // sending to 65000 i.e. App1
u1.Send(ASCIIEncoding.UTF32.GetBytes(s), ASCIIEncoding.UTF32.GetByteCount(s));

Using the code

Below, I have placed a complete listing of the library which can be compiled to a DLL. It's a simple wrapper of the code listed above.

C#
using System.Net;
using System.Net.Sockets;
namespace UDP
{            
public class SimpleUDP
{
    UdpClient u;
    public SimpleUDP(int port)
    {
        u = new UdpClient(port, AddressFamily.InterNetwork);
    }

    public void Write(string s, string host, int p)
    {
        UdpClient u1 = new UdpClient();
    u1.Connect(host, p);
    u1.Send(ASCIIEncoding.UTF32.GetBytes(s), ASCIIEncoding.UTF32.GetByteCount(s));
    u1.Close(); // release all recources allocated by UdpClient
    }

    public string Read()
    {
        if (u.Available > 0)
        {    
            IPEndPoint e = new IPEndPoint(IPAddress.Any, 0);
            byte[] b = u.Receive(ref e);
            return ASCIIEncoding.UTF32.GetString(b);
        }
        return "";
    }

    public void Close()
    {
        u.Close();
        u = null;
    }
}
}

You may use the class SimpleUDP in two or more applications. It's easy.

App1 uses the constructor and two methods to write to App2 and read from it.

C#
SimpleUDP u=new SimpleUDP(65000)
// ...
string s = u.Read();
// ...
u.Write("How do you do App2");

and for App2, we use a similar code for read and write:

C#
SimpleUDP u=new SimpleUDP(65001) // App2 reads data at port 65001
// ...
string s = u.Read();
// ...
u.Write("Welcome App1");

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)