Wednesday, February 15, 2012

Solving DeadLocks problems.

It has been a long time since I wrote my last post but as I promised this is the continuation. Last time I was talking about ReentrantLock class in the package java.util.concurrent.locks.

This package gives us an interface called 'Lock' which is implemented by the ReentrantLock class. This kind of object works very similar to synchronized code blocks, as we can have just one 'Lock' at the same time. Its main advantage is that it allows us to schedule alternative executions if the 'Lock' object has been obtained by another thread. The most important method of this object is the method tryLock, which will try to get the 'lock' of the object and if it is not possible it will return false.

This will give us the possibility to write code in order to take other actions. That's its main advantage with regard the synchronized code blocks, in which an infinite loop is started until it can get the 'lock'. Now we are going to use this kind of object in order to solve the deadlock problems in the previous example. We are going to have one Cashier class and one OperateCash class, we are going to create 2 objects from the Cashier class whose methods will be invoke in the OperateCashier class. This is the code example:

import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

public class Deadlock {
 
    static class Cashier {
 
       private double balance;
       private final String name;
       public final Lock lock = new ReentrantLock();
 
       public Cashier(double balanceIni, String name) {
         this.balance = balanceIni;
     this.name = name;
 }
 
        public void debit(double value) {
        balance += value;
 }
 
 public void credit(double value) {
      balance -= value;
 }
 
 public double getBalance() {
    return balance;
 }
 
 public String getName() {
     return name;
 }
 
    }
 
    static class OperateCashier {
 
        public boolean transfer(Cashier cashierFrom, Cashier cashierTo,
    double value, String h){
 
         Boolean lock1 = false;
      Boolean lock2 = false;
 
      System.out.println("Thread " + h + ": transfer cash from " + cashierFrom.getName() +
   " to " + cashierTo.getName());
      try {
  System.out.println("Thread " + h
          + ": get lock "
   + cashierFrom.getName());
  lock1 = cashierFrom.lock.tryLock();
  System.out.println("Thread " + h
          + ": get lock "
          + cashierTo.getName());
  lock2 = cashierTo.lock.tryLock();
      } finally {
   if (!(lock1 && lock2)) {
      if (lock1) {
   cashierFrom.lock.unlock();
      }
      if (lock2) {
   cashierTo.lock.unlock();
      }
       }
 }
 
 if (lock1 && lock2) {
  try {
          if (cashierFrom.getBalance() >= value) {
     cashierFrom.debit(value);
     cashierTo.credit(value);
     System.out.println("Thread " + h
     + ": transfer finished...");
   }
  } finally {
   cashierFrom.lock.unlock();
   cashierTo.lock.unlock();
  }
 } else {
  System.out.println("Thread " + h
  + ":It was not able to get the lock from both objects");
 }
 return (lock1 && lock2);
     }
   }
 
   public static void main(String[] args) {
 
 final Cashier cashier1 = new Cashier(60000, "CJ1");
 final Cashier cashier2 = new Cashier(80000, "CJ2");
 final OperateCashier opc = new OperateCashier();
 new Thread(new Runnable() {
  String nameThread = "H1";
  boolean go = false;
  long time = 100;
  public void run() {
        while (!go) {
   go=opc.transfer(cashier1,cashier2,20000,nameThread);
   if (!go) {
        try {
          System.out.println("Thread "+ nameThread
    + ": Wating " + time);
    Thread.sleep(time);
        } catch (InterruptedException e) {}
   }
      }
  }
   }).start();
 
   new Thread(new Runnable() {
       String nameThread = "H2";
       boolean go = false;
       long time = 100;
 
       public void run() {
   while (!go) {
         go=opc.transfer(cashier2, cashier1, 10000, nameThread);
   if (!go) {
      try {
           System.out.println("Thread "+nameThread
                               + ": Wating " + time);
                               Thread.sleep(time);
       } catch (InterruptedException e) {}
   }
   }
       }
    }).start();
 }
}

In the Cashier class in line number 10 a 'Lock' object has been created which is the object that will be used in order to lock the object thus preventing the other thread to use it. So when a Thread needs to use a Cashier object, it will invoke the method tryLock of the object Lock, this method will check if other thread have already locked the object, if so then it will return false, if not, it will lock the object and will return true.

