高峰期謹慎編譯業務物件

jason_yehua發表於2022-11-30

在日常運維中,“library cache”相關等待較為常見,主要分為“library cache lock”或“library cache pin”,前者維護“library object handle”上的併發訪問,後者維護“library object handle”下對應heap的併發訪問,lock管理併發,pin管理一致性。

當我們編譯儲存過程、函式或檢視的時候,Oracle  就會在這些物件的handle  上獲得一個“library cache lock  ”,然後在這些物件的heap  上獲得pin  ,這樣就能保證在編譯的時候其他程式不會來更改這些物件。

有了以上的理論基礎,當高峰期編譯物件出現會話堵塞的問題時,我們應該如何處理呢?  這裡主要會用到基表DBA_KGLLOCK  ,其包含如下兩個欄位。

  kgllkuse  欄位:“Address of the user session that holds the lock or pin  ”,主要用於記錄持有lock  pin  的使用者地址。

  kgllkhdl  欄位:“Address of the handle for the KGL object  ”,記錄handle  物件地址。

故障發生時,首先檢視後臺等待事件,命令及輸出具體如下:

SQL> select inst_id,sid, event, p1,p1text,p1raw,p2,p2text,p2raw from gv$session where wait_class<>'Idle';

 

INST_ID  SID EVENT                      P1 P1TEXT           P1RAW                    P2 P2TEXT       P2RAW

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

      1   33 library cache pin  2081944584 handle address   000000007C17F408 2087901056 pin address  000000007C72D780

根據等待事件“library cache pin  ”獲取“p1 handle address 000000007C17F408  ”。

關聯檢視“dba_kgllock dk,v$session  ”獲取鎖資訊,命令及輸出如下:

SQL> select s.sid,s.sql_id,s.event,dk.* from dba_kgllock dk,v$session s where s.saddr = dk.KGLLKUSE and KGLLKHDL='000000007C17F408';

 

SID SQL_ID        EVENT              KGLLKUSE         KGLLKHDL         KGLLKMOD KGLLKREQ KGLL

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

 33 087rrdjwc2act library cache pin  00000000A92FC040 000000007C17F408        3        0 Lock

 33 087rrdjwc2act library cache pin  00000000A92FC040 000000007C17F408        0        3 Pin

從以上返回結果中可以看出,我們並沒有找到pin  的持有者,KGLLKREQ  表示當前會話需要申請的鎖模式,KGLLKMOD  表示當前系統中持有的鎖模式,由於該系統為RAC  ,各節點之間記憶體結構不同,handle address  不能公用,因此我們需要定位出owner  object_name  在其他節點持有pin  的會話。命令及輸出如下:

SQL> select ADDR,INDX,INST_ID,KGLHDADR,KGLNAOWN,KGLNAOBJ from x$kglob where KGLHDADR='000000007C17F408';

 

ADDR             INDX INST_ID KGLHDADR         KGLNAOWN   KGLNAOBJ

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

00007FE9B0B45850 4979       1 000000007C17F408 SYS        DUMMY

其中,x$kglob  為“library cache object  ”物件的檢視。

RAC 2  節點根據object_name  查詢對應的handle address  資訊,命令及輸出如下:

SQL> select ADDR,INDX,INST_ID,KGLHDADR,KGLNAOWN,KGLNAOBJ from x$kglob where KGLNAOBJ='DUMMY'

 

ADDR             INDX INST_ID KGLHDADR         KGLNAOWN  KGLNAOBJ

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

00007F987B1D8ED0 4150       2 00000000AA193870 SYS       DUMMY

檢視鎖的持有情況,命令及輸出如下:

SQL> select s.sid,s.sql_id,s.event,dk.* from dba_kgllock dk,v$session s where s.saddr = dk.KGLLKUSE and KGLLKHDL='00000000AA193870';

 

SID SQL_ID        EVENT             KGLLKUSE         KGLLKHDL         KGLLKMOD  KGLLKREQ KGLL

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

424 d4wnj5j8y1mq7 PL/SQL lock timer 00000000A9787DA0 00000000AA193870        1         0 Lock

424 d4wnj5j8y1mq7 PL/SQL lock timer 00000000A9787DA0 00000000AA193870        2         0 Pin

最終定位  2  上的會話424  其持有模式為(即共享模式)的鎖,堵塞了KGLLKREQ 3  排它鎖的申請,為了能夠順利編譯,我們只需要殺掉節點上的會話424  即可。


   像“節點”“節點”“節點”,是否可以改為“節點”“節點”“節點”?


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/31547506/viewspace-2925944/,如需轉載,請註明出處,否則將追究法律責任。

相關文章