Commit 22b2c7a3 authored by Kirill Smelkov's avatar Kirill Smelkov

[ZEO4] server: Always iterate over snapshot of .connections[storage_id]

Or else such iteration can race with deletion of elements in that list
on client disconnection. StorageServer.close was already iteration over
snapshot, but StorageServer.invalidate was not.

As the result sending out invalidations were subject to race wrt client
disconnections, and some invalidations could be skipped to be delivered
causing further data corruption.

Fixes Bug2 from https://github.com/zopefoundation/ZEO/issues/209

Tests for this fix were developed as part of ZODB5:

    https://github.com/zopefoundation/ZODB/pull/368

    https://github.com/zopefoundation/ZODB/commit/942099c6c430
    https://github.com/zopefoundation/ZODB/commit/a03c47787698
    https://github.com/zopefoundation/ZODB/commit/c593c7d5baf1
    https://github.com/zopefoundation/ZODB/commit/fa8441591074
    https://github.com/zopefoundation/ZODB/commit/fc20f3aaddda
    https://github.com/zopefoundation/ZODB/commit/a94d63c552d6

and are too big and probably not worth it to backport.
parent bf80d23d
......@@ -1105,7 +1105,7 @@ class StorageServer:
else:
assert info is not None
for p in self.connections[storage_id]:
for p in self.connections[storage_id][:]:
try:
if invalidated is not None and p is not conn:
p.client.invalidateTransaction(tid, invalidated)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment