同步队列阻塞器AQS的执行流程,案例图

假设有A、B、C三个线程使用AQS抢占资源,A先到,抢占一段时间后释放,B后到,C最后到

同步队列阻塞器里面,初始,有head、tail指向null,state=0,当前抢占线程null,其中head,tail为Node类型,state为int类型,exclusiveOwnerThread(当前抢占线程)为Thread类型。

Node对象类型关键属性:next下一个节点指向、pre前一个节点指向、Thread拥有节点线程、waitStatus等待状态。

此时A线程最先到,通过CAS抢占资源。

state设置为1,代表已抢占。

抢占的线程为A,exclusiveOwnerThread=A

A抢到资源后继续执行。

此时B线程来到,发现同步队列阻塞器state=1,也就是已经被占用了,而且占有线程是A,所以B尝试CAS抢占资源,失败后开始排队。

排队流程是,线程B发现如果tail指向为null,先创建一个虚拟节点,同步队列阻塞器的head,tail指向虚拟节点

然后把线程B封装成Node节点。

线程B的pre指向虚拟节点,如果tail指向NodeB成功,则虚拟节点的next指向NodeB

把虚拟节点的等待标志设为-1,然后阻塞线程B

此时C线程来到,发现同步队列阻塞器state=1,也就是已经被占用了,而且占有线程是A,所以C尝试CAS抢占资源,失败后开始排队。

此时C发现tail指向不为null,所以直接在tail的指向,也就是NodeB后面排队。

节点C的pre先指向节点B

tail的节点如果指向节点C成功,节点B的next指向节点C

C线程会把节点B的等待状态设置为-1,然后阻塞线程C

如果此时A执行完了,会清空state和占有线程,让虚拟线程的waitStatus为0,并释放线程B

线程B释放后,会去占有资源,state=1,占有线程为线程B

会把虚拟节点置空,把NodeB变为虚拟节点

1.让head指向节点B

2.节点B的线程为null

3.节点B的pre指向null

4.虚拟节点的next指向null(为了被GC)

相关推荐
迷枫7121 小时前
SQL性能排查记录
java·数据库·sql
渡我白衣1 小时前
深入理解 Transformer:Transformer 究竟是什么?
java·linux·开发语言·c++·人工智能·深度学习·transformer
Tisfy4 小时前
LeetCode 1927.求和游戏:抵消+看最值
java·leetcode·游戏·题解·博弈论
东风破_9 小时前
从输入 juejin.cn 到看到页面:DNS、Nginx、服务器集群与 CDN 到底在做什么?
后端·mysql
东风破_9 小时前
从 0 设计一个博客数据库:用户、头像与文章表应该怎么建?
后端·mysql
大鸡腿同学10 小时前
黄仁勋点透的 AI 真相:能实现你知道但做不到的,却实现不了你不知道的
后端
FfHUCisI10 小时前
Go 编译过程全景
开发语言·后端·golang
FfHUCisI10 小时前
Golang 语法分析与 AST:Parser 与 go/ast
开发语言·后端·golang
秋饼10 小时前
JDK 27 企业级 AI 服务落地实战:G1 默认、紧凑对象头、后量子 TLS 与 JFR 脱敏全解析
java·ai·技术分享·后端开发
卓怡学长11 小时前
w176基于SpringBoot的医院管理系统
java·spring boot·spring·maven·intellij-idea