Gentoo Archives: gentoo-portage-dev

From: Zac Medico <zmedico@g.o>
To: gentoo-portage-dev@l.g.o
Cc: Zac Medico <zmedico@g.o>
Subject: [gentoo-portage-dev] [PATCH] dblink.treewalk: lock for parallel-install with blockers (bug 576888)
Date: Wed, 09 Mar 2016 21:57:37
Message-Id: 1457560643-21014-1-git-send-email-zmedico@gentoo.org
1 For parallel-install, lock when interacting with blocked packages, in
2 order to account for blocked packages being removed or replaced
3 concurrently.
4
5 X-Gentoo-Bug: 576888
6 X-Gentoo-Bug-url: https://bugs.gentoo.org/show_bug.cgi?id=576888
7 ---
8 pym/portage/dbapi/vartree.py | 45 ++++++++++++++++++++++++++++++++++----------
9 1 file changed, 35 insertions(+), 10 deletions(-)
10
11 diff --git a/pym/portage/dbapi/vartree.py b/pym/portage/dbapi/vartree.py
12 index e7effca..6d4514c 100644
13 --- a/pym/portage/dbapi/vartree.py
14 +++ b/pym/portage/dbapi/vartree.py
15 @@ -3932,9 +3932,25 @@ class dblink(object):
16 blockers = self._blockers
17 if blockers is None:
18 blockers = []
19 - collisions, dirs_ro, symlink_collisions, plib_collisions = \
20 - self._collision_protect(srcroot, destroot,
21 - others_in_slot + blockers, filelist, linklist)
22 +
23 + # For parallel-install, acquire a lock to interact
24 + # with blocked packages.
25 + with_lock = bool(blockers) and "parallel-install" in self.settings.features
26 +
27 + if with_lock:
28 + self.lockdb()
29 + self.vartree.dbapi._fs_lock()
30 + # Filter out any blocked packages that may have
31 + # been uninstalled concurrently.
32 + blockers = [blocker for blocker in blockers if blocker.exists()]
33 + try:
34 + collisions, dirs_ro, symlink_collisions, plib_collisions = \
35 + self._collision_protect(srcroot, destroot,
36 + others_in_slot + blockers, filelist, linklist)
37 + finally:
38 + if with_lock:
39 + self.vartree.dbapi._fs_unlock()
40 + self.unlockdb()
41
42 # Check for read-only filesystems.
43 ro_checker = get_ro_checker()
44 @@ -4290,13 +4306,22 @@ class dblink(object):
45 self._clear_contents_cache()
46 contents = self.getcontents()
47 destroot_len = len(destroot) - 1
48 - self.lockdb()
49 - try:
50 - for blocker in blockers:
51 - self.vartree.dbapi.removeFromContents(blocker, iter(contents),
52 - relative_paths=False)
53 - finally:
54 - self.unlockdb()
55 +
56 + if blockers:
57 + self.lockdb()
58 + self.vartree.dbapi._fs_lock()
59 + try:
60 + for blocker in blockers:
61 + # Blocked packages may have been removed
62 + # or replaced concurrently, so check if
63 + # they still exist, and clear contents cache.
64 + if blocker.exists():
65 + blocker._clear_contents_cache()
66 + self.vartree.dbapi.removeFromContents(blocker,
67 + iter(contents), relative_paths=False)
68 + finally:
69 + self.vartree.dbapi._fs_unlock()
70 + self.unlockdb()
71
72 plib_registry = self.vartree.dbapi._plib_registry
73 if plib_registry:
74 --
75 2.4.10

Replies