Oracle工作過程及原理_第1頁
Oracle工作過程及原理_第2頁
Oracle工作過程及原理_第3頁
Oracle工作過程及原理_第4頁
Oracle工作過程及原理_第5頁
免費預覽已結束,剩余11頁可下載查看

下載本文檔

版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領

文檔簡介

1、我們從一個用戶請求開始講ORACLE的完整的工作機制是怎樣的,首先一個用戶進程發(fā)出一個連接請求,如果使用的是主機命名或者 是本地服務命中的主機名使用的是機器名(非IP地址),那么這個請求 都會通過DNS服務器或HOST文件的服務名解析然后傳送到 ORACLE監(jiān)聽進程,監(jiān)聽進程接收到用戶請求后會采取兩種方式來處 理這個用戶請求,下面我們分專用服務器和共享服務器分別采用這兩 種方式時的情況來講:專用服務器模式下:一種方式是監(jiān)聽進程接收到用戶進程請求后, 產(chǎn) 生一個新的專用服務器進程,并且將對用戶進程的所有控制信息傳給 此服務器進程,也就是說新建的服務器進程繼承了監(jiān)聽進程的信息, 然后服務器進程給用

2、戶進程發(fā)一個 RESEND包,通知用戶進程可以 開始給它發(fā)信息了,用戶進程給這個新建的服務器進程發(fā)一個 CONNECT包,服務器進程再以ACCEPT包回應用戶進程,致此, 用戶進程正式與服務器進程確定連接。我們把這種連接叫做 HAND-OFF連接,也叫轉換連接。另一種方式是監(jiān)聽進程接收到用 戶進程的請求后產(chǎn)生一個新的專用服務器進程,這個服務器進程選用一個TCP/IP端口來控制與用戶進程的交互,然后將此信息回傳給監(jiān) 聽進程,監(jiān)聽進程再將此信息傳給用戶進程, 用戶進程使用這個端口 給服務器進程發(fā)送一個CONNECT包,服務器進程再給用戶進程發(fā) 送一個ACCEPT包,致此,用戶進程可以正式向服務器進

3、程發(fā)送信 息了。這種方式我們叫做重定向連接。 HAND-OFF連接需要系統(tǒng)平 臺具有進程繼承的能力,為了使 WINDOWSNT/2000 支持HAND-OFF必須在 HKEY_LOCAL_MACHINE>SOFTWARE>ORACLE>HOMEX 中設 置 USE_SHARED_SOCKET。共享服務器模式下:只有重定向連接的方式,工作方式是監(jiān)聽進程接 收到用戶進程的請求后產(chǎn)生一個新的調度進程, 這個調度進程選用一 個TCP/IP端口來控制與用戶進程的交互,然后將此信息回傳給監(jiān)聽 進程,監(jiān)聽進程再將此信息傳給用戶進程, 用戶進程使用這個端口給 調度進程發(fā)送一個CONNECT包

4、,調度進程再給用戶進程發(fā)送一個 ACCEPT包,致此,用戶進程可以正式向調度進程發(fā)送信息了??梢酝ㄟ^設置MAX_DISPIATCHERS這個參數(shù)來確定調度進程的最大數(shù) 目,如果調度進程的個數(shù)已經(jīng)達到了最大,或者已有的調度進程不是滿負荷,監(jiān)聽進程將不再創(chuàng)建新的調度進程, 而是讓其中一個調度進 程選用一個TCP/IP端口來與此用戶進程交互。調度進程每接收一個 用戶進程請求都會在監(jiān)聽進程處作一個登記,以便監(jiān)聽進程能夠均衡 每個調度進程的負荷,所有的用戶進程請求將分別在有限的調度進程 中排隊,所有調度進程再順序的把各自隊列中的部分用戶進程請求放入同一個請求隊列,等候多個 ORACLE的共享服務器進程進

5、行處理 (可以通過SHARED_SERVERS參數(shù)設置共享服務器進程的個數(shù)), 也就是說所有的調度進程共享同一個請求隊列,共享服務器模式下一 個實例只有一個請求隊列,共享服務器進程處理完用戶進程的請求后 將根據(jù)用戶進程請求取自不同的調度進程將返回結果放入不同的響 應隊列,也就是說有多少調度進程就有多少響應隊列,然后各個調度進程從各自的響應隊列中將結果取出再返回給用戶進程。以上我們講完了用戶與 ORACLE的連接方式,下面我們要講 ORACLE服務器進程如可處理用戶進程的請求,當一個用戶進程發(fā)出 了一條 SQL 語名:UPDATETABBLEASETSALARY二SALARY*2 ;首 先,服務

6、器進程把這條語句的字符轉換成 ASCII等效數(shù)字碼,接著這 個ASCII碼被傳遞給一個HASH函數(shù),并返回一個HASH值,服務 器進程將到SHAREDPOOL的共享PL/SQL區(qū)去查找是否存在同樣 的HASH值,如果存在,服務器進程將使用這條語句已高速緩存在 SHAREDPOOL中的已分析過的版本來執(zhí)行,如果不存在,服務器進 程將對該語句進行語法分析,首先檢查該語句的語法的正確性, 接著 對語句中涉及的表、索引、視圖等對象進行解析,并對照數(shù)據(jù)字典檢 查這些對象的名稱以及相關結構,并根據(jù) ORACLE選用的優(yōu)化模式 以及數(shù)據(jù)字典中是否存在相應對象的統(tǒng)計數(shù)據(jù)和是否使用了存儲大綱來生成一個執(zhí)行計劃或

7、從存儲大綱中選用一個執(zhí)行計劃,然后再用 數(shù)據(jù)字典核對此用戶對相應對象的執(zhí)行權限,最后生成一個編譯代 碼。ORACLE將這條語名的本身實際文本、HASH值、編譯代碼、 與此語名相關聯(lián)的任何統(tǒng)計數(shù)據(jù)和該語句的執(zhí)行計劃緩存在SHAREDPOOL的共享PL/SQL區(qū)。服務器進程通過 SHAREDPOOL 鎖存器來申請可以向哪些共享 PL/SQL區(qū)中緩存這此內容,也就是說 被SHAREDPOOL鎖存器鎖定的PL/SQL區(qū)中的塊不可被覆蓋,因 為這些塊可能被其它進程所使用。在 SQL分析階段將用到 LIBRARYCACHE,從數(shù)據(jù)字典中核對表、視圖等結構的時候,需要 將數(shù)據(jù)字典從磁盤讀入LIBRARYCA

8、CHE,因此,在讀入之前也要使 用LIBRARYCACHE鎖存器來申請用于緩存數(shù)據(jù)字典。生成編譯代碼之后,接著下一步服務器進程要準備開始更新數(shù)據(jù), 服 務器進程將到DBBUFFER中查找是否有相關對象的緩存數(shù)據(jù),下面 分兩個可能進行解釋:如果沒有,服務器進程將在表頭部請求一些行鎖,如果成功加鎖,服 務器進程將從數(shù)據(jù)文件中讀這些行所在的數(shù)據(jù)塊放入DBBUFFER中空閑的區(qū)域或者覆蓋已被擠出 LRU列表的非臟數(shù)據(jù)塊緩沖區(qū),并且 排列在LRU列表的頭部,如果這些非臟數(shù)據(jù)緩沖區(qū)寫完也不能滿足新數(shù)據(jù)的請求時,會立即觸發(fā)DBWN進程將臟數(shù)據(jù)列表中指向的緩 沖塊寫入數(shù)據(jù)文件,并且清洗掉這些緩沖區(qū),來騰出空間

