恭喜Spark2.0发布,今天会看一下2.0的源码。java
今天会讲下Tungsten内存分配和管理的内幕。Tungsten想要工做,要有数据源和数据结构,这时候会涉及到内存管理,而内存管理也是后续作不少分析和逻辑控制的基础。数组
咱们从内存分配的入口MemoryAllocator开始:数据结构
allocate() 分配的是一块连续干净的内存空间,若是不是干净的话,会先用zero方法,把里面填充为0。咱们注意到操做的数据结构都是MemoryBlock。jvm
MemoryBlock中pageNumber字段是public级别的,方便为TaskMemoryManager修改。内部有一个obj,onheap方式的话是一个字节数组,若是是offheap方式分配的是本地对象的指针。
其中会使用到一个Platform类,至关于Java Bean级别,提供对于数据一系列获取方法。大数据
至于具体的内存分配是如何操做的,咱们看一下具体的实现,首先是HeapMemoryAllocator,注释里说明能够分配16G原生数组。编码
从allocate里面看到,对于大数据量状况,会有一个Pool来管理,Pool中会预先存放各类尺寸的memory块,在获取时直接获取;小数据量的化通过字节对齐以后以后返回对象。spa
UnsafeMemoryAllocator中直接使用Platform的方法分配,这个方法没有实现,是经过jni,用C和C++实现的,其实就是用C语言分配个空间,跟new一个数组没有多大区别。指针
在申请内存时,若是不够的话会spill(溢出到磁盘),以后看下release的内容,继续进行获取。orm
不管是UNSAFE仍是HEAP的方式,都是采用了MemoryBlock来分配,这有一个很大的好处,是让咱们的内存使用者Task,能统一被内存的管理者TaskMemoryManager来分配.对象
TaskMemoryManager是如何来管理被task分配的内存呢,统一的方法是将地址编码成64字节的长整数。可是对于off-heap和on-heap编码方式是不一样。
咱们看下TaskMemoryManager中的代码,pageTable是个MemoryBlock的数组,会使用一个BitSet来进行索引。
最后,咱们有个问题,onheap模式下操做的时候,会根据offset来操做,有没有说操做多大的空间?
由于地址是64位的长整数,onheap方式得到逻辑地址时,会把起始offset和长度都编码进去,获取64位长整数时,有一套读取方式,虽然开始只知道offset,默认会知道下面有几位空间,也就是数据有多长。
DT大数据天天晚上20:00YY频道现场授课频道68917580