1"""
2Test the iteration protocol for some lldb container objects.
3"""
4
5from __future__ import print_function
6
7
8import lldb
9from lldbsuite.test.decorators import *
10from lldbsuite.test.lldbtest import *
11from lldbsuite.test import lldbutil
12
13
14class LLDBIteratorTestCase(TestBase):
15
16    def setUp(self):
17        # Call super's setUp().
18        TestBase.setUp(self)
19        # Find the line numbers to break inside main().
20        self.line1 = line_number(
21            'main.cpp', '// Set break point at this line.')
22        self.line2 = line_number('main.cpp', '// And that line.')
23
24    def test_lldb_iter_module(self):
25        """Test module_iter works correctly for SBTarget -> SBModule."""
26        self.build()
27        exe = self.getBuildArtifact("a.out")
28
29        target = self.dbg.CreateTarget(exe)
30        self.assertTrue(target, VALID_TARGET)
31
32        breakpoint = target.BreakpointCreateByLocation("main.cpp", self.line1)
33        self.assertTrue(breakpoint, VALID_BREAKPOINT)
34
35        # Now launch the process, and do not stop at entry point.
36        process = target.LaunchSimple(
37            None, None, self.get_process_working_directory())
38
39        if not process:
40            self.fail("SBTarget.LaunchProcess() failed")
41
42        from lldbsuite.test.lldbutil import get_description
43        yours = []
44        for i in range(target.GetNumModules()):
45            yours.append(target.GetModuleAtIndex(i))
46        mine = []
47        for m in target.module_iter():
48            mine.append(m)
49
50        self.assertEqual(len(yours), len(mine))
51        for i in range(len(yours)):
52            if self.TraceOn():
53                print("yours[%d]='%s'" % (i, get_description(yours[i])))
54                print("mine[%d]='%s'" % (i, get_description(mine[i])))
55            self.assertEqual(
56                yours[i], mine[i],
57                "UUID+FileSpec of yours[{0}] and mine[{0}] matches".format(i))
58
59    def test_lldb_iter_breakpoint(self):
60        """Test breakpoint_iter works correctly for SBTarget -> SBBreakpoint."""
61        self.build()
62        exe = self.getBuildArtifact("a.out")
63
64        target = self.dbg.CreateTarget(exe)
65        self.assertTrue(target, VALID_TARGET)
66
67        breakpoint = target.BreakpointCreateByLocation("main.cpp", self.line1)
68        self.assertTrue(breakpoint, VALID_BREAKPOINT)
69        breakpoint = target.BreakpointCreateByLocation("main.cpp", self.line2)
70        self.assertTrue(breakpoint, VALID_BREAKPOINT)
71
72        self.assertEqual(target.GetNumBreakpoints(), 2)
73
74        from lldbsuite.test.lldbutil import get_description
75        yours = []
76        for i in range(target.GetNumBreakpoints()):
77            yours.append(target.GetBreakpointAtIndex(i))
78        mine = []
79        for b in target.breakpoint_iter():
80            mine.append(b)
81
82        self.assertEqual(len(yours), len(mine))
83        for i in range(len(yours)):
84            if self.TraceOn():
85                print("yours[%d]='%s'" % (i, get_description(yours[i])))
86                print("mine[%d]='%s'" % (i, get_description(mine[i])))
87            self.assertEqual(yours[i], mine[i],
88                            "ID of yours[{0}] and mine[{0}] matches".format(i))
89
90    @skipIfWindows # This test is flaky on Windows
91    def test_lldb_iter_frame(self):
92        """Test iterator works correctly for SBProcess->SBThread->SBFrame."""
93        self.build()
94        exe = self.getBuildArtifact("a.out")
95
96        target = self.dbg.CreateTarget(exe)
97        self.assertTrue(target, VALID_TARGET)
98
99        breakpoint = target.BreakpointCreateByLocation("main.cpp", self.line1)
100        self.assertTrue(breakpoint, VALID_BREAKPOINT)
101
102        # Now launch the process, and do not stop at entry point.
103        process = target.LaunchSimple(
104            None, None, self.get_process_working_directory())
105
106        if not process:
107            self.fail("SBTarget.LaunchProcess() failed")
108
109        from lldbsuite.test.lldbutil import print_stacktrace
110        stopped_due_to_breakpoint = False
111        for thread in process:
112            if self.TraceOn():
113                print_stacktrace(thread)
114            ID = thread.GetThreadID()
115            if thread.GetStopReason() == lldb.eStopReasonBreakpoint:
116                stopped_due_to_breakpoint = True
117            for frame in thread:
118                self.assertEqual(frame.GetThread().GetThreadID(), ID)
119                if self.TraceOn():
120                    print(frame)
121
122        self.assertTrue(stopped_due_to_breakpoint)
123