死锁及排查

99 阅读1分钟

什么是死锁?

死锁是指两个或两个以上的线程在执行过程中,因争夺资源而造成的一种互相等待的现象,若无外力干涉那它们都将无法推进下去,如果系统资源充足,进程的资源请求都能够得到满足,死锁出现的可能性就很低,否则就会因争夺有限的资源而陷入死锁。

图像.jpg

产生死锁的原因是什么?

1、系统资源不足 2、进程运行推进的顺序不合适 3、资源分配不当

一个死锁代码

package com.atguigu.juc.senior.prepare;

import java.util.concurrent.TimeUnit;
public class DeadLockDemo
{
    public static void main(String[] args)
    {
        final Object objectLockA = new Object();
        final Object objectLockB = new Object();

        new Thread(() -> {
            synchronized (objectLockA)
            {
                System.out.println(Thread.currentThread().getName()+"\t"+"自己持有A,希望获得B");
                //暂停几秒钟线程
                try { TimeUnit.SECONDS.sleep(1); } catch (InterruptedException e) { e.printStackTrace(); }
                synchronized (objectLockB)
                {
                    System.out.println(Thread.currentThread().getName()+"\t"+"A-------已经获得B");
                }
            }
        },"A").start();

        new Thread(() -> {
            synchronized (objectLockB)
            {
                System.out.println(Thread.currentThread().getName()+"\t"+"自己持有B,希望获得A");
                //暂停几秒钟线程
                try { TimeUnit.SECONDS.sleep(1); } catch (InterruptedException e) { e.printStackTrace(); }
                synchronized (objectLockA)
                {
                    System.out.println(Thread.currentThread().getName()+"\t"+"B-------已经获得A");
                }
            }
        },"B").start();

    }
}

死锁的四个必要条件

1、互斥条件:一个资源每次只能被一个进程使用;

2、请求与保持条件:一个进程因请求资源而阻塞时,对已获得的资源保持不放;

3、不剥夺条件:进程已获得的资源,在末使用完之前,不能强行剥夺;

4、循环等待条件:若干进程之间形成一种头尾相接的循环等待资源关系;

如何排查一个死锁?

1、通过jps -l查看进程信息后再通过jstack 进程编号,查看线程状态

image.png

image.png

2、win+R输入jconsole打开java监视和管理控制台查看。