Drill 内存设置
你可以在任何Drill集群上,为查询处理的Drillbit进程,配置直接内存的大小。Drillbit进程默认的内存大小是8G,但是Drill推荐根据负载大小,设置16G及以上的内存。Drillbit进程分配给查询操作的直接内存大小不能超过这个参数值。这里插入一下“直接内存”的释义:直接内存不是jvm运行时数据区的一部分,也不是java虚拟机规范中定义的内存区域,但是这部分内存也被频繁的使用,而
你可以在任何Drill集群上,为查询处理的Drillbit进程,配置直接内存的大小。Drillbit进程默认的内存大小是8G,但是Drill推荐根据负载大小,设置16G及以上的内存。Drillbit进程分配给查询操作的直接内存大小不能超过这个参数值。
这里插入一下“直接内存”的释义:
直接内存不是jvm运行时数据区的一部分,也不是java虚拟机规范中定义的内存区域,但是这部分内存也被频繁的使用,而且也可能导致OutOfMemoryError的异常出现。
在jdk1.4中新加入了NIO类,引入了一直基于通道和缓存区的I/O方式,它可以使用Native函数库直接分配堆外内存,然后通过一个存储在Java堆里的DirectByteButter对象作为这块内存的引用进行操作。这样在一些场景中可以显著提高性能,因为避免了在java堆里和Native堆里来回复制数据。
显然,本机直接内存的分配不会受java堆内存大小的限制,但是,既然也是内存,则肯定还是会受到本机总物理内存大小及处理器寻址空间的限制。所以在配置jvm虚拟机参数时,一般会根据实际物理内存来设置-Xmx,-Xms等参数信息,但经常会忽略掉直接内存,使得jvm各个内存区域的和大于物理内存限制,从而导致动态扩展时出现OutOfMemeryError异常。
Drill使用java直接内存,通常在内存中执行操作,相比于在磁盘上操作,效果要好。不像MapReduce在一个工作的每个阶段都会写磁盘,除非绝对需要,Drill通常不写数据到磁盘上。
Jvm的堆内存不限制Drillbit进程的直接内存大小,Drill的非堆内存一般设置为4-8G(默认是4G),通常这已经足够,因为Drill避免数据存放在堆中。
Drill 1.5后,使用了一个新的收集器,可以提高操作使用直接内存的效率,并可以更准确的追踪内存的变化。基于这种变化,排序操作(早期版本查询可以运行成功)可能会因为内存不足,导致查询失败和内存溢出错误,而非溢写到磁盘上。
planner.memory.max_query_memory_per_node这个系统选型,可以设置在每个节点上的一次查询中,可以分配给排序操作的最大直接内存。
如果一个查询计划包含多个排序操作,它们共享这部分内存。如果你运行了包含排序操作的查询,出现了内存错误,可以试试增加这个参数的值。如果增加此值,你扔碰到内存错误,你可以减少planner.width.max_per_node所设置的值,从而减少每个节点的系统并发度。但是,这通常会增加查询完成的时间。
修改 Drillbit 的内存值
你可以在集群中修改每一个Drillbit节点的内存值,为了达到这个目的,可以在Drillbit的启动脚本drill-env.sh中(位于/conf下),设置DRILL_MAX_DIRECT_MEMORY变量,如下:
export DRILL_MAX_DIRECT_MEMORY=${DRILL_MAX_DIRECT_MEMORY:-“”}
注意:如果这个参数未设置,大小限制取决于实际可用的系统内存。
修改完 drill-env.sh后,记得重启每台节点上的Drillbit进程以使其生效。
关于Drillbit启动脚本
在drill-env.sh文件中包含以下的选项:
export DRILL_HEAP=${DRILL_HEAP:-"4G"}
export DRILL_MAX_DIRECT_MEMORY=${DRILL_MAX_DIRECT_MEMORY:-"8G"}
DRILL_MAX_HEAP 是每个节点上JVM理论上的堆最大值。
DRILL_MAX_DIRECT_MEMORY是每个节点java直接内存的最大值。
如果性能是一个问题,可以添加-Dbounds=false, 如下所示:
export DRILL_JAVA_OPTS=”$DRILL_JAVA_OPTS -Dbounds=false”
引用列表:
1. https://drill.apache.org/docs/configuring-drill-memory/
2. http://2387209.blog.51cto.com/2377209/1508621
更多推荐
所有评论(0)