前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >重量级锁的加锁-等待-撤销流程

重量级锁的加锁-等待-撤销流程

作者头像
执生
发布2020-11-11 17:28:00
3480
发布2020-11-11 17:28:00
举报
文章被收录于专栏:立权的博客立权的博客

上述有三个队列,这些队列中的节点,都是线程包装成的 ObjectWaiter

在默认策略情况下:

1.entry_list 中的 节点是等待被唤醒的节点,持有重量级锁的线程执行 exit 方法(Java层面:退出上述 synchronized区或调用 wait()方法 会调用 (C++层面)exit方法),exit方法会唤醒 本队列的头节点(unpark),避免惊群

2.cxq_list 中的 节点是 获取锁失败后的线程的节点,exit 方法会检查 entry_list 是否为空,如果是空的,就会从 cxq_list 中拿 节点,放到 entry_list,放入顺序默认是 把 cxq_list 直接插到 entry_list 后面

3.wait_set 是调用 java 层面的 wait() 方法 的线程 该待的地方,需要注意的是 ,只有 notify 和 notifyAll 能够把 wait_set 中的节点 移入到 cxq_list (默认是把 cxq_list 插入到 wait_set 后面,wait_set 做为新的 cxq_list)

下面这个案例中,执行 a 的线程不会被唤醒。因为执行 b 的线程退出 sychronized 区只是 调用了 c++ 层面的 exit 方法,没有把 wait_set 中的 执行 a 的线程 放入到 cxq_list

调用 notify 和 notifyAll 方法 不会让 wait_set 里的线程 被 unpark ,只是让他们移入 cxq_list。

代码语言:javascript
复制
     Runnable a = () -> {
            synchronized (lock) {
                System.out.println("working");
                try {
                    lock.wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println("finalize");
            }
        };

        Runnable b = () -> {
            synchronized (lock) {
                System.out.println("doSomething");
            }
            System.out.println("done");
        };
        new Thread(a).start();
        Thread.sleep(1000);
        new Thread(b).start();

默认的 cxq_list 进入 entry_list 的方式:

默认的 wait_set 节点进入 cxq_list 的方式(notifyAll)

默认的 wait_set 节点进入 cxq_list 的方式(notify)

也就是,如果有一个线程 a 先进入 synchronized , 但是调用了 wait,这是线程 b 进入了 synchronized,b还在synchronized中执行,c线程又进来了。

此时 a 在 wait_set ,b 不在任何队列,c 在 cxq_list ,假如 b 调用 notify,会把 a 插到 c 前面,也就是 b 退出synchronized的时候,会唤醒 a,a退出之后再唤醒 c

也就是 曾经获得过锁的线程 被唤醒后 优先得到锁

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2020-11-06 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档