fix: hold every data tree, present or not

export_native and cross_reference read data/ without the shared hold, so
a refresh could swap a tree mid-walk. hold_data_dirs skipped a cache not
yet on disk, so a refresh could install it between verify and the packs
of one pipeline run. Both now hold every registered tree.
This commit is contained in:
Abdessamad Derraz committed 2026-10-21 09:56:49 +02:00
1 parent 563ce1ebf2
commit 9bb1a73f91
4 files changed
+41 -3

No files matched your search

+4 -2
View File
@@ -99,11 +99,13 @@ def hold_data_dirs(stack: contextlib.ExitStack, registry: dict) -> None:
later. A refresh swapping the tree in between shipped bytes nobody
verified, or died on a file the new tree no longer has. A refresh waits
for the holders. Never called before a refresh in the same process:
the exclusive lock would wait on this one.
the exclusive lock would wait on this one. A cache not yet on disk is
held too: the lock sits beside the tree, and skipped, a refresh could
install the tree after verify ran and before the packs read it.
"""
for entry in registry.values():
cache = entry.get("local_cache", "")
if cache and os.path.isdir(cache):
if cache:
stack.enter_context(cache_lock(cache, shared=True))