理解锁和闩(3)TX锁和TM锁

来源:互联网 发布:webservice教程java 编辑:程序博客网 时间:2024/05/01 18:34

 

 

          oracle没有锁管理器和锁列表,这样可以避免行级锁维护的开销和行级锁数量不足导致的争用问题。在Oracle的每行数据上,都有一个标志位来表示该行数据是否被锁定,要查看某一行是否被锁定,必须直接找到这一行,而不要指望能从哪个列表得到答案,事务只是找到数据。其locking过程如下:
              ㈠ 找到想锁定的那一行的地址
              ㈡ 到达那一行
              ㈢ 锁定这一行
          在这行的位置,而非某个锁列表。如果这一行已经锁定,则等待锁定它的事务结束,除非使用nowait选项。

 

            保护元数据---->TM锁(表级锁)
            保护数据  ---->TX锁(事务锁)
            v$lock列:ID1、ID2
            对TM锁,ID1表示被locking对象的object_id,ID2始终为0
            对TX锁,ID1表示该事务的xidusn、xidslot,ID2表示xidsqn
            对ID1的拆解:

          

14:14:56 hr@ORCL (^ω^) select id1,id2,type from v$lock where type='TX';       ID1        ID2 TYPE---------- ---------- ----    524320       1748 TX14:16:56 hr@ORCL (^ω^) select 524320/65536 xidusn,mod(524320,65536) xidslot from dual;    XIDUSN    XIDSLOT---------- ----------8.00048828         32


            事务锁不是行级锁。行级锁触发事务锁。一个事务只有一个事务锁,但可以有多个行级锁。TX锁用作一种排队机制:请求锁的事务会排队,等待目前持有锁的事务执行,然后得到数据。
            事务中DML或select ...for update都会得到一个TX锁。

     session 1:scott
     SQL> update dept set dname=initcap(dname);
    
     已更新4行。
     SQL> select username,l.sid,trunc(id1/power(2,16)) xidusn,bitand(id1,to_number('ffff','xxxx'))+0 slot,
       2         id2 sqn,lmode,request
       3    from v$lock l,v$session s
       4   where l.type='TX' and
       5         l.sid=s.sid and
       6         s.username=USER
       7  /
    
     USERNAME          SID     XIDUSN       SLOT        SQN      LMODE    REQUEST
     ---------- ---------- ---------- ---------- ---------- ---------- ----------
     SCOTT             154         10         40       1395          6          0
     SQL> select xidusn,xidslot,xidsqn from v$transaction;
    
         XIDUSN    XIDSLOT     XIDSQN
     ---------- ---------- ----------
             10         40       1395
         注释:
         ① v$lock表中lmode=6为X锁(排他表级锁)。request=0则意味着你拥有这个锁
         ② oracle不会在任何地方存储行级锁列表。所以v$lock表只有一行,而不是四行
    
    
session 2:也是scott
     SQL> update emp set ename=upper(ename);
    
     已更新14行。
    
     SQL> update dept set deptno=deptno-10;
    
     现在会话被阻塞。
     SQL> select username,l.sid,trunc(id1/power(2,16)) xidusn,bitand(id1,to_number('ffff','xxxx'))+0 slot,
       2           id2 sqn,lmode,request
       3    from v$lock l,v$session s
       4   where   l.type='TX' and
       5           l.sid=s.sid and
       6           s.username=USER
       7  /
    
     USERNAME          SID     XIDUSN       SLOT        SQN      LMODE    REQUEST
     ---------- ---------- ---------- ---------- ---------- ---------- ----------
     SCOTT             135         10         40       1395          0          6
     SCOTT             135          2          1       1777          6          0
     SCOTT             154         10         40       1395          6          0
     SQL> select xidusn,xidslot,xidsqn from v$transaction;
    
         XIDUSN    XIDSLOT     XIDSQN
     ---------- ---------- ----------
              2          1       1777
             10         40       1395
             这里可以看到一个新的事务,xid为(2,1,1777)。request=6表明对一个X锁的请求。请求行的xid正是持有
     者的事务ID。
     SQL> select (select username from v$session where sid=a.sid) blocker,a.sid,
       2         'is blocking',
       3         (select username from v$session where sid=b.sid) blockee,b.sid
       4    from v$lock a,v$lock b
       5   where a.block=1 and
       6         b.request>0 and
       7         a.id1=b.id1 and
       8         a.id2=b.id2
       9  /
    
     BLOCKER           SID 'ISBLOCKING'           BLOCKEE         SID
     ---------- ---------- ---------------------- -------- ----------
     SCOTT             154 is blocking            SCOTT           135

 

            表级锁(table-level lock)的作用是对并发的 DDL 操作进行访问控制,例如防止在 DML 语句执行期间相关的表被移除。当用户对表执行 DDL 或 DML 操作时,将获取一个此表的表级锁。表级锁不会影响其他并发的 DML 操作。对于分区表来说,表级锁既可以针对整个表,也可以只针对某个分区。

            当用户执行以下 DML 语句对表进行修改:INSERT,UPDATE,DELETE,及 SELECT ... FOR UPDATE,或执行 LOCK TABLE 语句时,事务将获取一个表级锁。当一个未提交的事务拥有某个表上的锁时,此表就无法被修改定义或被移除。


            大家都知道TM锁共有6种模式,最常见的是3(插入,更新,删除);4(创建索引时);5(部分DDL操作如:删除列)等等

            RS
            行共享表级锁(row share table lock)(也称为 subshare table lock,SS)表明拥有此锁的事务已经锁定了表内的 某些数据行,并有意对数据行进行更新操作。当执行以下 SQL 语句时将获得表上的行共享表级锁:


            SELECT ... FROM table ... FOR UPDATE OF ... ;
            OR
            LOCK TABLE table IN ROW SHARE MODE;


            RS限制程度最低,因而能够保证表的最大的并发访问能力
            允许的操作:某个事务拥有了某个表的行共享表级锁后,其他事务依然可以并发地对相同数据表执行查询,插入,更新,删除操作,或对表内数据行加锁的操作.
            禁止的操作:LOCK TABLE table IN EXCLUSIVE MODE
           
           
