最近一直在研究Hbase,上班时间能去研究这些hbase一些稍微深层次的原理,或者作一些有用的优化是很是宝贵的,既能拿钱又能得到宝贵经验。咳。。有点扯远了。接下来进入正题。html
一、hbase-env.sh中的内存配置
hbase-env.sh中能够配置不少东西,好比hbase的heap大小,hbase的gc策略等等。其实主要就是heap的大小和GC相关的参数。
1)对于heap,也就是HBASE_HEAPSIZE,默认为1G,配置这个,至关于全部的hbase守护进程的heap都使用这个大小,hbase守护进程有这么几个,HMaster、HregionServicer、thrift、Zookeeper相关进程,这里面Zookeeper只的应该是hbase自带的zookeeper,生成环境通常不会使用它,在咱们的环境中也不会使用到thrift,那么对于HBASE_HEAPSIZE至关于给HMaster、HregionServicer配置的堆内存大小。
在网上我看到有篇文章说不要直接配置HBASE_HEAPSIZE,由于默认是全部的守护进程都会使用HBASE_HEAPSIZE这么大的内存,对于HBASE_ZOOKEEPER,是内存的浪费。这确实有道理,但在咱们系统中并无启动这些进程,因此暂时能够不考虑每个守护进程分配不一样的内存大小。
咱们目前的系统是使用export HBASE_HEAPSIZE=16384,16G的内存,这个数字从哪来呢?相信这还得查看官网,官网不是万能的,但不看官网是万万不能的。一下是官网的一段话:
Thus, ~20-24Gb or less memory dedicated to one RS is recommended
个人英文不是很好,前一句的大概意思是regionserver由于GC的缘由不能分配太大的内存,这句就不用我翻译了吧。20~24GB或者更小比较适合。嘿嘿。固然这个参数跟不少因素有关,之后我会再深刻总结影响这个内存参数的因素。姑且先这么多。java
2)GC配置
不要觉得配置了上面的参数就完了,由于你可能会遇到不少状况。好比OOM。为何?这就要说到java的内存机制了,简要说说吧,之后会有JVM调优的专题。
上图是JVM 分代垃圾收集系统的图表,简要说一下:apache
这里有 3 个堆分代:Perm(或是 Permanent)代【永久代】,Old Generation 代【老年代】,和 Young 代【年轻代】。年轻代由三个独立的空间组成,Eden 空间和两个 survivor 空间,S0 和 S1。
一般,对象被分配在年轻代的 Eden 空间,若是一个分配失败(Eden 满了),全部 java 线程中止,而且一个年轻代 GC(Minor GC)被调用。全部在年轻代存活的对象(Eden 和 S0 空间)被拷贝到 S1 空间。若是 S1 空间满了,对象被拷贝(提高)到老年代。当这个提高失败,老年代被收集(Major/Full GC)。永久代和老年代一般一块儿被收集。永久代被用于在存放类和对象中定义的方法。并发
回到本话题,咱们设置GC的参数为
export HBASE_OPTS="$HBASE_OPTS -XX:+UseConcMarkSweepGC -XX:CMSInitiatingOccupancyFraction=60 -XX:+UseParNewGC -XX:ParallelGCThreads=6"
简要说明一下,
-XX:+UseConcMarkSweepGC 表示年老代并发收集;
对于老年代来讲, 它能够更早的开始回收。当分配在老年代的空间比率超过了一个阀值,CMS 开始运行。若是 CMS 开始的太晚,HBase 或许会直接进行 full garbage collection。这种状况会致使block全部的线程,若是这个时间过长,就会致使hbase链接超时,结果就是regionserver集体下线。这是不能容忍额。为了不这种状况的发生,咱们建议设置 -XX:CMSInitiatingOccupancyFraction JVM 参数来精确指定在多少百分比 CMS 应该被开始,正如上面的配置中作的那样。在 百分之 60 或 70 开始是一个好的实践。当老年代使用 CMS,默认的年轻代 GC 将被设置成 Parallel New Collector。
再来看看hbase为何可能进行full gc,若是咱们不配置-XX:CMSInitiatingOccupancyFraction,jdk1.5之后会使用默认值90%,那么极可能,当老年代内存占用超过度配给他的内存大小的90%,会进行CMS(老年代的回收),可是不会阻止年轻代到老年代的迁移,若是迁移过快,CMS较慢,会出现老年代内存使用率100%,这时会致使full gc。若是咱们把这个参数调整小一点,那么能给年轻带到老年代迁移的同时作CMS时一些时间,也就减小了full gc的发生。固然这可能会频繁的gc,但总比整个hbase挂掉的好不是么?less