深入剖析:关于cache buffers chains的经典案例处理详解


卢文星

目前就职云和恩墨,南区交付工程师,有超过8年超大型数据库管理经验,擅长Oracle数据库性能优化与升级迁移。

故障现象

某省税务核心业务系统在7月13日11-12点出现业务处理非常缓慢,偶尔出现卡住不动。某业务功能处理时间是平时的10倍以上。

已知情况:

1、近两周开始,在白天业务高峰期业务系统会出现处理缓慢
2、数据库层面出现大量latch:cache buffers chains等待会话
3、每次问题大概持续了30分钟后,latch:cache buffers chains等待消失,业务恢复正常
4、缓慢期间系统CPU使用率达到80%

故障分析

了解了以上信息后,我们首先获取了故障期间1节点的awr信息,一小时的dbtime高达58,354 min。我们知道dbtime是数据库实例会话花费时间的总和,那么从dbtime上看,期间数据库确实出现问题,会话发生了严重的等待。

Top等待事件中看到latch: cache buffers chains等待事件排列第1,占据了dbtime 82%,等待次数1千万以上,其平均等待时间达到238ms。其余等待事件占比很少。可以推断cache buffers chains事件跟本次故障有极强的相关性。因此我们接下来从该等待事件着手进行分析。

latch cache buffers chains 定义

我们可以看到,一个latch保护多个hash bucket,一个hash bucket对应一个hash chain list,而hash chain list挂载了一个或者多个buffer header(注意:buffer header与Data block一一对应)。

也就是说,如果我要访问某个block,我们首先获得这个latch。当有多个会话同时访问一个hash chain时,就会发生竞争。Latch cbc等待就这样出现了。

以下情况下会发生 cache buffers chains等待:
1、同一个cache buffers chains下不同block被频繁访问,称为hot chains
2、同一个cache buffers chains下同一个block被频繁访问,称为hot block

一个块的访问过程

一个块的访问过程,一般会有2次cbc latch的获取、释放。

官方对cbc latch的描述。





以上内容简单来说就是一个用户进程获取latch来扫描buffer ,系统根据块地址和类型将数据块分配在buffer链表中,每个buffer链表会有一个latch来保护。防止其扫描过程链表里的块发生变动。

分析问题原因

首先,通过dba_hist_active_session_history视图还原故障期间发生等待的会话信息,包括用户、正执行的SQL等。

dba_hist_active_sess_history视图查询十几分钟都没出结果。

查看该视图基表WRH$_ACTIVE_SESSION_HISTORY,其分区达到了8GB,视图里又关联了WRH$_EVENT_NAME、WRM$_SNAPSHOT表,所以查询长时间未完成。

直接查基表WRH$_ACTIVE_SESSION_HISTORY。基表没有event_name列,需要通过event_id来查,获取latch: cache buffers chains的event_id 。


五分钟执行完,查看结果后发现,cph4kgcn7frzs、c85hrnmygbhz2、1tnz5r62b84gg 这三个sql执行时发生了严重的Latch cbc等待。

查看这三个sql的SQLTEXT,发现它们的子查询SQL一样的,子查询访问的表为swjg_dm。



再观察SQL的执行计划(3个SQL执行计划基本一样,此处以c85hrnmygbhz2展示),子查询里访问表swjg_dm是通过索引UK_DM_GY_SWJG

回到awr报告,Segments by Logical Reads部分TOP1可以看到是DM_GY_SWJG表的索引UK_DM_GY_SWJG,该索引正好3个SQL执行计划中都用到的索引UK_DM_GY_SWJG。说明它被频繁访问。

awr报告SQL Statistics,1小时内,每个SQL执行次数都超过3百万。

在以下查询中p1为LATCH: CBC的address。显示有三个不同的SQL,说明3个SQL竞争同一个LATCH:CBC。

根据latch地址,到v$latch_children视图中可以查找该latch .因为实例没有重启过,cbc对应latch的address没有变动(如果数据库重启,则latch的addr会重新分配,就查不到了).

下面将P1转化为p1raw与视图addr关联

