一. dump datafileblock 示例
oracle的一个数据块里的scn有三种,分别是块头的scn, csc (cleanout scn)和itl中记录的commit scn。 如果我们想查看某个或者某些block 里的内容,可以把这些block dump出来查看。
关于这个dump 方法,在之前的文章里有说明:
oracle rdba和 dba 说明
orace itl(interested transaction list) 说明
根据rowid 查询对应的block number 和datafile number:
sql> select
2dbms_rowid.rowid_relative_fno(rowid) rel_fno,
3dbms_rowid.rowid_block_number(rowid) blockno,
4dbms_rowid.rowid_row_number(rowid) rowno,
5 empno, ename
6 from emp where empno = 7369;
rel_fno blockno rowno empnoename
---------- -------------------- ---------- ----------
4 20 0 7369 smith
然后根据block id执行dump 命令:
sql> alter system dump datafile 4 block 20;
如果要dump 多个block,,命令如下:
sql>alter system dump datafile block min block max ;
sys@anqing2(rac2)> oradebug setmypid
statement processed.
sys@anqing2(rac2)> alter system dump datafile 1 block 292689;
system altered.
sys@anqing2(rac2)> oradebug tracefile_name
/u01/app/oracle/admin/anqing/udump/anqing2_ora_32276.trc
[oracle@rac2 ~]$ cat /u01/app/oracle/admin/anqing/udump/anqing2_ora_32276.trc
*** 2011-08-01 17:51:31.366
start dump data blocks tsn: 0file#: 1 minblk 292689 maxblk 292689
buffer tsn: 0 rdba: 0x00447751(1/292689)
-- buffertsn: 数据文件对应的tablespace 的 number ,这只是dump文件中记录的数据而已,block 中是没有记录tablespace 的 number 的
scn: 0x0000.005bdee1 seq: 0x01flg: 0x06 tail: 0xdee10601
frmt: 0x02 chkval: 0xaf6f type:0x06=trans data
hex dump of block: st=0,typ_found=1
dump of memory from 0x0dc34400to 0x0dc36400
dc34400 0000a206 00447751005bdee1 06010000 [....qwd...[.....]
......
dc363f0 c3040203 04261c0b65766164 dee10601 [......&.dave....]
block header dump: 0x00447751
object id on block? y
seg/obj: 0xd5ec csc: 0x00.5bcbe0 itc: 3 flg: - typ: 1 - data
fsl: 0 fnx: 0x0 ver: 0x01
itl xid uba flag lck scn/fsc
0x01 0x000e.007.00000236 0x00000000.0000.00 c-u- 0 scn 0x0000.005b1f7f
0x02 0x000c.005.000003b4 0x01401727.0144.13 c--- 0 scn 0x0000.005bbf0b
0x03 0x0011.007.00000406 0x0140015b.00c7.57 --u- 483 fsc 0x0000.005bdee1
data_block_dump,data header at0xdc34474
-- 其实这个block不是直接从data buffer 中 dump 出来的,这个表示真正dump时 block 的数据区的起始位置,也就是下面这部分开始的位置
===============
tsiz: 0x1f88
-- tsiz: hsiz: pbl: bdba: 在数据文件都是没有存储的
--total data area size
--8k的block: 8192-20(blockhead)-24(transaction header)-24*3(一个事务条)-4(block tail)=8072(0x1f88)
--将十六进制转换为10进制
sys@anqing2(rac2)> selectto_number('1f88','xxxx') from dual;
to_number('1f88','xxxx')
------------------------
8072
hsiz: 0x3d8
--data headersize
pbl: 0x0dc34474
-- pointer tobuffer holding the block
bdba: 0x00447751
76543210
flag=--------
ntab=1
nrow=483
frre=-1
fsbo=0x3d8
fseo=0x706
avsp=0x32e
tosp=0x32e
0xe:pti[0] nrow=483 offs=0
0x12:pri[0] offs=0x1f7b
0x14:pri[1] offs=0x1f6e
......
0x3d4:pri[481] offs=0x713
0x3d6:pri[482] offs=0x706
block_row_dump:
tab 0, row 0, @0x1f7b
tl: 13 fb: --h-fl-- lb:0x3 cc: 2
col 0: [ 4] c3 0b 1c 26
col 1: [ 4] 64 61 76 65
tab 0, row 1, @0x1f6e
tl: 13 fb: --h-fl-- lb:0x3 cc: 2
col 0: [ 4] c3 0b 1c 27
col 1: [ 4] 64 61 76 65
tab 0, row 2, @0x1f61
tl: 13 fb: --h-fl-- lb:0x3 cc: 2
col 0: [ 4] c3 0b 1c 28
col 1: [ 4] 64 61 76 65
......
tab 0, row 481, @0x713
tl: 13 fb: --h-fl-- lb:0x3 cc: 2
col 0: [ 4] c3 0b 21 13
col 1: [ 4] 64 61 76 65
tab 0, row 482, @0x706
tl: 13 fb: --h-fl-- lb:0x3 cc: 2
col 0: [ 4] c3 0b 21 14
col 1: [ 4] 64 61 76 65
--这里的row482 之类的都是每一条记录里的具体值。我dump 这个block 保存的记录比较简单,只有2列值。 可以将这个值转换成具体的字符串。 方法如下:
sys@anqing2(rac2)> setserveroutput on
sys@anqing2(rac2)> declare nnumber;
2 begin
3 dbms_stats.convert_raw_value('c30b2114',n);
4 dbms_output.put_line(n);
5 end;
6 /
103219
pl/sql procedure successfullycompleted.
sys@anqing2(rac2)> declarestr varchar2(100);
2 begin
3 dbms_stats.convert_raw_value('64617665',str);
4 dbms_output.put_line(str);
5 end;
6 /
dave --这个就是 col 1: [ 4] 64 61 76 65 对应的值
pl/sql procedure successfullycompleted.
end_of_block_dump
end dump data blocks tsn: 0file#: 1 minblk 292689 maxblk 292689
[oracle@rac2 ~]$
