美文网首页
synchronized分析

synchronized分析

作者: 大黑跟小白的日常 | 来源:发表于2020-07-20 00:51 被阅读0次

先讲CAS

如何解释

compare and swap
compare and set
compare and exchange

i++问题分析

常规操作

上锁,保证i++的同步操作,保证原子性。比如synchronized。

不加锁如何实现i++线程安全?CAS

image.png
如果不再是曾经的值,则可以重试,直到成功为止。
image.png
但是
比较 & 交换 是两个动作,底层是基于CPU指令实现的原子性。
CPU提供了指令支持这两个动作合二为一。
然而:在多核CPU情况下,这个指令执行的前提是要保证被操作值的内存可见性。还有就是,虽然CPU指令能将操作合二为一,那么多核CPU,可以同时执行指令cmpxchg又该如何?

ABA问题

具体算不算问题,得看具体业务场景
------------------------------------------------------------------------------> 时间t
线程1 读取i 值为0
线程2 ----------将值修改为1
线程3 --------------将值又修改为0
线程1 --------------------将值修改为1(这里线程1认为没人修改过i值)
ps:比如你女朋友跟你分手了,然后又经历了别的男人,你回来之后她还是你原来那个女朋友,那具体算不算问题,得看你怎么看。

如何解决

对i值加版本号,任意一次成功修改,针对当前i值的版本号+1,可以根据版本号判断是否还是原来的她;
ps:当初你跟她分手时,她的版本号是1.0,然后你又回来找她时,她版本号是99.0,然后你就知道她这过程中经历了多少次,然后你采取什么样的措施来处理就是你自己的事情;原谅她。

CAS具体运用

AtomicInteger

image.png
image.png
do-while...直到比较交换成功为止
image.png
底层native方法,c/c++实现
image.png
unsafe.cpp-------c++代码
image.png
image.png
Atomic::cmpxchg
image.png
最终
image.png
image.png
汇编语言实现 asm
image.png
一个宏操作
image.png
程序会根据当前处理器的类型来决定是否为cmpxchg指令添加lock前缀。如果程序是在多处理器上运行,就为cmpxchg指令加上lock前缀(lock cmpxchg)。反之,如果程序是在单处理器上运行,就省略lock前缀(单处理器自身会维护单处理器内的顺序一致性,不需要lock前缀提供的内存屏障效果)。
image.png
这里看到有一个LOCK_IF_MP,作用是如果是多处理器,在指令前加上LOCK前缀,因为在单处理器中,是不会存在缓存不一致的问题的,所有线程都在一个CPU上跑,使用同一个缓存区,也就不存在本地内存与主内存不一致的问题,不会造成可见性问题。然而在多核处理器中,共享内存需要从写缓存中刷新到主内存中去,并遵循缓存一致性协议通知其他处理器更新缓存。
Lock在这里的作用:
  1. 在cmpxchg执行期间,锁住内存地址[edx],其他处理器不能访问该内存,保证原子性。即使是在32位机器上修改64位的内存也可以保证原子性。
  2. 将本处理器上写缓存全部强制写回主存中去,也就是写屏障,保证每个线程的本地内存与主存一致。
  3. 禁止cmpxchg与前后任何指令重排序,防止指令重排序。
    可见CAS操作具有与读写volatile变量一致的作用,都能保证可见性。

最终实现 总结

lock cmpxchg //指令

硬件

lock指令在执行后面指令的时候锁定一个北桥信号。(不采用锁总线的方式)

用户态、内核态

操作系统能做的事情

普通程序能做的事情

需要向操作系统申请

JVM工作在用户态,锁资源,需要通过操作系统向申请。
通过用户态到内核态的调用(0x80)申请锁,申请到锁还需要从内核态返回给用户态。
申请锁时都需要经过操作系统,都需经过用户态到内核态的转换。

JDK早期,synchronized重量级锁,申请锁资源必须通过kernel(内核),系统调用。

ps:阿里P9的问题:0x80的执行过程

markword

对象内存布局

跟JVM虚拟机实现相关

hotspot实现

对象头 object header
8个字节markword 标记字
4个字节的class point 类型指针
?个字节 instance data成员 得看存在多少成员变量及类型
总大小需要 8字节对齐,所以还存在第四段 对齐 字节数

查看对象大小的工具 Java Object Layout JOL


image.png

打印分析


image.png
Object没有成员属性,固没有instance data
image.png

需要8个字节对齐


image.png

再看一个


image.png image.png image.png image.png

其中alignment/padding gap,属于属性间隙对齐,属性的总大小为4字节的整数倍


image.png
image.png image.png image.png

相关文章

网友评论

      本文标题:synchronized分析

      本文链接:https://www.haomeiwen.com/subject/jezrkktx.html