[ZODB-Dev] Tracking down a freeze (deadlock?)

Tim Peters tim at zope.com
Fri Feb 25 10:01:24 EST 2005


[Florent Guillaume]
>>   File "/opt/zope/lib/python/ZODB/Connection.py", line 257, in _setDB
>>     self._flush_invalidations()
>>   File "/opt/zope/lib/python/ZODB/Connection.py", line 552, in
>> _flush_invalidations
>>     self._cache.invalidate(self._invalidated)
>>   File
>>
"/appli/zeo/zeocli-192.168.106.6-8080/Products/DICOD/DICODMailingList.py",
line 125, in __del__
>>   File "/opt/zope/lib/python/ZODB/Connection.py", line 599, in setstate
>>     invalid = self._is_invalidated(obj)
>>   File "/opt/zope/lib/python/ZODB/Connection.py", line 617, in
_is_invalidated
>>     self._inv_lock.acquire()
>>
>> Hm I think I can answer that one. A persistent object is not supposed to
>> have a __del__ that accesses the ZODB right ? Otherwise, well, we see
>> what happens.

[Dieter Maurer]
> On the other hand, it should not cause a deadlock.

Why is that?  As far as I'm concerned, ZODB doesn't support persistent
objects with __del__ methods -- it was never intended to.  "Don't do that"
rules then.  In the case of the infinite loop in the memory cache I
mentioned before, there was insignificant runtime expense to avoid the
infinite loop due to the __del__ method (although the collective brainpower
expended on finding and testing that fix was obscene relative to the actual
benefit).

> It would not when "_inv_lock" were a reentrant lock. I think, it could be
> (as "acquire" and "release" are not called in different threads).

I agree it could be, but:

1. A reentrant lock is significantly more expensive to use, both
   to acquire and to release.

2. Avoiding the deadlock is only the tip of the iceberg.  Locks are
   meant to ensure invariants, and the latter are rarely documented
   in ZODB.  To ensure that invariants aren't violated when switching
   to a reentrant lock requires trying to figure out what all the
   intended invariants actually are, then checking every possibly
   relevant code path to ensure that those invariants remain satisfied
   in reentrant cases.

So, ya, it's a matter of seconds to change from a Lock to an RLock here, and
a matter of perhaps 20 minutes to write and debug a good new test case(s),
but every ZODB user would pay runtime expense for that forever after, and it
may or may not introduce subtle new bugs (depending on the analysis in #2,
and also on whether that analysis is wholly correct).  If the benefit is to
stop a deadlock in application code Florent is inclined to believe is
incorrect anyway, it sounds like a losing set of tradeoffs to me.



More information about the ZODB-Dev mailing list