[体系架构] [讨论话题]redolog switch会发生完全检查点还是增量检查点

 

网上有很多资料都没有说清楚发生log switch的时候,到底完全检查点还是增量检查点。有人说是完全检查点,也有人说是增量检查点。其实如果你深入了解完全检查点和增量检查点的的区别,就应该知道log switch到底是增量检查点还是完全检查点。

 

   8i以前,log switch的时候oracle确实是会做完全检查点;但从8i开始,oraclelog switch的时候做的是增量检查点,但从严格意义上来说并不能完全算是增量检查点,因为在log switch的时候,不仅会像增量检查点那样更新控制文件,而且还会像完全检查点那样会更新数据文件头。

 

   下面我们来一起来做做测试:证明了在log switch的时候,发生的既不是完全检查点,也不是严格意义上的增量检查点。

 

测试DB版本:

SYS @ prod >select * from v$version;

 

BANNER

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

Oracle Database 10g Enterprise Edition Release 10.2.0.1.0 - Prod

PL/SQL Release 10.2.0.1.0 - Production

CORE    10.2.0.1.0      Production

TNS for Linux: Version 10.2.0.1.0 - Production

NLSRTL Version 10.2.0.1.0 - Productionn

 

一、我们首先来验证在log switch的时候,发生的不是完全检查点:

 

查几个跟日志切换检查点相关的参数

idle> @?/rdbms/admin/show_para;

 

Enter value for p: _dbwr_scan_interval

old  12:     AND upper(i.ksppinm) LIKE upper('%&p%')

new  12:     AND upper(i.ksppinm) LIKE upper('%_dbwr_scan_interval%')

 

P_NAME               P_DESCRIPTION                 P_VALUE             ISDEFAULT ISMODIFIED ISADJ

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

_dbwr_scan_interval                      dbwriter scan interval                             300                    

TRUE      FALSE       FALSE

 

idle> @?/rdbms/admin/show_para

 

Enter value for p: _disable_selftune_checkpointing

old  12:     AND upper(i.ksppinm) LIKE upper('%&p%')

new  12:     AND upper(i.ksppinm) LIKE upper('%_disable_selftune_checkpointing%')

 

P_NAME          P_DESCRIPTION                P_VALUE             ISDEFAULT ISMODIFIED ISADJ

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

_disable_selftune_checkpointing          Disable self-tune checkpointing                    FALSE                  

TRUE      FALSE       FALSE

 

idle> show parameter log_checkpoint_timeout

 

NAME                                 TYPE        VALUE

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

log_checkpoint_timeout               integer     1800

 

没修改参数之前:

idle>  select group#,status from v$log;

 

    GROUP# STATUS

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

         1 CURRENT

         2 INACTIVE

         3 INACTIVE

 

idle> alter system switch logfile;

 

idle> !date

 

Sun May 12 19:43:20 CST 2013

 

idle> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 ACTIVE

         2 CURRENT

         3 INACTIVE

 

idle> !date

Sun May 12 19:49:25 CST 2013

 

idle> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 INACTIVE

         2 CURRENT

         3 INACTIVE

 

1号日志组从ACTIVE变成INACTIVE大约要5分钟左右

 

修改参数可以命alter system switch logfile;时redo log file的状态一直是active(保持一天):

 

_dbwr_scan_interval=24*3600

log_checkpoint_timeout=24*3600

_disable_selftune_checkpointing=TRUE

idle> alter system set "_dbwr_scan_interval"=86400;

System altered.

idle> alter system set log_checkpoint_timeout=86400;

System altered.

 

idle> alter system set "_disable_selftune_checkpointing"=true;

 

System altered.

 

哈哈。。。可以观察一下是不是一直是ACTIVE

idle> !date

 

Sun May 12 19:55:54 CST 2013

 

idle> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 INACTIVE

         2 INACTIVE

         3 CURRENT

 

idle> ALTER SYSTEM SWITCH LOGFILE;

 

System altered.

 

idle> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 CURRENT

         2 INACTIVE

         3 ACTIVE

 

执行完上述switch logfile操作后等待12小时,然后再次执行上述查询语句:

idle> !date

 

Sun May 13 7:56:58 CST 2013

 

idle> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 CURRENT

         2 INACTIVE

         3 ACTIVE

 

从结果里我们可以看到现在redo log group 3还是处于active状态,我现在的这个库是测试库只有我一个人在用,所以很空闲,如

