java

位置:IT落伍者 >> java >> 浏览文章

Java偏向锁实现原理(Biased Locking)


发布日期:2021年04月20日
 
Java偏向锁实现原理(Biased Locking)

Java 偏向锁(Biased Locking)是Java引入的一项多线程优化它通过消除资源无竞争情况下的同步原语进一步提高了程序的运行性能

轻量级锁也是一种多线程优化它与偏向锁的区别在于轻量级锁是通过CAS来避免进入开销较大的互斥操作而偏向锁是在无竞争场景下完全消除同步连CAS也不执行(CAS本身仍旧是一种操作系统同步原语始终要在JVM与OS之间来回有一定的开销)

所谓的无竞争场景举个例子就是单线程访问带同步的资源或方法

偏向锁实现原理

偏向锁顾名思义它会偏向于第一个访问锁的线程如果在接下来的运行过程中该锁没有被其他的线程访问则持有偏向锁的线程将永远不需要触发同步

如果在运行过程中遇到了其他线程抢占锁则持有偏向锁的线程会被挂起JVM会尝试消除它身上的偏向锁将锁恢复到标准的轻量级锁(偏向锁只能在单线程下起作用)

通过下图可以更直观的理解偏向锁

这张图省略了轻量级锁相关的几处步骤将关注点更多地聚焦在偏向锁的状态变化上

偏向模式和非偏向模式 在下面的mark word表中主要体现在thread ID字段是否为空

挂起持有偏向锁的线程 这步操作类似GC的pause但不同之处是它只挂起持有偏向锁的线程(非当前线程)

在抢占模式的橙色区域说明中有提到指向当前堆栈中最近的一个lock record(在轻量级锁原理一文有讲到lock record是进入锁前会在stack上创建的一份内存空间)

这里提到的最近的一个lock record其实就是当前锁所在的stack frame上分配的lock record

整个步骤是从偏向锁恢复到轻量级锁的过程

偏向锁也会带来额外开销

在JDK偏向锁是默认启用的它提高了单线程访问同步资源的性能

但试想一下如果你的同步资源或代码一直都是多线程访问的那么消除偏向锁这一步骤对你来说就是多余的事实上消除偏向锁的开销还是蛮大的

所以在你非常熟悉自己的代码前提下大可禁用偏向锁 XX:UseBiasedLocking

上一篇:全面了解Java媒体架构JMF

下一篇:使用JAVA数字证书做数字签名认证