这里不讨论oracle中锁的概念,只是讨论实际情况中遇到锁应该怎么办。有时候客户会跟你说,他的某个DML操作被卡住了,让你看看是不是有锁。这时候你可以通过一下的一些步骤来查找出详细信息。
1. dba_blockers
这个视图只有一列,内容是SID,也就是session的ID。但是即使系统中存在了锁,这个视图也不一定会有内容,因为这里的SID是blocker的ID,也就是说只有那个加锁的session block了某些操作的时候才会成为一个blocker,才会在这里体现,如果没有操作被它block,那么就不会体现在这里。非常要注意的是,在RAC环境里,这个视图不太适用,因为它只能查到同一个实例上的信息。
2. v$locked_object
这个视图显示当前被锁住的对象,锁的信息,以及持有锁的session的一些信息
3. v$lock
这个视图中显示了数据库中所有锁的信息。
-------------------
下面用这些视图来做一个测试。
1. 创建用户,并创建测试表
CREATE USER u01 IDENTIFIED BY u01;
GRANT CONNECT , RESOURCE TO u01;
CREATE TABLE tstlock(id NUMBER, val VARCHAR2(18));
INSERT INTO tstlock VALUES(1,'a');
INSERT INTO tstlock VALUES(2,'b');
COMMIT;
2. 用u01登录RAC节点中的一个节点,并在表上施加锁,要注意自己的SID
SELECT SYS_CONTEXT(‘USERENV’,'SID') FROM DUAL;
SELECT * FROM tstlock WHERE id=1 FOR UPDATE;
3. 查看gv$lock视图
SQL> SELECT SID , TYPE , ID1 , ID2 , LMODE , REQUEST , BLOCK FROM GV$LOCK WHERE SID=211;
SID TY ID1 ID2 LMODE REQUEST BLOCK
---------- -- ---------- ---------- ---------- ---------- ----------
211 TX 262183 71402 6 0 2
211 TM 228597 0 3 0 2
SID TY ID1 ID2 LMODE REQUEST BLOCK
---------- -- ---------- ---------- ---------- ---------- ----------
211 TX 262183 71402 6 0 2
211 TM 228597 0 3 0 2
这里解释一下这个输出,SID代表持有锁的session 的ID,也就是第二步中session的ID. 在type=TM这一行里,ID1表示被锁的对象ID.LMODE表示当前的锁模式,REQUEST表示一个被阻塞的锁想要获得的锁的模式。BLOCK这里不知道怎么解释。在非rac环境中block不为0表示该操作阻塞了其它操作,可是在这里并没有阻塞其它的操作,但不知道为什么还是非0值。(BLOCK应该是这样的,如果在非RAC环境中,0表示没有阻塞其它,1表示阻塞其它,这很明确。 如果是RAC环境中,那么0当前想要申请锁的动作被阻塞了。1表示了你正在阻塞别人,但这个别人或者说别人们,一定是和你在同一个instance上的。而2则表现不出太多的信息,它只能告诉你这一行没有被阻塞,因为如果被阻塞了应该是0.除此之外从2这个值上判断不出更多,因为它可能是什么都没发生,也可能是阻塞了其它instance上的session
)
4. 在另外一个session里执行某项会被锁挡住的操作来实现
DELETE FROM U01.TSTLOCK WHERE ID=2;
5. 检查锁
SQL> SELECT SID , TYPE , ID1 , ID2 , LMODE , REQUEST , BLOCK FROM GV$LOCK WHERE CTIME<200000;
SID TY ID1 ID2 LMODE REQUEST BLOCK
---------- -- ---------- ---------- ---------- ---------- ----------
147 PS 2 3599 4 0 2
197 PS 2 3599 4 0 2
197 PS 1 3599 4 0 2
308 XR 4 0 1 0 2
137 PS 1 3599 4 0 2
174 TM 228597 0 3 0 2
174 TX 262183 71402 0 6 0
194 TO -40016333 1 3 0 2
211 TX 262183 71402 6 0 1
211 TM 228597 0 3 0 2
SID TY ID1 ID2 LMODE REQUEST BLOCK
---------- -- ---------- ---------- ---------- ---------- ----------
147 PS 2 3599 4 0 2
197 PS 2 3599 4 0 2
197 PS 1 3599 4 0 2
308 XR 4 0 1 0 2
137 PS 1 3599 4 0 2
174 TM 228597 0 3 0 2
174 TX 262183 71402 0 6 0
194 TO -40016333 1 3 0 2
211 TX 262183 71402 6 0 1
211 TM 228597 0 3 0 2
可以看到174这一session被锁住了。而且阻塞它的正是211。因为看 174 的TX锁在REQUEST模式是6,说明正在申请一个X锁。而对应的TM锁与211的TM锁锁住了同一个表,所以可以判断这两个session之间发生了锁竞争。
本文介绍在Oracle数据库中如何排查锁定问题。通过使用dba_blockers、v$locked_object和v$lock等视图,可以定位导致操作卡住的锁。特别针对RAC环境中的锁现象进行了分析。
1963

被折叠的 条评论
为什么被折叠?