果switch logfile的时候发生的是full checkpoint,则当我等待24小时后再次查询v$log的时候redo log group 3必然是处于inactive状态:

即现在我们已经证明了在log switch的时候,发生的不是完全检查点。

 

idle> !date

Sun May 13 20:56:58 CST 2013

 

idle> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 CURRENT

         2 INACTIVE

         3 INACTIVE

 

哈哈。。。你可以试试,那些参数的威力。。牛B的一比。。。

 

现在我们来证明在log switch的时候,发生的不是严格意义上的增量检查点。增量检查点只会更新control file不会更新

datafile header,知道这个那就很好验证了,利用BBED恢复神器:

 

查看当前的日志组

SYS @ prod >select group#,status from v$log;

 

    GROUP# STATUS

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

         1 INACTIVE

         2 CURRENT

         3 INACTIVE

 

使用bbed查看 1号数据文件的第一个块的内部结构

BBED> set file 1 block 1

        FILE#           1

        BLOCK#          1

 

BBED> p kcvfhckp

struct kcvfhckp, 36 bytes                   @484    

   struct kcvcpscn, 8 bytes                 @484    

      ub4 kscnbas                           @484      0x002be87d

      ub2 kscnwrp                           @488      0x0000

   ub4 kcvcptim                             @492      0x325ce214

   ub2 kcvcpthr                             @496      0x0001

   union u, 12 bytes                        @500    

      struct kcvcprba, 12 bytes             @500    

         ub4 kcrbaseq                       @500      0x0000007e

         ub4 kcrbabno                       @504      0x00000002

         ub2 kcrbabof                       @508      0x0010

   ub1 kcvcpetb[0]                          @512      0x02

   ub1 kcvcpetb[1]                          @513      0x00

   ub1 kcvcpetb[2]                          @514      0x00

   ub1 kcvcpetb[3]                          @515      0x00

   ub1 kcvcpetb[4]                          @516      0x00

   ub1 kcvcpetb[5]                          @517      0x00

   ub1 kcvcpetb[6]                          @518      0x00

   ub1 kcvcpetb[7]                          @519      0x00

 

即现在的system01.dbf的datafile header的checkpoint scn的base是0x002be87d

 

 

现在我执行一次switch logfile,再来观察system01.dbf的datafile header的checkpoint scn:

SYS @ prod >conn hr/hr

Connected.

HR @ prod > update employees set salary=salary+1000;

 

107 rows updated.

 

HR @ prod >commit;

 

Commit complete.

 

SYS @ prod >alter system switch logfile;

 

System altered.

 

SYS @ prod >select group#,status from v$log;

 

    GROUP# STATUS

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

         1 INACTIVE

         2 INACTIVE

         3 CURRENT

 

BBED>  set file 1 block 1

        FILE#           1

        BLOCK#          1

 

BBED>  p kcvfhckp

struct kcvfhckp, 36 bytes                   @484    

   struct kcvcpscn, 8 bytes                 @484    

      ub4 kscnbas                           @484      0x002be98d

      ub2 kscnwrp                           @488      0x0000

   ub4 kcvcptim                             @492      0x325ce4dd

   ub2 kcvcpthr                             @496      0x0001

   union u, 12 bytes                        @500    

      struct kcvcprba, 12 bytes             @500    

         ub4 kcrbaseq                       @500      0x0000007f

         ub4 kcrbabno                       @504      0x00000002

         ub2 kcrbabof                       @508      0x0010

   ub1 kcvcpetb[0]                          @512      0x02

   ub1 kcvcpetb[1]                          @513      0x00

   ub1 kcvcpetb[2]                          @514      0x00

   ub1 kcvcpetb[3]                          @515      0x00

   ub1 kcvcpetb[4]                          @516      0x00

   ub1 kcvcpetb[5]                          @517      0x00

   ub1 kcvcpetb[6]                          @518      0x00

   ub1 kcvcpetb[7]                          @519      0x00

 

我们发现现在的system01.dbf的datafile header的checkpoint scn的base还是0x000c592e,也就是说oracleswitch logfile

时候的checkpoint并不是马上发生,oracle在等待一个发生的时机。

 

我们现在强制让log switch checkpoint马上发生:

 

hr@OCP> alter system switch logfile;

 

System altered.

 

hr@OCP> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 CURRENT

         2 ACTIVE

         3 ACTIVE

 

等待日志组2变成INACTIVE

 

hr@OCP> select group#,status from v$log;

 

    GROUP# STATUS

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

         1 CURRENT

         2 INACTIVE

         3 ACTIVE

 

