Beispiel #1
0
    def test_path_between_returns_True_only_if_there_exists_at_least_a_path_between_two_nodes_in_the_slice(
            self):
        my_slice = CFGSliceToSink(None, {1: [2, 3], 2: [4]})

        self.assertTrue(my_slice.path_between(1, 2))
        self.assertTrue(my_slice.path_between(1, 3))
        self.assertTrue(my_slice.path_between(2, 4))
        self.assertTrue(my_slice.path_between(1, 4))

        self.assertFalse(my_slice.path_between(3, 4))
Beispiel #2
0
    def test_add_transitions_updates_the_slice(self):
        my_slice = CFGSliceToSink(None, {1: [2, 3]})
        transitions_to_add = {1: [4], 2: [4]}

        result = my_slice.add_transitions(transitions_to_add)

        expected_result = {
            1: [2, 3, 4],
            2: [4],
        }

        self.assertDictEqual(result, expected_result)
Beispiel #3
0
    def test_transitions_as_tuples(self):
        my_slice = CFGSliceToSink(None, {1: [2, 3], 2: [3]})

        expected_result = [(1, 2), (1, 3), (2, 3)]
        result = my_slice.transitions_as_tuples

        self.assertListEqual(result, expected_result)
Beispiel #4
0
    def test_nodes(self):
        my_slice = CFGSliceToSink(None, {
            1: [2, 3],
            2: [3],
        })

        expected_result = [1, 2, 3]
        result = my_slice.nodes

        self.assertListEqual(result, expected_result)
Beispiel #5
0
    def test_slice_cfg_graph_mutates_the_original_graph(self):
        my_graph, nodes = _a_graph_and_its_nodes()

        transitions = {nodes[0].addr: [nodes[1].addr]}
        my_slice = CFGSliceToSink(None, transitions)

        sliced_graph = slice_cfg_graph(my_graph, my_slice)

        self.assertEqual(len(my_graph.nodes), 2)
        self.assertEqual(len(my_graph.edges), 1)
        self.assertEqual(my_graph, sliced_graph)
    def test_init_the_call_stack_with_a_slice_as_subject_does_not_change_the_call_stack(
            self):
        binary_path = _binary_path('all')
        project = angr.Project(binary_path,
                               load_options={'auto_load_libs': False})

        initial_call_stack = []

        reaching_definitions = project.analyses.ReachingDefinitions(
            subject=CFGSliceToSink(None, {}), call_stack=initial_call_stack)

        self.assertEqual(reaching_definitions._call_stack, initial_call_stack)
Beispiel #7
0
    def test_slice_function_graph_mutates_the_original_function_graph(self):
        # Imagine a CFG being:    0 -> 0x42, 0x42 -> 1, 1 -> 2, 0 -> 3
        # And the function graph: 0 -> 1, 1 -> 2, 0 -> 3
        my_function_graph, nodes = _a_graph_and_its_nodes()

        transitions = {nodes[0].addr: [0x42], 0x42: [nodes[1].addr]}
        my_slice = CFGSliceToSink(None, transitions)

        sliced_function_graph = slice_function_graph(my_function_graph,
                                                     my_slice)

        self.assertEqual(len(my_function_graph.nodes), 2)
        self.assertEqual(len(my_function_graph.edges), 1)
        self.assertEqual(my_function_graph, sliced_function_graph)
Beispiel #8
0
    def test_slice_function_graph_remove_nodes_not_in_a_cfg_slice_to_sink(
            self):
        # Imagine a CFG being:    0 -> 0x42, 0x42 -> 1, 1 -> 2, 0 -> 3
        # And the function graph: 0 -> 1, 1 -> 2, 0 -> 3
        my_function_graph, nodes = _a_graph_and_its_nodes()

        transitions = {nodes[0].addr: [0x42], 0x42: [nodes[1].addr]}
        my_slice = CFGSliceToSink(None, transitions)

        sliced_function_graph = slice_function_graph(my_function_graph,
                                                     my_slice)
        result_nodes = list(sliced_function_graph.nodes)
        result_edges = list(sliced_function_graph.edges)

        self.assertListEqual(result_nodes, [nodes[0], nodes[1]])
        self.assertListEqual(result_edges, [(nodes[0], nodes[1])])
