Oracle锁机制学习

锁的简介

成都创新互联公司-专业网站定制、快速模板网站建设、高性价比嵩县网站开发、企业建站全套包干低至880元,成熟完善的模板库,直接使用。一站式嵩县网站制作公司更省心,省钱,快速模板网站建设找我们,业务覆盖嵩县地区。费用合理售后完善,10余年实体公司更值得信赖。

  Oracle实现并发访问控制,通过锁来实现。

  锁分为悲观锁(事务调度可能会串行调度)--事务级别的行级锁。

      乐观锁(事务被串行调度)-- 时间戳和基于验证的事务调度。

  所谓乐观锁是指事务调度串行机制不会打乱,保证每个事务之间数据更改彼此不会受影响,维护数据一致性。

  Oracle默认隐式执行锁定机制,采用影响行数最少的行级锁,在数据库块中存储锁定行的信息。

  锁针对某个事务的整个过程,在发出commit或rollback后锁自动消失。

锁的锁定方法

  Oracle采用行级粒度的方式来进行锁定对象,一个事务操作影响几条数据就锁定几行。

  粒度越小,支持的并发越大。

锁类型

  锁的对象可以是用户级的表、索引等,也可是共享数据结构(数据字典)。

  1. DML锁

    针对保护用户的表和索引,在事务操作的行上加了一把独占行级锁,防止相同数据行同时被多个事务同时更改,在一事务未提交前,后一事务只能等待直到前一事务提交。

    在DML锁的同时会持有一个DDL表锁,在DML(insert,update,delete)操作时另一事务不能对表进行定义表结构操作。同一事务可以操作,等待时间取决于操作ddl_lock_timeout

    此参数默认值为0

    show parameter ddl_;

    NAME                                 TYPE        VALUE
    ------------------------------------ ----------- ------
    ddl_lock_timeout                     integer     0

    可以在session级别设定等待事件

    alter session set ddl_lock_timeout = 30;

    -- 设定同一事务ddl锁等待dml锁的时间为30秒,默认为不等待立即执行。

    操作等待时间超过设定值直接失效。前提是dml操作时间很长,超过了ddl等待时间。

  2. DDL锁

    在DML锁时有附带对应表的DDL锁

  3. 闩用于保护sga中共享数据结构,控制对内存结构的访问。

  4. 数据字典锁

    字典对象被修改时的对应的锁

  5. 分布锁

    在RAC结构或分布式系统中使用的锁

  6. 内部锁

    Oracle为保护访问数据文件、表空间、回滚段而使用的锁

锁管理:

在实际应用系统中,会出现进程等待现象,这是阻塞锁导致,有人俗称‘死锁’这是错误的。

死锁 是两个进程彼此等待,造成的死循环。阻塞锁是一个进程等待另外一个进程,当前一进程提交或回滚后,后一进程就能得到对应对象的控制权。

死锁有Oracle内部处理,杀死后请求事务,无需人为参与

  1. 阻塞锁

    当一个事务在某个对象上的锁阻止或阻塞了其他事务访问相同对象时,阻塞锁就会出现。

    在视图 dba_blocks中可查询当前被阻塞的会话ID

    select * from dba_blockers;

    HOLDING_SESSION
    ---------------
                 39

    也可在v$session视图中查询当前阻塞的会话

    select t.SID,t.USERNAME,t.BLOCKING_SESSION_STATUS,t.BLOCKING_SESSION from v$session  t
    where t.BLOCKING_SESSION_STATUS = 'VALID';

           SID USERNAME                       BLOCKING_SE BLOCKING_SESSION
    ---------- ------------------------------ ----------- ----------------
            42 halee                           VALID                     39

  2. 死锁

    两个事务同时对相同对象持有行级独占锁,彼此阻塞就会形成死锁。Oracle自动杀死对改对象锁的后持有者

  3. 管理视图

    dba_blockers -- 记录当期库中阻塞其他进程的进程

    dba_waiters -- 记录等待进程,被阻塞进程,锁类型,即将请求的锁类型

    select * from dba_waiters;
    WAITING_SESSION HOLDING_SESSION LOCK_TYPE   MODE_HELD  MODE_REQUESTED LOCK_ID1 LOCK_ID2
    --------------- --------------- ---------   ---------  ----------     -------  ------
         42           39            Transaction  Exclusive  Exclusive       39214  2964

    dba_locks -- 记录每个会话具体的锁类型

  4. 生成库中锁的情况

    执行安装目录下的utllockt.sql文件,可以生成对应锁等待的具体情况

    WAITING_SESSION   LOCK_TYPE         MODE_REQUESTED  MODE_HELD       LOCK_ID1          LOCK_ID2
    ----------------- ----------------- --------------- --------------- ----------------- -----------------
    39                None
       42             Transaction       Exclusive       Exclusive       393241            2964

    返回结果说明:
    会话42在等待会话39提交或回滚来回去行独占锁

    可采用如下sql 查询对应锁对应的操作

    SELECT /*+ ORDERED */sql_text
FROM v$sqltext a
WHERE (a.hash_value, a.address) IN (
SELECT DECODE (sql_hash_value,
0, prev_hash_value,
sql_hash_value
),
DECODE (sql_hash_value, 0, prev_sql_addr, sql_address)
FROM v$session b,dba_blockers c
WHERE b.SID = c.holding_session);


网站栏目:Oracle锁机制学习
本文来源:http://ybzwz.com/article/ghhcei.html