数据库版本:Oracle 11.2.0.4.0
CBC latch出现的原因: --只在逻辑读时产生
1.CBC latch保护不同的链表、不同BH :同一LATCH下多个BUCKET被同时访问时,(一个LATCH对应多个BUCKET)
2.CBC latch保护同一链表下同一BH :同一LATCH下同一BH被同时访问时
latch: cache buffers chains 解决方法:
1、_db_block_hash_latches加大latch数量,作用是减少同一LATCH下多个桶被同时访问的情况。即多个表的相应块在BUFFER CACHE中对应不同BH,不同BH又对应在不同HASH BUCKETS,但是这多个HASH BUCKETS是属于同一个LATCH。。
alter system set "_db_block_hash_latches"=10240 scope=spfile;
2、热块:调整BUFFER _CACHE,参数:db_cache_size,big integer 100M
热块是:同一表在BUFFER CACHE中的块(一个块对应一个BH,BH对应一个HASH BUCKET)被多个会话同时读,--全表扫描时容易出现。可以使用多个会话同时读取同一表的同一行的方式来模拟产生CBC latch,查询时使用ROWID做条件,查询速度快,更容易引起CBC latch。
3、修改应用,减少全表扫描
BH上Buffer pin锁状态:
0 未加锁
1 共享锁,读BUFFER BLOCK ---SELECT
2 独占锁,写BUFFER BLOCK ---DML语句
Buffer pin锁争用引起:buffer busy waits等待事件 --热块
如何解决:buffer busy waits等待事件 --热块
1.增大PCTFREE
2.使用小数据块-2K-4K
3.使用HASH表分区
3.反向索引
同时出现CBC latch buffer busy waits的情况是:
会话1已经获得Buffer pin锁,且已经释放CBC latch,正在持有Buffer pin锁。
此时会话2获得与会话1同一个的CBC latch,并要获得与会话1 同一个块的Buffer pin锁,此时因会话1正持有Buffer pin锁,产生buffer busy waits等待事件。
而会话1需要获得CBC latch,来释放持有的Buffer pin锁,此时会话2正在持有CBC latch,所以也将会产生CBC latch等待事件。
下面通过多会话同时访问产生热块的方式来模拟产生这两种等待:
1.查出表TEST相关信息--在数据量大的表实验更容易产生buffer busy waits
select rowid,
dbms_rowid.rowid_row_number(rowid) rowid_rownum,
dbms_rowid.rowid_relative_fno(rowid) file_id,
dbms_rowid.rowid_block_number(rowid) block_id,test.* from test;
ROWID ROWID_ROWNUM FILE_ID BLOCK_ID OBJECT_NAME STATUS
------------------ ------------ ---------- ---------- ------------ -------
AAAFSJAAEAAAACkAAA 0 4 164 10 15
AAAFSJAAEAAAACkAAB 1 4 164 10 15
可以看到,TEST表的两条记录在同一文件的同一个BLOCK中。
2.写一个循环:
循环执行查询语句一百万次:--查询164数据块的第一行
declare
aa varchar2(100);
begin
for i in 1..1000000 loop
select object_name into aa from test where rowid='AAAFSJAAEAAAACkAAA';
end loop;
end;
/
循环更新查询语句200次 --查询164数据块的第二行
declare
begin
for i in 1..200 loop
update test set status=15 where rowid='AAAFSJAAEAAAACkAAB';
end loop;
commit;
end;
/