Oracle中checkpoint的討論
2024-08-29 13:37:04
供稿:網(wǎng)友
 
                 什么是checkpoint?
    checkpoint是一個數(shù)據(jù)庫事件,它將已修改的數(shù)據(jù)從高速緩存刷新到磁盤,并更新控制文件和數(shù)據(jù)文件。
    
    什么時候發(fā)生checkpoint?
                                                                                                我們知道了checkpoint會刷新臟數(shù)據(jù),但什么時候會發(fā)生checkpoint呢?以下幾種情況會觸發(fā)checkpoint。
    1.當(dāng)發(fā)生日志組切換的時候
    2.當(dāng)符合LOG_CHECKPOINT_TIMEOUT,LOG_CHECKPOINT_INTERVAL,fast_start_io_target,fast_start_mttr_target參數(shù)設(shè)置的時候
    3.當(dāng)運行ALTER SYSTEM SWITCH LOGFILE的時候
    4.當(dāng)運行ALTER SYSTEM CHECKPOINT的時候
    5.當(dāng)運行alter tablespace XXX begin backup,end backup的時候
    6.當(dāng)運行alter tablespace ,datafile offline的時候;
    
    增量檢查點(incremental checkpoint)
    Oracle8以后推出了incremental checkpoint的機(jī)制,在以前的版本里每次checkpoint時都會做一個full thread checkpoint,這樣的話所有臟數(shù)據(jù)會被寫到磁盤,巨大的i/o對系統(tǒng)性能帶來很大影響。為了解決這個問題,oracle引入了checkpoint queue機(jī)制,每一個臟塊會被移到檢查點隊列里面去,按照low rdb(第一次對此塊修改對應(yīng)的redo block address)來排列,靠近檢查點隊列尾端的數(shù)據(jù)塊的low rba值是最小的,而且假如這些贓塊被再次修改后它在檢查點隊列里的順序也不會改變,這樣就保證了越早修改的塊越早寫入磁盤。每隔3秒鐘ckpt會去更新控制文件和數(shù)據(jù)文件,記錄checkpoint執(zhí)行的情況。
    
    數(shù)據(jù)字典
    完全檢查點
select * from X$KCCRT where indx=0;ADDR           
INDX    INST_ID      RTNUM      RTSTA RTCKP_SCN        RTCKP_TIM   
RTCKP_THR RTCKP_RBA_SEQ RTCKP_RBA_BNO 
RTCKP_RBA_BOF RTCKP_ETB         RTOTF      RTOTB         RTNLF      
RTLFH      RTLFT      RTCLN      RTSEQ RTENB            
RTETS    RTDIS                     RTDIT                     
RTLHP RTSID            RTOTS-------- ---------- ---------- ---------- ---------- 
---------------- -------------------- ---------- ------------- ------------- ------------- 
---------------- ---------- ----------  ---------- ---------- ---------- ---------- -------
--- ---------------- --------------------   ---------------- -------------------- ---------
- ---------------- --------------------4084B228          0          
1          1         15 720368521        06/25/2004 18:49:37         
1           949             2     16 0600000000000000          
2          0              3          1          3          1        949 1               
05/16/2004 13:29:03  0               1389 tbdb2in1         
06/12/2004 12:30:50 
                         
    這里顯示了上一次的完全檢查點是在06/25/2004 18:49:37發(fā)生,所以我們推斷06/25/2004 18:49:37發(fā)生了一次日志切換,再去操作系統(tǒng)上去看生產(chǎn)的歸檔,果然18:49有一個歸檔生產(chǎn)。
    -rw-r-----    1 oracle   oinstall 83532800 Jun 25 18:49 1_948.dbf
    
    增量檢查點
SQL> select * from X$KCCCP where indx=0;ADDR           
INDX    INST_ID      CPTNO      CPSTA      CPFLG      
CPDRT      CPRDBCPLRBA_SEQ CPLRBA_BNO 
CPLRBA_BOF  CPODR_SEQ  CPODR_BNO  
CPODR_BOF CPODSCPODT                   
CPODT_I      CPHBT CPRLS                 
CPRLC      CPMIDCPSDR_SEQ  
CPSDR_BNO  CPSDR_ADB-------- ---------- ---------- 
---------- ---------- ---------- ---------- ---------- ---------- --
-------- ---------- ---------- ---------- ---------- --------------
-- -------------------- ---------- ---------- ---------------- ----
------ ---------- ---------- ---------- ----------4084B45C          
0          1          1          2          0      10762      29753       
949      76847          0        949     106814              
0 721554970        06/25/2004 21:05:10   
529794310  529036227 1                 
526310932        1413781667        949              
1          0
                                        
                            這里顯示了low-rba,on-disk rba,checkpoint time等信息。
    每隔3秒鐘ckpt會去更新控制文件和數(shù)據(jù)文件,記錄checkpoint執(zhí)行的情況。
    
    
    這里應(yīng)該是只更新控制文件,每3秒不是更新數(shù)據(jù)文件
    說 記錄 checkpoint 的執(zhí)行情況,這個說法,沒錯,但不夠具體,應(yīng)該說,由于增量檢查點和 checkpoint  queue 的原理,ckpt 進(jìn)程每次只是告訴 dbwr ,寫dirty  buffer將要一直寫到最新這個位置,僅僅是告訴 dbwr 一個 checkpoint queue  中的結(jié)束點,而 ckpt 每3秒中,在控制文件中報告一下 dbwr 最新寫入的位置。 這樣使得,比如數(shù)據(jù)庫要做恢復(fù)的時候(instance  recovery)可以從這個最新位置開始做恢復(fù),而不是從數(shù)據(jù)文件中的 checkpoint  scn 開始做恢復(fù),這樣將縮短恢復(fù)時間,尤其是 instance  crash 的情況下啟動更快
    
    另外要注重的是,檢查點發(fā)生的時候,ckpt 去更新數(shù)據(jù)文件頭和控制文件,并不是把當(dāng)前檢查點發(fā)生時候的 scn 更新進(jìn)去,而是把上一次dbwr寫入已經(jīng)完成的檢查點發(fā)生時候的  scn 更新進(jìn)去 ,也就是說,更新控制文件和數(shù)據(jù)文件頭 是 滯后于檢查點的發(fā)生的,這個從恢復(fù)的原理也很輕易理解,因為檢查點發(fā)生的時候 dirty buffer還沒有寫入,自然不能立即更新成當(dāng)前的 scn 了。