9、緩沖新讀入 的數(shù)據(jù),也就是在放入 DBBUFFER之前也是要先申請 DBBUFFER中 的鎖存器,成功鎖定后,再寫入 DBBUFFER,然后服務器程將該語 句影響的被讀入DBBUFFER塊中的這些行的ROWID及將要更新的 原值和新值及SCN等信息逐條的寫入REDOLOGBUFFER,在寫入 REDOLOGBUFFER之前也是先請求REDOLOGBUFFER塊的鎖存 器,成功鎖定之后才開始寫入,當寫入達到REDOLOGBUFFER大小 的三分之一或寫入量達到1M或超過三秒后或發(fā)生檢查點時或者 DBWN 之前發(fā)生,LGWR將把REDOLOGBUFFER中的數(shù)據(jù)寫入磁 盤上的重做日志文件,已被寫入

10、重做日志文件的 REDOLOGBUFFER 中的塊上的鎖存器被釋放,并可被后來寫入的信息所覆蓋, REDOLOGBUFFER以循環(huán)的方式工作。當一個重做日志文件寫滿后, LGWR將切換到下一個重做日志文件,如果是歸檔模式,歸檔進程 還將前一個寫滿的重做日志進程寫入歸檔日志文件,重做日志文件也是循環(huán)工作方式。寫完所有的REDOLOGBUFFER之后,服務器進程 開始改寫這個DBBUFFER塊頭部的事務列表并寫入 SCN,然后 COPY包含這個塊的頭部事務列表及 SCN信息的數(shù)據(jù)副本放入回滾 段中,我們將回滾段中的副本稱為數(shù)據(jù)塊的“前映像”。(回滾段可 以存儲在專門的回滾表空間中,這個表空間由一個

11、或多個物理文件組成,并專用于回滾表空間,回滾段也可在其它表空間中的數(shù)據(jù)文件中 開辟。)然后改寫這個 DBBUFFER塊的數(shù)據(jù),并在其頭部寫入對應 的回滾段地址,如果對一行數(shù)據(jù)多次 UPDATE而不COMMIT則在 回滾段中將會有多個“前映像”,除第一個“前映像”含有SCN信息外,其它的每個“前映像”的頭部還含有 SCN信息和“前前映 像”的回滾段地址。一次 UPDATE操作只對應一個SCN。然后服務 器進程在臟數(shù)據(jù)列表中建立一條指向此緩沖塊的指針。接著服務器進程會從數(shù)據(jù)文件讀入第二個塊重復以上讀入,記日志,建立回滾段, 修改,放入臟列表的動作,當臟數(shù)據(jù)列表達到一定長度時,DBWN進程將臟數(shù)據(jù)列

12、表中指向的緩沖塊全部寫入數(shù)據(jù)文件,也就是釋放加在這些DBBUFER塊上的鎖存器。其實ORACLE可以一次從數(shù)據(jù)文 件中讀入幾個塊放入 DBBUFFER,可以通過參數(shù) DB_FILE_MULTIBLOCK_READ_COUNT來設置一次讀入的塊的個 數(shù)。如果要查找的數(shù)據(jù)已緩存,則根據(jù)用戶的 SQL操作類型決定如何操 作,如果是SELECT則查看DBBUFFER塊的頭部是否有事務,如果 有,將從回滾段讀取,如果沒有則比較 SELECT的 SCN與DBBUFFER 塊頭部的SCN如果比自己大,仍然從回滾段讀取,如果比自己小則 認這是一個非臟緩存,可以直接從這個 DBBUFFER塊中讀取。如果 是UP

13、DATE則即使在DBBUFFER中找到一個沒有事務,而且 SCN 比自己小的非臟緩存數(shù)據(jù)塊,服務器進程仍然要到表的頭部對這條記 錄申請加鎖,加鎖成功則進行后續(xù)動作,如果不成功,則要等待前面 的進程解鎖后才能進行動作。只有當SQL語句影響的所有行所在的最后一個塊被讀入 DBBUFFER 并且重做信息被寫入REDOLOGBUFFER (僅是指重做日志緩沖,而 非重做日志文件)之后,用戶才可以發(fā)出COMMIT,COMMIT觸發(fā) LGRW,但并不強制立即DBWN來釋放所有相應的DBBUFFER塊 上的鎖,也就是說有可能出現(xiàn)已 COMMIT,但在隨后的一段時間內 DBWN還在寫這條語句涉及的數(shù)據(jù)塊的情形

