1.TLAB 分配概念:
TLAB,全称Thread Local Allocation Buffer, 即:线程本地分配缓存。这是一块线程专用的内存分配区域。TLAB占用的是eden区的空间。在TLAB启用的情况下(默认开启),JVM会为每一个线程分配一块TLAB区域
1.1 为什么需要TLAB?
这是为了加速对象的分配。由于对象一般分配在堆上,而堆是线程共用的,因此可能会有多个线程在堆上申请空间,而每一次的对象分配都必须线程同步,会使分配的效率下降。考虑到对象分配几乎是Java中最常用的操作,因此JVM使用了TLAB这样的线程专有区域来避免多线程冲突,提高对象分配的效率。
1.2 局限性:
TLAB空间一般不会太大(占用eden区),所以大对象无法进行TLAB分配,只能直接分配到堆上。
1.3 分配策略:
一个100KB的TLAB区域,如果已经使用了80KB,当需要分配一个30KB的对象时,TLAB是如何分配的呢?
此时,虚拟机有两种选择:第一,废弃当前的TLAB(会浪费20KB的空3.4 间);第二,将这个30KB的对象直接分配到堆上,保留当前TLAB(当有小于20KB的对象请求TLAB分配时可以直接使用该TLAB区域)。
JVM选择的策略是:在虚拟机内部维护一个叫refill_waste的值,当请求对象大于refill_waste时,会选择在堆中分配,反之,则会废弃当前TLAB,新建TLAB来分配新对象。
【默认情况下,TLAB和refill_waste都是会在运行时不断调整的,使系统的运行状态达到最优】
1.4 JVM参数解析
-XX:+UseTLAB启用TLAB默认启用
-XX:TLABRefillWasteFraction设置允许空间浪费的比例默认值:64,即:使用1/64的TLAB空间大小作为refill_waste值
-XX:-ResizeTLAB禁止系统自动调整TLAB大小
-XX:TLABSize指定TLAB大小单位:B,默认0
-XX:+EliminateAllocations 标量替换(默认打开),允许将对象打散分配到栈上