官方对于kfed repair命令的描述比较简单:Recover the disk header from the redundant copy of it maintained on an unused portion of the disk. 其主要用来disk header的头4096 bytes的KFBTYP_DISKHEAD结构,这个恢复是基于10.2.0.5以后的Disk Header自动备份机制的。其在PST即AU=1的最后第二个数据块中(Read from PST(AU 1)’s penultimate Block)自动备份了KFBTYP_DISKHEAD。
如:
[oracle@mlab2 oracleasm]$ kfed read asm-disk04 aun=1 blkn=254|less kfbh.endian: 1 ; 0x000: 0x01 kfbh.hard: 130 ; 0x001: 0x82 kfbh.type: 1 ; 0x002: KFBTYP_DISKHEAD kfbh.datfmt: 1 ; 0x003: 0x01 kfbh.block.blk: 0 ; 0x004: blk=0 kfbh.block.obj: 2147483651 ; 0x008: disk=3 kfbh.check: 98849704 ; 0x00c: 0x05e453a8 kfbh.fcn.base: 0 ; 0x010: 0x00000000 kfbh.fcn.wrap: 0 ; 0x014: 0x00000000 kfbh.spare1: 0 ; 0x018: 0x00000000 kfbh.spare2: 0 ; 0x01c: 0x00000000 kfdhdb.driver.provstr: ORCLDISK ; 0x000: length=8 kfdhdb.driver.reserved[0]: 0 ; 0x008: 0x00000000 kfdhdb.driver.reserved[1]: 0 ; 0x00c: 0x00000000 kfdhdb.driver.reserved[2]: 0 ; 0x010: 0x00000000 kfdhdb.driver.reserved[3]: 0 ; 0x014: 0x00000000 kfdhdb.driver.reserved[4]: 0 ; 0x018: 0x00000000 kfdhdb.driver.reserved[5]: 0 ; 0x01c: 0x00000000 kfdhdb.compat: 168820736 ; 0x020: 0x0a100000 kfdhdb.dsknum: 3 ; 0x024: 0x0003 kfdhdb.grptyp: 3 ; 0x026: KFDGTP_HIGH kfdhdb.hdrsts: 3 ; 0x027: KFDHDR_MEMBER kfdhdb.dskname: DATA1_0003 ; 0x028: length=10 kfdhdb.grpname: DATA1 ; 0x048: length=5 kfdhdb.fgname: DATA1_0003 ; 0x068: length=10 kfdhdb.capname: ; 0x088: length=0 kfdhdb.crestmp.hi: 33006980 ; 0x0a8: HOUR=0x4 DAYS=0xc MNTH=0x9 YEAR=0x7de kfdhdb.crestmp.lo: 2555232256 ; 0x0ac: USEC=0x0 MSEC=0x370 SECS=0x4 MINS=0x26 kfdhdb.mntstmp.hi: 33008247 ; 0x0b0: HOUR=0x17 DAYS=0x13 MNTH=0xa YEAR=0x7de kfdhdb.mntstmp.lo: 3341018112 ; 0x0b4: USEC=0x0 MSEC=0xf9 SECS=0x32 MINS=0x31 kfdhdb.secsize: 512 ; 0x0b8: 0x0200 kfdhdb.blksize: 4096 ; 0x0ba: 0x1000 kfdhdb.ausize: 1048576 ; 0x0bc: 0x00100000 kfdhdb.mfact: 113792 ; 0x0c0: 0x0001bc80 kfdhdb.dsksize: 128800 ; 0x0c4: 0x0001f720 kfdhdb.pmcnt: 3 ; 0x0c8: 0x00000003 kfdhdb.fstlocn: 1 ; 0x0cc: 0x00000001 kfdhdb.altlocn: 2 ; 0x0d0: 0x00000002 :
由于ASM 有这个备份,所以kfed repair可以自动修复ASM disk header的最开始的4096 bytes,但又由于这个备份只备份4096字节的metadata,所以它不能应对整体metadata(除掉KFBTYP_DISKHEAD外)还有大量的其他必须的metadata元数据。
之前在用户现场发现kfed repair也能修复PST KFBTYP_PST_META中的部分逻辑讹误/损坏,但一直无法在自己的环境中重现。
具体STRACE了下 kfed repair的处理过程:
[oracle@mlab2 oracleasm]$ dd if=/dev/zero of=asm-disk04 bs=4096 count=1 conv=notrunc 1+0 records in 1+0 records out 4096 bytes (4.1 kB) copied, 6.9811e-05 seconds, 58.7 MB/s [oracle@mlab2 oracleasm]$ [oracle@mlab2 oracleasm]$ kfed read asm-disk04 kfbh.endian: 0 ; 0x000: 0x00 kfbh.hard: 0 ; 0x001: 0x00 kfbh.type: 0 ; 0x002: KFBTYP_INVALID kfbh.datfmt: 0 ; 0x003: 0x00 kfbh.block.blk: 0 ; 0x004: blk=0 kfbh.block.obj: 0 ; 0x008: file=0 kfbh.check: 0 ; 0x00c: 0x00000000 kfbh.fcn.base: 0 ; 0x010: 0x00000000 kfbh.fcn.wrap: 0 ; 0x014: 0x00000000 kfbh.spare1: 0 ; 0x018: 0x00000000 kfbh.spare2: 0 ; 0x01c: 0x00000000 7F70E2F06400 00000000 00000000 00000000 00000000 [................] Repeat 255 times KFED-00322: Invalid content encountered during block traversal: [kfbtTraverseBlock][Invalid OSM block type][][0] [oracle@mlab2 oracleasm]$ [oracle@mlab2 oracleasm]$ [oracle@mlab2 oracleasm]$ www.askmaclean.com [oracle@mlab2 oracleasm]$ [oracle@mlab2 oracleasm]$ strace -o kfed1.log kfed repair asm-disk04 munmap(0x7fd80aa2d000, 143360) = 0 stat("asm-disk04", {st_mode=S_IFREG|0644, st_size=135056588800, ...}) = 0 access("asm-disk04", F_OK) = 0 statfs("asm-disk04", {f_type="EXT2_SUPER_MAGIC", f_bsize=4096, f_blocks=961422084, f_bfree=454635689, f_bavail=405808746, f_files=244187136, f_ffree=24 4182184, f_fsid={-138681668, -1790432782}, f_namelen=255, f_frsize=4096}) = 0 open("asm-disk04", O_RDWR) = 7 lseek(7, 2088960, SEEK_SET) = 2088960 read(7, "/1/202/1/1/0/0/0/0/3/0/0/200/250S/344/5/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0"..., 4096) = 4096 lseek(7, 0, SEEK_SET) = 0 read(7, "/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0"..., 4096) = 4096 lseek(7, 0, SEEK_SET) = 0 write(7, "/1/202/1/1/0/0/0/0/3/0/0/200/250S/344/5/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0/0"..., 4096) = 4096 close(7)
在以上场景中未重现KFED 修复KFBTYP_PST_META的元数据,其仅仅读取了偏移量为2088960的(2088960/4096=510=255+255 即AUN=1的最后第二个块)的4096字节,并写入到OFFSET=0的地方。
具体查看了以下KFED的源代码 , 也并未发现其会修复其他地方metadata的线索:
#define KFEDOP_REPAIR ((kfedop)13) /* Repair ASM disk header */ www.askmaclean.com case KFEDOP_REPAIR: /* Read from PST(AU 1)'s penultimate Block */ cx->aunum_kfedcx = (ub4)1; cx->blknum_kfedcx = (ub4)(bfact - 2); if (!kfedReadBlk(cx)) goto done; /* Validate the Disk Header block read from PST */ if(!kfedValidateBlk(cx, KFBTYP_DISKHEAD)) goto done; /* Fix the block number and checksum in the buffer */ if (!kfedFixBackupHeader(cx)) www.askmaclean.com goto done; /* Write to Disk Header(AU 0 and Block 0) */ cx->aunum_kfedcx = (ub4)0; cx->blknum_kfedcx = (ub4)0; if (!kfedWriteBlk(cx)) goto done; break;
以上代码可以理解为,KFEDOP_REPAIR操作读取PST(AU 1)’s penultimate Block即AUN=1的最后第二个块,若无法读取则直接报错,若可以读取则验证从PST中读取的DISK header的block,并FIX其中的block number以及checksum值,之后写出到disk header即AUN=0 BLKN=0的地方。
总之,如果确实遇到了此类ASM的问题,那么在充分备份DISK HEADER后(备份前200MB是必要的),在有DISK HEADER自动备份的情况下,尝试KFED REPAIR一下吧,如果不能成功那么后续会有一堆的诊断metadata和手动修复工作等着我们呢。
服务热线 : 400-690-3643 备用电话: 18501767907 邮箱:service@parnassusdata.com
ORACLE PRM是诗檀软件独立研发的ORACLE数据库灾难恢复软件,其具有全程图形化界面、简单高效等特点。
欢迎下载使用ORACLE PRM。 下载地址:http://parnassusdata.com/sites/default/files/ParnassusData_PRMForOracle_3206.zip
PRM用户使用手册。http://www.parnassusdata.com/sites/default/files/ParnassusData%20Recovery%20Manager%20For%20Oracle%20Database%E7%94%A8%E6%88%B7%E6%89%8B%E5%86%8C%20v0.3.pdf