Elasticsearch JVM Heap Size大于32G,有什么影响?
0、引言
在规划ES部署的时候,会涉及到data node的分配堆内存大小,而Elasticsearch默认安装后设置的内存是1GB,对于任何一个业务部署来说,这个都太小了。
设置Heap Size的方式有两种,现将参考文献[1]摘录如下:
1) 指定ES_HEAP_SIZE环境变量。服务进程在启动时候会读取这个变量,并相应的设置堆的大小。
export ES_HEAP_SIZE=10g
2) 命令行参数的形式,在程序启动的时候把内存大小传递给它
./bin/elasticsearch -Xmx10g -Xms10g
这里的xmx和xms以前常用,但是究竟为什么要事先分配?参考文献[2]中的几个点我觉得讲的吼啊,我整理下:
a) -Xms和-Xmx设置相同时可避免Java堆自动扩展
b) 大部分 GC 算法依赖于被分配为连续的内存块的堆,因此不能在堆需要扩大时再分配更多本机内存。所有堆内存必须预先保留
c) Xmx指定内存并不是真正的分配,而是一种保留,内存保留 != 内存分配。即预先跑马圈地,并没有实际都用到。例如Xmx=512M是直接预留出512M的内存空间,但启动时的Java进程并不一定全部使用,但512M是它的“领地”。
1、那么将Java Heap Size设置的大于32G会对性能有什么影响?
开门见山的说,结果有几点(这几点其实也是内部关联):
- 触发JVM的临界值,优化策略Compressed OOPS失效(之前Heap Size在[4G~32G]区间内采用此优化)
- 由于优化策略失效,同时堆内存>32G,所以JVM被迫使用8字节(64位)来对Java对象寻址(之前4字节(32位)就够了)
- 通常64位JVM消耗的内存会比32位的大1.5倍,这是因为对象指针在64位架构下,长度会翻倍(事实上当内存到达40-50GB的时候,有效内存才相当于使用Compressed OOPS技术时候的32G内存)
- 更大的指针在主内存和缓存器(例如LLC, L1等)之间移动数据的时候,会占用更多的带宽(参考文献[1]中表示很糟糕)
- 让JVM的GC面临更大压力的指针对象(在实际应用中构建大于12-16G的堆时,若无很好的性能调优与测评,你很容易就会引起一个耗时数分钟的完全GC)
1.1 JVM的OOPS
OOP = “ordinary object pointer” 普通对象指针
启用CompressOops后,会压缩的对象:
- 每个class的属性指针(静态成员变量)
- 每个对象的属性指针
- 普通对象数组的每个元素指针
1.2 JVM的优化策略Compressed OOPS
从JDK 1.6 update14开始,64 bit JVM正式支持了 -XX:+UseCompressedOops ,这个可以压缩指针,起到节约内存占用的新参数。
Compressed OOPS,即大雾的对象压缩技术,压缩引用到32位,以降低堆的占用空间。其伪代码原理就不贴了,在参考文献[3]中,大家自取。
在堆大小在[4G~32G]的时候,这项技术会被触发,在JVM执行时加入编/解码指令,即
JVM在将对象存入堆时编码,在堆中读取对象时解码
内存地址确定公式类似于
<narrow-oop-base(64bits)> +(<narrow-oop(32bits)><< 3) +<field-offset>
Zero Based Compressed OOPS(零基压缩优化)则进一步将基地址置为0(并不一定是内存空间地址为0,只是JVM相对的逻辑地址为0,如可用CPU的寄存器相对寻址) 这样转换公式变为:
(<narrow-oop << 3) +<field-offset>
从而进一步提高了压解压效率。
参考文献[1]中举一个简单的例子,有点像BitMap的思想,即
使用Zero Based Compressed OOPS后,它的指针不再表示对象在内存中的精确位置,而是表示偏移量。这意味着32位的指针可以引用40亿个对象,而不是40亿个字节。
1.3 Zero Based Compressed OOPS的多种策略
它可以针对不同的堆大小使用多种策略,具体可以 ps + grep查看:
- 堆小于4G,无需编/解码操作,JVM会使用低虚拟地址空间(low virutal address space,64位下模拟32位)
- 小于32G而大于4G,使用Zero Based Compressed OOPS
- 大于32G,不使用Compressed OOPS
2、结论
- Compressed OOPS,可以让跑在64位平台下的JVM,不需要因为更宽的寻址,而付出Heap容量损失的代价
- 它的实现方式是在机器码中植入压缩与解压指令,可能会给JVM增加额外的开销
- 如果希望更大的堆内存。可以考虑一台机器上创建两个或者更多ES节点(封顶32G堆内存),而不要部署一个使用32+GB内存的节点(仍然要坚持50%原则)
999、参考文献
[2]【原创】深入理解Java堆内存分配策略(Xmx和Xms)
[3] 主题:JVM优化之压缩普通对象指针(CompressedOops)
Elasticsearch JVM Heap Size大于32G,有什么影响?的更多相关文章
- Setting Tomcat Heap Size (JVM Heap) in Eclipse
this article picked from:http://viralpatel.net/blogs/setting-tomcat-heap-size-jvm-heap-eclipse/ Rece ...
- soapUI启动报错:The JVM could not be started. The maximum heap size (-Xmx) might be too large or an antivirus or firewall tool could block the execution.
版本: soapUI-5.2.1 问题: 启动soapUI时报错:The JVM could not be started. The maximum heap size (-Xmx) might be ...
- JVM heap中各generation的大小(Sizing the Generations)
查看参数 使用 -XX:+PrintFlagsFinal 打印当前环境JVM参数默认值, 比如: java -XX:PrintFlagsFinal -version, 也可以用java [生产环境参数 ...
- “Invalid maximum heap size” when running Maven
运行mvn package,报错: Invalid maximum heap size: -Xmx512m. Error: Could not create the Java Virtual Mach ...
- Java内存泄漏分析系列之六:JVM Heap Dump(堆转储文件)的生成和MAT的使用
原文地址:http://www.javatang.com JVM Heap Dump(堆转储文件)的生成 正如Thread Dump文件记录了当时JVM中线程运行的情况一样,Heap Dump记录了J ...
- Exception in thread "main" java.lang.IllegalArgumentException: System memory 202768384 must be at least 4.718592E8. Please use a larger heap size.
Spark-submit 提交任务时候报错 Exception in thread "main" java.lang.IllegalArgumentException: Syste ...
- 为什么Java进程使用的RAM比Heap Size大?
Java进程使用的虚拟内存确实比Java Heap要大很多.JVM包括很多子系统:垃圾收集器.类加载系统.JIT编译器等等,这些子系统各自都需要一定数量的RAM才能正常工作. 当一个Java进程运行时 ...
- Java heap size
今天在性能诊断工作中遇到 Java heap size, 下面是它的相关的概念. 什么是Java heap size ? Java heap size 堆栈大小, 指Java 虚拟机的内存大小.我的理 ...
- elasticsearch jvm优化
测试环境elasticsearch jvm 4G jdk1.8 [serveradm@test-log-server elasticsearch]$ java -version java versio ...
随机推荐
- JDBC JdbcUtils( 本博多次出现的简陋工具类)
package test; import java.sql.Connection; import java.sql.DriverManager; import java.sql.ResultSet; ...
- ORACLE expdp/impdp详解(转)
ORCALE10G提供了新的导入导出工具,数据泵.Oracle官方对此的形容是:Oracle DataPump technology enables Very High-Speed movement ...
- Linux操作系统中多线程的同步
1 互斥锁 互斥锁用来保证一段时间内只有一个线程在执行一段代码.必要性显而易见:假设各个线程向同一个文件顺序写入数据,最后得到的结果一定是灾难性的. 先看下面一段代码.这是一个读/写程序,它们公用一个 ...
- 深层神经网络框架的python实现
概述 本文demo非常适合入门AI与深度学习的同学,从最基础的知识讲起,只要有一点点的高等数学.统计学.矩阵的相关知识,相信大家完全可以看明白.程序的编写不借助任何第三方的深度学习库,从最底层写起. ...
- String的split()方法探索和大揭秘
事实上没打算写这么一篇博文的,可是昨天在逛论坛的时候,发现一帖子,然后我又把帖子的内容在群里发了一通,结果出现了让人吃惊的结果,所以这里简单的给大家分享一下split()方法,免得大伙儿以后还会出现这 ...
- webqq协议分析之~~~~登陆
最近好几个新项目积一起了,比较忙,所以博客迟迟未更新,还请各位见谅!下面来继续分析webqq协议,本章将说明如何实现登陆 1:输入QQ号和密码登陆,检测HTTP请求url如下,这是第一次登陆 http ...
- 快速排序以及第k小元素的线性选择算法
简要介绍下快速排序的思想:通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有数据都要小,然后再按此方法对这两部分数据分别进行快速排序,整个排序过程可以递归进行,以此 ...
- SortedDictionary<TKey,TValue>正序与反序排序及Dicttionary相关
SortedDictionary<TKey,TValue>能对字典排序 using System; using System.Collections.Generic; using Syst ...
- github提交一个空目录
github默认不上传空目录,有的时候需要空目录来保持程序的结构. 二个小问题. 1.始终保持空目录,即时里面有文件,也全部忽略掉. 建立一个.gitignore文件放到空目录内. mkdir emp ...
- ubuntu下禁用和恢复触摸板
1.一般禁用选项在 settings > mouse and touchpad 中.(16.04通过实验)如果无法禁用或者希望恢复,向下看. 2.命令行键入: xinput ,插卡touchpa ...