Programmatic deadlock detection in java

前端 未结 9 1392
无人及你
无人及你 2020-11-29 17:36

How can I programmatically detect that a deadlock has occurred in a Java program?

9条回答
  •  予麋鹿
    予麋鹿 (楼主)
    2020-11-29 18:06

    JArmus is a library for deadlock detection and avoidance. It includes support for: Thread.join, CyclicBarrier, CountDownLatch, Phaser, and ReentrantLock.

    To use JArmus you need to instrument your code. Either through one of its instrumented classes or automatically with the JArmus instrumentar jarmusc.

    java -jar jarmusc.jar yourprogram.jar checkedprogram.jar

    The input yourprogram.jar is the program you want to check. The output is the same program with checks to automatically find any deadlock.

    Barriers need some help

    Verifying deadlocks with classes CyclicBarrier, CountDownLatch, Phaser is a bit tricky --- for example, JConsole cannot detect these types of deadlocks. JArmus needs a little help from you: you must specify which threads are influencing synchronization, we call these registered threads.

    As soon as possible, the thread must mark itself as registered. A good place to mark registered threads is at the beginning method Runnable.run. JArmus.register(latch);

    Example

    The following program that deadlocks is correctly identified by JArmus:

    final CountDownLatch latch = new CountDownLatch(2);
    final CyclicBarrier barrier = new CyclicBarrier(2);
    final Queue exceptions = new ArrayDeque<>();
    Thread t1 = new Thread(new Runnable() {
        @Override
        public void run() {
            try {
                JArmus.register(barrier); // do not forget to register!
                JArmus.register(latch); // do not forget to register!
                latch.countDown();
                latch.await();
                barrier.await();
            } catch (Exception e) {
                exceptions.add(e);
            }
        }
    });
    Thread t2 = new Thread(new Runnable() {
        @Override
        public void run() {
            try {
                JArmus.register(barrier); // do not forget to register!
                JArmus.register(latch); // do not forget to register!
                barrier.await();
                latch.countDown();
                latch.await();
            } catch (Exception e) {
                exceptions.add(e);
            }
        }
    });
    t1.start();
    t2.start();
    

提交回复
热议问题