14、,表頭部的行鎖,并不 是在COMMIT 一發(fā)出就馬上釋放,實際上要等到相應的 DBWN進 程結束才會釋放。一個用戶請求鎖定另一個用戶已 COMMIT的資源 不成功的機會是存在的,從 COMMIT到DBWN進程結束之間的時 間很短,如果恰巧在這個時間斷電,由于 COMMIT已觸發(fā)LGWR 進程,所以這些未來得及寫入數(shù)據(jù)文件的改變會在實例重啟后由 SMON進程根據(jù)重做日志文件來前滾。如果未 COMMIT就斷電, 由于DBWN之前觸發(fā)LGWR,所有DBWN在數(shù)據(jù)文件上的修改都會被先一步記入重做日志文件,實例重啟后,SMON進程再根據(jù)重做日志文件來回滾。如果用戶ROOLBACK,則服務器進程會根據(jù)數(shù)據(jù)

15、文件塊和 DBBUFFER中塊的頭部的事務列表和SCN以及回滾段地址找到回滾 段中相應的修改前的副本,并且用這些原值來還原當前數(shù)據(jù)文件中已 修改但未提交的改變。如果有多個“前映像”,服務器進程會在一個“前映像”的頭部找到“前前映像”的回滾段地址,一直找到同一事務下的最早的一個“前映像”為止。一旦發(fā)出了COMMIT,用戶就不能ROOLBACK,這使得COMMIT后DBWN進程還沒有全部完 成的后續(xù)動作得到了保障。下面我們要提到檢查點的作用,當一個全部檢查點發(fā)生的時候,首先 讓LGWR進程將REDOLOGBUFFER中的所有緩沖(包含未提交的 重做信息)寫入重做日志文件,然后讓 DBWN進程將DB

16、BUFFER 中所有已提交的緩沖寫入數(shù)據(jù)文件(不強制寫未提交的)。然后更新 控制文件和數(shù)據(jù)文件頭部的SCN,表明當前數(shù)據(jù)庫是一致的,如果 在發(fā)生檢點之前斷電,并且當時有一個未提交的改變正在進行, 實例 重啟之后,SMON進程將從上一個檢查點開始核對這個檢查點之后 記錄在重做日志文件中已提交的和未提交改變,因為DBWN之前會觸發(fā)LGWR ,所以DBWN對數(shù)據(jù)文件的修改一定會被先記錄在重做 日志文件中。因此,斷電前被 DBWN寫進數(shù)據(jù)文件的改變將通過重 做日志文件中的記錄進行還原,叫做回滾,如果斷電時有一個已提交, 但DBWN動作還沒有完全完成的改變存在,因為已經(jīng)提交,提交會 觸發(fā)LGWR進程,所

17、以不管DBWN動作是否已完成,該語句將要影 響的行及其產(chǎn)生的結果一定已經(jīng)記錄在重做日志文件中了,則實例重啟后,SMON進程根據(jù)重做日志文件進行前滾。由此可見,實例失 敗后用于恢復的時間由兩個檢查點之間的間隔大小來決定,我們可以通個四個參數(shù)設置檢查點執(zhí)行的頻率,LOG_CHECKPOINT_IMTERVAL決定了兩個檢查點之間寫入重做日 志文件的系統(tǒng)物理塊的大小,LOG_CHECKPOINT_TIMEOUT 決定了 兩個檢查點之間的時間長度,F(xiàn)AST_START_IO_TARGET決定了用于 恢復時需要處理的塊的大小,F(xiàn)AST_START_MTTR_TARGET直接決 定了用于恢復的時間的長短。

