Some time ago, in the C# Forum occurred the question how to check if an application is still running or has crashed. The only way to check if the application is running is to have another application that does this job. The application can not control itself, because 'a dead dog will not bark'.
To check if an application is running, this application sends regularly an UDP packet, the heartbeat. The observing application listens for the heartbeat (the UDP Packets). If the heartbeat is missing for a certain period, we have to assume that our observed application has crashed. As this works with UDP packets, this supervision can work on the same machine, on another machine in the LAN, or even over the Internet.
Description of the Code
The code is really small and documented, so I will not write a big story about this code.
ClientForm class represents the observed application. In the
Eventhandler function of the
SendUdpPacket() function is called when the checkbox is checked (to simulate a working/non-working application).
private void SendUdpPacket()
byte data = new byte;
Socket udpClientSocket = new Socket( AddressFamily.InterNetwork,
data = Encoding.ASCII.GetBytes(this.Text);
ServerForm class represents the observing application. In the constructor, the Listening Socket and the
Timer are initialized:
udpServerSocket = new Socket(AddressFamily.InterNetwork,
checkTimer.Interval = 1000;
checkTimer.AutoReset = true;
checkTimer.Elapsed += new
The most important part of the callback function
ReceiveData() is the updating of the timestamp
void ReceiveData(IAsyncResult iar)
IPEndPoint sender = new IPEndPoint(IPAddress.Any, 0);
EndPoint tempRemoteEP = (EndPoint)sender;
Socket remote = (Socket)iar.AsyncState;
int recv = remote.EndReceiveFrom(iar, ref tempRemoteEP);
string stringData = Encoding.ASCII.GetString(buffer,0,recv);
lastUpdate = DateTime.Now.ToUniversalTime();
EventHandler of the
Timer, the time span since the last update of the timestamp
lastUpdate is checked. If the time span is too big, the
Label text and color are changed.
private void checkTimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
TimeSpan timeSinceLastHeartbeat = DateTime.Now.ToUniversalTime() - lastUpdate;
if(timeSinceLastHeartbeat > TimeSpan.FromSeconds(3))
lblError.Text = "No Answer from ClientForm";
lblError.BackColor = Color.Red;
lblError.Text = "ClientForm OK";
lblError.BackColor = Color.Green;
Application 'in the Wild'
For a serious observing application, it should not just change the color or text of a label but send an email, send a SMS or paging message or something else. It would make sense to create a service for the observing application and to implement it so that it observes several different applications, maybe also on different machines.
The observed applications should send the heartbeat not from a thread only for this task but from the working thread, if this is possible. When the heartbeat is sent from a thread only for this task, you will not recognize if the important thread of your application has died or is blocked (maybe from a deadlock) because the heartbeat signal is still sent.
The given example was only one way to observe an application. There are other ways (like TCP Connection, Pipes etc.), but you need always another application to observe your application. You can build even more complex heartbeats, like sending a status, and you can use the same mechanism to send warnings and errors to your observing application. So your observing application can become your 'application supervision and alarm management central'.
Version 1.01, Posted 29. September 2004
Made Observer 'daylight saving time'-save. Thanks to jbryner for his advice.
Version 1.00, Posted 22. September 2004