轻量级锁加锁
线程在执行同步块之前,JVM会先在当前线程的栈帧中创建用于存储锁记录的空间,并将对象头中的Mark Word复制到锁记录中,官方成为Displaced Mark Word。然后线程尝试使用CAS将对象头中的Mark Word替换为指向锁记录的指针。
- 如果成功,当前线程获得锁,如果失败,表示其他线程竞争锁,当前线程便尝试使用自旋锁来获取锁
- 如果仍未获取到锁,则升级为重量级锁。
轻量级锁解锁
轻量级锁解锁时,会使用原子的CAS操作将Displaced Mark Word替换回到对象头
- 如果成功,则表示没有竞争发生
-
如果失败,表示当前锁存在竞争,升级为重量级锁。
因为自旋会消耗CPU,为了避免无用的自旋(比如获取锁的线程被阻塞了),一旦锁升级成重量锁,就不会再恢复到轻量级锁状态。当锁处于这个状态下,其他线程试图获取锁时,都会被阻塞住,当持有锁的线程释放锁之后会唤醒这些线程,被唤醒的线程就会进行新一轮的夺锁之争。