The OperateCashier class have a method named 'transfer', this method makes money transfers from one cashier to another cashier, the two objects which represent those cashiers are given as parameters and so also the value to transfer and a String value that will tell us which Thread is running at the moment. In order for the transfer operation be sucessfull, it is needed that none other thread already be making the transfer. So it will be necessary lock both cashiers. Thus any other thread will have to wait until the current transaction is complete. 

In line number 49 we try to get the 'lock' of the cashier which is going to make the transfer, while in line number 53 we try to do the same with the cashier that will receive the transfer. The checking whether both cashier has been locked or not is done inside of the finally block, because in case it's not possible to lock both cashiers, it may be that at least one of them has been already locked so it should be released, we do not want an object locked for ever. In line number 65 again we check whether or not we managed lock both objects. If so then we go ahead and make the money transfer. Then we must unlock both objects. Finally a boolean value is returned pointing out if the transfer was sucessfull. 

Now let's see what is happening in the method main. The two Threads that will invoke the method transfer are created in there. Each one of these threads will try to make a money transfer. The first, from cashier1 to cashier2 and the second from cashier2 to cashier1. It's for sure that in some point during execution, one thread will find that other thread have already locked one or both cashiers, but it won't be a problem because in that case the method will return false and then we can decide what to do. In this case we will have a while loop trying to complete the transaction every 100 ms. eventually it will have its chance but in the real life you could decide to make other things.

if we execute this program many times. We can see that always both transaction are completed successfully, in whatever order, preventing a deadlock. So this is one of the ways to reduce deadlocks in programs.
6:21 PMNo comments

Friday, August 20, 2010

Java concurrency and deadlock problems

It's known by many programmers that the use of the key word 'synchronized' is either for establishing methods or establishing synchronized code blocks that affect the optimal performance of the applications with regard to process speed. Although misuse of synchronized code blocks is forbidden. Constant improvements of the JVM through the years has made the percentage of performance affected versus the benefits to resolve concurrency problems tilt the balance towards the latter. The main issue associated with the misuse of synchronized code blocks is, if we increase such methods or blocks in an application then the greater the chance that at some point in the program's execution, DeadLock may occur and the application starts an infinite loop and finally is forced to restart.

In particular, DeadLock happens when at least two threads try to lock on an object at the same time. In order to be more clear I will give an example: Thread 'A' gets the 'Lock' of the object 'obj1', while thread 'B' gets the 'Lock' of the object 'obj2'. Then thread 'A' tries to get the 'Lock' of 'obj2' before releasing the 'Lock' of 'obj1'. At the same time, thread 'B' tries to get the 'Lock' of 'obj1' before releasing the 'Lock'of 'obj2' . What we have in here is thread 'A' will wait until the thread 'B' releases the 'Lock'of 'obj2' while thread 'B' is waiting for thread 'A' to release the 'Lock' of 'obj1' . So they will be waiting on each other until the judgement day. Let's see the example:
    public static Object obj1 = new Object();
public static Object obj2 = new Object();
public void metodo1() {
synchronized (obj1) {
synchronized (obj2) {
process1();
}
}
}
public void metodo2{
synchronized (obj2) {
synchronized (obj1) {
process2();
}
}
}
As You can see there are two synchronized code blocks in two methods. First thread 'A' invokes to 'method1' and gets the 'Lock' of the object 'obj1', at the same time thread 'B' gets the 'Lock' of the object 'obj2'. Then thread 'A' tries to get the 'Lock' of the 'obj2', but it turns out that thread 'B' already has 'obj2' so thread A will have to wait until 'obj2' is released. But the problem is that thread 'B' is waiting for the release of the object 'obj1' before releasing 'obj2'. Hence DeadLock and both threads will be in an eternal wait.

Knowing when a 'Deadlock' will happen is very difficult because of the low possibility that two threads will gain access to both methods simultaneously. However, it can happen without warning. It may be just once during a period of time or it may happen many times within the same period. To detect this type of problem by just analyzing the code can be difficult. A mistake as mentioned above can be detected easily and infer that the problem can be solved by chaning the order in which the objects are locked. In other words, they must be locked in the same order in both methods in such a way that the 'Deadlock' is not possible. Let's see an example more complex:
  public class Deadlock {
static class Auto {
private final String model;
private final long miles;
public Auto(String model, long ml) {
this.model = model;
this.miles = ml;
}
public String getModel() {
return this.model;
public synchronized long difMiles(Auto auto) {
System.out.println("Calculate Difference in miles ");
return Math.abs((auto.getMiles() - getMiles()))
}
public synchronized long getMiles() {
System.out.println(" Get miles for " + getModel());
return miles;
}
}
public static void main(String[] args) {
final Auto mazda = new Auto("Mazda", 60000);
final Auto renault = new Auto("Renault", 80000);
new Thread(new Runnable() {
public void run() { System.out.println("Difference in miles "
+ mazda.difMiles(renault)); }
}).start();
new Thread(new Runnable() {
public void run() { System.out.println("Difference in miles "
+ renault.difMiles(mazda)); }
}).start();
}
}
As you can see two instances of Auto class were created. The Auto class have a method which calculate the difference between two cars by miles. When the first thread is executed the Mazda object invokes difMiles method and gains the Lock of the object Mazda. On the other hand, the second thread happens at the same time and this object gains Lock of the 'Renault' object. But what happens when both threads invoke getMiles method using the object that has been passed as a prameter?.

The first thread tries to gain the Lock of 'Renault' object while the second thread tries to gain the Lock on the 'Mazda' object. As you can see, neither thread is going to get what they want and the application will get hung up. It is exactly like the first case we looked at. It is just that this time it is not so obvious and truly things could get worse when there are more lines of code. This case is a seed to germinate a potential 'DeadLock'. If you executed this code 10 consecutive times, it will probably do fine for 6 or 7 of those times, but at least 3 or 4 times it will make the application get hung up.

The fact that the application gets hung up only sometimes, makes it more difficult to find the cause of the problem. You might think there is no reason in real life for two threads to start doing such operations, therefore, let's see a typical example a little more close to real life. Let's suppose that we have to do a transfer of money between two cash accounts. We will have two objects 'account1' and 'account2' which are, in this instance, of the same Account Class. The code would go like this:
  public class Deadlock {
static class Cash {
double balance;
public Cash(double balInit) {
this.balance = balInit;
}
public void debit(double val) {
balance += val;
}
public void credit(double val) {
balance -= val;
}
public double getBalance() {
return balance;
}
}
static class OperCash{
public void transfer(Cash from, Cash to, double val) {
System.out.println("balance transfer...");
System.out.println("lock acquired from...");
synchronized (from) {
System.out.println("lock acquired to...");
synchronized (to) {
if (from.getBalance() >= val) {
from.debit(val);
to.credit(val);
System.out.println("transfer finished...");
}
}
}
}
}
public static void main(String[] args) {
final Cash cash1 = new Cash(60000);
final Cash cash2 = new Cash(80000);
final OperCash opc = new OperCash();
new Thread(new Runnable() {
public void run() {
opc.transfer(cash1, cash2, 20000);
}
}).start();
new Thread(new Runnable() {
public void run() {
opc.transfer(cash2, cash1, 10000);
}
}).start();
}
}
The messages printed in every step are there, not just to show us what is happening during execution, but also to delay a little of the execution of the threads as it would happen in a real application which responds to multiple calls. As expected, this code is intended to get stuck in a 'DeadLock' at some point of its life cycle. This is because different threads can call the same method with parameters ordered in a different way, such as in previous examples.

Well, now the question we've been raiding is how to prevent such problems from happening when we need to synchronize access to an object?. One of the possible solutions is to carefully sort the way in which the synchronizaed methods are called from different threads or the order in which parameters are passed to methods containing synchronized code blocks. In order to do this, we must observe in what order the locks are obtained within the method. This is usually a very hard task when dealing with very complex applications. Fortunately, more recent versions of Java language give us a package which help us deal with these kinds of problems. I am talking about package java.util.concurrent.locks.

For now I am just going to say that this package gives us an interface called 'Lock' which is implemented by the ReentrantLock class. This kind of object works very similar to synchronized code blocks, as we can have just one 'Lock' at the same time. Its main advantage is that it allows us to schedule alternative executions if the 'Lock' object has been obtained by another thread. The way to use this object to solve the problems presented above, I leave for another post.

2:02 PMNo comments

Monday, July 26, 2010

Running a Java program as a daemon.

Sometimes we need a Java program that works as a service starting manually or every time that our OS starts. These services are executing themselves as background processes, constantly waiting for events or executing certain tasks between defined periods of time. These services are known also as daemons. As opposed to a normal application, daemons are controlled by the OS. The OS either starts or stops the deamon. This allows the completion of the task of liberation of resources every time the service is finished or when the machine is turned off.
In order to created an application which works as a daemon we must implement the daemon interface using the package provided by Apache. We can find it in http://commons.apache.org/daemon.com. The interface has the following methods that we must implement:


public interface Daemon {
public void init(DaemonContext context) throws Exception;
public void start() throws Exception;
public void stop() throws Exception;
public void destroy();
}
The method 'init' is executed just once when the class which implements the interface daemon is initiated. In this method it is possible to initialize instant attributes that we need. To initialize sockets but not to initialize threads, like those which listen on ports and neither other threads.

The method 'start' is the point of entry for the daemon. like the method 'main' for conventional application. It is here in this method where we can initialize the threads that are going to do the tasks for which the daemon has been created.

The method 'stop' is used when it is necessary to stop the daemon. Here operations such as disconnections from the database are executed, but not liberation of resources. These must be preserved because the daemon can be required to restart.

The method 'destroy' is executed when we need the daemon to finish all tasks and free up all the resources it is using. It is here where we can liberate any resource that is in use, like sockets, databases, objects, etc.

We can, for example, have two threads, one which works as a server that listens constantly in the port 6000, waiting for a package. The other thread could be a client application which is monitoring a database table. Every time that it finds a new record, it packs it and sends it to a remote server. These two threads should be started in the method 'start' or in any other method that is called from 'start'. Let's do a simple example:

First of all let's define a 'server' class.


public class Server {
private static Server ctrlComm;
public static int PTO_SERVER = 6000;
boolean activeServer = true;
Vector vDaemons = new Vector();
private Server() { }
public static Server getInstance() {
if (ctrlComm == null) {
ctrlComm = new Server();
}
return ctrlComm;
}
public void initServer() throws Exception {
new ThreadServer().start();
}
public void stopServer() {
activeServer = false;
for (Iterator iter = vDaemons.iterator(); iter.hasNext();) {
ThreadProcessInfo item = (ThreadProcessInfo ) iter.next();
item.continuar = false;
}
}
private void serverTCP() throws Exception {
ServerSocket serverSocket = new ServerSocket(PTO_SERVER);
ThreadProcessInfo process = null;
while (activeServer) {
try {
Socket socket = serverSocket.accept();
process= new ThreadProcessInfo(socket);
} catch (Exception ex) {
ex.printStackTrace();
throw new Exception("Error initializing ThreadProcessInfo instance");
}
process.start();
vDaemons.add(process);
}
//Now the thread that initialized the server.
private class ThreadServer extends Thread {
int type = 0;
public ThreadServer() {}
public void run() {
try {
serverTCP();
} catch (Exception ex) {
ex.printStackTrace();
stopServer();
}
}
}
}
Now the client thread.


public class Client extends Thread {
private boolean serverActive = true;
public Client() {}
public void stopServer() {
this.serverActive = false;
}
public void process() throws Exception {
/*Here all the code for manipulate data*/
}
public void run() {
while (serverActive) {
try {
processs();
} catch (Exception e) {
try {
/*close sockets connection*/
} catch (Exception e2) {}
}
}
}
Now the main class that implements the daemon interface.

public class MainDaemons implements Daemon {
private static Server servComm;
private static DaemonClient cliComm;
public static void initService() {
try {
servComm = Server.getInstance();
servComm.initServer();
cliComm = new Client();
cliComm.start();
} catch (Exception ex) {
System.out.println("Server abort: " + ex.getMessage());
System.exit(0);
}
}
public static void stopService() {
if (servComm != null) {
servComm.stopService();
servComm = null;
System.out.println("Service stopped " + new Date());
}
}
public void init(DaemonContext context) throws Exception { }
public void start() throws Exception {
initService();
}
public void stop() throws Exception {
stopService();
}
public void destroy() { }

}
Well that is all. To start the daemon, we use JSVC, but the explanation about its use will be for another post in the blog. Although, the example is missing other things and controls. I hope you can figure out how you can implement and use the daemon interface. I hope this information is useful.
12:48 PM3 comments