可以看到该latch地址是一个cache buffers chains latch

目前,我们只确认热块在索引UK_DM_GY_SWJG,但具体哪个块,我们还不确定。再根据latch的地址,通过x$hb联合dba_objects视图来查看。

再通过x$hb联合dba_objects视图来查看该CBC下中有哪些对象、块等

看到熟悉的对象索引UK_DM_GY_SWJG,它是9号文件的31109号块在这个CBC中。该cbc里只有1个UK_DM_GY_SWJG索引块。那么该块是不是热块,该索引的其他块在哪个cbc?

我们通过dump索引的结构来确认以下。


我们看到tree dump该索引有1个枝块和3个叶块,总共4个块,该所索引有1千多条记录。通过索引块地址dba转换后,看到9号文件31109号块是索引的叶子块。

再次通过x$bh确认,该索引的4个块分别在4个CBC中

分析结论

本次系统故障原因是,由于业务高峰期“cph4kgcn7frzs”、“c85hrnmygbhz2”、“1tnz5r62b84gg”这3个SQL执行频繁,并发访问索引UK_DM_GY_SWJG的9号文件31109号,对应的latch addr:07000100F6A6C8E8,引起严重latch: cache buffers chains竞争阻塞,从而导致业务处理缓慢。

优化措施

官方提供的Solution方法
1、Splitting the buffer pool into multiple pools
我们的问题情况是热块不是热链,不适合

2、Altering PCTFREE/PCTUSED to allow fewer rows per block, thus reducing contention on a certain block
对于索引记录分块,因为SQL访问该索引块中存在一定的热记录。所以对LATCH CBC问题的缓解效果不是很明显。

3、Reducing the frequency the application accesses the object in question.
客户确认,业务量上看该SQL不需要这么多次执行,与开发商确认存程序在BUG,但开发商回复bug短期内无法修复。

4、Tuning queries so that they won’t touch as many blocks. This will alleviate the problem with this latch if the query is heavily executed.
从前执行计划上看,对索引UK_DM_GY_SWJG访问,基本没有优化空间。

5、 Avoid doing too many concurrent DML and Queries against the same row/block. Too many concurrent DML and Queries against the same block can result in multiple versions of the block created in the same cache buffer chain. Longer chains means more time spent by the session traversing through the chain while holding on to the latch.
不存在dml,主要query SQL

我们问题的现状:

优化构思

优化措施

实现方法:

我们可以在表dm_gy_swjg 的swjg_dm列,再创建两个索引(复合索引),swjg_dm为前缀列,通过SQL PROFILE概要文件将c85hrnmygbhz2、1tnz5r62b84gg索引访问分别指向新建的两个复合索引,cph4kgcn7frzs不变动,则使用原UK_DM_GY_SWJG索引。

实施步骤:

dm_gy_swjg表创建两个新的复合索引,复合列为(swjg_dm , xybz)、(swjg_dm, yxbz)。
使用hint将c85hrnmygbhz2、1tnz5r62b84gg分别指定使用新建立两个复合索引,并获取outline信息。

通过SQL PROFILE概要固定c85hrnmygbhz2、1tnz5r62b84gg执行计划。

优化结果

在优化调整实施后一周,客户反馈,那3个sql在每小时3百万执行量的情况下,已经无发现有明显的latch: cache buffer chains等待,说明问题得以缓解。

时间: 2024-10-19 20:57:32

深入剖析:关于cache buffers chains的经典案例处理详解的相关文章

【转载】latch: cache buffers chains

       当一个数据块读入sga区,相应的buffer header会被放置到hash列表上,我们称其这hash chains,chain在中文的意为链条或串的意思,表达就是关连性.如果一个进程想访问或修改hash chain上的block,它首先要获得"cache buffers chains" latch.   原因一:低效率的SQL语句(主要体现在逻辑读过高) cache buffers chains latch很大程度与逻辑读有关,所以要观注v$sql中BUFFER_GET

[20150121]关于latch cache buffers chains

