読者です 読者をやめる 読者になる 読者になる

「Java」ロック獲得待ちを表すスレッドダンプ

スレッドロック獲得待ちとなっている状態のスレッドダンプを取得してみます。サンプルは簡単に以下のようなものを用意しました。

package test.threaddump;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class ThreadExample {

  private static ExecutorService es = Executors.newFixedThreadPool(5);
  private static Object lock = new Object();

  public static void main(String[] args) {
    for (int i = 0; i < 10; i++) {
      es.execute(new Runnable() {
        @Override
        public void run() {
          synchronized (lock) {
            System.out.println("[" + Thread.currentThread().getName() + "] get lock !!");
            try {
              Thread.sleep(3 * 1000);
            } catch (InterruptedException e) {
              e.printStackTrace();
            }
          }
        }
      });
    }
    es.shutdown();
  }
}


ExecutorService で 10 回タスクを実行していますが、タスクの中で lock オブジェクトのロックを獲得して 3 秒止まるという処理としています。後からタスクを実行するスレッドは lock オブジェクトのロックが獲得できませんので、しばらくロック獲得待ち状態となります。その際のスレッドダンプが以下になります。

2016-04-19 23:21:02
Full thread dump Java HotSpot(TM) 64-Bit Server VM (25.74-b02 mixed mode):

"DestroyJavaVM" #16 prio=5 os_prio=0 tid=0x00000000025f2800 nid=0x1e94 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"pool-1-thread-5" #15 prio=5 os_prio=0 tid=0x000000001bd02000 nid=0x29ec waiting on condition [0x000000001cdee000]
   java.lang.Thread.State: TIMED_WAITING (sleeping)
	at java.lang.Thread.sleep(Native Method)
	at test.threaddump.ThreadExample$1.run(ThreadExample.java:19)
	- locked <0x0000000780228e20> (a java.lang.Object)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
	at java.lang.Thread.run(Thread.java:745)

"pool-1-thread-4" #14 prio=5 os_prio=0 tid=0x000000001bd01000 nid=0x24fc waiting for monitor entry [0x000000001ccee000]
   java.lang.Thread.State: BLOCKED (on object monitor)
	at test.threaddump.ThreadExample$1.run(ThreadExample.java:17)
	- waiting to lock <0x0000000780228e20> (a java.lang.Object)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
	at java.lang.Thread.run(Thread.java:745)

"pool-1-thread-3" #13 prio=5 os_prio=0 tid=0x000000001bd00800 nid=0x4f4 waiting for monitor entry [0x000000001cbef000]
   java.lang.Thread.State: BLOCKED (on object monitor)
	at test.threaddump.ThreadExample$1.run(ThreadExample.java:17)
	- waiting to lock <0x0000000780228e20> (a java.lang.Object)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
	at java.lang.Thread.run(Thread.java:745)

"pool-1-thread-2" #12 prio=5 os_prio=0 tid=0x000000001bcfd800 nid=0x3b9c waiting for monitor entry [0x000000001caef000]
   java.lang.Thread.State: BLOCKED (on object monitor)
	at test.threaddump.ThreadExample$1.run(ThreadExample.java:17)
	- waiting to lock <0x0000000780228e20> (a java.lang.Object)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
	at java.lang.Thread.run(Thread.java:745)

"pool-1-thread-1" #11 prio=5 os_prio=0 tid=0x000000001bcfd000 nid=0x1df4 waiting for monitor entry [0x000000001c9ef000]
   java.lang.Thread.State: BLOCKED (on object monitor)
	at test.threaddump.ThreadExample$1.run(ThreadExample.java:17)
	- waiting to lock <0x0000000780228e20> (a java.lang.Object)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
	at java.lang.Thread.run(Thread.java:745)

 --- ( 以下略 ) ---


上記ですと、"pool-1-thread-5" が 0x0000000780228e20 のロックを獲得してスリープ状態、ほかのスレッド達は waiting to lock <0x0000000780228e20> (a java.lang.Object) とあるようにロック獲得待ち状態となっていることが確認できます。

非常に簡単ですが、以上になります。

[ 環境情報 ]
Windows 7 SP1
Java SE 8 Update 74