BBED> set file 1 block 1

        FILE#           1

        BLOCK#          1

BBED> p kcvfhckp

struct kcvfhckp, 36 bytes                   @484     

   struct kcvcpscn, 8 bytes                 @484     

      ub4 kscnbas                           @484      0x000c59cf

      ub2 kscnwrp                           @488      0x0000

   ub4 kcvcptim                             @492      0x3097eb6d

   ub2 kcvcpthr                             @496      0x0001

   union u, 12 bytes                        @500     

      struct kcvcprba, 12 bytes             @500     

         ub4 kcrbaseq                       @500      0x0000003b

         ub4 kcrbabno                       @504      0x00000002

         ub2 kcrbabof                       @508      0x0010

   ub1 kcvcpetb[0]                          @512      0x02

   ub1 kcvcpetb[1]                          @513      0x00

   ub1 kcvcpetb[2]                          @514      0x00

   ub1 kcvcpetb[3]                          @515      0x00

   ub1 kcvcpetb[4]                          @516      0x00

   ub1 kcvcpetb[5]                          @517      0x00

   ub1 kcvcpetb[6]                          @518      0x00

   ub1 kcvcpetb[7]                          @519      0x00

 

看到了吗?现在system01.dbf的datafile header的checkpoint scn的base已经变成了0x000c59cf,也就是说----log switch

时候,发生的不是严格意义上的增量检查点,因为其不仅更新了control file,还更新了datafile header。

 

最后,我们来说一下oracle中checkpoint的种类。oracle中的checkpoint一共有七种,它们分别是:

 

1、Full Checkpoint

2、Thread Checkpoint

3、File Checkpoint

4、Object Checkpoint

5、Parallel Query Checkpoint

6、Incremental Checkpoint

7、Log Switch Checkpoint

 

 

******************************************************************

增量checkpoint

 

增量checkpoint工作过程

因为每次完全的checkpoint都需要把buffer cache所有的脏块都写入到数据文件中,这样就是产生一个很大的IO消耗,频繁的完全checkpoint操作很对系统的性能有很大的影响,为此 Oracle引入的增量checkpoint的概念,buffer cache中的脏块将会按照BCQ队列的顺序持续不断的被写入到磁盘当中,同时CKPT进程将会每3秒钟检查DBWn的写入进度并将相应的RBA信息记录 到控制文件中。有了增量checkpoint之后在进行实例恢复的时候就不需要再从崩溃前的那个完全checkpoint开始应用重做日志了,只需要从控制文件中记录的RBA开始进行恢复操作,这样能节省恢复的时间。

      

发生增量checkpoint的先决条件

* 恢复需求设定 FAST_START_IO_TARGET/FAST_START_MTTR_TARGET

* LOG_checkpoint_INTERVAL参数值

* LOG_checkpoint_TIMEOUT参数值

* 最小的日志文件大小

* buffer cache中的脏块的数量

   

增量checkpoint的特点

* 增量checkpoint是一个持续活动的checkpoint

* 没有checkpoint RBA,因为这个checkpoint是一直都在进行的,所以不存在normal checkpoint里面涉及的checkpoint RBA的概念。

* checkpoint advanced in memory only

* 增量checkpoint所完成的RBA信息被记录在控制文件中。

* 增量checkpoint可以减少实例恢复时间。

   

****************************************************************************************************

完全checkpoint:

 

完全检查点主要包括以下步骤:

①首先,在日志缓冲中确定当前的(也就是最新的)重做记录,提取其RBASCN作为检查点目标

LGWR清空日志缓存,将重作记录写入在线日志

DBWn进程将检查点目标(RBASCN)产生的及检查点目标之前产生的脏数据块,按RBA的顺序写入数据文件

④最后,CKPT进程将检查点目标(RBASCN)写入数据文件的头部和控制文件

   

触发完全检查点的条件:

执行shutdown immediate命令

执行alter system checkpoint命令

 

****************************************************************************************************

CHECKPOINT 优化

 

从9I开始CHECKPOINT的优化大大简化了

设置FAST_START_MTTR_TARGET

较大的值:恢复时间较长

较小的值:增加IO负载

 

10g 的CHECKPOINT的自动优化

fast_start_mttr_target设置为非零的值或者不设置

 

源文档 <http://www.itpub.net/forum.php?mod=viewthread&tid=1785072>

创建时间:2022-03-30 20:51
浏览量:0