I have a little problem with it comes to thread safe locking that I cannot seem to solve. The problem is that a thread has to own 2 locks on two different objects, it then needs to wait on one of them, but somehow before waiting, release the lock on the first.
This is basically a database problem, I have a lock manager that needs to perform it's locking in isolation, hence a synchronised method called lock. Once in the method if the record the thread is looking for is locked alread it needs to wait on the lock so that when the record is unlocked only threads waiting for that record are woken, not all threads waiting for all other records. To do this the thread needs to obtain the lock on the lock object. Therefore a synchonized block with in the lock method.
The trouble is, when the thread waits, it still holds the lock on the Lock Manager, which then causes deadlock...
I have been trying to solve this paradigm in a threadsafe way and have so far not come to much.
I am not sure the beast way of doing it. Maybe the way I am doing it is wrong, but I am not sure another way that is totally thread safe.
Didn't we answer this question, a few topics down???
To clarify, there are some really subtle race conditions that exist, if you need to do a wait() on two locks simultaneously. If this is your situation, I would suggest you create an explicit locking object, and have your two objects share the lock.
For the explicit locking object...
If you are using JDK 1.5, take a look at the ReentrantLock class and the Condition interface.
If you are using something eariler, you will need to get one from somewhere. In the Java Threads book, we create a quick and dirty one for this case. It is probably simple enough that you don't need to buy the book. Download the source code at: http://examples.oreilly.com/jthreads3/. The code should be located in the appendix package -- take a peek at the busyflag, and condvar class.
Thank you for your response... I have been having a lot of trouble with this.
My design is causing this to trouble me...trouble is that I can't change the method signatures or interface methods as it's for the SCJD.
Thanx for your help.
Ko Ko Naing
Joined: Jun 08, 2002
Originally posted by Henry Wong: If you are using JDK 1.5, take a look at the ReentrantLock class and the Condition interface.
Henry, Could u explain a bit about them with some examples so that we can get the idea quickly? I have been thinking that Generics and foreach features are the most important features of Tiger... If the ReentrantLock class can contribute a lot to Threads, we should pay attention to it also...
Ko Ko a good start to understand the concurrent features added in JDK1.5 would be the concurrent package of Doug Lea which represents the origin of the new packages. Than you can continue with looking at JDK 1.5 API for java.util.concurrent, java.util.concurrent.atomic and java.util.concurrent.locks.
Could u explain a bit about them with some examples so that we can get the idea quickly? I have been thinking that Generics and foreach features are the most important features of Tiger... If the ReentrantLock class can contribute a lot to Threads, we should pay attention to it also...
The ReentrantLock isn't doing anything that Java programmers haven't done for years. The only difference is that the support class is now part of the core, instead of a downloaded class... basically the ReentrantLock class implements an explicit lock. It basically implements synchronized functionality as a separate class... Now why would you want to do that?
First, is scope. With the synchronized keyword, the only scope available were at a block or method level. With explicit locks, the scope can be multiple methods, it can be based on a user session, or data model, or any scope you want.
Second, is usage. You can have many locks in an object. You can share a lock among many objects, or any combinations you like.
The Condition interface implements condition variables -- which are the wait-and-notify counterpart to the ReentrantLock class. If you use this new lock class, you need to use the new condition class.
Also, the condition variable is an independent object. A lock can have multiple condition variables. A classic case is of a buffer. You need one lock to protect the buffer, but many need multiple condition variables; one when the buffer is empty waiting for data, one when the buffer is full waiting for space. Without separate condition variables, you typically have to use a notify all instead of just a notify on the specific condition variable.