java并发编程系列第一篇:多核CPU缓存架构

直接开始........

1.cpu缓存架构有哪些内容?

现代计算机模型是基于-冯诺依曼计算机模型,主要包括五大核心部分,1.控制器,2.运算器,3.存储器,4.输入,5.输出。
图如下:
                                  java并发编程系列第一篇:多核CPU缓存架构_第1张图片
再贴一张CPU原理图
                                  java并发编程系列第一篇:多核CPU缓存架构_第2张图片
大致意思是说,CPU在运算数据的时候(比如 1+1=2),会首先从CUP寄存器读取数据(速度最快,因为内置在CPU里面),如果没有,就从三级缓存里读取,如果三级缓存也没有,则会经过系统总线及内存总线,从总存储器中读取(此处的总存储器主要是指主内存)。

2.工作原理

工作原理如下:

首先CPU工作的时候,由控制单元充当大脑,负责协调。让运算单元做运算的时候,会首先从最靠近CPU的寄存器(其实是和CPU一体的)上读取数据,在寄存器上有CPU运行的常用指令,如果寄存器上没有想要的数据,则就从三级缓存的L1级缓存中获取,如果L1取到数据了,会加载到寄存器中,再转输给CPU运算单元。如果L1中没有,则从L2级缓存中读取,同理,如果没有,则从L3中取。如果L3中也没有,这个时候,就比较麻烦了。要从主内存中取。而从主内存中取的时候,会经过系统总线及内存总线。这时因受到总线的限制,速度会大大降低。而且会存在众多问题。这些问题会在下面注意事项中讲到。而接下来的一系列并发文章,都是围绕着怎么解决这些事情展开发。

原理图也来一张

                                  java并发编程系列第一篇:多核CPU缓存架构_第3张图片

3.注意事项

1.缓存一致性问题
在多处理器系统中,每个处理器都有自己的高速缓存,而它们又共享同一主内存
(MainMemory)。基于高速缓存的存储交互很好地解决了处理器与内存的速度矛盾,但是
也引入了新的问题:缓存一致性(CacheCoherence)。当多个处理器的运算任务都涉及同一
块主内存区域时,将可能导致各自的缓存数据不一致的情况,如果真的发生这种情况,那同步
回到主内存时以谁的缓存数据为准呢?
为了解决一致性的问题,需要各个处理器访问缓存时都 遵循一些协议,在读写时要根据协议来进行操作。常用的方法是总线加锁或是缓存一致性协议- MESI 
                        java并发编程系列第一篇:多核CPU缓存架构_第4张图片
这里重点说一个什么是缓存一致性协议mesi:
概念:CPU最小存储单元:缓存行
MESI代表的四种状态:
M:修改
E:独享。互斥
S:共享
I:无效
MESI缓存一致性协议原理:
假如现在有CPU1和CPU2,主内存有变量X= 1 。现在要做 x+1的操作。
如果在变量 x = 1 上加上 volatile,则就会触发MESI
当CPU1从主内存中读取到X=1时,CPU1会把此变量标记成独享状态
并监听总线,是否有其它CPU去读取此变量
当CPU2从主内存中读取X=1变量时,CPU1会通过嗅探机制监听到。
此时CPU1的X变量会变成共享状态。继续进行计算,计算完变成X=2。
此时要回写到主内存之前。先锁住缓存行。并标记X变量为修改状态。并向总线发消息。
其它CPU2监听总线时,会监听到,并把X标记成无效状态。
CPU1把变量X=2回写到主内存后,会由修改状态变成独享状态。
此时,如果CPU2如果想修改X变量时,要重启从主内存中读取。然后开始新的轮回。
 
2.指令重排序问题
为了使得处理器内部的运算单元能尽量被充分利用,处理器可能会对输入代码进行乱序执 行(Out-Of-Order Execution)优化,处理器会在计算之后将乱序执行的结果重组,保证该 结果与顺序执行的结果是一致的,但并不保证程序中各个语句计算的先后顺序与输入代码中的 顺序一致。因此,如果存在一个计算任务依赖另一个计算任务的中间结果,那么其顺序性并不 能靠代码的先后顺序来保证。
与处理器的乱序执行优化类似,Java虚拟机的即时编译器中也有 类似的指令重排序(Instruction Reorder)优化

4.心得

1.了解计算机内部的工作原理。
2.了解了为什么多线程时,数据会存在安全问题(数据不一致)。

3.怎么可以充分利用计算机资源,又保证不会出现问题

你可能感兴趣的:(IT,java)