Oracle Lab – Storage Structure
1.实验一
1.1.dump数据块到trace文件
CREATE TABLE T_TESTBLOCK( ID NUMBER, NAME VARCHAR(4) ) ;
INSERT INTO T_TESTBLOCK VALUES (1, 'a');
INSERT INTO T_TESTBLOCK VALUES (2, 'b');
INSERT INTO T_TESTBLOCK VALUES (3, 'c');
COMMIT;
SELECT ROWID, DBMS_ROWID.ROWID_RELATIVE_FNO(ROWID) REL_FNO, DBMS_ROWID.ROWID_BLOCK_NUMBER(ROWID) BLOCKNO FROM T_TESTBLOCK;
ROWID REL_FNO BLOCKNO
------------------ ---------- ----------
AAASTiAABAAAZXhAAA 1 103905
AAASTiAABAAAZXhAAB 1 103905
AAASTiAABAAAZXhAAC 1 103905
这3行数据都在1号数据文件的第103905个块。将该数据块dump出来:
ALTER SYSTEM DUMP DATAFILE 1 BLOCK 103905;
set pages 500
set linesize 500
col name for a25
col value for a75
select name, value from vdiag_info;
select name, value from vdiag_info where name like 'Default%';
NAME VALUE
------------------------- --------------------------------------------------------------------------------
Diag Enabled TRUE
ADR Base /oracle/app/oracle
ADR Home /oracle/app/oracle/diag/rdbms/hamster/HAMSTER
Diag Trace /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace
Diag Alert /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/alert
Diag Incident /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/incident
Diag Cdump /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/cdump
Health Monitor /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/hm
Default Trace File /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/HAMSTER_ora_62379.trc
Active Problem Count 0
Active Incident Count 0
cd /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/
more HAMSTER_ora_62379.trc
1.2.块头信息
Block dump from disk:
buffer tsn: 0 rdba: 0x004195e1 (1/103905)
scn: 0x1e5a43 seq: 0x01 flg: 0x04 tail: 0x5a430601
frmt: 0x02 chkval: 0xdff5 type: 0x06=trans data
- buffer tsn: 0 表示该块对应的表空间号,这里是0号表空间
- rdba: 0x004195e1 (1/103905) 其中,rdba(relative data block address)表示相对数据块地址,其中(1/103905)表示该块为1号数据文件第103905个块,用4个字节32位来表示,前10位为相对数据文件号,后22位为块号。01c00083(十六进制)=0000 0000 0100 0001 1001 0101 1110 0001(二进制),不难看出前10位(0000 0000 01)转换成十进制就是1,后22位(00 0001 1001 0101 1110 0001)转换成十进制就是103905。rdba在数据块中的offset是4,即rdba存在于数据块中的第5-9字节中(offset从0开始算),数据块中的每个部分在数据块中的偏移量通过BBED可以展示出来
- scn: 0x1e5a43 表示数据块头部SCN.
总共占用6个字节,前2个字节(0000)表示SCN Wrap,后4个字节(00752951)表示SCN Base。如果SCN Base达到了4个字节表示的最大值,SCN Wrap+1,SCN Base清0。在数据块中的offset是8。这里的SCN号为7678289 - seq: 0x01 表示Sequence number即日志序列号。在数据块中的offset是14
- flg: 0x04 flg即Flag,其中,0x01代表New block即新建块;0x02代表Delayed Logging Change advanced SCN即数据块延迟清洗推进scn和seq;0x04代表Check value即设置校验和;0x08代表Temporary block即临时块。其它值都是01、02、04、08的组合。在数据块中的offset是15
- tail: 0x5a430601 即tail check,存放于数据块的最后4个字节,用于数据块一致性检查。tail check的组成:SCN Base的低2个字节+type+seq。即tail:0x5a430601=5a43+06+01
- frmt: 0x02 代表块格式。01表示Oracle 7,02表示Oracle 8+
- chkval: 0xdff5 代表块检查值。如果参数DB_BLOCK_CHECKSUM=TRUE,那么数据块在读入buffer和写回数据文件之前都要做检查计算,如果计算值和数据块中记录的计算值不匹配就会标记该块是坏块
- type: 0x06=trans data 代表块类型,参考以下的表格:
1.3.事务列表
Block header dump: 0x004195e1
Object id on Block? Y
seg/obj: 0x124df csc: 0x00000000001e5a42 itc: 2 flg: - typ: 2 - INDEX
fsl: 0 fnx: 0x0 ver: 0x01
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0000.000.00000000 0x00000000.0000.00 ---- 0 fsc 0x0000.00000000
0x02 0xffff.000.00000000 0x00000000.0000.00 C--- 0 scn 0x00000000001e5a42
- Object id on Block? Y 表示该块是否属于某个对象
-
seg/obj: 0x124df 表示该数据块中对象的OBJECT_ID。
select to_number('124df','xxxxxx') from dual;
select to_number('124df','xxxxxx') from dual;
TO_NUMBER('124DF','XXXXXX')
---------------------------
74975
col object_name for a20
select object_name, object_type from dba_objects where object_id=74975;
OBJECT_NAME OBJECT_TYPE
-------------------- -----------------------
IDX_SALES_INFO INDEX
- csc: 0x00000000001e5a42 表示SCN at last Block CleanOut,表示最后一次块清除(Block CleanOut)时候的SCN
- itc: 2 块中ITL slot的数量,0x01 和 0x02
- flg: – 0表示此块被放置在自由列表(freelist)中,E指的是ASSM
- typ: 2 – INDEX 表示数据库块的类型,1表示数据,2表示索引
ITL(Interested Transaction List,事务槽)
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0000.000.00000000 0x00000000.0000.00 ---- 0 fsc 0x0000.00000000
0x02 0xffff.000.00000000 0x00000000.0000.00 C--- 0 scn 0x00000000001e5a42
ITL是Oracle数据块内部的一个组成部分,用来记录在该块上发生的所有事务。1个ITL可以看作是一个记录,在一个时间,可以记录一个事务(包括提交或者未提交事务)。当然,如果这个事务已经提交,那么这个ITL的位置就可以被反复使用了,因为LTL与记录非常类似,所以,有的时候也叫ITL槽位。
ITL位于数据块头(Block Header),ITL事务槽由槽位号(Itl)、Xid(Transaction ID)、Uba(Undo Block Address)、Flag、Lck和Scn/Fsc几个部分组成。Oracle的每个数据块中都有一个或者多个事务槽,每一个对数据块的并发访问事务都会占用一个事务槽。对于已经提交的事务,ITL槽位不会马上被覆盖,因为一致性读可能会用到这个信息,一致性读的时候,可能需要从这里获得回滚段的入口,并从回滚段中获得一致性读。
当发出一条SQL语句时,Oracle会记录下这个时刻的SCN,然后在Buffer Cache中查找需要的BLOCK,或者从磁盘上读。当别的会话修改了数据,或者正在修改数据时,就会在相应的块上记录ITL,此时Oracle发现ITL中记录的SCN大于SELECT时刻的SCN,那么Oracle就会根据ITL中的Uba找到Undo信息获得该BLOCK的前镜像,然后在Buffer Cache中构造出CR(consistent read)块,此时Oralce也会检查构造出来的BLOCK中ITL记录的SCN。如果SCN还大于SELECT时刻的SCN,那么一直重复构造前镜像,然后Oracle找到前镜像BLOCK中的ITL的SCN是否小于SELECT的SCN,同时检查这个事务有没有提交或者回滚。如果没有,那么继续构造前镜像,直到找到需要的BLOCK,如果在构造前镜像的过程中所需的Undo信息被覆盖了,就会报快照过旧的错误。
如果一个事务一直没有提交,那么这个事务将一直占用一个ITL槽位。如果这个事务已经提交,那么,ITL槽位中还保存的有这个事务提交时候的SCN号。
ITL的个数受参数INITRANS控制,最大ITL个数受MAXTRANS控制(Oracle 10g已废弃MAXTRANS,默认最大支持255个并发)。在一个块内部,默认分配了2个ITL的个数。如果这个块内还有空闲空间(Free Space),那么Oracle是可以利用这些空闲空间并再次分配ITL。如果没有了空闲空间,那么这个块会因为不能分配新的ITL可能发生ITL等待,即enq: TX – allocate ITL entry等待事件。
在并发量特别大的系统中,最好分配足够的ITL个数,或者设置足够的PCTFREE,保证ITL能扩展。但是,PCTFREE有可能是被行数据给消耗掉的,如UPDATE,所以,也有可能导致块内部的空间不够而导致ITL等待。对于表(数据块)来说,INITRANS这个参数的默认值是1。对于索引(索引块)来说,这个参数默认值是2。
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0000.000.00000000 0x00000000.0000.00 ---- 0 fsc 0x0000.00000000
0x02 0xffff.000.00000000 0x00000000.0000.00 C--- 0 scn 0x00000000001e5a42
- Itl:ITL事务槽编号
- Xid:代表对应的事务id(transac[X]tion identified),在回滚段事务表中有一条记录和这个事务对应。Xid由3列使用十六进制编码的数字列表示,分别是:Undo Segment Number + Transaction Table Slot Number + Wrap,即由undo段号+undo槽号+undo槽号的覆盖次数三部分组成,即usn.slot.sqn。
INSERT INTO T_TESTBLOCK VALUES (4, 'd');
不要commit.
SQL> SELECT ROWID, DBMS_ROWID.ROWID_RELATIVE_FNO(ROWID) REL_FNO, DBMS_ROWID.ROWID_BLOCK_NUMBER(ROWID) BLOCKNO FROM T_TESTBLOCK;
ROWID REL_FNO BLOCKNO
------------------ ---------- ----------
AAASTiAABAAAZXhAAA 1 103905
AAASTiAABAAAZXhAAB 1 103905
AAASTiAABAAAZXhAAC 1 103905
AAASTiAABAAAZXhAAD 1 103905
SQL> ALTER SYSTEM DUMP DATAFILE 1 BLOCK 103905;
System altered.
SQL> select value from v$diag_info where name like 'Default%';
VALUE
--------------------------------------------------------------------------------
/oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/HAMSTER_ora_88283.trc
SQL> !more /oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/HAMSTER_ora_88283.trc
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0003.020.00000509 0x01000b87.0167.09 --U- 3 fsc 0x0000.001e5edd
0x02 0x0005.018.0000053a 0x010007f9.016d.1b ---- 1 fsc 0x0000.00000000
Xid: 0x0005.018.0000053a 十进制:5.24.1338,和查询V$TRANSACTION的结果是相对应的。
SQL> SELECT XIDUSN, XIDSLOT, XIDSQN, UBAFIL, UBABLK, UBASQN, UBAREC FROM V$TRANSACTION;
XIDUSN XIDSLOT XIDSQN UBAFIL UBABLK UBASQN UBAREC
---------- ---------- ---------- ---------- ---------- ---------- ----------
5 24 1338 4 2041 365 27
- Uba:即Undo Block Address,该事务对应的回滚段地址,记录了最近一次的该记录的前镜像(修改前的值)。Uba组成:Undo块地址(undo文件号和数据块号)+回滚序列号+回滚记录号。多版本一致读是Oracle保证读操作不会被事务阻塞的重要特性。当Server Process需要查询一个正在被事务修改,但是尚未提交的数据时,就根据ITL上的Uba定位到对应Undo前镜像数据位置。这里的Uba为:0x010007f9.016d.1b,其中:
0x010007f9(16进制)=0000 0001 0000 0000 0000 0111 1111 1001(2进制,共32位,前10位代表文件号,后22位代表数据块号)=文件号为4,块号为2041(10进制);
016d(16进制)=365(10进制);
1b(16进制)=27(10进制)。
Uba的值可以从V$TRANSACTION查询出来:
SQL> SELECT UBAFIL 回滚段文件号,UBABLK 数据块号,UBASQN 回滚序列号,UBAREC 回滚记录号 FROM v$transaction ;
回滚段文件号 数据块号 回滚序列号 回滚记录号
------------ ---------- ---------- ----------
4 2041 365 27
- Flag:事务标志位,即当前事务槽的状态信息。这个标志位记录了这个事务的操作状态,各个标志的含义分别是:
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0003.020.00000509 0x01000b87.0167.09 --U- 3 fsc 0x0000.001e5edd
0x02 0x0005.018.0000053a 0x010007f9.016d.1b ---- 1 fsc 0x0000.00000000
- Lck:表示这个事务所影响的行数,锁住了几行数据,对应有几个行锁。在这里,可以看到01号事务槽Lck为3,因为该事务槽中的事务Flag为U,证明该事务已经提交,但是锁还没有清除。
-
Scn/Fsc:Scn表示提交时的SCN。Commit SCN或者快速提交(Fast Commit,Fsc)的SCN。Scn=SCN of commited TX;Fsc=Free space credit(bytes)。
对于一个Oracle事务来说,可以是快速提交、也可以是延迟提交,目的都是为了提高提交的速度。提交以后,Oracle需要对ITL事务槽、每一行的锁定标记进行清除。如果是快速提交,那么在提交的时候,会将事务表和每一个数据块的ITL槽进行清除。但是锁定标记可能没有清除,等下次用到的时候再进行清除。如果是延迟提交,那么在提交的时候,只是将事务表进行清除,并没有对ITL事务槽进行清除,每一行的锁定标记也没有清除。因此,C和U的情况特别多。块清除的过程并不包括每个行的锁定标记的清除,主要指的是ITL的清除。
① 事务槽中首先记录的是XID和UBA,只有在提交以后,当对这个数据块进行CLEANOUT的时候,才会更新FLAG和SCN。因此,Oracle总是以事务表中对这个数据块的SCN以及FLAG为准。
② 一个事务开始以后,在一个数据块上得到一个事务槽,那么在这个事务提交以前,这个事务槽会一直占用,直到这个事务提交才会释放这个事务槽。
③ 只有在已经提交以后,这个ITL事务槽中的SCN才会有数值。
④ 事务是否已经提交、事务对应的SCN,这些信息都是以回滚段事务表中的为主,事务槽中的不准确。
⑤ 事务槽中的事务ID和UBA地址是准确的。
⑥ 事务槽中的事务ID和回滚段中的事务ID肯定不是一样的,不同回滚段中的事务ID也一定不一样。
1.3.用户数据头区(data_block_dump)
行目录(Row Directory)记录了数据块里每一行相对于起点的偏移量,Oracle正是通过行目录找到所需的数据行。
bdba: 0x004195e1
data_block_dump,data header at 0x7f319d4a605c
===============
tsiz: 0x1fa0
hsiz: 0x1a
pbl: 0x7f319d4a605c
76543210
flag=--------
ntab=1
nrow=4
frre=-1
fsbo=0x1a
fseo=0x1f80
avsp=0x1f62
tosp=0x1f62
0xe:pti[0] nrow=4 offs=0
0x12:pri[0] offs=0x1f98
0x14:pri[1] offs=0x1f90
0x16:pri[2] offs=0x1f88
0x18:pri[3] offs=0x1f80
block_row_dump:
tab 0, row 0, @0x1f98
tl: 8 fb: --H-FL-- lb: 0x1 cc: 2
col 0: [ 2] c1 02
col 1: [ 1] 61
tab 0, row 1, @0x1f90
tl: 8 fb: --H-FL-- lb: 0x1 cc: 2
col 0: [ 2] c1 03
col 1: [ 1] 62
tab 0, row 2, @0x1f88
tl: 8 fb: --H-FL-- lb: 0x1 cc: 2
col 0: [ 2] c1 04
col 1: [ 1] 63
tab 0, row 3, @0x1f80
tl: 8 fb: --H-FL-- lb: 0x2 cc: 2
col 0: [ 2] c1 05
col 1: [ 1] 64
- bdba: 0x004195e1 block dba/rdba(数据块地址),用4个字节32位来表示,前10位为相对数据文件号,后22位为块号。01c00083(十六进制)=0000 0000 0100 0001 1001 0101 1110 0001(二进制),可以看到前10位(0000 0000 0100)转换成十进制就是1,后22位(00 0001 1001 0101 1110 0001)转换成十进制就是1039051,即1号文件103905号数据块
-
tsiz: 0x1fa0 Total Data Area Size(数据区的大小,块的总大小),转换为10进制即8096字节
- hsiz: 0x1a 数据块头大小,转换为10进制即26字节
- pbl: 0x7f319d4a605c 指向这个数据块在内存中映像的指针
- flag=——– N=pcrfree hit(clusters);F=do not put on free list;K=flushable cluster keys
- ntab=1 number of tables (>1 is a cluster)
- nrow=4 即行数,这里表示这个表有4行数据
- frre=-1 first free row index entry, -1=you have to add one(没有创建索引)
- fsbo=0x1a free space begin offset(空闲空间起始位置),叫起始空间:可以存放数据空间的起始位置(即定义了数据层中空闲空间的起始offset)
- fseo=0x1f80 free space end offset(空闲空间结束位置),叫结束空间:可以存放数据空间的结束位置(即定义了数据层中空闲空间的结束offset)
- avsp=0x1f62 available space in the block(可用空间),叫空闲空间:定义了数据层中空闲空间的字节数
- tosp=0x1f62 total available space when all txs commit,叫最终空闲空间:定义了ITL中事务提交后,数据层中空闲空间的字节数
- 0xe:pti[0] nrow=4 offs=0 Table directory,整个表的开始,该块有3条记录
- 0x12:pri[0] offs=0x1f98 第1条记录在偏移量为0x1f98的地方,下面两行以此类推
- 0x14:pri[1] offs=0x1f90
- 0x16:pri[2] offs=0x1f88
1.4.用户数据区(block_row_dump)
block_row_dump:
tab 0, row 0, @0x1f98
tl: 8 fb: --H-FL-- lb: 0x1 cc: 2
col 0: [ 2] c1 02
col 1: [ 1] 61
tab 0, row 1, @0x1f90
tl: 8 fb: --H-FL-- lb: 0x1 cc: 2
col 0: [ 2] c1 03
col 1: [ 1] 62
tab 0, row 2, @0x1f88
tl: 8 fb: --H-FL-- lb: 0x1 cc: 2
col 0: [ 2] c1 04
col 1: [ 1] 63
end_of_block_dump
- tab 0, row 0, @0x1f98 第一个表第一行的位置,定义了该表在行索引中的起始插槽号
- lb: 0x1 表示lock byte。锁定该行的这个事务在ITL的入口,0x1说明事务在该数据行上的锁还没清除,并且该锁指向01号事务槽。lb: 0x0说明事务在该数据行上的锁已经被清除
- tl: 8 表示Row Size(number of bytes plus data)
- fb Flag Byte
K- Cluster key
H- head of row piece
D- Deleted row
F- first data piece
L- last data piece
P- First column cintinues from previous row N- Last column cintinues in next piece
当DELETE一行数据的时候,数据并不是物理地被删除,而是把该行标记为删除,这个时候fb应该是–HDFL–而不是原来的–H-FL–。 - cc 表示number of columns in this Row piece
关于行中的数据,可以以第一行来说明一下。由于表的第2行数据为(2,’b’),所以可以使用dump函数来验证一下。dump函数可以按指定的格式显示输入数据的内部表示,这里显示16进制:
tl: 8 fb: --H-FL-- lb: 0x1 cc: 2
col 0: [ 2] c1 03
col 1: [ 1] 62
SQL> select dump(2,16),dump('b',16) from dual;
DUMP(2,16) DUMP('B',16)
----------------- ----------------
Typ=2 Len=2: c1,3 Typ=96 Len=1: 62
2.实验二
2.1.创建测试表
create table t4 (id number, vname varchar2(10));
insert into t4 values (1, 'id');
insert into t4 values (2, 'ix');
查询数据段:
select HEADER_FILE, HEADER_BLOCK, BYTES, BLOCKS, EXTENTS from dba_segments where owner='SYS' and segment_name='T4';
HEADER_FILE HEADER_BLOCK BYTES BLOCKS EXTENTS
----------- ------------ ---------- ---------- ----------
1 104088 65536 8 1
commit;
2.1.无事务状态下的ITL
使用dbms_rowid包的方法解析数据行rowid信息。
select id, dbms_rowid.rowid_relative_fno(rowid) fno, dbms_rowid.rowid_block_number(rowid) bno, dbms_rowid.rowid_row_number(rowid) row_num from t4;
ID FNO BNO ROW_NUM
---------- ---------- ---------- ----------
1 1 104089 0
2 1 104089 1
两个数据行均在文件1的104089数据块上。我们接下来使用dump数据块的方法,将该块的逻辑结构dump到当前会话对应的跟踪文件中。
alter system dump datafile 1 block 104089;
select value from v$diag_info where name like 'Default%';
VALUE
--------------------------------------------------------------------------------
/oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/HAMSTER_ora_31103.trc
打开跟踪文件,可以找到对应的itl信息片段。
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0006.018.00000534 0x0100130d.01a1.09 C--- 0 scn 0x00000000001e9326
0x02 0x0006.012.00000534 0x0100130d.01a1.15 --U- 1 fsc 0x0000.001e947b
数据块默认是创建两个ITL对象。当并发事务操作较多的时候,会进行自动的拓展,最大值是255。
Xid是由三列使用十六进制编码的数字列表示,该列表示对应的事务编号。在Oracle中,标识一个事务是通过usn.slot.sqn表示。事务槽起作用的时候,每一个事务槽都与一个事务相关联。
Uba应当为undo block address的缩写。多版本一致读是Oracle保证读操作不会被事务阻塞的重要特性。当Server Process需要查询一个正在被事务修改,但是尚未提交的数据时,就根据ITL上的uba定位到对应Undo前镜像数据位置。
Flag对应的是当前事务槽的状态信息,标志着不同的事务状态(参考实验一)。
Lck表示该事务槽涉及到的记录数目。Scn/Fsc:表示快速提交和已经提交的SCN编号。
2.2.启动单会话事务
SQL> select sid from v$mystat where rownum<2;
SID
----------
271
SQL> update t4 set vname='ig' where id=1;
1 row updated.
事务信息和锁信息如下:
SQL> select ADDR, XIDUSN, XIDSLOT, XIDSQN from v$transaction;
ADDR XIDUSN XIDSLOT XIDSQN
---------------- ---------- ---------- ----------
000000006424A120 10 24 1224
dump出数据块,ITL如下:
select id, dbms_rowid.rowid_relative_fno(rowid) fno, dbms_rowid.rowid_block_number(rowid) bno, dbms_rowid.rowid_row_number(rowid) row_num from t4;
ID FNO BNO ROW_NUM
---------- ---------- ---------- ----------
1 1 104089 0
2 1 104089 1
SQL> alter system dump datafile 1 block 104089;
System altered.
SQL> select value from v$diag_info where name like 'Default%';
/oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/HAMSTER_ora_32255.trc
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0006.005.0000053b 0x01000492.01a2.1d --U- 2 fsc 0x0000.001ea045
0x02 0x0000.000.00000000 0x00000000.0000.00 ---- 0 fsc 0x0000.00000000
第二行事务槽,锁定影响记录数量为2。对应的xid为0x0006.005.0000053b。转换为十进制后分别为:6,5和1339。与v$transaction中对应的事务标识一致。说明0x01事务槽对应的是我们会话事务。
2.3.启动第二个会话事务
SQL> select sid from v$mystat where rownum<2;
SID
----------
31
SQL> update t4 set vname='ik' where id=2;
1 row updated.
事务信息和锁信息如下:
SQL> select ADDR, XIDUSN, XIDSLOT, XIDSQN from vtransaction;
ADDR XIDUSN XIDSLOT XIDSQN
---------------- ---------- ---------- ----------
000000006424A120 10 24 1224
000000006433F040 4 25 982
select addr, kaddr, sid, type, id1, id2, lmode from vlock where sid=17 or sid=271 or sid =31 order by 1;
ADDR KADDR SID TY ID1 ID2 LMODE
---------------- ---------------- ---------- -- ---------- ---------- ----------
000000006424A120 000000006424A1A8 271 TX 655384 1224 6
000000006433F040 000000006433F0C8 31 TX 262169 982 6
000000006741F710 000000006741F790 31 AE 133 0 4
000000006741F958 000000006741F9D8 271 AE 133 0 4
000000006741FB88 000000006741FC08 17 AE 133 0 4
00007F3BAA25B538 00007F3BAA25B5A8 31 TM 74986 0 3
00007F3BAA25B538 00007F3BAA25B5A8 271 TM 74986 0 3
dump出数据块,ITL如下:
select id, dbms_rowid.rowid_relative_fno(rowid) fno, dbms_rowid.rowid_block_number(rowid) bno, dbms_rowid.rowid_row_number(rowid) row_num from t4;
ID FNO BNO ROW_NUM
---------- ---------- ---------- ----------
1 1 104089 0
2 1 104089 1
SQL> alter system dump datafile 1 block 104089;
System altered.
SQL> select value from v$diag_info where name like 'Default%';
/oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/HAMSTER_ora_31103.trc
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0004.019.000003d6 0x01000333.016b.05 ---- 1 fsc 0x0000.00000000
0x02 0x000a.018.000004c8 0x01000405.0100.0b ---- 1 fsc 0x0000.00000000
4.25.982
10.24.1224
两条ITL被占据!
2.4.启动第三个会话事务
SQL> select sid from v$mystat where rownum<2;
SID
----------
253
SQL> insert into t4 values (3,'i3');
1 row created.
事务信息和锁信息如下:
SQL> select ADDR, XIDUSN, XIDSLOT, XIDSQN from vtransaction;
ADDR XIDUSN XIDSLOT XIDSQN
---------------- ---------- ---------- ----------
000000006424A120 10 24 1224
000000006433F040 4 25 982
00000000643637D0 5 8 1343
select addr, kaddr, sid, type, id1, id2, lmode from vlock where sid=17 or sid=271 or sid =31 or sid=253 order by 1;
ADDR KADDR SID TY ID1 ID2 LMODE
---------------- ---------------- ---------- -- ---------- ---------- ----------
000000006424A120 000000006424A1A8 271 TX 655384 1224 6
000000006433F040 000000006433F0C8 31 TX 262169 982 6
00000000643637D0 0000000064363858 253 TX 327688 1343 6
000000006741F710 000000006741F790 31 AE 133 0 4
000000006741F958 000000006741F9D8 271 AE 133 0 4
000000006741FB88 000000006741FC08 17 AE 133 0 4
000000006741FFE8 0000000067420068 253 AE 133 0 4
00007F28693135F8 00007F2869313668 31 TM 74986 0 3
00007F28693135F8 00007F2869313668 253 TM 74986 0 3
00007F28693135F8 00007F2869313668 271 TM 74986 0 3
dump出数据块,ITL如下:
select id, dbms_rowid.rowid_relative_fno(rowid) fno, dbms_rowid.rowid_block_number(rowid) bno, dbms_rowid.rowid_row_number(rowid) row_num from t4;
ID FNO BNO ROW_NUM
---------- ---------- ---------- ----------
1 1 104089 0
2 1 104089 1
3 1 104089 2
SQL> alter system dump datafile 1 block 104089;
System altered.
SQL> select value from v$diag_info where name like 'Default%';
/oracle/app/oracle/diag/rdbms/hamster/HAMSTER/trace/HAMSTER_ora_31103.trc
Itl Xid Uba Flag Lck Scn/Fsc
0x01 0x0004.019.000003d6 0x01000333.016b.05 ---- 1 fsc 0x0000.00000000
0x02 0x000a.018.000004c8 0x01000405.0100.0b ---- 1 fsc 0x0000.00000000
0x03 0x0005.008.0000053f 0x010000c4.016e.32 ---- 1 fsc 0x0000.00000000
4.25.982
10.24.1224
5.8.1343
增加一个Itl, 当前准备的事务槽个数小于数据块进行的事务个数时,会进行事务槽自动拓展。