1"""
2Test some lldb command abbreviations.
3"""
4from __future__ import print_function
5
6
7import lldb
8from lldbsuite.test.decorators import *
9from lldbsuite.test.lldbtest import *
10from lldbsuite.test import lldbutil
11
12
13class ExecTestCase(TestBase):
14
15    NO_DEBUG_INFO_TESTCASE = True
16
17    mydir = TestBase.compute_mydir(__file__)
18
19    @expectedFailureAll(archs=['i386'],
20                        oslist=no_match(["freebsd"]),
21                        bugnumber="rdar://28656532")
22    @expectedFailureAll(oslist=["ios", "tvos", "watchos", "bridgeos"], bugnumber="rdar://problem/34559552") # this exec test has problems on ios systems
23    @expectedFailureNetBSD
24    @skipIfAsan # rdar://problem/43756823
25    @skipIfWindows
26    def test_hitting_exec (self):
27        self.do_test(False)
28
29    @expectedFailureAll(archs=['i386'],
30                        oslist=no_match(["freebsd"]),
31                        bugnumber="rdar://28656532")
32    @expectedFailureAll(oslist=["ios", "tvos", "watchos", "bridgeos"], bugnumber="rdar://problem/34559552") # this exec test has problems on ios systems
33    @expectedFailureNetBSD
34    @skipIfAsan # rdar://problem/43756823
35    @skipIfWindows
36    def test_skipping_exec (self):
37        self.do_test(True)
38
39    def do_test(self, skip_exec):
40        self.build()
41        exe = self.getBuildArtifact("a.out")
42        secondprog = self.getBuildArtifact("secondprog")
43
44        # Create the target
45        target = self.dbg.CreateTarget(exe)
46
47        # Create any breakpoints we need
48        breakpoint1 = target.BreakpointCreateBySourceRegex(
49            'Set breakpoint 1 here', lldb.SBFileSpec("main.cpp", False))
50        self.assertTrue(breakpoint1, VALID_BREAKPOINT)
51        breakpoint2 = target.BreakpointCreateBySourceRegex(
52            'Set breakpoint 2 here', lldb.SBFileSpec("secondprog.cpp", False))
53        self.assertTrue(breakpoint2, VALID_BREAKPOINT)
54
55        # Launch the process
56        process = target.LaunchSimple(
57            None, None, self.get_process_working_directory())
58        self.assertTrue(process, PROCESS_IS_VALID)
59
60        if self.TraceOn():
61            self.runCmd("settings show target.process.stop-on-exec", check=False)
62        if skip_exec:
63            self.dbg.HandleCommand("settings set target.process.stop-on-exec false")
64            def cleanup():
65                self.runCmd("settings set target.process.stop-on-exec false",
66                            check=False)
67
68            # Execute the cleanup function during test case tear down.
69            self.addTearDownHook(cleanup)
70
71        # The stop reason of the thread should be breakpoint.
72        self.assertTrue(process.GetState() == lldb.eStateStopped,
73                        STOPPED_DUE_TO_BREAKPOINT)
74
75        threads = lldbutil.get_threads_stopped_at_breakpoint(
76        process, breakpoint1)
77        self.assertTrue(len(threads) == 1)
78
79        # We had a deadlock tearing down the TypeSystemMap on exec, but only if some
80        # expression had been evaluated.  So make sure we do that here so the teardown
81        # is not trivial.
82
83        thread = threads[0]
84        value = thread.frames[0].EvaluateExpression("1 + 2")
85        self.assertTrue(
86            value.IsValid(),
87            "Expression evaluated successfully")
88        int_value = value.GetValueAsSigned()
89        self.assertTrue(int_value == 3, "Expression got the right result.")
90
91        # Run and we should stop due to exec
92        process.Continue()
93
94        if not skip_exec:
95            self.assertFalse(process.GetState() == lldb.eStateExited,
96                             "Process should not have exited!")
97            self.assertTrue(process.GetState() == lldb.eStateStopped,
98                            "Process should be stopped at __dyld_start")
99
100            threads = lldbutil.get_stopped_threads(
101                process, lldb.eStopReasonExec)
102            self.assertTrue(
103                len(threads) == 1,
104                "We got a thread stopped for exec.")
105
106            # Run and we should stop at breakpoint in main after exec
107            process.Continue()
108
109        threads = lldbutil.get_threads_stopped_at_breakpoint(
110            process, breakpoint2)
111        if self.TraceOn():
112            for t in process.threads:
113                print(t)
114                if t.GetStopReason() != lldb.eStopReasonBreakpoint:
115                    self.runCmd("bt")
116        self.assertTrue(len(threads) == 1,
117                        "Stopped at breakpoint in exec'ed process.")
118