[20150121]关于latch cache buffers chains事件.txt --最近一直在看,关于latch: cache buffers chains的等待事件. --造成这个事件的主要原因有2个:一个是热链,另外一个是热块.我喜欢通过例子来说明,实际上书上写的更加详细. --这里主要测试热块造成的情况. 1.建立测试环境: SCOTT@test> @ver1 PORT_STRING                    VERSION        BANNER -------

ORACLE等待事件latch: cache buffers chains

    今天上午,电渠生产库维护人员通知,ORACLE生产库中有比较多的latch: cache buffers chains引起的会话,造成堵塞,相关处理过程如下    环境:hp-unix    数据库版本:10.2.0.5    登录数据库查询等待事件:      根据等待事件latch: cache buffers chains查询相关的SQL_ID,引起争用的对象所在的文件号和块号 select * from (select      count(*),      sql_id,   

深入理解latch: cache buffers chains

事件背景:   一个客户的数据库发生了宕机事件,查看了数据库的awr报告,原来是由于出现大量的latch: cache buffers chains等待事件导致系统消耗量大量的CPU,最终导致系统hang住: 说明:   要理解latch: cache buffers chains并解决这个问题,就需要深入的了解Buffer Cache及其原理.1.Buffer Cache概述:   Buffer Cache是SGA的一部分,Oracle利用Buffer Cache来管理data block,B

缓解latch: cache buffers chains的案例

这两天我们的一个核心系统U*S,正在做压力测试,虽然压测的服务器配置不如生产,但可以反映出一些问题,初始测试的TPS可以说非常低,据测试同事反映,压测一会,数据库服务器CPU就上来了,业务上有积报现象,找不着原因. 既然数据库服务器CPU飙升上来了,说明数据库服务器上有压力,这就需要看压测期间,数据库有何负载变化.Oracle提供了我们非常丰富的工具,AWR就是其中之一,可以让我们了解特定时间段,数据库相关负载信息,具体使用方法可以参考<一个执行计划异常变更的案例 - 外传之AWR>. 测试数

javascript常用经典算法实例详解_javascript技巧

本文实例讲述了javascript常用算法.分享给大家供大家参考,具体如下: 入门级算法-线性查找-时间复杂度O(n)--相当于算法界中的HelloWorld //线性搜索(入门HelloWorld) //A为数组,x为要搜索的值 function linearSearch(A, x) { for (var i = 0; i < A.length; i++) { if (A[i] == x) { return i; } } return -1; } 二分查找(又称折半查找) - 适用于已排好序的

数据挖掘十大经典算法(详解)

数据挖掘十大经典算法  一. C4.5  C4.5算法是机器学习算法中的一种分类决策树算法,其核心算法是ID3 算法.   C4.5算法继承了ID3算法的优点,并在以下几方面对ID3算法进行了改进:  1) 用信息增益率来选择属性,克服了用信息增益选择属性时偏向选择取值多的属性的不足:  2) 在树构造过程中进行剪枝:  3) 能够完成对连续属性的离散化处理:  4) 能够对不完整数据进行处理.  C4.5算法有如下优点:产生的分类规则易于理解,准确率较高.其缺点是:在构造树的过程中,需要对数据

buffer cache实验5-latch:cache buffers chain

1.CBC latch产生的原理: 一次逻辑读时CBC latch锁及Buffer pin锁的获取和释放过程如下: 1.加Latch X 2.进入hash chain,在相应的BH上加Buffer pin S (0-->1) 3.释放Latch X 4.进行逻辑读--也就是通过BH中的buffer adderss找到数据块在内存中真实位置  ---假如读了1MS 5.加Latch X 6.释放Buffer pin S (1-->0)  0:没锁  1:共享锁  2:独占锁 7.释放Latch

0821Cache Buffers chains与共享模式疑问4

[20170821]Cache Buffers chains与共享模式疑问4.txt --//昨天别人问的问题,就是在读读模式下,访问相同数据块,11.2.0.4不再出现cache buffers chains latch等待事件. --//我查询我以前写的博客,链接如下:http://blog.itpub.net/267265/viewspace-1822491/ --//也就是oracle在这样模式下不再采用EXCLUSIVE模式获取cache buffers chains latch.当时