1 死锁
1.1 死锁的经典例子
下面介绍一个经典的死锁情况
一桌人吃饭,每一个人都需要获得左右两边的叉子才可以用餐,即critical section中是用餐的操作,
如果A的左右两边分别是 x和 y,B的左右两边分别是 y和z,c
x<->A<->y
y<->b<->z
z<->c <->x
A取了右边的叉子y
B取了右边的叉子z
C取了右边的叉子x
A尝试取左边的叉子x
这个对于x来说,
他需要c signal x(只有在c取得了他所需要的z和x之后,才会释放)这个资源,才可以让a来取得这个x
B尝试取左边的叉子y
这个对于y来说,
他需要a signal y(同理)这个资源,才可以让b来取得这个y
C尝试取左边的叉子z
这个对于z来说,
他需要b signal z(同理)这个资源,才可以让c来取得这个z
A必须等待c完成
C需要等到b完成
B又需要等待a完成
便永远不会完成了
1.2 数据库中的Concurrency
Conflict serializable
T1的输出取决于T2,T2的输出又取决于T1,那么就会有一定的问题,需要设计一个锁
Two-Phase Locking
- 分为两个阶段:growing phase以及shrinking phase,在growing phase时只能获得锁,不能丢锁,在shrinking phase时只能丢失锁,不能获得新的锁。
如果开始了shrinking phase,即开始释放锁,T1就不能够再获得锁了。
Strict Two-Phase Locking (Strict 2PL)
Strict Two-Phase Locking和Two-Phase Locking的区别在于其必须等到所有操作完成后,才能释放任何锁。 对于Two-Phase Locking来说,只要在shrinking阶段不再获取任何锁就可以,不需要等待所有的操作结束后再释放锁。
View Equivalence(视图等价)
如果在两个schedule中,如果Ti都读取了A的初始值读取、A的变化、以及写了A的变化,那么S1和S2视图等价。
Lock Management数据库的锁的管理
- 锁的管理由lock manager来管理。
- 在lock table中,每一个entry需要记录
- 有多少个事务 (Transaction)当前正拥有这个锁
- 这个锁的类型,类型可以是共享或者独占
- 需要维护一个指针,这个指针指向对这个锁的释放的请求
- 上锁和不上锁必须是原子性的(atomic)
- Lock upgrade: 锁的升级:共享锁可以升级为独享锁
数据库事务中的死锁(dead lock)
Cycle of transactions waiting for locks to be released by each other.
预防deadlock
Assume Ti wants a lock that Tj holds. Two policies are possible:
假设Ti想要一个tj拥有的锁
◦ Wait-Die: If Ti has higher priority, Ti waits for Tj; otherwise Ti aborts
如果Ti有更高的priority,那么ti等待,不然ti直接abort
◦ Wound-wait: If Ti has higher priority, Tj aborts; otherwise Ti waits
如果Ti有更高的priority那么 tj直接被abort,不然ti等待tj结束
发现死锁
Create a waits-for graph:
◦ Nodes are transactions
◦ There is an edge from Ti to Tj if Ti is waiting for Tj to release a lock
查看Ti是否在等待Tj的同时Tj也在等到Ti
多granularity lock
- 数据库包含table,table包含页码,pages包含tuple,那么lock也可以在每一层设置好.
解决方法1
- 在lock一个item时,必须首先获得其更高级别的锁。如果要进行unlock,则从低级别的概念开始解锁
- 比如说这个transaction只是处理了page level里的一些tuples,那么我们在处理这些tuple之前就需要获得这个page的锁
IS (Intention Shared) and IX (Intention Exclusive) 意向锁,表示想要创造共享锁和独享锁的意向
S (Shared) 共享锁,常用于reading
X (Exclusive) 独享锁,常用于write
SIX 锁:表明 T1 可能会对 R 中的某些元组进行共享读操作,并对部分元组进行更新。SIX 锁允许 T1 在表级别持有共享锁的同时,在元组级别对某些元组加排他锁。即表达这个事务想要允许别的transaction访问这个表,但是独享某些tuple