天天看点

Oracle ASM 翻译系列第二十六弹:ASM 高级知识 Where is my dataWhere is my data

有时候我们想要知道一个特定的database block位于asm的哪个磁盘,磁盘的哪个au以及au的哪一个块。本篇文章将向大家展示如何解决这个问题。

首先在数据库里创建测试表空间:

sql> create tablespace t1 datafile '+data';

tablespace created.

sql> select f.file#, f.name "file", t.name "tablespace"

from v$datafile f, v$tablespace t

where t.name='t1' and f.ts# = t.ts#;

file# file                               tablespace

----- ---------------------------------- ----------

   6  +data/br/datafile/t1.272.797809075 t1

sql>

注意到asm file number是272。

现在创建一张测试表并插入数据:

sql> create table tab1 (n number, name varchar2(16))

tablespace t1;

table created.

sql> insert into tab1 values (1, 'cat');

1 row created.

sql> commit;

commit complete.

查询块号:

sql> select rowid, name from tab1;

rowid name

------------------ ----

aaasxxaagaaaachaaa cat

sql> select

dbms_rowid.rowid_block_number('aaasxxaagaaaachaaa')

"block number" from dual;

block number

------------

135

查询数据文件的块大小:

sql> select block_size from v$datafile where file#=6;

block_size

----------

8192

可以看到插入的数据位于135号块,数据文件块大小为8k。

连接asm实例,查询272号文件的区分布:

sql> select group_number from v$asm_diskgroup where name='data';

group_number

           1

sql> select pxn_kffxp, -- physical extent number

xnum_kffxp,            -- virtual extent number

disk_kffxp,            -- disk number

au_kffxp               -- allocation unit number

from x$kffxp

where number_kffxp=272 -- asm file 272

and group_kffxp=1      -- group number 1

order by 1;

pxn_kffxp  xnum_kffxp disk_kffxp   au_kffxp

---------- ---------- ---------- ----------

         0          0          0       1175

         1          0          3       1170

         2          1          3       1175

         3          1          2       1179

         4          2          1       1175

...

可以看到文件的区分布在所有磁盘,由于数据文件为normal冗余,每个区都是两副本。注意我说的是数据文件为normal冗余。默认情况下,文件会继承磁盘组的冗余策略。控制文件是个例外:即使在normal冗余的磁盘组,如果磁盘组包含至少3个failgroup,控制文件也会被创建为high冗余。

查询磁盘组的au大小:

sql> select value from v$asm_attribute where

name='au_size' and group_number=1;

value

-------

1048576

au大小为1mb。注意每个磁盘组可以有不同的au大小。

现在已知测试数据在272号asm file的135号块。数据块为8k的情况下,每个au可以包含128个块。这就意味着135号块位于第二个virtual extent的第7个块。第二个virtual extent包含3号磁盘的1175号au和2号磁盘的1179号au.

查询磁盘2和3的名字:

sql> select disk_number, name

from v$asm_disk

where disk_number in (2,3);

disk_number name

----------- ------------------------------

         2 asmdisk3

         3 asmdisk4

我使用了asmlib,所以在os层面,对应的磁盘名为:

/dev/oracleasm/disks/asmdisk3和/dev/oracleasm/disks/asmdisk4

测试数据位于1175号au的第7个块。我们首先将这个au的数据dd出来:

$ dd if=/dev/oracleasm/disks/asmdisk4 bs=1024k count=1 skip=1175 of=au1175.dd

1+0 records in

1+0 records out

1048576 bytes (1.0 mb) copied, 0.057577 seconds, 18.2 mb/s

$ ls -l au1175.dd

-rw-r--r-- 1 grid oinstall 1048576 oct 27 22:45 au1175.dd

$

注意几个参数的含义:

· bs=1024k -- au的大小

· skip=1175 -- 我们需要导出的au

· count=1 -- 只需要导出一个au

然后将7号块的数据从au中导出:

$ dd if=au1175.dd bs=8k count=1 skip=7 of=block135.dd

注意bs指定为8k(数据块大小),skip指定为7(要导出的块号)。

查看数据块内容:

$ od -c block135.dd

0017760 \0 \0 , 001 002 002 301 002 003 c a t 001 006 332 217

0020000

在内容的最后可以看到插入的数据 -- cat.注意oracle数据块从下向上填充。如果去查看磁盘/dev/oracleasm/disks/asmdisk3的1179号au,结果是一样的。

要定位asm中数据块的位置,需要知道数据块位于哪个数据文件。然后通过x$kffxp视图查看数据文件的区分布。还需要数据块大小和asm au大小去定位数据块位于哪个au。 以上操作和asm或者rdbms的版本无关。(v$asm_attribute视图除外,因为在10g中没有该视图)在normal和high冗余模式下,将会有多副本数据。但是定位数据块的方法是相同的。

<b>本文来自云栖社区合作伙伴“dbgeek”</b>