RMAN备份恢复时遇到的ORA-19566(坏块处理操作)

发布时间:2026/10/27 9:50:16
RMAN备份恢复时遇到的ORA-19566(坏块处理操作) 目录一、概述二、数据库坏块及数据一致性2.1.什么是数据库坏块2.2.什么是数据一致性三、坏块产生的原因3.1.硬件问题3.2.操作系统BUG3.3.操作系统的I/O错误或缓冲问题3.4.Oracle软件BUG3.5.非Oracle进程扰乱Oracle共享内存区域3.6.异常关机掉电终止服务四、物理坏块和逻辑坏块4.1.物理坏块Physical Corruption / Media Corruption4.2.逻辑坏块Logical Corruption五、检查数据块的一致性参数配置5.1.使用初始化参数检查数据块的一致性六、此次ORA-19566修复6.1.对坏块进行诊断1检查数据文件2检查单个数据文件3检查整个库6.2.确定存在坏块的对象是什么6.3.修复坏块七、后续补充7.1.坏块的恢复理论7.2.不丢数据的恢复方法7.3.可能会丢数据的恢复方法7.3.1.确认坏块类型7.3.2.确定文件号7.3.3.确认损坏数据块的类型7.3.4.按照不同的类型设置不同的恢复策略1用户表2分区表3索引7.4.恢复数据7.4.1.dbms_repair方法7.4.2.使用10231事件一、概述在做rman备份时我们有时候可能会遇到ORA-19566错误Exceeded Limit Of 0 Corrupt Blocks该错误说明在备份过程中遇到坏块。二、数据库坏块及数据一致性2.1.什么是数据库坏块数据库的数据块有固定的格式和结构分三层cache layertransaction layerdata layer。在我们对数据块进行读取写入操作的时候数据库会对要读写的数据块做一致性的检查其中包括数据块的类型、数据块的地址信息、数据块的 SCN 号以及数据块的头部和尾部。如果发现其中有不一致的信息那数据库就会标记这个数据块为坏块了。在 Oracle 数据块的最后通常是最后 4 个字节有一个校验和Checksum和块尾 SCN。当数据块在内存中被修改后Oracle 会重新计算校验和并写回块尾。如果读取时算出来的校验和与块尾记录的不一致就会立刻抛出坏块错误通常是 ORA-01578 或 ORA-19566。这也是为什么在底层存储如 NAS/SAN 网络抖动导致数据包错乱时最先暴露的就是坏块。2.2.什么是数据一致性在数据库中有一个概念叫做数据块的一致性Oracle的数据块的一致性包括了两个层次物理一致性和逻辑一致性。在每一个数据块的头部有一个校验和字段每当数据块要被写回磁盘前Oracle都会重新计算 这个数据块的校验和并记录到这个字段最终写会磁盘。下次数据块被读入内存Oracle会重新 计算数据块的校验和并和块头的字段相比较如果有差异Oracle就知道这个数据块有错误 会报出ORA-1578错误。通过校验和字段进行的检查就是物理一致性检查这个功能可以让Oracle检查到所有底层的错误 包括磁盘、存储、IO子系统所以称做物理一致性检查。在Oracle中每当要修改一个数据块中会先对数据块内容做一个一致性检查如检查记录 是否被不存在的食物锁定、记录和索引是否对应等。如果这种一致性检查失败就会抛出 ORA-600的Internal错误。当Oracle检查到数据块的逻辑一致性时会尝试对数据块做 Cache Recovery,如果不能把数据块恢复到一致状态Oracle就会把这个数据块标志为 Software Corrupt,当有查询访问到这数据块时也会抛出前面ORA-1578错误。物理一致性检查利用校验和字段工作主要侧重于检查硬件故障并不关心内容正确与否而逻辑一致性检查就是侧重于内容的检查内容检查要比校验和检查复杂的多。 逻辑一致性检查内容要多于物理一致性检查。三、坏块产生的原因坏块产生的原因大致有以下几种3.1.硬件问题Oracle进程在处理一个数据块时首先将其读入物理内存空间在处理完成后再由特定进程将其写回磁盘如果在这个过程中出现内存故障CPU计算失误都会导致内存数据块的内容混乱最后反映到写回磁盘的数据块内容有误。同样如果存储子系统出现异常数据块损坏也就随之出现了。3.2.操作系统BUG由于Oracle进程对数据块的读写都是以操作系统内核调用system call的方式完成的如果操作系统在内核调用存在问题必然导致Oracle进程写入非法的内容。3.3.操作系统的I/O错误或缓冲问题3.4.Oracle软件BUGOracle软件特定版本上可能出现导致数据块的内容出现异常BUG。3.5.非Oracle进程扰乱Oracle共享内存区域如上文所述在当数据块的内容被读入主机的物理内存时如果其他非Oracle进程对Oracle使用的共享内存区域形成了扰乱最终导致写回磁盘的数据块内容混乱。3.6.异常关机掉电终止服务异常关机掉电终止服务使进程异常终止而破坏数据块的完整性导致坏块产生。注这也是为什么突然断电会导致数据库无法启动由上可见造成数据块损坏的原因多种多样可是因为物理原因导致也可能人为原因或Oracle bug导致。比较常见的其它原因是异常关机、掉电、终止服务使进程异常终止从而破坏数据的完整性导致坏块的产生。发生数据块损坏的原因时最典型的表现是遇到ORA-01578错误比如在全表扫描时有时也可能是ORA-600内部错误。四、物理坏块和逻辑坏块两种坏块的本质区别与应对4.1.物理坏块Physical Corruption / Media Corruption本质操作系统或底层存储读取出来的字节流完全不符合 Oracle 数据块的格式。比如磁盘物理损伤、扇区损坏、或者存储底层数据被其他程序覆盖。特征块头部的 magic number 都对不上Oracle 根本不知道这是个什么东西。应对这类坏块往往具有“传染性”或底层关联性。如果 DBV 检查出物理坏块说明底层存储介质大概率出问题了比如坏道需要结合 RAID 状态、存储硬件日志一起排查然后通过 RMAN 备份恢复。4.2.逻辑坏块Logical Corruption本质数据块的物理结构完好无损格式正确、校验和也是对的但块内部的数据逻辑乱了。比如字典表记录不一致、行链接Row Chaining指向了错误的地址。特征Oracle 软件 Bug比如某些版本的 BUG 导致数据写入错位、人为错误操作、或者系统异常宕机导致内存数据只写了一半。应对逻辑坏块往往可以通过 DBMS_REPAIR 标记跳过或者重建索引/表来解决。如果发生在系统元数据如数据字典上往往需要打补丁或使用特殊事件如 10231 event来绕过错误进行导出。Oracle数据库出现坏块现象是指在Oracle数据库的一个或多个数据块一个数据块的容量在创建数据库时由db_block_size参数指 定缺省为8K内出现内容混乱的现象。由于正常的数据块都有固定的合法内容格式坏块的出现导致数据库进程无法正常解析数据块的内容进而使数据库进 程报错乃至挂起并级联导致整个数据库实例出现异常。五、检查数据块的一致性参数配置5.1.使用初始化参数检查数据块的一致性为了及时发现物理坏块和准确定位坏块产生的原因oracle建议设置初始化参数DB_BLOCK_CHECKSUMTYPICAL默认值。一般情况下物理坏块是由于底层OS/disk系统错误/损坏导致数据块被修改数据块标志为坏块(corruption)。通过设置初始化参数db_block_checksumtrue/false来启用、关闭物理一致性检查启用该参数这会增加1%10%的负载尤其DML操作越密集性能影响越大。将这个参数设置为false,这将意味数据库只对System表空间做逻辑一致性检查。Oracle推荐启用该参数。在Oracle9i、10g中,默认是启用的。常见的物理坏块Physical Block Corruptions有块头和块尾信息不一致(Fractured/Incomplete)checksum值无效数据块信息全部为0等情况并且可能伴随错误ORA-1578和ORA-1110。DBWR进程将数据块写入disk时会计算数据块的Checksum并且将Checksum值记录在数据块的位置offset 16和17当从disk读取该数据块时oracle重新计算数据块的Checksum并且与记录在数据块中的Checksum做异或运算Xor如果异或结果为非0说明数据块被修改过数据块为坏块(corruption)。六、此次ORA-19566修复6.1.对坏块进行诊断使用DBV进行坏块检测此工具需要额外安装此次未采用dbv file/opt/xbzx/products/oradata/orcl/orclpdb/ISP_DEP3_03.dbf blocksize8192使用rman工具检查 :1检查数据文件backup check logical validate [database];2检查单个数据文件backup check logical validate datafile 1,2;3检查整个库backup check logical validate database检查的结果放在v$database_block_corruption这个动态视图中。*这个命令对系统性能有一定的影响。6.2.确定存在坏块的对象是什么前面已经说过RMAN的检查结果会存放在v$database_block_corruption记录了数据库所有坏块信息的视图与 dba_extents记录了所有段/对象占用的块范围进行关联。通过比对“文件号”以及“坏块号是否落在对象占用的块范围内”从而精准定位出到底是哪个表、哪个索引或者哪个分区发生了坏块。SELECT DISTINCT file#,segment_name,segment_type,tablespace_name,partition_nameFROM dba_extents a,v$database_block_corruption bWHERE a.file_id b.file#AND a.block_id b.block#AND a.block_id a.blocks b.block#;通过上面这个查询语句就可以查出当前存在坏块的对象是什么是什么类型的对象索引。需要注意的是如果是 temp 文件中出现坏块是没有记录返回的。从图片最下方的输出结果来看已经成功定位到了文件号 (FILE#):8对象名称 (SEGMENT_NAME):IX_TEST对象类型 (SEGMENT_TYPE):INDEX索引表空间 (TABLESPACE_NAME):TEST_INDEX6.3.修复坏块此次上图受损对象为索引直接删除索引重建就可以了。1、对于普通表索引重建需要使用 alter index ... rebuild online语法如果不带online关键字会依据旧的索引(包含坏块的)重建索引。2、对于分区表索引可以使用alter index xxx rebuild partition yyy的语句因为分区索引的重建不会使用旧索引所以可以不加online关键字。七、后续补充7.1.坏块的恢复理论对于发生数据块不一致的数据块如果当前数据库有备份且处于归档模式那么就可以利用rman工具数据块恢复功能对数据块进行恢复这种方法最简单有效而且可以在数据文件在线时进行不会发生数据丢失。对于没有备份的数据库发生数据块损坏可能会发生数据的丢失或数据不丢失这要根据发生坏块的所在的对象决定的如索引块发生损坏数据就不会丢失重建索引就可以了发生数据丢失的多发生在表或分区表数据块上。7.2.不丢数据的恢复方法利用rman工具blockrecover datafile xx block yy;--修复单个坏块blockrecover corruption list;--修复全部坏块7.3.可能会丢数据的恢复方法7.3.1.确认坏块类型当一个坏块发生时我们首先要确认这个块到底是什么样的块是普通表的数据块分区表的上数据块、索引块等针对不同的坏块类型我们来确认不同的恢复方法。7.3.2.确定文件号Oracle有两种数据文件号来标识数据文件。绝对文件号(Absolute File# AFN)和相对文件号(Relative File# RFN)。AFN是数据文件在整个系统范围内的编号而RFN是数据文件在表空间范围内的编号。两个文件可能有相同的RFN,但是不会有相同的ASN。在ORA-01578中提示的文件号是RFN在ORA-1110中提示的文件号是AFN在ORA-600中提示的文件号为AFN,从视图中看到的文件号、数据块号属于哪个segment 使用的也是AFN 。7.3.3.确认损坏数据块的类型7.3.4.按照不同的类型设置不同的恢复策略1用户表对于损害的数据块属于用户表的数据丢失是不可避免的这时需要做的就是把其他数据块中的数据抢救出来而受损数据块的数据就永久丢失了。这时的恢复策略是尽可能的减少用户的损失。如果这种数据损失不能接受就必须考虑其他特殊手段来尝试恢复受损数据块中的数据这种情况我们可以采用两种办法*放弃坏块上的数据抢救其他数据块上的数据并重建对象;*把数据快标记为skiped,然后放任不管也就是给这个数据块打上个标签这样以后所有的操作都会跳过这个数据块。在处理数据表的坏块时也要考虑关联对象的后续处理--索引select owner,index_name,index_type from dba_indexes where table_ownerowner and table_namesemeng_name;如果因为数据快损坏导致记录丢失那么这些索引也就失效了应该被删除然后重建索引。--主键Oracle通过对主键字段创建唯一索引来实现主键约束所以主键的处理方式和索引的处理方式一样重建这个唯一索引。select owner,constraint_name,constraint_type,table_name from dba_constraints where ownerowner and table_namesegment_name and constraint_typeP;--指向该主键的外键查询出指向该主键的外键主键外键处理方法相同都需要重建索引。select owner,constraint_name,constraint_type,table_name from dba_constraints where r_ownerowner and r_constraint_nameconstraint_name;2分区表分区表的处理和普通表类似确认数据属于哪个分区然后对受损的分区可以通过exchange操作和一个相同表结构的空表进行交换不影响程序的正常运行然后与普通表相同的方法处理。3索引如果受损对象为索引直接删除索引重建就可以了。对于普通表索引重建需要使用 alter index ... rebuild online语法如果不带online关键字 会依据旧的索引(包含坏块的)重建索引。 对于分区表索引可以使用alter index xxx rebuild partition yyy的语句因为分区索引的 重建不会使用旧索引所以可以不加online关键字。索引坏块注意以下--确认索引所属的表select table_owner,table_name from dba_indexes where ownerowner and index_namesegment_name;--如果是分区索引查看属于分区select partition_name from dba_extents where file_idAFN and bad_block_id between block_id and block_id blocks-1;--确认这个索引是否用于某个约束select owner,constrint_name,constraint_type,table_name from dba_constraints where ownertable_owner and constraint_nameindex_name;--如果这个索引是主键索引确认是否有外键指向这个索引select owner,constraint_name,constraint_type,table_name from dba_constraints where r_ownerowner and r_constraint_nameconstraint_name;7.4.恢复数据恢复数据就是通过其他好的数据块把其它受损的数据全部抢救出来。简单地说就是把受损数据块标识成software corrupt, 然后让Oracle做全表扫描时跳过这些块而不是抛出异常从而通过CTAScreate table xx as select ...方法把数据抢救出来。要想让Oracle做全表扫描时跳过这些块前提是先被打上software corrupt标记可以使用两种方法 使用dbms_repair包或使用10231事件。如果遇到ORA-1578错误说明数据块已经被标识为software corrupt。如果是其他错误如ORA-600就说明损坏的数据块还没有被标识为software corrupt。查看数据坏快是否被标记为software corrupt可以通过DBMS_REPAIR.CHECK_OBJECT方法检查后查询REPAIR_TABLE表1.如果数据块已经被标识成software corrupt,那么 REPAIR_TABLE 表 marked_corrupt列为true,repair_description 列没内容2.如果数据块没有被标识成software corrupt,REPAIR_TABLE 表 marked_corrupt列为FALSErepair_description列会提示mark block software corrupt,也就是需要把数据块标识为software corrupt。当数据块被标识为software corrupt后就可以利用 dbms_repair.skip_corrupt_blocks或者10231事件对segment做一个标志代表扫描该对象时如果遇到software corrupt的数据块可以直接跳过而不是抛出ORA-01578错误终止这样就可以完成对所有好的数据块的扫描实现抢救数据。从视图dba_tables.skip_corrupt字段可以看出表是否设置了这个标志。7.4.1.dbms_repair方法设置标志exec dbms_repair.skip_corrupt_block(schema,tablename);设置完标识后再扫描到数据就不会提示错误而是会在log日志中记录一条条目table scan:segment file# 6 block# 4 skipping corrupt block file#6 block# 5清除标志exec dbms_repair.skip_corrupt_block(schema,tablename,flagsdbms_repair.noskip_flag);7.4.2.使用10231事件会话级别设置alter session set events 10231 trace name context forever,level 10;通过初始化参数在实例级别设置event10231 trace name context forever,level 10;以上方法为网上收集整理

关于本文作者

来自尧图内容编辑团队

尧图内容编辑团队 内容团队

尧图内容编辑团队

本文由尧图网络内容编辑团队执笔。团队由资深项目经理、前端工程师与设计师组成,所有内容均来自亲手交付的真实项目,先讲清问题、再给出可落地的解法。尧图深耕北京网站建设十年,服务过京华建材集团、智造科技等各行业客户,把一线经验沉淀为可复用的行业观察。

  • 十年建站经验,覆盖建材、制造、服务、文创等
  • 项目经理把关选题与事实准确性
  • 工程师与设计师联合撰写专业细节
  • 统一编辑规范,保证文风与排版一致
  • 每月复盘转化数据,迭代选题方向

延伸阅读

相关资讯与近期热门内容

深度阅读推荐

建站决策前值得细读的三篇

网站改版的5个关键决策
2024-08-12

网站改版的5个关键决策

什么时候该改版、改到什么程度、如何避免流量掉光,京华建材集团改版复盘给出答案。

获取专属建站方案

看完文章,把您的行业与预算告诉我们,免费获取一份量身定制的官网建设方案与报价。

立即免费咨询