summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJames Ennis <james.ennis@codethink.co.uk>2019-06-24 18:06:33 +0100
committerbst-marge-bot <marge-bot@buildstream.build>2019-07-16 09:13:39 +0000
commit69d7d1a86931946dda2d2437035de32159532790 (patch)
tree9ad4c83ac6f75debac2c27111bcdb927e99950f4
parent17091995171936d6e7bbdba8fe6ed8094226266d (diff)
downloadbuildstream-69d7d1a86931946dda2d2437035de32159532790.tar.gz
element.py: Introduce __update_ready_for_runtime()
An element becomes ready for runtime once it has a cache key and all of its transitive runtime dependencies have cache keys. This patch introduces the method __update_ready_for_runtime() which is called once the cache key of an Element is calculated. When called, we immediately notify reverse dependencies and, if appropriate, try to calculate their cache keys.
-rw-r--r--src/buildstream/element.py51
1 files changed, 50 insertions, 1 deletions
diff --git a/src/buildstream/element.py b/src/buildstream/element.py
index 25f18c351..453e6b3fa 100644
--- a/src/buildstream/element.py
+++ b/src/buildstream/element.py
@@ -211,10 +211,12 @@ class Element(Plugin):
self.__reverse_runtime_deps = set() # Direct reverse runtime dependency Elements
self.__build_deps_without_strict_cache_key = None # Number of build dependencies without a strict key
self.__runtime_deps_without_strict_cache_key = None # Number of runtime dependencies without a strict key
+ self.__build_deps_without_cache_key = None # Number of build dependencies without a cache key
+ self.__runtime_deps_without_cache_key = None # Number of runtime dependencies without a cache key
self.__build_deps_uncached = None # Build dependencies which are not yet cached
self.__runtime_deps_uncached = None # Runtime dependencies which are not yet cached
self.__updated_strict_cache_keys_of_rdeps = False # Whether we've updated strict cache keys of rdeps
- self.__ready_for_runtime = False # Whether the element has all dependencies ready and has a cache key
+ self.__ready_for_runtime = False # Whether the element and its runtime dependencies have cache keys
self.__ready_for_runtime_and_cached = False # Whether all runtime deps are cached, as well as the element
self.__sources = [] # List of Sources
self.__weak_cache_key = None # Our cached weak cache key
@@ -967,6 +969,7 @@ class Element(Plugin):
dependency.__reverse_runtime_deps.add(element)
no_of_runtime_deps = len(element.__runtime_dependencies)
element.__runtime_deps_without_strict_cache_key = no_of_runtime_deps
+ element.__runtime_deps_without_cache_key = no_of_runtime_deps
element.__runtime_deps_uncached = no_of_runtime_deps
for meta_dep in meta.build_dependencies:
@@ -975,6 +978,7 @@ class Element(Plugin):
dependency.__reverse_build_deps.add(element)
no_of_build_deps = len(element.__build_dependencies)
element.__build_deps_without_strict_cache_key = no_of_build_deps
+ element.__build_deps_without_cache_key = no_of_build_deps
element.__build_deps_uncached = no_of_build_deps
element.__preflight()
@@ -3056,6 +3060,10 @@ class Element(Plugin):
if context.get_strict():
self.__cache_key = self.__strict_cache_key
+ # The Element may have just become ready for runtime now that the
+ # strong cache key has just been set
+ self.__update_ready_for_runtime()
+
# If the element is cached, and has all of its runtime dependencies cached,
# now that we have the cache key, we are able to notify reverse dependencies
# that the element it ready. This is a likely trigger for workspaced elements.
@@ -3133,6 +3141,10 @@ class Element(Plugin):
# Strong cache key could not be calculated yet
return
+ # The Element may have just become ready for runtime now that the
+ # strong cache key has just been set
+ self.__update_ready_for_runtime()
+
# If the element is cached, and has all of its runtime dependencies cached,
# now that we have the strong cache key, we are able to notify reverse dependencies
# that the element it ready. This is a likely trigger for workspaced elements.
@@ -3168,6 +3180,43 @@ class Element(Plugin):
if rdep.__build_deps_without_strict_cache_key == 0:
rdep._update_state()
+ # __update_ready_for_runtime()
+ #
+ # An Element becomes ready for runtime when:
+ #
+ # 1. The Element has a strong cache key
+ # 2. The Element's keys are considered stable
+ # 3. The runtime dependencies of the Element are ready for runtime
+ #
+ # These criteria serve as potential trigger points as to when an Element may have
+ # become ready for runtime.
+ #
+ # Once an Element becomes ready for runtime, we notify the reverse
+ # runtime dependencies and the reverse build dependencies of the Element,
+ # decrementing the appropriate counters.
+ #
+ def __update_ready_for_runtime(self):
+ if not self.__ready_for_runtime:
+ if self.__runtime_deps_without_cache_key == 0 and \
+ self.__cache_key is not None and not self.__cache_keys_unstable:
+ self.__ready_for_runtime = True
+
+ # Notify reverse dependencies
+ for rdep in self.__reverse_runtime_deps:
+ rdep.__runtime_deps_without_cache_key -= 1
+ assert not rdep.__runtime_deps_without_cache_key < 0
+
+ # If all of our runtimes have cache keys, we can calculate ours
+ if rdep.__runtime_deps_without_cache_key == 0:
+ rdep.__update_ready_for_runtime()
+
+ for rdep in self.__reverse_build_deps:
+ rdep.__build_deps_without_cache_key -= 1
+ assert not rdep.__build_deps_without_cache_key < 0
+
+ if rdep.__build_deps_without_cache_key == 0:
+ rdep._update_state()
+
def _overlap_error_detail(f, forbidden_overlap_elements, elements):
if forbidden_overlap_elements: