DEADLOCK IN JAVA MULTITHREADING
What is Deadlock in Java?
Deadlock in Java is a part of multithreading. Deadlock can occur in a situation when a thread is waiting for an object lock, that is acquired by another thread and second thread is waiting for an object lock that is acquired by first thread. Since, both threads are waiting for each other to release the lock, the condition is called deadlock.
A Java multithreaded program may suffer from the deadlock condition because the synchronized keyword causes the executing thread to block while waiting for the lock, or monitor, associated with the specified object.
In simple words, Deadlock is a condition where the threads are waiting infinitely for the resources(locks).
So, an example:
Resource A and resource B are used by process X and process Y
- X starts to use A.
- X and Y try to start using B
- Y 'wins' and gets B first
- now Y needs to use A
- A is locked by X, which is waiting for Y
Mutual exclusion - Each resource is either currently allocated to exactly one process or it is available. (Two processes cannot simultaneously control the same resource or be in their critical section).
Hold and Wait - processes currently holding resources can request new resources.
No preemption - Once a process holds a resource, it cannot be taken away by another process or the kernel.
Circular wait - Each process is waiting to obtain a resource which is held by another process.
Now Let’s Write a Program and See What’s the Issue With This Program....
There are two threads in the program and two locks are created. Each thread needs both locks to execute the critical section. Hence both threads are synchronized on these two locks but in a different order.
- The thread-1 first acquires lock1 and then lock2 to execute completely.
- But the thread-2 first acquires lock2 and then lock1 to execute completely.
Now let’s go through the program and find why the deadlock can occur?
public class Main { | |
public static Object lock1 = new Object(); | |
public static Object lock2 = new Object(); | |
public static void main(String[] args) { | |
new Thread1().start(); | |
new Thread2().start(); | |
} | |
private static class Thread1 extends Thread { | |
@Override | |
public void run() { | |
synchronized (lock1) { | |
System.out.println("Thread-1 acquired lock1"); | |
try { | |
Thread.sleep(1000); | |
} catch (InterruptedException e) { | |
System.out.println("Thread-1 interrupted."); | |
} | |
System.out.println("Thread-1 waiting for lock2"); | |
synchronized (lock2) { | |
System.out.println("Thread-1 acquired lock2"); | |
try { | |
Thread.sleep(1000); | |
} catch (InterruptedException e) { | |
System.out.println("Thread-1 interrupted."); | |
} | |
} | |
System.out.println("Thread-1 releases lock2"); | |
} | |
System.out.println("Thread-1 releases lock1"); | |
} | |
} | |
private static class Thread2 extends Thread { | |
@Override | |
public void run() { | |
synchronized (lock2) { | |
System.out.println("Thread-2 acquired lock2"); | |
try { | |
Thread.sleep(1000); | |
} catch (InterruptedException e) { | |
System.out.println("Thread-2 interrupted."); | |
} | |
System.out.println("Thread-2 waiting for lock1"); | |
synchronized (lock1) { | |
System.out.println("Thread-2 acquired lock1"); | |
try { | |
Thread.sleep(1000); | |
} catch (InterruptedException e) { | |
System.out.println("Thread-2 interrupted."); | |
} | |
} | |
System.out.println("Thread-2 releases lock1"); | |
} | |
System.out.println("Thread-2 releases lock2"); | |
} | |
} | |
} |
OUTPUT:
Comments
Post a Comment