ORACLE死锁检测:
以下测试使用scott用户的emp作测试对象,
测试目的是检测oracle死锁检测功能。
1.在shell1使用sqlplus连接scott用户,并对emp的ename='SMITH'记录进行for update锁定。
SQL> select empno, ename from emp;
EMPNO ENAME
---------- ----------
7369 SMITH
7499 ALLEN
7521 WARD
SQL> select ename from emp where ename = 'SMITH' for update;
ENAME
----------
SMITH
2.在shell2中使用sqlplus连接scott用户,并对emp的ename='ALLEN'记录进行for update锁定。
SQL> select ename from emp where ename = 'ALLEN' for update;
ENAME
----------
ALLEN
3.在shell1中,继续对emp的ename='ALLEN'记录进行for update锁定。
SQL> select ename from emp where ename = 'ALLEN' for update;
4.在shell1中,继续对emp的ename='SMITH'记录进行for update锁定,在过了3秒左右的时间,SQLPLUS报出死锁错误,并退出等待。
SQL> select ename from emp where ename = 'SMITH' for update;
select ename from emp where ename = 'SMITH' for update
*
ERROR at line 1:
ORA-00060: deadlock detected while waiting for resource
在第四步发出而未报出死锁错误前使用sys用户观察锁的状态:
SQL> select SID,TYPE,LMODE,REQUEST,BLOCK from v$lock where type = 'TX';
SID TY LMODE REQUEST BLOCK
---------- -- ---------- ---------- ----------
142 TX 0 6 0
154 TX 0 6 0
142 TX 6 0 1
154 TX 6 0 1
报出死锁错误后以sys用户观察锁的状态:
SQL> select OBJECT_ID,SESSION_ID,LOCKED_MODE from v$locked_object;
OBJECT_ID SESSION_ID LOCKED_MODE
---------- ---------- -----------
51148 142 3
51148 154 3
SQL> select SID,TYPE,LMODE,REQUEST,BLOCK from v$lock where type = 'TX';
SID TY LMODE REQUEST BLOCK
---------- -- ---------- ---------- ----------
154 TX 0 6 0
142 TX 6 0 1
154 TX 6 0 0
SQL> select WAITING_SESSION, HOLDING_SESSION from dba_waiters;
WAITING_SESSION HOLDING_SESSION
--------------- ---------------
154 142
SID=154为shell1
SID=142为shell2
从以上视图可以看出,
未报死锁错误前:
142持有2个TX锁,其中一个阻塞另一锁(154)。
154持有2个TX锁,其中一个阻塞另一锁(142)。
形成死锁状态。
报死锁错误后:
142持有1个TX锁,并阻塞另一锁(154),而第二次发出的锁定已被oracle清除。
154持有1个TX锁并且有一个锁处于等待状态(等待142)。
解除死锁状态。
避免死锁的方法:
按相同顺序访问资源,从而避免互锁和死锁的发生。
来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/13605188/viewspace-626444/,如需转载,请注明出处,否则将追究法律责任。
转载于:http://blog.itpub.net/13605188/viewspace-626444/