自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

Oracle Redo log并行機(jī)制詳解

數(shù)據(jù)庫 Oracle 數(shù)據(jù)庫運(yùn)維
Redo log是Oracle數(shù)據(jù)庫的日志,可以用于恢復(fù)和一個(gè)高級特性的重要數(shù)據(jù);這里我們通過一些實(shí)例來深入了解Oracle Redo log的并行機(jī)制。

Oracle的數(shù)據(jù)庫日志稱為Redo log,所有數(shù)據(jù)改變都記錄Redo log,可以用于修復(fù)受損的數(shù)據(jù)庫。Redo log 是用于恢復(fù)和一個(gè)高級特性的重要數(shù)據(jù),一個(gè)redo條目包含了相應(yīng)操作導(dǎo)致的數(shù)據(jù)庫變化的所有信息,所有redo條目最終都要被寫入redo文件中去。

Redo log buffer是為了避免Redo文件IO導(dǎo)致性能瓶頸而在sga中分配出的一塊內(nèi)存。一個(gè)redo條目首先在用戶內(nèi)存(PGA)中產(chǎn)生,然后由oracle服務(wù)進(jìn)程拷貝到log buffer中,當(dāng)滿足一定條件時(shí),再由LGWR進(jìn)程寫入redo文件。由于log buffer是一塊“共享”內(nèi)存,為了避免沖突,它是受到redo allocation latch保護(hù)的,每個(gè)服務(wù)進(jìn)程需要先獲取到該latch才能分配redo buffer。因此在高并發(fā)且數(shù)據(jù)修改頻繁的oltp系統(tǒng)中,我們通??梢杂^察到redo allocation latch的等待。Redo寫入redo buffer的整個(gè)過程如下:

在PGA中生產(chǎn)Redo Enrey -> 服務(wù)進(jìn)程獲取Redo Copy latch(存在多個(gè)---CPU_COUNT*2) -> 服務(wù)進(jìn)程獲取redo allocation latch(僅1個(gè)) -> 分配log buffer -> 釋放redo allocation latch -> 將Redo Entry寫入Log Buffer -> 釋放Redo Copy latch;

shared strand

為了減少redo allocation latch等待,在oracle 9.2中,引入了log buffer的并行機(jī)制。其基本原理就是,將log buffer劃分為多個(gè)小的buffer,這些小的buffer被成為strand(為了和之后出現(xiàn)的private strand區(qū)別,它們被稱之為shared strand)。每一個(gè)strand受到一個(gè)單獨(dú)redo allocation latch的保護(hù)。多個(gè)shared strand的出現(xiàn),使原來序列化的redo buffer分配變成了并行的過程,從而減少了redo allocation latch等待。

shared strand的初始數(shù)據(jù)量是由參數(shù)log_parallelism控制的;在10g中,該參數(shù)成為隱含參數(shù),并新增參數(shù)_log_parallelism_max控制shared strand的最大數(shù)量;_log_parallelism_dynamic則控制是否允許shared strand數(shù)量在_log_parallelism和_log_parallelism_max之間動(dòng)態(tài)變化。

  1. HELLODBA.COM>select  nam.ksppinm, val.KSPPSTVL, nam.ksppdesc      
  2.   2  from    sys.x$ksppi nam,      
  3.   3          sys.x$ksppsv val      
  4.   4  where nam.indx = val.indx      
  5.   5  --AND   nam.ksppinm LIKE '_%'      
  6.   6  AND   upper(nam.ksppinm) LIKE '%LOG_PARALLE%';      
  7.      
  8. KSPPINM                    KSPPSTVL   KSPPDESC      
  9. -------------------------- ---------- ------------------------------------------      
  10. _log_parallelism           1          Number of log buffer strands      
  11. _log_parallelism_max       2          Maximum number of log buffer strands      
  12. _log_parallelism_dynamic   TRUE       Enable dynamic strands  

每一個(gè)shared strand的大小 = log_buffer/(shared strand數(shù)量)。strand信息可以由表x$kcrfstrand查到(包含shared strand和后面介紹的private strand,10g以后存在)?!?/P>

  1. HELLODBA.COM>select indx,strand_size_kcrfa from x$kcrfstrand where last_buf_kcrfa != '00';      
  2.      
  3.       INDX STRAND_SIZE_KCRFA      
  4. ---------- -----------------      
  5.          0           3514368      
  6.          1           3514368      
  7.      
  8. HELLODBA.COM>show parameter log_buffer      
  9.      
  10. NAME                                 TYPE        VALUE      
  11. ------------------------------------ ----------- ------------------------------      
  12. log_buffer                           integer     7028736    

關(guān)于shared strand的數(shù)量設(shè)置,16個(gè)cpu之內(nèi)最大默認(rèn)為2,當(dāng)系統(tǒng)中存在redo allocation latch等待時(shí),每增加16個(gè)cpu可以考慮增加1個(gè)strand,最大不應(yīng)該超過8。并且_log_parallelism_max不允許大于cpu_count。

注意:在11g中,參數(shù)_log_parallelism被取消,shared strand數(shù)量由_log_parallelism_max、_log_parallelism_dynamic和cpu_count控制。

Private strand

為了進(jìn)一步降低redo buffer沖突,在10g中引入了新的strand機(jī)制——Private strand。Private strand不是從log buffer中劃分的,而是在shared pool中分配的一塊內(nèi)存空間。

  1. HELLODBA.COM>select * from V$sgastat where name like '%strand%';  
  2.  
  3.   POOL NAME BYTES  
  4.  
  5.   ------------ -------------------------- ----------  
  6.  
  7.   shared pool private strands 2684928  
  8.  
  9.   HELLODBA.COM>select indx,strand_size_kcrfa from x$kcrfstrand where last_buf_kcrfa = '00';  
  10.  
  11.   INDX STRAND_SIZE_KCRFA  
  12.  
  13.   ---------- -----------------  
  14.  
  15.   2 66560  
  16.  
  17.   3 66560  
  18.  
  19.   4 66560  
  20.  
  21.   5 66560  
  22.  
  23.   6 66560  
  24.  
  25.   7 66560  
  26.  
  27.   8 66560  
  28.  
  29.   ... 

Private strand的引入為Oracle的Redo/Undo機(jī)制帶來很大的變化。每一個(gè)Private strand受到一個(gè)單獨(dú)的redo allocation latch保護(hù),每個(gè)Private strand作為“私有的”strand只會(huì)服務(wù)于一個(gè)活動(dòng)事務(wù)。獲取到了Private strand的用戶事務(wù)不是在PGA中而是在Private strand生成Redo,當(dāng)flush private strand或者commit時(shí),Private strand被批量寫入log文件中。如果新事務(wù)申請不到Private strand的redo allocation latch,則會(huì)繼續(xù)遵循舊的redo buffer機(jī)制,申請寫入shared strand中。事務(wù)是否使用Private strand,可以由x$ktcxb的字段ktcxbflg的新增的第13位鑒定:

  1. HELLODBA.COM>select decode(bitand(ktcxbflg, 4096),0,1,0) used_private_strand, count(*)  
  2.  
  3.   2 from x$ktcxb  
  4.  
  5.   3 where bitand(ksspaflg, 1) != 0  
  6.  
  7.   4 and bitand(ktcxbflg, 2) != 0  
  8.  
  9.   5 group by bitand(ktcxbflg, 4096);  
  10.  
  11.   USED_PRIVATE_STRAND COUNT(*)  
  12.  
  13.   ------------------- ----------  
  14.  
  15.   1 10  
  16.  
  17.   0 1 

對于使用Private strand的事務(wù),無需先申請Redo Copy Latch,也無需申請Shared Strand的redo allocation latch,而是flush或commit是批量寫入磁盤,因此減少了Redo Copy Latch和redo allocation latch申請/釋放次數(shù)、也減少了這些latch的等待,從而降低了CPU的負(fù)荷。過程如下:

事務(wù)開始 -> 申請Private strand的redo allocation latch (申請失敗則申請Shared Strand的redo allocation latch) -> 在Private strand中生產(chǎn)Redo Enrey -> Flush/Commit -> 申請Redo Copy Latch -> 服務(wù)進(jìn)程將Redo Entry批量寫入Log File -> 釋放Redo Copy Latch -> 釋放Private strand的redo allocation latch 。#p#

注意:對于未能獲取到Private strand的redo allocation latch的事務(wù),在事務(wù)結(jié)束前,即使已經(jīng)有其它事務(wù)釋放了Private strand,也不會(huì)再申請Private strand了。

