From 45cece8d9a20edcfdefce66efbda73476aee35aa Mon Sep 17 00:00:00 2001 From: Benjamin Schubert Date: Fri, 31 May 2019 16:57:08 +0100 Subject: _loader/loader: Extract check_circular_deps to utils and Cythonize - This requires access to 'LoadElement' from _loader/loadelement, we therefore add a definition file for this module and export it. --- src/buildstream/_loader/loader.py | 55 ++------------------------------------- 1 file changed, 2 insertions(+), 53 deletions(-) (limited to 'src/buildstream/_loader/loader.py') diff --git a/src/buildstream/_loader/loader.py b/src/buildstream/_loader/loader.py index 5386eaf00..0767e3687 100644 --- a/src/buildstream/_loader/loader.py +++ b/src/buildstream/_loader/loader.py @@ -29,7 +29,7 @@ from .._profile import Topics, PROFILER from .._includes import Includes from .types import Symbol -from .utils import valid_chars_name +from .utils import check_circular_deps, valid_chars_name from .loadelement import LoadElement, LoadDependency, _extract_depends_from_node from .metaelement import MetaElement from .metasource import MetaSource @@ -128,7 +128,7 @@ class Loader(): ) with PROFILER.profile(Topics.CIRCULAR_CHECK, "_".join(targets)): - self._check_circular_deps(dummy_target) + check_circular_deps(dummy_target) ret = [] # @@ -327,57 +327,6 @@ class Loader(): # Nothing more in the queue, return the top level element we loaded. return top_element - # _check_circular_deps(): - # - # Detect circular dependencies on LoadElements with - # dependencies already resolved. - # - # Args: - # element (str): The element to check - # - # Raises: - # (LoadError): In case there was a circular dependency error - # - @staticmethod - def _check_circular_deps(top_element): - - sequence = [top_element] - sequence_indices = [0] - check_elements = set(sequence) - validated = set() - - while sequence: - this_element = sequence[-1] - index = sequence_indices[-1] - if index < len(this_element.dependencies): - element = this_element.dependencies[index].element - sequence_indices[-1] = index + 1 - if element in check_elements: - # Create `chain`, the loop of element dependencies from this - # element back to itself, by trimming everything before this - # element from the sequence under consideration. - chain = [element.full_name for element in sequence[sequence.index(element):]] - chain.append(element.full_name) - raise LoadError(LoadErrorReason.CIRCULAR_DEPENDENCY, - ("Circular dependency detected at element: {}\n" + - "Dependency chain: {}") - .format(element.full_name, " -> ".join(chain))) - if element not in validated: - # We've not already validated this element, so let's - # descend into it to check it out - sequence.append(element) - sequence_indices.append(0) - check_elements.add(element) - # Otherwise we'll head back around the loop to validate the - # next dependency in this entry - else: - # Done with entry, pop it off, indicate we're no longer - # in its chain, and mark it valid - sequence.pop() - sequence_indices.pop() - check_elements.remove(this_element) - validated.add(this_element) - # _sort_dependencies(): # # Sort dependencies of each element by their dependencies, -- cgit v1.2.1