1"""
2Test lldb data formatter subsystem.
3"""
4
5from __future__ import print_function
6
7
8import lldb
9from lldbsuite.test.lldbtest import *
10import lldbsuite.test.lldbutil as lldbutil
11
12
13class ValueObjectRecursionTestCase(TestBase):
14
15    mydir = TestBase.compute_mydir(__file__)
16
17    def setUp(self):
18        # Call super's setUp().
19        TestBase.setUp(self)
20        # Find the line number to break at.
21        self.line = line_number('main.cpp', '// Set break point at this line.')
22
23    def test_with_run_command(self):
24        """Test that deeply nested ValueObjects still work."""
25        self.build()
26        self.runCmd("file " + self.getBuildArtifact("a.out"), CURRENT_EXECUTABLE_SET)
27
28        lldbutil.run_break_set_by_file_and_line(
29            self, "main.cpp", self.line, num_expected_locations=1, loc_exact=True)
30
31        self.runCmd("run", RUN_SUCCEEDED)
32
33        # The stop reason of the thread should be breakpoint.
34        self.expect("thread list", STOPPED_DUE_TO_BREAKPOINT,
35                    substrs=['stopped',
36                             'stop reason = breakpoint'])
37
38        # This is the function to remove the custom formats in order to have a
39        # clean slate for the next test case.
40        def cleanup():
41            self.runCmd('type format clear', check=False)
42            self.runCmd('type summary clear', check=False)
43
44        # Execute the cleanup function during test case tear down.
45        self.addTearDownHook(cleanup)
46
47        root = self.frame().FindVariable("root")
48        child = root.GetChildAtIndex(1)
49        if self.TraceOn():
50            print(root)
51            print(child)
52        for i in range(0, 15000):
53            child = child.GetChildAtIndex(1)
54        if self.TraceOn():
55            print(child)
56        self.assertTrue(
57            child.IsValid(),
58            "could not retrieve the deep ValueObject")
59        self.assertTrue(
60            child.GetChildAtIndex(0).IsValid(),
61            "the deep ValueObject has no value")
62        self.assertTrue(
63            child.GetChildAtIndex(0).GetValueAsUnsigned() != 0,
64            "the deep ValueObject has a zero value")
65        self.assertTrue(
66            child.GetChildAtIndex(1).GetValueAsUnsigned() != 0,
67            "the deep ValueObject has no next")
68