• Bug
  • Status: Open
  • 2 Major
  • Resolution:
  • ehcache-core
  • cdennis
  • Reporter: dogukan
  • February 01, 2012
  • 0
  • Watchers: 3
  • February 08, 2012

Attachments

Description

We are using BlockingCache and after upgrading version from 1.3.0 to 2.4.6 we faced deadlock issue while operating heavy concurrent put on BlockingCache. Based on our implementation in case of an exception we put empty element into BlockingCache then threads which are waiting on BlockingCache get operation trying to put same key to BlockingCache and this is causing deadlock. Following code snippet is illustrating the case that I mentioned.

 Object obj  = blockingCache.get(key);
 if(obj == null){
   try{
     obj = createNewElement(parameters)
   catch(Exception e){
     blockingCache.put(new Element(key,null));
   }

When an exception occurred while creating new element, thread which are waiting an object for same key are getting exception while creating new element and all of them are trying to execute put operation and blockingCache.put(new Element(key,null)) cause deadlock.

Deadlock occurs at line 216 in BlockingCache.java class.

215 if (!lock.isHeldByCurrentThread(LockType.WRITE)) { 216 lock.lock(LockType.WRITE); 217 }

There are some differences between BlockingCache.java 1.30 and BlockingCache.java 2.5.0 (P.S.: BlockingCache 2.4.6 and 2.5.0 is same)

Right now we have a workaround solution but it would be nice if we have constant solution for this case.

Kind Regards, Dogukan Sonmez

Comments

Fiona OShea 2012-02-08

Chris what are your thoughts on this?

Chris Dennis 2012-02-08

After discussing this with some of the other developers at Terracotta we suspect that what you are seeing is not a deadlock but a thread starvation issue. One of the main differences between the BlockingCache implementation in 1.3.0 versus the one in 2.4.6 is that 2.4.6 version uses shared read locks when first reading a given key. This improves throughput when multiple threads are reading the same key which has already been loaded. It can however lead to starvation of writers in some scenarios - we’ve seen this to be more of a problem in Java 1.5.

If this is indeed what you are seeing and you are using Java 1.5 you may see some improvement by upgrading to Java 1.6. I’m also attaching to this issue a subclass of BlockingCache that only uses write locks - if starvation is the issue this should also fix your problem. I’ve not done any testing on this class - I just threw it together in the last few minutes - so I’m obviously providing no guarantees of it helping (or working).