每個(gè)Private strand的大小為65K。10g中,shared pool中的Private strands的大小就是活躍會(huì)話數(shù)乘以65K,而11g中,在shared pool中需要為每個(gè)Private strand額外分配4k的管理空間,即:數(shù)量*69k。

  1. --10g:  
  2.  
  3.   SQL> select * from V$sgastat where name like '%strand%';  
  4.  
  5.   POOL NAME BYTES  
  6.  
  7.   ------------ -------------------------- ----------  
  8.  
  9.   shared pool private strands 1198080  
  10.  
  11.   HELLODBA.COM>select trunc(value * KSPPSTVL / 100) * 65 * 1024  
  12.  
  13.   2 from (select value from v$parameter where name = 'transactions') a,  
  14.  
  15.   3 (select val.KSPPSTVL  
  16.  
  17.   4 from sys.x$ksppi nam, sys.x$ksppsv val  
  18.  
  19.   5 where nam.indx = val.indx  
  20.  
  21.   6 AND nam.ksppinm = '_log_private_parallelism_mul') b;  
  22.  
  23.   TRUNC(VALUE*KSPPSTVL/100)*65*1024  
  24.  
  25.   -------------------------------------  
  26.  
  27.   1198080  
  28.  
  29.   --11g:  
  30.  
  31.   HELLODBA.COM>select * from V$sgastat where name like '%strand%';  
  32.  
  33.   POOL NAME BYTES  
  34.  
  35.   ------------ -------------------------- ----------  
  36.  
  37.   shared pool private strands 706560  
  38.  
  39.   HELLODBA.COM>select trunc(value * KSPPSTVL / 100) * (65 + 4) * 1024  
  40.  
  41.   2 from (select value from v$parameter where name = 'transactions') a,  
  42.  
  43.   3 (select val.KSPPSTVL  
  44.  
  45.   4 from sys.x$ksppi nam, sys.x$ksppsv val  
  46.  
  47.   5 where nam.indx = val.indx  
  48.  
  49.   6 AND nam.ksppinm = '_log_private_parallelism_mul') b;  
  50.  
  51.   TRUNC(VALUE*KSPPSTVL/100)*(65+4)*1024  
  52.  
  53.   -------------------------------------  
  54.  
  55.   706560 

Private strand的數(shù)量受到2個(gè)方面的影響:logfile的大小和活躍事務(wù)數(shù)量。

參數(shù)_log_private_mul指定了使用多少logfile空間預(yù)分配給Private strand,默認(rèn)為5。我們可以根據(jù)當(dāng)前l(fā)ogfile的大小(要除去預(yù)分配給log buffer的空間)計(jì)算出這一約束條件下能夠預(yù)分配多少個(gè)Private strand:

  1. HELLODBA.COM>select bytes from v$log where status = 'CURRENT';  
  2.  
  3.   BYTES  
  4.  
  5.   ----------  
  6.  
  7.   52428800  
  8.  
  9.   HELLODBA.COM>select trunc(((select bytes from v$log where status = 'CURRENT') - (select to_number(value) from v$parameter where name = 'log_buffer'))*  
  10.  
  11.   2 (select to_number(val.KSPPSTVL)  
  12.  
  13.   3 from sys.x$ksppi nam, sys.x$ksppsv val  
  14.  
  15.   4 where nam.indx = val.indx  
  16.  
  17.   5 AND nam.ksppinm = '_log_private_mul') / 100 / 66560)  
  18.  
  19.   6 as "calculated private strands" 
  20.  
  21.   7 from dual;  
  22.  
  23.   calculated private strands  
  24.  
  25.   --------------------------  
  26.  
  27.   5  
  28.  
  29.   HELLODBA.COM>select count(1) "actual private strands" from x$kcrfstrand where last_buf_kcrfa = '00';  
  30.  
  31.   actual private strands  
  32.  
  33.   ----------------------  
  34.  
  35.   5 

當(dāng)logfile切換后(和checkpoint一樣,切換之前必須要將所有Private strand的內(nèi)容flush到logfile中,因此我們在alert log中可能會(huì)發(fā)現(xiàn)日志切換信息之前會(huì)有這樣的信息:"Private strand flush not complete",這是可以被忽略的),會(huì)重新根據(jù)切換后的logfile的大小計(jì)算對Private strand的限制:

  1. HELLODBA.COM>alter system switch logfile;  
  2.  
  3.   System altered.  
  4.  
  5.   HELLODBA.COM>select bytes from v$log where status = 'CURRENT';  
  6.  
  7.   BYTES  
  8.  
  9.   ----------  
  10.  
  11.   104857600  
  12.  
  13.   HELLODBA.COM>select trunc(((select bytes from v$log where status = 'CURRENT') - (select to_number(value) from v$parameter where name = 'log_buffer'))*  
  14.  
  15.   2 (select to_number(val.KSPPSTVL)  
  16.  
  17.   3 from sys.x$ksppi nam, sys.x$ksppsv val  
  18.  
  19.   4 where nam.indx = val.indx  
  20.  
  21.   5 AND nam.ksppinm = '_log_private_mul') / 100 / 66560)  
  22.  
  23.   6 as "calculated private strands" 
  24.  
  25.   7 from dual;  
  26.  
  27.   calculated private strands  
  28.  
  29.   --------------------------  
  30.  
  31.   13  
  32.  
  33.   HELLODBA.COM>select count(1) "actual private strands" from x$kcrfstrand where last_buf_kcrfa = '00';  
  34.  
  35.   actual private strands  
  36.  
  37.   ----------------------  
  38.  
  39.   13 

