[20150309]逻辑读产生CBC Latch的解析.txt

[20150309]逻辑读产生Cache Buffer Chain(简称CBC) Latch的解析.txt

--参考链接http://blog.csdn.net/guoyjoe/article/details/8585391,自己也做1次。

逻辑读的过程
1、Oracle以每个块的文件号、块号和类型做HASH运算,得到HASH值。根据HASH值,到HASH表中取出指定块的内存地址
2、获取CBC Latch(实验的重点测试部分)
3、根据HASH值,搜索CBC链表
4、根据DBA找到BH(Buffer Header)加Buffer Pin
5、加完Buffer Pin马上释放CBC Latch
6、访问Buffer开始fetch数据
7、获取CBC Latch
8、释放Buffer Pin
9、释放CBC Latch

--可以发现读取块需要获得2次CBC LATCH。

1.建立测试环境:

SCOTT@test> @ver1
PORT_STRING                    VERSION        BANNER
------------------------------ -------------- --------------------------------------------------------------------------------
x86_64/Linux 2.4.xx            11.2.0.3.0     Oracle Database 11g Enterprise Edition Release 11.2.0.3.0 - 64bit Production

SCOTT@test> select /*+ full(dept) */ rowid,dept.* from dept where deptno=10;
ROWID                    DEPTNO DNAME          LOC
------------------ ------------ -------------- -------------
AABBrlAAEAAAAWDAAB           10 ACCOUNTING     NEW YORK

SCOTT@test> @lookup_rowid AABBrlAAEAAAAWDAAB
      OBJECT         FILE        BLOCK          ROW DBA                  TEXT
------------ ------------ ------------ ------------ -------------------- ----------------------------------------
      269029            4         1411            1 4,1411               alter system dump datafile 4 block 1411

2.根据文件号块号获取CBC Latch的地址:

SCOTT@test> select hladdr from x$bh where file#=4 and dbablk=1411;
HLADDR
----------------
00000000BC852DE0

3.根据CBC Latch的地址可以查出这个CBC Latch被获得的次数:
SCOTT@test> select addr,name,gets from v$latch_children  where addr='00000000BC852DE0';
ADDR             NAME                                                       GETS
---------------- -------------------------------------------------- ------------
00000000BC852DE0 cache buffers chains                                       1784

SCOTT@test> select * from dept where rowid='AABBrlAAEAAAAWDAAB';
      DEPTNO DNAME          LOC
------------ -------------- -------------
          10 ACCOUNTING     NEW YORK

SCOTT@test> select addr,name,gets from v$latch_children  where addr='00000000BC852DE0';
ADDR             NAME                                                       GETS
---------------- -------------------------------------------------- ------------
00000000BC852DE0 cache buffers chains                                       1786

--可以发现一次逻辑读产生2次CBC Latch.
--补充测试,实际上可以测试每次逻辑读都会获取2次cbc latch:
SCOTT@test> select addr,name,gets from v$latch_children  where addr='00000000BC852DE0';

ADDR             NAME                       GETS
---------------- -------------------- ----------
00000000BC852DE0 cache buffers chains   80275738

SCOTT@test> select * from dept ;
    DEPTNO DNAME          LOC
---------- -------------- -------------
        10 ACCOUNTING     NEW YORK
        20 RESEARCH       DALLAS1
        30 SALES          CHICAGO
        40 OPERATIONS     BOSTON

SCOTT@test> select addr,name,gets from v$latch_children  where addr='00000000BC852DE0';
ADDR             NAME                       GETS
---------------- -------------------- ----------
00000000BC852DE0 cache buffers chains   80275742
--可以发现80275742-80275738=4,需要4次,可以参考我写的一篇blog:
http://blog.itpub.net/267265/viewspace-1430902/

--如果我设置array=2,这样将增加6次。逻辑读仅仅比前面增加1次。
--注意我的测试设置最小array=2,即使你设置1实际上结果与设置2的逻辑读是一样的.

SCOTT@test> set array 2
SCOTT@test> select addr,name,gets from v$latch_children  where addr='00000000BC852DE0';
ADDR             NAME                       GETS
---------------- -------------------- ----------
00000000BC852DE0 cache buffers chains   80275742

SCOTT@test> select * from dept ;
    DEPTNO DNAME          LOC
---------- -------------- -------------
        10 ACCOUNTING     NEW YORK
        20 RESEARCH       DALLAS1
        30 SALES          CHICAGO
        40 OPERATIONS     BOSTON

SCOTT@test> select addr,name,gets from v$latch_children  where addr='00000000BC852DE0';
ADDR             NAME                       GETS
---------------- -------------------- ----------
00000000BC852DE0 cache buffers chains   80275748

-- 80275748-80275742=6

4.使用oradebug来测试看看:

SQL> oradebug setmypid
Statement processed.

SYS@test> oradebug peek 0xBC852DE0 16                        --查0xBC852DE0地址开始的4字节信息的值为0
[0BC852DE0, 0BC852DF0) = 00000000 00000000 00000730 0000009B

SYS@test> oradebug poke 0xBC852DE0 8 0x1;                    --修改0xBC852DE0地址开始的4字节信息的值为1,相当于获取了Latch
BEFORE: [0BC852DE0, 0BC852DE8) = 00000000 00000000           --修改前的值
AFTER:  [0BC852DE0, 0BC852DE8) = 00000001 00000000           --修改后的值

SYS@test> oradebug peek 0xBC852DE0 4                         --查0xBC852DE0地址开始的4字节信息的值为1
[0BC852DE0, 0BC852DE4) = 00000001

--注意执行select * from dept 没有没有问题。我不知道是我的版本问题还是那里出了问题。

SCOTT@test> update dept set loc=lower(loc) where deptno=10 ;
--才会挂起,不知道是否是版本的问题。

SYS@test> select sid,seq#,event,state,wait_time_micro,seconds_in_wait,p1,p2 from v$session where wait_class'Idle' order by event ;
       SID       SEQ# EVENT                                    STATE      WAIT_TIME_MICRO SECONDS_IN_WAIT         P1         P2
---------- ---------- ---------------------------------------- ---------- --------------- --------------- ---------- ----------
       400        557 SQL*Net message to client                WAITED SHO               2               0 1650815232          1
                                                               RT TIME

         5         70 latch: cache buffers chains              WAITING           56594939              57 3162844640        155

--oracle也太复杂了。 3162844640 = 0xbc852de0

SYS@test> oradebug poke 0xBC852DE0 8 0x0
BEFORE: [0BC852DE0, 0BC852DE8) = 00000001 40000000
AFTER:  [0BC852DE0, 0BC852DE8) = 00000000 00000000

时间: 2024-09-13 19:10:10

[20150309]逻辑读产生CBC Latch的解析.txt的相关文章

逻辑读产生Cache Buffer Chain(简称CBC) Latch的解析

测试环境:版本11gR2 SQL> select * from v$version where rownum=1; BANNER -------------------------------------------------------------------------------- Oracle Database 11g Enterprise Edition Release 11.2.0.1.0 - 64bit Production 一.逻辑读的过程  1.Oracle以每个块的文件号.

数据读取的逻辑读简单解析:关于BUFFER CACHE

数据读取之逻辑读简单解析--BUFFER CACHE   关于consistent read--一致性读--Logical read-逻辑读-current read当前读--物理读,详见:http://blog.csdn.net/haibusuanyun/article/details/11489091 一.实验数据准备--查出一条数据的ROWID,及FILE_ID,BLOCK_ID等信息 BYS@ bys3>select rowid,test.* from test where rownum

buffer cache实验9:从buffer caceh中读取数据块解析-从逻辑读到物理读

先来张大图: 所用SQL语句: BYS@ ocm1>select dbms_rowid.rowid_relative_fno(rowid) file#,dbms_rowid.rowid_block_number(rowid) block#,deptno from bys.test;     FILE#     BLOCK#     DEPTNO ---------- ---------- ----------         4        391         10 就以上图为例,文字描述

如何模拟产生CBC LATCH与buffer busy wait等待事件

数据库版本: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下多个

Oracle Arraysize设置对于逻辑读的影响实例分析_oracle

当执行一条SQL查询的时候,为了获得满足的数据,查询在这个过程中完成解析,绑定,执行和提取数据等一系列步骤,这些步骤都是单独执行的,满足条件的数据行必须由数据库返回给应用:对于任何大小的结果集,需要返回的数据行很可能不是在一次往返调用过程中传递给应用的! 每次调用过程中,数据库与客户端之间的往返回路数将一定层次上影响总的响应时间,其中除了提取数据(FETCH)步骤,其余步骤(解析,绑定,执行)都只执行一次,这也是必要的,Oracle需要获得满足查询条件的所有数据结果从而执行多次提取操作. 关于提

浅析Oracle全表扫描下的逻辑读

T1表全表扫描产生逻辑读的分析 做个实验给你演示一下:以表t1为例,对段t1做dump 1.t1表就一条数据 gyj@OCM> select * from t1;      ID NAME ---------- ----------       1 AAAAA 2.找t1段的段头块 gyj@OCM> select  header_file,header_block from dba_segments where segment_name='T1' and owner='GYJ'; HEADER

ORACLE 物理读 逻辑读 一致性读 当前模式读总结浅析

     在ORACLE数据库中有物理读(Physical Reads).逻辑读(Logical Reads).一致性读(Consistant Get).当前模式读(DB Block Gets)等诸多概念,如果不理解或混淆这些概念的话,对你深入理解一些知识无疑是一个障碍,但是这些概念确实挺让让人犯晕的.下面我们总结.学习一下这方面的知识点.捋一捋他们的关系和特点,希望对你有所帮助.   物理读(Physical Reads)   从磁盘读取数据块到内存的操作叫物理读,当SGA里的高速缓存(Cac

【SQL 优化】异常的逻辑读

实验环境 SQL> select * from v$version; BANNER                                                                          -------------------------------------------------------------------------------- Oracle Database 11g Enterprise Edition Release 11.1.0.

理解SQL SERVER中的逻辑读,预读和物理读

SQL SERVER数据存储的形式 在谈到几种不同的读取方式之前,首先要理解SQL SERVER数据存储的方式.SQL SERVER存储的最小单位为页(Page).每一页大小为8k,SQL SERVER对于页的读取是原子性,要么读完一页,要么完全不读,不会有中间状态.而页之间的数据组织结构为B树.所以SQL SERVER对于逻辑读,预读,和物理读的单位是页. SQL SERVER一页的总大小为:8K 但是这一页存储的数据会是:8K=8192字节-96字节(页头)-36字节(行偏移)=8060字节