I have a controller class as follows:
public class Controller {
private Driver driver;
public void method1() {/**/}
public void method2() {/**/}
public void method3() {/**/}
}
Each method uses the driver
to perform some action. method2
however is a longer-running process and requires a lock on the driver
, because if the other methods use the driver
while method2
is running, then errors will occur.
Now the way I am currently set up, I have implemented a ReentrantLock
with fair scheduling in the controller's calling class which takes care of thread safety as follows:
public class Caller {
private static final Lock LOCK = new ReentrantLock(true);
private Controller controller;
public void startStuff() { // Runs in multiple threads.
...
...
LOCK.lock();
try {
controller.method1();
} finally {
LOCK.unlock();
}
...
...
LOCK.lock();
try {
controller.method2();
} finally {
LOCK.unlock();
}
}
}
I would instead like to make the Controller
class thread safe instead of having any calling classes deal with it. The way I assume this is to be done is by implementing the try-finally block at the beginning and end of each method, but I have around 15 methods in the class. Is this really the way to do it? It seems like a tonne of boilerplate code:
public class Controller {
private static final Lock LOCK = new ReentrantLock(true);
private Driver driver;
public void method1() {
LOCK.lock();
try {
/**/
} finally {
LOCK.unlock();
}
}
public void method2() {
LOCK.lock();
try {
/**/
} finally {
LOCK.unlock();
}
}
public void method3() {
LOCK.lock();
try {
/**/
} finally {
LOCK.unlock();
}
}
}
I cannot just add synchronized
to each method because I require fair scheduling for the application to work, and using a ReentrantLock
works perfectly.
How exactly do I make the Controller
class thread-safe using a ReentrantLock
?