18、SMON進程執(zhí)行的前滾和回滾與用戶 的回滾是不同的,SMON是根據(jù)重做日志文件進行前滾或回滾,而 用戶的回滾一定是根據(jù)回滾段的內容進行回滾的。在這里我們要說一下回滾段存儲的數(shù)據(jù),假如是 delete操作,則回滾段將會記錄整個 行的數(shù)據(jù),假如是update,則回滾段只記錄被修改了的字段的變化前 的數(shù)據(jù)(前映像),也就是沒有被修改的字段是不會被記錄的,假如是insert,則回滾段只記錄插入記錄的rowid。這樣假如事務提交, 那回滾段中簡單標記該事務已經(jīng)提交;假如是回退,則如果操作是是delete,回退的時候把回滾段中數(shù)據(jù)重新寫回數(shù)據(jù)塊,操作如果是 update,則把變化前數(shù)據(jù)修改回去,操作如果是

19、 insert,則根據(jù)記 錄的rowid把該記錄刪除。下面我們要講DBWN如何來寫數(shù)據(jù)文件,在寫數(shù)據(jù)文件前首先要找 到可寫的空閑數(shù)據(jù)塊,ORACLE中空閑數(shù)據(jù)塊可以通過FREELIST或 BITMAP來維護,它們位于一個段的頭部用來標識當前段中哪些數(shù)據(jù) 塊可以進行INSERT。在本地管理表空間中 ORACLE自動管理分配給 段的區(qū)的大小,區(qū)的分配信息存儲在組成表空間的數(shù)據(jù)文件的頭部, 而數(shù)據(jù)字典管理的表空間用戶可以在創(chuàng)建時決定區(qū)的大小,并且區(qū)的分配信息是存儲在數(shù)據(jù)字典中的,只在本地管理的表空間中才能選用 段自動管理,采用自動段空間管理的本地管理表空間中的段中的空閑 數(shù)據(jù)塊的信息就存放在段的頭部

20、并且使用位圖來管理,采用手動管理 的本地管理表空間中的段和數(shù)據(jù)字典管理的表空間中的段中的空閑 數(shù)據(jù)塊的管理都使用位于段頭部的空閑列表來管理,空閑列表的工作方式:首先一個空的數(shù)據(jù)塊被加入空閑列表,當其中空閑空間小于 PCTFREE設置的值之后,這個塊從空閑列表刪除,當這個塊中的內 容降至PCTUSED設置的值之下后,這個數(shù)據(jù)塊被再次加入空閑列表,位于空閑列表中的數(shù)據(jù)塊都是可以向其中INSERT的塊,當一個 塊移出了空閑列表,但只要其中還有保留空間就可以進行UPDATE ,當對其中一行UPDATE 一個大數(shù)據(jù)時,如果當前塊不能完全放下整 個行,只會把整個行遷移到一個新的數(shù)據(jù)塊, 并在原塊位置留下一

21、個 指向新塊的指針,這叫行遷移。如果一個數(shù)據(jù)塊可以INSERT,當插入一個當前塊裝不下的行時,這個行會溢出到兩個或兩個幾上的塊 中,這叫行鏈接。如果用戶的動作是INSERT則服務器進程會先鎖定 FREELIST,然后找到空閑塊的地址,再釋放 FREELIST,當多個服務 器進程同時想要鎖定FREELIST時即發(fā)生FREELIST的爭用,可以在 非采用自動段空間管理的表空間中創(chuàng)建表時指定 FREELIST的個數(shù), 默認為1,如果是在采用自動段空間管理的表空間中創(chuàng)建表,即使指 定了 FREELIST也會被忽略,因為此時將使用 BITMAP而不是 FREELIST來管理段中的空閑空間。如果用戶動作是

22、UPDATE服務器 進程將不會使用到FREELIST和BITMAP,因為不要去尋找一個空閑 塊,而使用鎖的隊列。下面來講一下ORACLE鎖的機制,ORACLE分鎖存器和鎖兩種。鎖 存器是用來保護對內存結構的訪問,比如對 DBBUFFER中塊的鎖存 器申請,只有在DBWN完成后,這些DBBUFFER塊被解鎖。然后 用于其它的申請。鎖存器不可以在進程間共享,鎖存器的申請要么成功要么失敗,沒有鎖存器申請隊列。主要的鎖存器有SHAREDPOOL 鎖存器,LIBRARYCACHE 鎖存器,CACHEBUFFERSLRUCHAIN 鎖 存器,CACHEBUFFERSCHAINS 鎖存器,REDOALLOC

