Exemplo n.º 1
0
    def AddActionListToGraph(parent: ActionNode, current: ActionNode,
                             action_list: List[Action], end: ActionNode,
                             partial_tests: Set[CoverageTest]) -> None:
        nonlocal root_node
        assert isinstance(parent, ActionNode)
        assert isinstance(end, ActionNode)
        assert len(action_list) > 0
        only_state_check_actions = True
        current.AssertValidity()
        end.AssertValidity()
        for action in action_list:
            assert isinstance(action, Action)
            if action.is_state_check:
                parent.AddStateCheckAction(action, ActionCoverage.PARTIAL)
                parent.partial_coverage_tests.update(partial_tests)
                continue
            only_state_check_actions = False
            if action.name in parent.children:
                current = parent.children[action.name]
            else:
                current = ActionNode(action)
                current.coverage = ActionCoverage.PARTIAL
                parent.AddChild(current)
            current.partial_coverage_tests.update(partial_tests)
            parent = current
        if current == end:
            return
        if only_state_check_actions:
            # If only state_check actions were added, then no need to add a new
            # edge.
            return
        logging.info("Merging children of\n{" + parent.GetGraphPathStr() +
                     "}\n{" + end.GetGraphPathStr() + "}")
        if current.action.name is end.action.name:
            MergeNodes(current, end)
        else:
            MergeChildren(current, end)

        root_node.AssertChildrenValidity()
Exemplo n.º 2
0
    def MergeNodes(node_a: ActionNode, node_b: ActionNode) -> ActionNode:
        assert not node_a.dead
        assert not node_b.dead
        if node_a == node_b:
            return node_a
        assert node_a.action.name == node_b.action.name
        logging.info("Merging nodes with paths:\n{" +
                     node_a.GetGraphPathStr() + "},\n{" +
                     node_b.GetGraphPathStr() + "}")
        new_node = ActionNode(node_a.action)
        new_node.coverage = (ActionCoverage.FULL
                             if node_a.coverage == ActionCoverage.FULL
                             or node_b.coverage == ActionCoverage.FULL else
                             ActionCoverage.PARTIAL)
        new_node.state_check_actions = node_a.state_check_actions
        new_node.state_check_actions.update(node_b.state_check_actions)
        new_node.state_check_actions_coverage = MergeStateCheckCoverage(
            node_a.state_check_actions_coverage,
            node_b.state_check_actions_coverage)
        new_node.full_coverage_tests = node_a.full_coverage_tests
        new_node.full_coverage_tests.update(node_b.full_coverage_tests)
        new_node.partial_coverage_tests = node_a.partial_coverage_tests
        new_node.partial_coverage_tests.update(node_b.partial_coverage_tests)
        children_a = node_a.children.copy()
        children_b = node_b.children.copy()
        parents_a = node_a.parents.copy()
        parents_b = node_b.parents.copy()

        # Fully remove the merging nodes from the graph
        for child in list(children_a.values()) + list(children_b.values()):
            if new_node.action.name in child.parents:
                del child.parents[new_node.action.name]
        for parent in list(parents_a.values()) + list(parents_b.values()):
            if new_node.action.name in parent.children:
                del parent.children[new_node.action.name]

        # Merge children.
        # Start by adding the non-intersecting children to the dictionary.
        children = ({
            k: children_a.get(k, children_b.get(k)).ResolveToAliveNode()
            for k in (children_a.keys() ^ children_b.keys())
        })
        # For all children that are the same, they must be merged.
        children.update({
            k: MergeNodes(children_a[k].ResolveToAliveNode(),
                          children_b[k].ResolveToAliveNode())
            for k in (children_a.keys() & children_b.keys())
        })

        # Merge parents.
        # Start by adding the non-intersecting parents to the dictionary.
        parents = ({
            k: parents_a.get(k, parents_b.get(k)).ResolveToAliveNode()
            for k in (parents_a.keys() ^ parents_b.keys())
        })
        # For all parents that are the same, they must be merged.
        parents.update({
            k: MergeNodes(parents_a[k].ResolveToAliveNode(),
                          parents_b[k].ResolveToAliveNode())
            for k in (parents_a.keys() & parents_b.keys())
        })

        # Re-add the node back into the graph.
        for child in children.values():
            child = child.ResolveToAliveNode()
            new_node.AddChild(child)
        for parent in parents.values():
            parent = parent.ResolveToAliveNode()
            parent.AddChild(new_node)

        node_a.dead = new_node
        node_b.dead = new_node
        new_node.AssertValidity()
        return new_node