RX
            行排他表级锁(row exclusive table lock)(也被称为 subexclusive table lock, SX)通常表明拥有此锁的事务已经对表内的某些数据行进行了更新操作。当事务使用以下语句修改数据表时将自动地获得行排他表级锁:
            INSERT INTO table ... ;
            or
            UPDATE table ... ;
            or
            DELETE FROM table ... ;
            or
            LOCK TABLE table IN ROW EXCLUSIVE MODE;
            RX比RS限制程度略高。
            允许的操作:某个事务拥有了某个表的行排他表级锁后,其他事务依然可以并发地对相同数据表执行查询,插入,更新,删除操作,或对表内数据行加锁的操作。
            禁止的操作:
            LOCK TABLE table IN SHARE MODE;
            or
            LOCK TABLE table IN SHARE EXCLUSIVE MODE;
            or
            LOCK TABLE table IN EXCLUSIVE MODE;
           
           
S
            以下语句能够获得表上的共享表级锁(share table lock):
            LOCK TABLE table IN SHARE MODE;


            注意,在创建索引时,会缺省地加上S锁。7*24业务这条语句(等价于建索引)会使得所有DML都被阻塞!!
            允许的操作:某个事务拥有了某个表的S锁后,其他事务可以查询表,可以使用 SELECT ... FOR UPDATE 语句锁定选中的数据行,也能够成功执行 LOCK TABLE ... IN SHARE MODE 语句。多个事务可以并发地获得同一个表上的S锁,在此种情况下任何事务都不能对表进行更新。拥有S锁的事务只有在此表上没有其他事务的S锁时,才能对表进行更新操作。
            禁止的操作:
            LOCK TABLE table IN ROW EXCLUSIVE MODE;
            OR
            LOCK TABLE table IN SHARE ROW EXCLUSIVE MODE;
            OR
            LOCK TABLE table IN EXCLUSIVE MODE;
           
           
SRX
            共享行排他表级锁(share row exclusive table lock)(也称为 share-subexclusive table lock,SSX)与S锁相比限制更为严格。用户可以使用以下语句获得SRX:
            LOCK TABLE table IN SHARE ROW EXCLUSIVE MODE;
            允许的操作:同一时间只有一个事物能够获得表的共享行排他表级锁。某个事务拥有了某个表的共享行排他表级锁后,其他事务可以查询表,可以使用SELECT ... FOR UPDATE 语句锁定选中的数据行,但不能对表进行更新操作。
            禁止的操作:
            LOCK TABLE table IN ROW EXCLUSIVE MODE;
            or
            LOCK TABLE table IN SHARE MODE;
            or
            LOCK TABLE table IN SHARE ROW EXCLUSIVE MODE; 
            or
            LOCK TABLE table IN EXCLUSIVE MODE;
           
           
X
            排他表级锁(exclusive table lock)是限制程度最高的表级锁,她能使获得此锁的事务排他地对表进行写操作。排他表级锁可以使用以下语句获得:
            LOCK TABLE table IN EXCLUSIVE MODE;
            允许的操作:同一时间只有一个事务能获得表上的X锁。一个事务获得X后,其他事务只能对表进行查询操作。
            禁止的操作:一个事务获得X锁后,将禁止其他事务对表执行任何 DML 操作,其他事务也无法获取表上任何类型的锁。

 

                                                                       限制程度表

 

lmodetype2RS3RX4S5SRX6X

 

    当TM锁获得后,系统会自动申请TX锁,并将实际locking的行级锁的锁标志位置位(指向该TX锁)。

原创粉丝点击