Hardware Stoage
RAM: 一般一次读取一个cache line 64 bytes;对于ram自身,一次访存64 bit,即8 bytes。ram的一个cell 4bit/8bit/16bit
HDD: 一般一次读取一个sector 512 bytes;
OS Memory
page (一般用于os虚拟内存,default 4kB)& block(一般用于fs物理文件,大多default 4kB)
memory-> page(4kB) <-swap
memory-> block(4kB) <-disk
# tune2fs -l /dev/sda1 |grep 'Block size'
Block size: 4096
# getconf PAGESIZE
4096
free
total used free shared buffers cached
Mem: 7856 7304 551 779 31 1161
-/+ buffers/cache: 6111 1744
Swap: 8062 4431 3631
total(Mem) = total phi memory
used(Mem) = used phi memory
shard(Mem) = shared phi memory
buffers(Mem) = cached disk block = Metadata/Directory phi memory
cached(Mem) = cached file pages = Content/File phi memory
total os phi memopry 7856=(Mem)used + (Mem)free=(-/+ buffers/cache)used + (-/+ buffers/cache)free
left available phi memory 1744= (Mem)free + (Mem)buffers + (Mem)cached = (-/+ buffers/cache)
-/+ buffers/cache: 6111 1744
=>
Mem: total=Mem(total):7856 used=Mem(used)-buffers/cache:7304-(31+1161) free=Mem(free) + buffers/cache:551+(31+1161)
top
KiB Mem: 8044800 total, 7479220 used, 565580 free, 31720 buffers
KiB Swap: 8256508 total, 4537380 used, 3719128 free. 1184292 cached Mem
JVM Memory
( -Xss单个线程栈内存用大小 )
(-Xms初始堆内存大小,包含新生代和老年代 -XX:初始PermSize持久代内存大小 => JVM 8 -XX:MetaspaceSize初始元空间内存大小)
(-Xmx初最大堆内存大小,包含新生代和老年代 -XX:最大PermSize持久代内存大小 => JVM 8 -XX:MaxMetaspyuSize最大元空间内存大小)
分配预估
- about (-Xmx) * 1.5
- (-Xmx) + (-XX:MaxPermSize) + Thread_Number * (-Xss) + Others
Others: NIO + Socker_Buffer + JNI ... (about 5% of the JVM memory)
setttings
-XX:+PrintFlagsInitial
-XX:+PrintFlagsFinal
-XX:+PrintCommandLineFlags
-XX:+PrintReferenceGC
-XX:-PrintGC
-XX:+PrintGCDetails
-XX:+PrintGCTimeStamps
-XX:+PrintAdaptiveSizePolicy
-XX:+PrintClassHistogram
-XX:+PrintHeapAtGC
-XX:+PrintCodeCache
-XX:-PrintCompilation
-XX:+PrintTenuringDistribution
-Xloggc:<file>
-XX:+HeapDumpOnOutOfMemoryError
-XX:HeapDumpPath=<path>
-XX:OnOutOfMemoryError="sh ~/cleanup.sh"
-Xms 物理内存的1/64
-Xmx 物理内存的1/4
-Xmn eden+ 2 survivor space, -XX:MaxNewSize and -XX:NewSize use the same value
-Xss 1m, -XX:ThreadStackSize
1,整个堆包括年轻代,老年代。其中年轻代又包括一个Eden区和两个Survivor区
-XX:InitialHeapSize==<value> 即-Xms
-XX:MaxHeapSize=<value> 即-Xmx
-XX:MinHeapFreeRatio=<value>设置JVM堆最小空闲比率(default 40)
-XX:MaxHeapFreeRatio=<value>设置JVM堆最大空闲比率(default 70)
老年代:三分之二的堆空间
年轻代:三分之一的堆空间
eden区: 8/10 的年轻代空间
survivor0 : 1/10 的年轻代空间
survivor1 : 1/10 的年轻代空间
2,年轻代
-XX:NewSize=<value> 设置JVM堆的‘新生代’的默认大小
-XX:MaxNewSize=<value> 设置JVM堆的‘新生代’的最大大小
3.年老代
-XX:OldSize=<value> 设置JVM堆的‘老生代’的大小
4,年轻代和老年代的比例:
-XX:NewRatio=<value>(年轻代和老年代的比值,年轻代多,除去持久代, defalult 2)
当设置了-XX:+UseConcMarkSweepGC后,会使-XX:NewRatio=4失效,此时需要使用-Xmn设置年轻代大小
5,Eden与Survivor的比例
-XX:InitialSurvivorRatio=<value> (新生代Eden/Survivor空间的初始比例)
-XX:SurvivorRatio=<value> (Eden区与两个Survivor区的比值,Eden区多, default 8)
6.元数据区: 类数据、方法数据,(注意:static field还存在GC heap中),
如果不指定MaxMetaspaceSize的话,Metaspace的大小仅受限于native memory的剩余大小
-XX:MetaspaceSize=8m
-XX:MaxMetaspaceSize=50m
-XX:MinMetaspaceFreeRatio,在GC之后,最小的Metaspace剩余空间容量的百分比,减少为分配空间所导致的垃圾收集
-XX:MaxMetaspaceFreeRatio,在GC之后,最大的Metaspace剩余空间容量的百分比,减少为释放空间所导致的垃圾收集
7. code cache: 在方法区,只有Major GC才能够清理code cache,
Java代码在执行时一旦被编译器编译为机器码,下一次执行的时候就会直接执行编译后的代码,也就是说,编译后的代码被缓存了起来。
缓存编译后的机器码的内存区域就是codeCache。这是一块独立于java堆之外的内存区域。
除了jit编译的代码之外,java所使用的本地方法代码(JNI)也会存在codeCache中。
不同版本的jvm、不同的启动方式codeCache的默认大小也不同
随着时间推移,会有越来越多的方法被编译,codeCache使用量会逐渐增加,直至耗尽
当codeCache满了之后会导致编译线程无法继续,并且消耗大量cpu导致系统运行变慢
被编译过的代码仍然以编译方式执行,但是尚未被编译的代码就只能以解释方式执行了
-XX:InitialCodeCacheSize=<value> 默认情况下,初始值为48MB,最大值为240MB
-XX:ReservedCodeCacheSize=300M 默认情况下,初始值为48MB,最大值为240MB
-XX:+UseCodeCacheFlushing enable code cache flushing, 当代码缓存被填满时让JVM放弃一些编译代码
-XX:-UseCodeCacheFlushing disable code cache flushing
-XX:CodeCacheMinimumFreeSpace=<value> 默认情况下,值为500K
8.类指针压缩空间:
--CompressedClassSpaceSize=1G 类指针压缩空间,有是64位平台上启用了类指针压缩-XX:+UseCompressedClassPointers才会存在这个区域, 默认1G
9.BufferPool: Direct Memory
ByteBuffer.allocateDirect() (注意和 ByteBuffer.allocate()的区别)DirectMemory是java nio引入的,直接以native的方式分配内存,不受jvm管理
-XX:MaxDirectMemorySize=<value> 默认大小是64M(在sun.misc.Vm中如果设置了-Xmx,则为-Xms的值)
BufferPool: Mapped Memory FileChannel.map() 由程序和os控制,无大小限制
10.Stack/Thread Size
-XX:ThreadStackSize 线程堆栈大小,默认1m
即-Xss1m
11.G1 Region Size
--G1HeapRegionSize (1~32M,最大32M, 默认是根据最小的Java堆(Xms)大小划分出约2048个区域(即Xms/2048))
12.LargePageSizeInBytes
(cat /proc/meminfo | grep Huge)
(Hugepagesize就是默认的大内存页size)
(echo 4294967295 > /proc/sys/kernel/shmmax)
(echo 154 > /proc/sys/vm/nr_hugepages)
-XX:+UseLargePages
-XX:LargePageSizeInBytes=10m
其他:
-Xint jvm启动以解释方式执行,启动时间短,但执行很慢
-Xmixed jvm启动默认编译方式, 有些地方解释执行,有些地方编译执行, 依据运行时的profile统计分析
-Xcomp jvm启动采用纯编译模式,所有方法在第一次被调用的时候就会被编译成机器代码,启动时间变长,但执行加速
-XX:+TieredCompilation jvm启动采用分层编译方式
-XX:-TieredCompilation jvm启动禁用分层编译方式
-client jvm启动以client模式运行,使用C1编译器,禁用分层编译方式(-XX:+TieredCompilation无效)
-server jvm启动以server模式运行,使用C2编译器,默认启用分层编译方式, 可以使用-XX:-TieredCompilation禁用分层编译
分层编译方式是一种折衷方式,在系统启动之初执行频率比较高的代码将先被C1编译器编译,以便尽快进入编译执行。随着时间推进,一些执行频率高的代码会被C2编译器再次编译,从而达到更高的性能