问题描述
银行某客户某生产数据库某RAC节点在2018-08-05凌晨06:48分左右,告警出现ORA-04031报错,接着后续一大推告警报错一直到上午10.40数据库shutdown abort,最终导致smon进程终止,数据库宕机
环境版本: 11.2.0.4 RAC
系统: linux x86 64-bit
数据库使用ASMM管理方式管理数据库内存,ORA-04031报错"unable to allocate shared memory",主要原因还是在数据库内存方面,所以关注点也是侧重于SGA组件内存分配
问题现象
1、告警日志产生的ORA-04031 trc文件太多,因为后续数据库系统进程都是由于申请不到shared pool内存导致进程死掉,产生的trc,为此,我们先找到产生报错的源头,也就是凌晨06:48分产生的trc文件
2、分析OTODB2_ora_954403.trc文件
trc文件中显示,SGA内部组件内存变动历史,可以看到shared pool 跟 Buffer cache发生了收缩现象.Buffer cache 缩小了0.31G,而shared pool增长差不多也是0.3G的样子,符合ASMM特性…并且由于采用了ASMM特性,数据库内部的share pool大小以及buffer cache大小由shared_pool_size 和 db_cache_size两个参数控制,这个两个参数是变动的
从trc部分发现SGA Heap 1 - 7,也就是trc文件中的TOP 10 MEMORY USES FOR SGA HEAP SUB POOL X (X表示1-7)汇总信息…其实整个SGA 内部剩余内存很少不到1G,其中KGH: NO ACCESS占用最多15G,这个KGH:NO ACCESS查看你MOS得知该部分占用的内存其实就是Buffer Cache,只不过在Shared Pool标志为:KGH: NO ACCESS
This memory component in the Shared Pool marked as ‘KGH: NO ACCESS’ is used by the Buffer Cache.
综合上面两点结合AWR报告,AWR报告显示
主机内存其实是比较充足的,但是数据库的内存占用量还不足40%,的确有点过少,并且根绝SGA Target优化建议,当前sga内存设置虽然Szie Factor=1,但是可以看到其实物理读还是比较高的,建议调整到33-38G,这样加PGA 4G左右,总共38G左右,占主机内存60%的样子,也比较符合ORACLE官方推荐.
问题主要可能出现以下情况:
1、SGA过小
2、SGA中shared pool设置过小,导致增长
3、查看MOS
How To Prevent The Growth Of The Component ‘KGH: NO ACCESS’ In The Shared Pool When ASMM Is Enabled (文档 ID 451960.1)
ORA-04031: “unable to allocate shared memory” Error When Using AMM or ASMM and Each Shared Pool Subpool Has Adequate Free Memory (文档 ID 2382705.1)
其实,这两篇MOS说的比较详细,有需要的请自行下载查看,尤其是ORA-04031文档具体的说明了造成的原因(即使高版本做了这方面的优化其实也有可能出现),并且实际也是可以通过隐含参数设置来避免解决的.具体解决方案见下节
问题解决方案
综上所述:
1、根绝MOS文章(文档 ID 2382705.1),其中一种解决方案,设置隐含参数"_enable_shared_pool_durations"=false
该隐含参数解释为:this eliminates shared pool durations so that all free memory in a subpool is available to the entire subpool. The only downside is that granules cannot move from the shared pool to the buffer cache upon demand. However, granule movement from the buffer cache to the shared pool is still possible.
翻译:它可以消除了共享池持续时间,以便子池中的所有可用内存可用于整个子池。唯一的缺点是粒子无法根据需要从共享池移动到缓冲区缓存。但是,从缓冲区高速缓存到共享池的粒度移动仍然是可能的
简单白话文就是说,共享池Shared Pool只能扩展,不能再次被收缩.(因为从共享池移动到缓冲区缓存。但是,从缓冲区高速缓存到共享池的粒度移动仍然是可能的),可能造成在某些情况下,shared pool一直扩展,Buffer cache不断的被缩小...造成缓冲区热点数据过少,数据库物理读过高现象
个人认为:
1、该参数调整最好是在硬件无法得到补充扩展的情况下使用,比较合适...比如:内存无法得到增加,调整的情况下使用
2、当数据库宕机后,无法被重启时,可以手工修改该隐含参数到spfile文件,进行起库操作,后续再调整完SGA后再改动回来(当时客户就出现无法启动数据库的情况,修改该参数到Spfile后,成功起库......)
2、调整SGA大小
该解决应该是比较稳妥的,这样也可以继续使用ASMM自动管理
3、禁用ASMM特性,手工管理
3.1、整体SGA内存大小不变,根据上面Shared POOL收缩情况来看应该至少调整到3G,调整共享池以及buffer cache大小
该解决方案影响就是Buffer Cache变小了,势必影响到数据库,造成数据库物理读偏高,其实根据AWR报告来看,该数据库在空闲的情况下,逻辑读都偏高,该调整相对有影响
3.2、结合第二点调整SGA大小,并手工设置Shared Pool以及Buffer Cache大小
版权声明:本文为博主原创文章,未经博主允许不得转载。



