1""" Test that stop-on-sharedlibrary-events works and cooperates with breakpoints. """
2import lldb
3from lldbsuite.test.decorators import *
4from lldbsuite.test.lldbtest import *
5from lldbsuite.test import lldbutil
6
7class TestStopOnSharedlibraryEvents(TestBase):
8
9    mydir = TestBase.compute_mydir(__file__)
10
11    @skipIfRemote
12    @skipIfWindows
13    @no_debug_info_test
14    def test_stopping_breakpoints(self):
15        self.do_test()
16
17    @skipIfRemote
18    @skipIfWindows
19    @no_debug_info_test
20    def test_auto_continue(self):
21        def auto_continue(bkpt):
22            bkpt.SetAutoContinue(True)
23        self.do_test(auto_continue)
24
25    @skipIfRemote
26    @skipIfWindows
27    @no_debug_info_test
28    def test_failing_condition(self):
29        def condition(bkpt):
30            bkpt.SetCondition("1 == 2")
31        self.do_test(condition)
32
33    @skipIfRemote
34    @skipIfWindows
35    @no_debug_info_test
36    def test_continue_callback(self):
37        def bkpt_callback(bkpt):
38            bkpt.SetScriptCallbackBody("return False")
39        self.do_test(bkpt_callback)
40
41    def do_test(self, bkpt_modifier = None):
42        self.build()
43        main_spec = lldb.SBFileSpec("main.cpp")
44        # Launch and stop before the dlopen call.
45        target, process, thread, _ = lldbutil.run_to_source_breakpoint(self,
46                "// Set a breakpoint here", main_spec, extra_images=["load_a",
47                    "load_b"])
48
49        # Now turn on shared library events, continue and make sure we stop for the event.
50        self.runCmd("settings set target.process.stop-on-sharedlibrary-events 1")
51        self.addTearDownHook(lambda: self.runCmd(
52            "settings set target.process.stop-on-sharedlibrary-events 0"))
53
54        # Since I don't know how to check that we are at the "right place" to stop for
55        # shared library events, make an breakpoint after the load is done and
56        # make sure we don't stop there:
57        backstop_bkpt_1 = target.BreakpointCreateBySourceRegex("Set another here - we should not hit this one", main_spec)
58        self.assertGreater(backstop_bkpt_1.GetNumLocations(), 0, "Set our second breakpoint")
59
60        process.Continue()
61        self.assertEqual(process.GetState(), lldb.eStateStopped, "We didn't stop for the load")
62        self.assertEqual(backstop_bkpt_1.GetHitCount(), 0, "Hit our backstop breakpoint")
63
64        # We should be stopped after the library is loaded, check that:
65        found_it = False
66        for module in target.modules:
67            if module.file.basename.find("load_a") > -1:
68                found_it = True
69                break
70        self.assertTrue(found_it, "Found the loaded module.")
71
72        # Now capture the place where we stopped so we can set a breakpoint and make
73        # sure the breakpoint there works correctly:
74        load_address = process.GetSelectedThread().frames[0].addr
75        load_bkpt = target.BreakpointCreateBySBAddress(load_address)
76        self.assertGreater(load_bkpt.GetNumLocations(), 0, "Set the load breakpoint")
77
78        backstop_bkpt_1.SetEnabled(False)
79
80        backstop_bkpt_2 = target.BreakpointCreateBySourceRegex("Set a third here - we should not hit this one", main_spec)
81        self.assertGreater(backstop_bkpt_2.GetNumLocations(), 0, "Set our third breakpoint")
82
83        if bkpt_modifier == None:
84            process.Continue()
85            self.assertEqual(process.GetState(), lldb.eStateStopped, "We didn't stop for the load")
86            self.assertEqual(backstop_bkpt_2.GetHitCount(), 0, "Hit our backstop breakpoint")
87            self.assertEqual(thread.stop_reason, lldb.eStopReasonBreakpoint, "We attributed the stop to the breakpoint")
88            self.assertEqual(load_bkpt.GetHitCount(), 1, "We hit our breakpoint at the load address")
89        else:
90            bkpt_modifier(load_bkpt)
91            process.Continue()
92            self.assertEqual(process.GetState(), lldb.eStateStopped, "We didn't stop")
93            self.assertTrue(thread.IsValid(), "Our thread was no longer valid.")
94            self.assertEqual(thread.stop_reason, lldb.eStopReasonBreakpoint, "We didn't hit some breakpoint")
95            self.assertEqual(backstop_bkpt_2.GetHitCount(), 1, "We continued to the right breakpoint")
96
97
98
99
100
101