FMDatabaseQueue lead to a deadlock

问题

Assertion failed: (currentSyncQueue != self && “inDatabase: was called reentrantly on the same queue,which would lead to a deadlock”),function -[FMDatabaseQueue inDatabase:],file /Users/LaoTao/Documents/CIM/cim-ios/HealthGuard/Class/Lib/Tools/LocalDB/FMDB/FMDatabaseQueue.m, line 153.

今天运行app,发现在“assert(currentSyncQueue != self && “inDatabase: was called reentrantly on the same queue, which would lead to a deadlock”);”这句crash掉了。 然后就去先看一下大意:

断言失败(Assertion 单元测试的时候会经常碰到),inDatabase 在相同的queue队列中被重复调用,引发死锁。

原因

在使用时,如果在queue里面的block执行过程中,又调用了 indatabase方法,则会检查 是不是同一个queue,如果是同一个queue会死锁;原因很简单:

队列里面 放了一个block,该block又在 本队列 后面放了一个 block;

从而:前一个block 里面 调用了 后一个block,必须等后一个block执行完成了,

前一个block才会 出队列;

而后一个block想要执行,则又必须先等 前一个block出队列;

因此 死锁!!!!

解决方法

在indatabase的block中,不要再调用indatabase方法。这个细心一下,多数时候很容易发现。

可是有时候因代码封装等问题,大家可能很难发现问题所在。那么就来个暴力断点吧。在每一个使用indatabase的地方都 NSLog(或者print)一下一个编号。 然后crash的时候,看一下最后是哪两个相互发生的影响造成的死锁。

Licensed under CC BY-NC-SA 4.0
comments powered by Disqus
Built with Hugo
Theme Stack designed by Jimmy