Beispiel #9
0
    def test_slice_cfg_graph_remove_content_not_in_a_cfg_slice_to_sink(self):
        my_graph, nodes = _a_graph_and_its_nodes()

        transitions = {
            nodes[0].addr: [nodes[1].addr],
            nodes[1].addr: [nodes[2].addr]
        }
        my_slice = CFGSliceToSink(None, transitions)

        sliced_graph = slice_cfg_graph(my_graph, my_slice)
        result_nodes = list(sliced_graph.nodes)
        result_edges = list(sliced_graph.edges)

        self.assertListEqual(result_nodes, [nodes[0], nodes[1], nodes[2]])
        self.assertListEqual(result_edges, [(nodes[0], nodes[1]),
                                            (nodes[1], nodes[2])])
Beispiel #10
0
    def test_slice_callgraph_mutates_the_original_graph(self):
        my_callgraph, nodes = _a_graph_and_its_nodes()

        # Let's imagine a node (0x42), not a function entry point, not in my_callgraph, such as:
        # 1 -> 0x42, 0x42 -> 2
        transitions = {
            nodes[0]: [nodes[1]],
            nodes[1]: [0x42],
            0x42: [nodes[2]]
        }
        cfg_slice_to_sink = CFGSliceToSink(None, transitions)

        sliced_callgraph = slice_callgraph(my_callgraph, cfg_slice_to_sink)

        self.assertEqual(len(my_callgraph.nodes), 3)
        self.assertEqual(len(my_callgraph.edges), 2)
        self.assertEqual(my_callgraph, sliced_callgraph)
Beispiel #11
0
    def test_slice_callgraph_remove_content_not_in_a_cfg_slice_to_sink(self):
        my_callgraph, nodes = _a_graph_and_its_nodes()

        # Let's imagine a node (0x42), not a function entry point, not in my_callgraph, such as:
        # 1 -> 0x42, 0x42 -> 2
        transitions = {
            nodes[0]: [nodes[1]],
            nodes[1]: [0x42],
            0x42: [nodes[2]]
        }
        cfg_slice_to_sink = CFGSliceToSink(None, transitions)

        sliced_callgraph = slice_callgraph(my_callgraph, cfg_slice_to_sink)

        result_nodes = list(sliced_callgraph.nodes)
        result_edges = list(sliced_callgraph.edges)

        self.assertListEqual(result_nodes, [nodes[0], nodes[1], nodes[2]])
        self.assertListEqual(result_edges, [(nodes[0], nodes[1]),
                                            (nodes[1], nodes[2])])
Beispiel #12
0
    def disable_emptyness(self):
        # disabled since binaries-private is not checked out for angr CI
        binaries_path = os.path.join(os.path.dirname(__file__), '..', '..',
                                     '..', '..', 'binaries-private',
                                     'operation-mango')
        binary_path = os.path.join(binaries_path, 'air-live-bu-2015',
                                   'cgi_test.cgi')
        project = Project(binary_path, auto_load_libs=False)
        cfg = project.analyses.CFGFast()
        printf = cfg.kb.functions.function(name='printf', plt=False)
        printf_node = cfg.model.get_all_nodes(printf.addr)[0]

        printf_predecessor = printf_node.predecessors[0]

        empty_slice = CFGSliceToSink(printf, {})
        non_empty_slice = CFGSliceToSink(
            printf, {printf_predecessor.addr: [printf.addr]})

        self.assertEqual(empty_slice.is_empty(), True)
        self.assertEqual(non_empty_slice.is_empty(), False)
Beispiel #13
0
def test_can_be_instantiated_with_a_slice(_):
    cfg_slice_to_sink = CFGSliceToSink(None, {})
    subject = Subject(cfg_slice_to_sink, None)

    nose.tools.assert_equals(subject.content, cfg_slice_to_sink)
    nose.tools.assert_equals(subject.type, SubjectType.CFGSliceToSink)
Beispiel #14
0
    def test_path_between_deals_with_loops(self):
        my_slice = CFGSliceToSink(None, {1: [2, 3], 2: [1]})

        self.assertFalse(my_slice.path_between(1, 4))
Beispiel #15
0
    def test_get_transitions_from_slice(self):
        transitions = {1: [2, 3]}
        my_slice = CFGSliceToSink(None, transitions)

        self.assertDictEqual(my_slice.transitions, transitions)
Beispiel #16
0
    def test_get_entrypoints_from_slice(self):
        transitions = {0: [2], 1: [2, 3], 2: [4, 5]}
        my_slice = CFGSliceToSink(None, transitions)

        self.assertListEqual(my_slice.entrypoints, [0, 1])