对sqlite3的锁机制简单分析,本人新手,欢迎大家指正。
sqlite用五种锁实现ACID:
1. Nolock:应用处于初始状态
2. Shared:在读操作前获得的锁。(可以有多个应用共享Shared lock)
3. Reserved:表示应用将来有写的意图。(此时其他应用可以获得Shared lock)
4. Pending:表示应用正在因为要执行写操作而等全部Shared lock释放。(此时其他应用不能再获得任何锁)
5. Exclusive:表示应用已经获得锁并在执行写操作。(此时其他应用不能再获得任何锁)
[一次仅有读的事务具有以下锁转换过程]:
Nolock->Shared->Nolock
应用要启动事务读数据,那么首先要尝试获得shared lock,此时如果没有其他应用处于Pending或Exclusive,那么可以顺利完成读任务,并在提交以后释放锁,回到Nolock状态。
[一次有写的事务具有以下锁转换过程]:
Nolock->Shared->Reserved->Pending->Nolock
应用要启动事务写(读写)数据,那么首先要尝试获得shared lock,在获得shared lock以后,可以执行读操作。当应用调用写函数以后,并且还没有执行提交以前,会尝试获得Reserved lock,此时如果没有其他应用处于Reserved,Pending或Exclusive,那么可以进入Reserved状态,注意此时其他应用依然可以获得shared lock。当应用调用commit函数以后,会尝试获得Pendinglock,如果此时没有其他应用处于Pending或Exclusive,那么可以进入Pending状态,直到所有shared lock释放,本应用立即获得Exclusive lock,执行写操作。
四种sqlite锁与linux OS原生锁(文件读/写锁)的对应关系:
B:Reserved是对db文件的一个特定字节(reserved标志字节)加写锁
C:Pending是对db文件的一个特定字节(pending标志字节)加写锁
D:Exclusive是对db文件的部分页加write lock
以下是一些说明:
1.为什么需要Reserved状态?
其中一个原因是为了提高并发度,因为如果事务执行到写操作,但是没有commit,那么此时就阻塞其他读操作是不合适的,所以此时进入Reserved状态,允许读,禁止写。
2.获得Reserved lock时,是否可以释放Shared lock了?
不可以,为了保证ACID,第一个获得Reserved lock的事务必须第一个完成写操作,但是Reserved状态只表示获得了reserved byte的write lock,此时如果其他事务成功申请db page的write lock,那么就违反了ACID,因此需要保留shared lock。
3.
原文地址:https://www.jb51.cc/sqlite/201525.html
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。