当前位置: 首页 > news >正文

java锁升级过程

整体过程:无锁->偏向锁->轻量级锁->重量级锁
1.无锁:加锁对象被实例化,但还未有线程调用,此时对象头中的markword记录的是hashcode、锁标识等该对象的初始信息。
2.偏向锁:
2.1 初次获取:当线程A获取锁时,根据当前加锁对象锁标识进行不同的操作,如果是无锁,进行CAS将线程ID写入markword替换hashcode,写入成功,则表示线程获取锁成功,代码执行完毕释放锁后,也不会将markword内容恢复。
2.2 再次获取:线程A再次尝试获取,但markword内容已经被修改为线程ID,直接获取,不需要再进行set操作。
3.轻量级锁:
3.1 epoch不相等:该锁已经被A使用,且markword信息已被修改为A线程id,此时线程B来竞争锁,线程id没匹配上,但是该加锁对象的epoch和类的epoch也不相等,代表加锁对象不是最新版本,线程B可以CAS获取而不进行锁升级。
3.2 epoch相等:需要JVM介入,发生锁撤销(该加锁对象的markword被还原为无锁状态),在一个安全点(Stop The World)进行检查线程A是否完全释放资源,如果没有释放,升级为轻量级锁,jvm替A在栈上创建一条lockrecord,线程A执行结束后释放锁,线程B通过CAS来竞争锁;如果释放了,则线程B在栈创建lockrecord,通过CAS将这条lockrecord写入到加锁对象的markword中,同时将无锁的markword信息记录到lockrecord的displaced markword中,还把加锁对象的引用也存到了lockrecord中(用于释放锁时还原无锁状态)。
3.3 批量重偏向:假设一个类有100个加锁对象,JVM会记录这100个对象发生锁撤销的次数,当达到阈值时(20),使类的epoch+1(版本更新了,属于线程A的加锁对象是老版本),导致类的epoch和加锁对象的epoch不相等,这样线程B依然通过一次CAS就获取到了加锁对象,而不用再等升级成轻量级锁。(达到阈值的20个已经升级成轻量级锁不可逆,剩余的80个因epoch更新而直接CAS继续维持偏向锁状态)。
4.重量级锁:线程B尝试CAS获取被线程A持有的加锁对象,没成功,发生自旋(while true里一直CAS),当自旋达到阈值后,升级成重量级锁,引入monitor资源监视器,上升到了操作系统级别,线程B进入阻塞状态进入等待池,等线程A释放资源后唤醒线程B。
4.1 锁池:自旋失败后,进入锁池等待锁释放,等待被唤醒,锁池内线程优先级比等待池要高。
4.2 等待池:线程A持有锁,但是需要等其他线程的资源,所以调用wait()使其释放锁(sleep()方法不会释放锁!),由于在JVM看来是主动释放锁,优先级在锁池之后。

http://www.rkmt.cn/news/3133.html

相关文章:

  • GAS_Aura-Setting Up Click to Move
  • 【刷题笔记】cf808f
  • C# 操作 DXF 文件指南
  • 玩转n8n测试自动化:核心节点详解与测试实战指南
  • (笔记)多项式基础 FFT
  • MySqlException: Incorrect string value: \xE6\x99\xBA\xE8\x83\xBD... for column FieldName at row 1
  • Burp Suite Professional 2025.9 发布 - Web 应用安全、测试和扫描
  • 征稿倒计时3天/武汉科技大学主办/医学人工智能/现可享优惠
  • 生成更智能,调试更轻松,SLS SQL Copilot 焕新登场!
  • NOI linux使用教程
  • springboot 文件处理框架
  • 将 seata 2.5 发布到私服
  • 一些感悟
  • 五款免费低代码平台深度横评:斑斑、简道云、宜搭、氚云、织信如何选?
  • 从需求出发:教你判断选斑斑还是织信
  • python如何在函数中使用全局变量?
  • C++ - STL - 键值对pair
  • 第四天学习:LSTM
  • MATLAB的稀疏自编码器实现
  • 题解:P2157 [SDOI2009] 学校食堂
  • vue3 与 element-plus
  • 第二周作业
  • 代码随想录算法训练营第一天| 704.二分查找、27.移除元素、977.有序数组的平方
  • 强制横屏 ios
  • 张量链式法则(下篇):揭秘Transpose、Summation等复杂算子反向传播,彻底掌握深度学习求导精髓!
  • 美客分销商城小程序系统介绍
  • C++ - STL - 静态数组array
  • C++ - STL - 集合set(元素具有排他性)
  • 批量删除所有 LXC 容器以及用户名
  • C++ - STL - 动态数组vector(矢量)