參數(shù)_log_private_parallelism_mul用于推算活躍事務(wù)數(shù)量在最大事務(wù)數(shù)量中的百分比,默認(rèn)為10。Private strand的數(shù)量不能大于活躍事務(wù)的數(shù)量。

  1. HELLODBA.COM>show parameter transactions  
  2.  
  3.   NAME TYPE VALUE  
  4.  
  5.   ------------------------------------ ----------- ------------------------------  
  6.  
  7.   transactions integer 222  
  8.  
  9.   transactions_per_rollback_segment integer 5  
  10.  
  11.   HELLODBA.COM>select trunc((select to_number(value) from v$parameter where name = 'transactions') *  
  12.  
  13.   2 (select to_number(val.KSPPSTVL)  
  14.  
  15.   3 from sys.x$ksppi nam, sys.x$ksppsv val  
  16.  
  17.   4 where nam.indx = val.indx  
  18.  
  19.   5 AND nam.ksppinm = '_log_private_parallelism_mul') / 100 )  
  20.  
  21.   6 as "calculated private strands" 
  22.  
  23.   7 from dual;  
  24.  
  25.   calculated private strands  
  26.  
  27.   --------------------------  
  28.  
  29.   22  
  30.  
  31.   HELLODBA.COM>select count(1) "actual private strands" from x$kcrfstrand where last_buf_kcrfa = '00';  
  32.  
  33.   actual private strands  
  34.  
  35.   ----------------------  
  36.  
  37.   22 

注:在預(yù)分配Private strand時(shí),會(huì)選擇上述2個(gè)條件限制下最小一個(gè)數(shù)量。但相應(yīng)的shared pool的內(nèi)存分配和redo allocation latch的數(shù)量是按照活躍事務(wù)數(shù)預(yù)分配的。

因此,如果logfile足夠大,_log_private_parallelism_mul與實(shí)際活躍進(jìn)程百分比基本相符的話,Private strand的引入基本可以消除redo allocation latch的爭用問題。

【編輯推薦】

  1. 淺談在Oracle中如何利用REDO實(shí)現(xiàn)故障恢復(fù)
  2. 簡析REDO LOGFILE
  3. 詳解Oracle中數(shù)字與大寫交換
  4. 淺析Oracle對象和數(shù)據(jù)的導(dǎo)入導(dǎo)出
  5. 分析探討Oracle Data Guard
責(zé)任編輯:佚名 來源: HelloDBA
相關(guān)推薦

2010-04-30 13:44:36

Oracle Redo

2019-05-06 15:27:48

Oracle數(shù)據(jù)庫數(shù)據(jù)

2024-06-11 00:00:02

MySQL數(shù)據(jù)庫系統(tǒng)

2021-07-28 08:32:03

MySQLRedo存儲(chǔ)

2023-11-23 13:17:39

MySQL?數(shù)據(jù)庫

2009-09-02 18:52:38

Oracle數(shù)據(jù)庫并行

2021-10-04 09:23:30

Redo日志內(nèi)存

2025-01-20 08:20:00

redo logMySQL數(shù)據(jù)庫

2010-04-07 14:22:46

2021-05-28 11:18:50

MySQLbin logredo log

2021-01-26 13:47:08

MySQL存儲(chǔ)數(shù)據(jù)

2020-08-20 12:10:42

MySQL日志數(shù)據(jù)庫

2024-05-28 00:10:00

JavaMySQL數(shù)據(jù)庫

2011-05-26 09:36:07

Oracle數(shù)據(jù)庫Redo故障

2025-01-15 13:19:09

MySQL日志事務(wù)

2024-05-30 08:03:17

2011-03-24 17:21:42

Oracle數(shù)據(jù)庫Redo故障

2019-12-03 09:00:59

Oracle數(shù)據(jù)庫等待事件

2010-05-07 12:46:08

Oracle redo

2009-07-16 09:46:20

iBATIS Log機(jī)
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號