23、ATION 鎖存 器,REDOCOPY鎖存器。ORACLE的鎖是用來保護數(shù)據(jù)訪問的,鎖 的限制比鎖存器要更寬松,比如,多個用戶在修改同一表的不同行時, 可以共享一個表上的一個鎖,鎖的申請可以按照被申請的順序來排隊 等候,然后依次應用,這種排隊機制叫做隊列(ENPUEUE),如果 兩個服務器進程試圖對同一表的同一行進行加鎖,則都進入鎖的申請隊列,先進的加鎖成功,后面的進程要等待,直到前一個進程解鎖才 可以加鎖,這叫做鎖的爭用,而且一旦加鎖成功,這個鎖將一直保持 到用戶發(fā)出COMMIT或ROOLBACK命令為止。如果兩個用戶鎖定 各自的一行并請求對方鎖定的行的時候將發(fā)生無限期等待即死鎖,死鎖的發(fā)生

24、都是由于鎖的爭用而不是鎖存器的爭用引起的,ORACLE在遇到死鎖時,自動釋放其中一個用戶的鎖并回滾此用戶的改變。 正 常情況下發(fā)生鎖的爭用時,數(shù)據(jù)的最終保存結果由SCN來決定哪個進程的更改被最終保存。兩個用戶的服務器進程在申請同一表的多個 行的鎖的時候是可以交錯進入鎖的申請隊列的。 只有其中發(fā)生爭用才 會進行等待。創(chuàng)建表時指定的MAXTRANS參數(shù)決了,表中的一個數(shù) 據(jù)塊最多可以被幾個事務同時鎖定F面是幾個關于回滾段和死鎖的事例: 有表:Test(idnumber(10) 有記錄 1000000 條一,大 SELECT,小 UPDATEA 會話-Select*fromtest;-設 sen=1

25、01- 執(zhí)行時間 09:10:11B 會話Updatetestsetid=9999999whereid=1000000-設sen=102- 執(zhí)行時間 09:10:12我們會發(fā)現(xiàn)B會話會在A會話前完成,A會話中顯示的ID=100000 是從回滾段中讀取的,因為 A會話在讀到ID=1000000所在的BLOCK時發(fā)現(xiàn)BLOCK上有事務信息,因此要從回滾段中讀,如果UPDATE在SELECT讀至吐匕BLOCK之前已經(jīng)COMMIT,貝卩SELECT 讀到此BLOCK時發(fā)現(xiàn)其BLOCK上沒有事務信息,但是會發(fā)現(xiàn)其 BLICK的SCN比SELECT自己的SCN大,因此也會從回滾段中讀取。 因此是否從回滾段

26、讀一是看是否有事務信息二是比較SCN大小。如果B會話在A會話結束前連續(xù)多次對同一條記錄 UPDATE并COMMIT,那么在回滾段中將記錄多個“前映像”,而每個“前映像”中不但包括了原BLOCK的數(shù)據(jù)和SCN也記錄了“前前映像”的回滾段地 址,因此A會話在查詢到被UPDATE過的BLOCK時,會根據(jù)BLOCK 記錄的回滾段的地址,找到回滾段中的“前映像”,發(fā)現(xiàn)這個“前映 像”的SCN也比自己的大,因此將根據(jù)這個“前映像”中記錄的“前前映像”的回滾段地址,在回滾段中找到“前前映像”,再與這 個“前前映像”比較SCN,如果比自己小就讀取,如果還比自己大, 則重復以上步驟,直到找到比自己 SCN小的“前前映像”為止, 如果找不到,就會報ORA-01555快照太舊這個錯誤。二、大 UPDATE,小 SELECTA 會話-Updatetestsetid=1;-設 sen

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
  • 4. 未經(jīng)權益所有人同意不得將文件中的內容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
  • 6. 下載文件中如有侵權或不適當內容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論