在oracle中存在 dirty list(也就是write list)的說法,但是同時又有checkpoint queue 。這兩個東西往往讓人容易混淆。他們是同一個東西嗎?之間關係如何?
在闡述之前,我們先來看一段大師的描述
http://www.ixora.com.au/q+a/0103/07160329.htm
That information is not quite right. It is more accurate to say that there are 10 lists, because there are 5 types of buffers and there is a MAIN and AUXILIARY list for each type. Also, there is no separate hot list. The hot list is a sublist of the main replacement list. Of course, there are separate lists for each working set (LRU latch set) of buffers.
You can see all these structures in BUFFERS dumps. Here is an extract ...
(WS) size: 10000 wsid: 1 state: 0 (WS_REPL_LIST) main_prev: 32aefbc main_next: 32ae51c aux_prev: 32c94a0 aux_next: 32c94a0 curnum: 10000 auxnum: 0 cold: 32a307c hbmax: 5000 hbufs: 5000 (WS_WRITE_LIST) main_prev: 32c94b4 main_next: 32c94b4 aux_prev: 32c94bc aux_next: 32c94bc curnum: 0 auxnum: 0 (WS_PING_LIST) main_prev: 32c94d0 main_next: 32c94d0 aux_prev: 32c94d8 aux_next: 32c94d8 curnum: 0 auxnum: 0 (WS_XOBJ_LIST) main_prev: 32c94ec main_next: 32c94ec aux_prev: 32c94f4 aux_next: 32c94f4 curnum: 0 auxnum: 0 (WS_XRNG_LIST) main_prev: 32c9508 main_next: 32c9508 aux_prev: 32c9510 aux_next: 32c9510 curnum: 0 auxnum: 0
Other than the replacement lists, the other lists are for different types of write buffers. From the bottom up they are buffers that have to be written for a checkpoint range call, a checkpoint object call, a ping, or merely because they are dirty. In each case the main list holds buffers which have yet to be written, and the auxiliary list holds buffers for which a write is pending. The auxiliary replacement list holds unpinned buffers for which a write has been completed, and any other buffers that are immediately reusable. The main replacement list is what is commonly called the LRU list. The operation of the LRU list was explained under the heading The 8i buffer cache in the October issue of Ixora News. You may also be interested in the section on DBWn's new tricks in the September issue.
These 10 lists are mutually exclusive. Each buffer can only be on one of the lists at a time. For completeness it should also be mentioned that dirty buffers are also on a thread checkpoint queue and a file checkpoint queue. These queues are maintained in first modification (low RBA) order and are used to optimize checkpoint processing.
也就是說,在oracle 8 中,buffer cache 中實際存在著5大類lists,加輔助的lists共10小類。其中的4大類(8小類lists)統稱write list。他們記錄了dirty buffer 的各種狀態資訊。而通常的LRU list 只有一個大類,實際共兩小類lists。也就是 replacement lists 。實際上,在9i開始版本,lists又有所增加,大致是12小類lists,這裡就不過多的闡述了。(注意這裡都說的是類而不是條數,因為條數實際上和 db_block_lru_latches參數有關,9i中這是隱藏參數)
在4大類的write lists 中,記錄了buffer的狀態(they are buffers that have to be written for a checkpoint range call, a checkpoint object call, a ping, or merely because they are dirty) 。由於write lists 中的buffer 的狀態可能是轉換的,也是沒有時間順序的,也就是說,如果按照這個lists寫buffer到磁碟,其順序和buffer變化發生的時間順序並不是一致的。這也直接造成在oracle 8以前版本中,檢查點都是 完全重新整理 dirty buffer 的,也就是說檢查點發生的時候,所有dirty buffer都要被寫入磁碟,而且這個時候是不能有dirty buffer產生的,否則oracle將無法知道是否將所有的檢查點時刻之前的dirty buffer 都寫入了磁碟。
從oracle 8開始,出現了checkpoint queue 。checkpoint queue 是按照buffer的 low RBA 排序的,也就是說按照buffer 第一次發生變化的時候的時間點排序的。同一個dirty buffer ,既存在與 write lists中(記錄著buffer的狀態)又存在於checkpoint queue 中,記錄著buffer 第一次發生變化的時間順序。這樣dbwr根據checkpoint queue中順序寫出dirty buffer 就一定能保證是按照 buffer 首次發生變化的時間順序寫到磁碟的。這樣的一個機制,就支援了oracle的增量檢查點的功能的實現。也就是說,當增量檢查點發生的時候,只確定寫的buffer的結束時間點,在這個檢查點過程中,可以繼續產生dirty buffer,dbwr也不是一次要把 所有dirty buffer 全部寫到磁碟。這樣大大地提高了檢查點的效率。
實際上,checkpoint queue 與 write list 的配合,更是可以在實現增量檢查點的同時類比非同步IO。這個問題就留待以後進行討論了。
關於checkpoint的更多的內容,請參考
http://blog.csdn.net/biti_rainy/archive/2004/07/12/learn_oracle_20040712_1.aspx